diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 00000000..bac5503f --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,41 @@ +name: CI + +on: + pull_request: {} + push: + branches: + - master + - rc/* + +jobs: + Tests: + name: Test ${{ matrix.os }} + runs-on: ${{ matrix.os }} + + strategy: + matrix: + os: [ubuntu-latest, macOS-latest, windows-latest] + + steps: + - uses: actions/checkout@v2 + + - name: Setup latest stack + uses: haskell-actions/setup@v2 + with: + enable-stack: true + stack-version: 'latest' + + - name: Cache .stack-root + uses: actions/cache@v4 + env: + cache-name: stack-root + with: + path: .stack-root + key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ hashFiles('stack.yaml') }} + + - name: Test + shell: bash + run: | + set -ex + export STACK_ROOT=$(pwd)/.stack-root + stack test --haddock --no-haddock-deps diff --git a/.gitignore b/.gitignore index ec9dcef8..73751a2d 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,7 @@ .stack-work *.swp -.detected-contract-addresses .DS_Store build/ dist/ +docs/_build +stack.yaml.lock diff --git a/.hlint.yaml b/.hlint.yaml deleted file mode 100644 index fb57b973..00000000 --- a/.hlint.yaml +++ /dev/null @@ -1,82 +0,0 @@ -# HLint configuration file -# https://github.com/ndmitchell/hlint -########################## - -# This file contains a template configuration file, which is typically -# placed as .hlint.yaml in the root of your project - - -# Specify additional command line arguments -# -# - arguments: [--color, --cpp-simple, -XQuasiQuotes] -- arguments: - - --color - - -XTemplateHaskell - - -XQuasiQuotes - - -XTypeApplications - - -XTypeFamilies - - -XTypeOperators - - -XDataKinds - - -XPolyKinds - - -XMultiParamTypeClasses - - -XScopedTypeVariables - - -XFlexibleContexts - - -XFlexibleInstances - - -XLambdaCase - - -XArrows - - -XPatternSynonyms - -# Control which extensions/flags/modules/functions can be used -# -# - extensions: -# - default: false # all extension are banned by default -# - name: [PatternGuards, ViewPatterns] # only these listed extensions can be used -# - {name: CPP, within: CrossPlatform} # CPP can only be used in a given module -# -# - flags: -# - {name: -w, within: []} # -w is allowed nowhere -# -# - modules: -# - {name: [Data.Set, Data.HashSet], as: Set} # if you import Data.Set qualified, it must be as 'Set' -# - {name: Control.Arrow, within: []} # Certain modules are banned entirely -# -# - functions: -# - {name: unsafePerformIO, within: []} # unsafePerformIO can only appear in no modules - - -# Add custom hints for this project -# -# Will suggest replacing "wibbleMany [myvar]" with "wibbleOne myvar" -# - error: {lhs: "wibbleMany [x]", rhs: wibbleOne x} - - -# Turn on hints that are off by default -# -# Ban "module X(module X) where", to require a real export list -# - warn: {name: Use explicit module export list} -# -# Replace a $ b $ c with a . b $ c -# - group: {name: dollar, enabled: true} -# -# Generalise map to fmap, ++ to <> -# - group: {name: generalise, enabled: true} - - -# Ignore some builtin hints -- ignore: {name: Redundant do} -- ignore: {name: Redundant $} -- ignore: {name: Parse error} -- ignore: {name: Eta reduce} -- ignore: {name: Reduce duplication} -- ignore: {name: Use .} -- ignore: {name: Use asks} -- ignore: {name: Use newtype instead of data} -# - ignore: {name: Use const, within: SpecialModule} # Only within certain modules - - -# Define some custom infix operators -# - fixity: infixr 3 ~^#^~ - - -# To generate a suitable file for HLint do: -# $ hlint --default > .hlint.yaml diff --git a/.stylish_haskell.yaml b/.stylish_haskell.yaml index d3de67f6..e3505850 100644 --- a/.stylish_haskell.yaml +++ b/.stylish_haskell.yaml @@ -85,7 +85,7 @@ steps: # > ) # # Default: inline - long_list_align: inline + long_list_align: multiline # Align empty list (importing instances) # @@ -124,7 +124,7 @@ steps: # > import Data.Foldable (Foldable(fold, foldl, foldMap)) # # Default: true - separate_lists: true + separate_lists: false # Language pragmas - language_pragmas: diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index 01db77a0..00000000 --- a/.travis.yml +++ /dev/null @@ -1,57 +0,0 @@ -sudo: required -language: haskell - -services: -- docker - -before_install: -- nvm install 8.9.4 -- nvm use 8.9.4 -- npm i -g purescript@0.11.7 bower pulp -- if [ $STACK ]; then mkdir -p ~/.local/bin; export PATH=$HOME/.local/bin:$PATH; - travis_retry curl -L https://www.stackage.org/stack/linux-x86_64 | tar xz --wildcards --strip-components=1 -C ~/.local/bin '*/stack'; - else export PATH=/opt/ghc/$GHCVER/bin:/opt/cabal/$CABALVER/bin:$PATH; - fi - -install: -- $STACK || if [ -f $HOME/.cabal/packages/hackage.haskell.org/00-index.tar.gz ]; then zcat $HOME/.cabal/packages/hackage.haskell.org/00-index.tar.gz - > $HOME/.cabal/packages/hackage.haskell.org/00-index.tar; ls -l $HOME/.cabal/packages/hackage.haskell.org/; - fi; cabal update; sed -i 's/^jobs:/-- jobs:/' ${HOME}/.cabal/config; if [ -n "$CABALCONFIG" - ]; then cp $CABALCONFIG cabal.config; fi; if [ -n "$STACKAGESNAPSHOT" ]; then curl - --silent https://www.stackage.org/$STACKAGESNAPSHOT/cabal.config | grep -v "$(cabal - info . -v0 | head -n 1 | awk '{ print $2 }' | sed -E 's/-[0-9]+(\.[0-9]+)+//') ==" - > cabal.config; fi; cabal install --only-dependencies --enable-tests $CABALCONFOPTS --dry -v > - installplan.txt; sed -i -e '1,/^Resolving /d' installplan.txt; cat installplan.txt; - if diff -u $HOME/.cabsnap/installplan.txt installplan.txt; then echo "cabal build-cache - HIT"; rm -rfv .ghc; cp -av $HOME/.cabsnap/ghc $HOME/.ghc; cp -av $HOME/.cabsnap/lib - $HOME/.cabsnap/share $HOME/.cabsnap/bin $HOME/.cabal/; else echo "cabal build-cache - MISS"; rm -rf $HOME/.cabsnap; mkdir -p $HOME/.ghc $HOME/.cabal/lib $HOME/.cabal/share - $HOME/.cabal/bin; cabal install --only-dependencies --enable-tests $CABALCONFOPTS; fi; if [ ! -d - $HOME/.cabsnap ]; then echo "snapshotting package-db to build-cache"; mkdir $HOME/.cabsnap; - cp -av $HOME/.ghc $HOME/.cabsnap/ghc; cp -av $HOME/.cabal/lib $HOME/.cabal/share - $HOME/.cabal/bin installplan.txt $HOME/.cabsnap/; fi; - -script: -- docker run --rm -d -p 8545:8545 foamspace/cliquebait:latest && sleep 15 -- cd test-support && make install && make compile-contracts && make deploy && cd .. -- if [ $STACK ]; then stack -j2 --no-terminal --install-ghc test --test-arguments="--skip=multiEvent"; - else cabal update && cabal install --only-dependencies --enable-tests $CABALCONFOPTS && cabal configure --enable-tests $CABALCONFOPTS -v2 && cabal build web3 $CABALBUILDOPTS && cabal test --test-option="--skip=multiEvent"; - fi - -matrix: - include: -# - env: GHCVER=8.2.2 CABALVER=2.0 -# addons: {apt: {packages: [cabal-install-2.0,ghc-8.2.2], sources: [hvr-ghc]}} -# - env: GHCVER=8.4.2 CABALVER=2.2 -# addons: {apt: {packages: [cabal-install-2.2,ghc-8.4.2], sources: [hvr-ghc]}} - - env: STACK=YES - -before_cache: - - rm -fv $HOME/.cabal/packages/hackage.haskell.org/build-reports.log - - rm -fv $HOME/.cabal/packages/hackage.haskell.org/00-index.tar - -cache: - directories: - - $HOME/.stack - - $HOME/.cabsnap - - $HOME/.cabal/packages diff --git a/CHANGELOG.md b/CHANGELOG.md index 79882327..58204860 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,122 @@ # Changelog All notable changes to this project will be documented in this file. +## [1.1.0.0] 2026-02-09 +### Added +- Implement EIP712Signature module (#145) +- Add `chainId` call (#150) +- Add `eth_feeHistory` method to Eth API (#146) + +### Changed +- Update dependencies, switch to LTS-24.30 +- Fix build problems and CI workflow (#151) +- Update TxReceipt API according to the RPC ethereum documentation (#148) +- Fix block struct according to the spec (#147) +- Fix signature encoding for shorter integer values of r, s (#144) +- Update Types.hs (#142) + +## [1.0.1.0] 2024-10-03 +### Changed +- Update dependencies, switch to LTS-21.25 + +### Removed +- IPFS library as outdated + +## [1.0.0.0] 2020-10-00 +### Changed +- Library splitted for multiple independent packages + +## [0.9.1.0] 2020-06-07 +### Added +- SCALE codec implementation and tests +- SCALE codec example + +### Changed +- Supported GHC version: >=8.4.4 +- Imports optimized + +### Removed +- LTS-14 support + +## [0.9.0.0] 2020-05-24 +### Added +- Experimental IPFS REST API client +- Experimental Polkadot JSON-RPC API client + +### Changed +- Web3 abstraction moved to `Network.Web3` +- Ethereum entry point renamed `Network.Ethereum.Web3` -> `Network.Ethereum` +- Split from common ECDSA staff from `Crypto.Ethereum` to `Crypto.Ecdsa` +- Ethereum related tests moved to `Network.Ethereum.Test` + +### Removed +- Support for build on LTS-11, LTS-12, LTS-13 + +## [0.8.4.0] 2020-05-03 +### Added +- Tuple support for `pragma experimental ABIEncoderV2` +- Fixed dependencies bounds for stackage LTS-15 + +### Changed +- Fixed reusing of HTTP request Manager + +## [0.8.3.2] 2019-05-13 +### Changed +- Fixed dependencies bounds for stackage distribution +- Optimized LANGUAGE pragmas + +## [0.8.3.1] 2019-01-21 +### Changed +- Fixed dependencies bounds for stackage distribution + +## [0.8.3.0] 2019-01-09 +### Added +- Web3 secret storage v3 support + +### Changed +- Cryptonite based ECC signer for messages and transactions, it removes secp256k1 dependency +- Fixed dependencies bounds for stackage LTS-13 + +## [0.8.2.1] 2018-11-19 +### Changed +- Fixed dependencies bounds for stackage distribution + +## [0.8.2.0] 2018-11-07 +### Changed +- Gas estimation runs when gas limit is not set before + +## [0.8.1.0] 2018-10-29 +### Added +- Support vinyl-0.10 in `MultiFilter` module + +## [0.8.0.0] 2018-10-26 +### Added +- Support for Ethereum cryptography +- Local private key transaction signer +- Generalized JSON-RPC monad for API methods +- Support for multiple transaction sending methods via one `Account` api +- Monad based transaction sending parametrization +- Experimental support for solidity compiler (disabled by default) +- Support for Ethereum mainnet ENS resolver +- Contract typeclass with api/bytecode getters +- Gas estimation for sending transactions +- Contract typeclass TH generator +- Function for creating contracts +- Event single/multi filters +- HexString data type +- Personal api calls +- Address checksum + +### Changed +- package.yaml instead web3.cabal package descriptor +- Solidity related data types and codecs moved to Data.Solidity +- Solidity related parsers and compiler moved to Language.Solidity +- Modules in Network.Ethereum.Web3 moved to Network.Ethereum.Api +- fromWei/toWei from `Unit` typeclass now operates over `Integral` + +### Removed +- `convert` function from `Unit` typeclass + ## [0.7.3.0] 2018-05-22 ### Added - 'Network.Ethereum.ABI.Prim' meta-module as primitive types and instances aggregator. diff --git a/LICENSE b/LICENSE index 87e6c6c9..95f71d48 100644 --- a/LICENSE +++ b/LICENSE @@ -1,30 +1,211 @@ -Copyright Alexander Krupenkin (c) 2016 - -All rights reserved. - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions are met: - - * Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - - * Redistributions in binary form must reproduce the above - copyright notice, this list of conditions and the following - disclaimer in the documentation and/or other materials provided - with the distribution. - - * Neither the name of Alexander Krupenkin nor the names of other - contributors may be used to endorse or promote products derived - from this software without specific prior written permission. - -THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. \ No newline at end of file + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2021 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/Makefile b/Makefile deleted file mode 100644 index c7b89c3a..00000000 --- a/Makefile +++ /dev/null @@ -1,8 +0,0 @@ -.PHONY: hlint stylish - -hlint: ## Run hlint on all haskell projects - stack exec hlint -- -h .hlint.yaml src test - -stylish: ## Run stylish-haskell over all haskell projects - find ./src -name "*.hs" | xargs stylish-haskell -c ./.stylish_haskell.yaml -i - find ./test -name "*.hs" | xargs stylish-haskell -c ./.stylish_haskell.yaml -i diff --git a/README.md b/README.md index a8cea1e8..7c6b7fa5 100644 --- a/README.md +++ b/README.md @@ -1,71 +1,84 @@ -## Ethereum Haskell API +Web3 API for Haskell +==================== -This is the Ethereum compatible Haskell API which implements the [Generic JSON RPC](https://github.com/ethereum/wiki/wiki/JSON-RPC) spec. +This library implements Haskell API client for popular Web3 platforms. -[![Build Status](https://travis-ci.org/f-o-a-m/hs-web3.svg?branch=master)](https://travis-ci.org/f-o-a-m/hs-web3) +[![Documentation Status](https://readthedocs.org/projects/hs-web3/badge/?version=latest)](https://hs-web3.readthedocs.io/en/latest/?badge=latest) +[![CI](https://github.com/airalab/hs-web3/workflows/CI/badge.svg)](https://github.com/airalab/hs-web3/actions) [![Hackage](https://img.shields.io/hackage/v/web3.svg)](http://hackage.haskell.org/package/web3) -![Haskell Programming Language](https://img.shields.io/badge/language-Haskell-blue.svg) -![BSD3 License](http://img.shields.io/badge/license-BSD3-brightgreen.svg) -[![Code Triagers Badge](https://www.codetriage.com/airalab/hs-web3/badges/users.svg)](https://www.codetriage.com/airalab/hs-web3) +[![Stackage](http://stackage.org/package/web3/badge/lts-24)](http://stackage.org/lts-24/package/web3) +[![Code Triagers](https://www.codetriage.com/airalab/hs-web3/badges/users.svg)](https://www.codetriage.com/airalab/hs-web3) -### Installation +Install +------- - $ git clone https://github.com/airalab/hs-web3 && cd hs-web3 - $ stack setup - $ stack ghci +`stack install web3` -> This library runs only paired with [geth](https://github.com/ethereum/go-ethereum) -> or [parity](https://github.com/ethcore/parity) Ethereum node, -> please start node first before using the library. +Usage +----- -### Web3 monad +```haskell +{-# LANGUAGE OverloadedStrings #-} -Any Ethereum node communication wrapped with `Web3` monadic type. +module Main where - > import Network.Ethereum.Web3.Web3 - > :t clientVersion - clientVersion :: Web3 Text +-- Basic imports +import Network.Ethereum +import Network.Web3 -To run this computation used `runWeb3'` or `runWeb3` functions. +-- Eth API support +import qualified Network.Ethereum.Api.Eth as Eth +import Network.Ethereum.Api.Types - > import Network.Ethereum.Web3 - > runWeb3 clientVersion - Right "Parity//v1.4.5-beta-a028d04-20161126/x86_64-linux-gnu/rustc1.13.0" +-- ENS support +import qualified Network.Ethereum.Ens as Ens -Function `runWeb3` use default `Web3` provider at `localhost:8545`. +-- Lens to simple param setting +import Lens.Micro ((.~)) - > :t runWeb3 - runWeb3 - :: MonadIO m => Web3 a -> m (Either Web3Error a) +main :: IO () +main = do + -- Use default provider on http://localhost:8545 + ret <- runWeb3 $ do -### TemplateHaskell generator + -- Get address of default account + me <- head <$> Eth.accounts -[Quasiquotation](https://wiki.haskell.org/Quasiquotation) is used to parse contract ABI or load from JSON file. [TemplateHaskell](https://wiki.haskell.org/Template_Haskell) driven Haskell contract API generator can automatical create ABI encoding instances and contract method helpers. + -- Get balance of default account on latest block + myBalance <- Eth.getBalance me Latest - > :set -XQuasiQuotes - > import Network.Ethereum.Contract.TH - > putStr [abiFrom|data/sample.json|] - Contract: - Events: - Action1(address,uint256) - Action2(string,uint256) - Methods: - 0x03de48b3 runA1() - 0x90126c7a runA2(string,uint256) + -- Get half of balance + let halfBalance = fromWei (myBalance / 2) -Use `-ddump-splices` to see generated code during compilation or in GHCi. See `examples` folder for more use cases. + -- Use default account + withAccount () $ do + -- Get Ethereum address via ENS + alice <- Ens.resolve "alice.address.on.eth" + bob <- Ens.resolve "bob.address.on.eth" -### Testing + -- Send transaction with value + withParam (value .~ halfBalance) $ do -Testing the `web3` is split up into two suites: `unit` and `live`. -The `unit` suite tests internal library facilities, while the `live` tests that -the library adequately interacts with a Web3 provider. + -- Send transaction to alice account + withParam (to .~ alice) $ send () -One may simply run `stack test` to run both suites, or `stack test web3:unit` or `stack test web3:live` -to run the test suites individually. + -- Send transaction to bob account + withParam (to .~ bob) $ send () -The `unit` suite has no external dependencies, while the `live` suite requires some npm dependencies. There is a `Makefile` in the `test-support` directory to help. + -- Return sended value + return halfBalance -The `live` suite also requires a Web3 provider with Ethereum capabilities, as well as -an unlocked account with ether to send transactions from. It uses Chanterelle to deploy testing contracts, -generating ABIs for them in the process, then using said ABIs as part of a TemplateHaskell step in the suite. + -- Web3 error handling + case ret of + Left e -> error $ show e + Right v -> print (v :: Ether) -- Print returned value in ethers +``` + +--- + +Read more in the [documentation on ReadTheDocs](https://hs-web3.readthedocs.io). + +License +------- + +* Licensed under [Apache 2.0](https://github.com/airalab/hs-web3/blob/master/LICENSE-APACHE2) diff --git a/docs/Makefile b/docs/Makefile new file mode 100644 index 00000000..c704c6f4 --- /dev/null +++ b/docs/Makefile @@ -0,0 +1,20 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line. +SPHINXOPTS = +SPHINXBUILD = sphinx-build +SPHINXPROJ = hs-web3 +SOURCEDIR = . +BUILDDIR = _build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) \ No newline at end of file diff --git a/docs/conf.py b/docs/conf.py new file mode 100644 index 00000000..400c85e8 --- /dev/null +++ b/docs/conf.py @@ -0,0 +1,155 @@ +# -*- coding: utf-8 -*- +# +# Configuration file for the Sphinx documentation builder. +# +# This file does only contain a selection of the most common options. For a +# full list see the documentation: +# http://www.sphinx-doc.org/en/master/config + +# -- Path setup -------------------------------------------------------------- + +# If extensions (or modules to document with autodoc) are in another directory, +# add these directories to sys.path here. If the directory is relative to the +# documentation root, use os.path.abspath to make it absolute, like shown here. +# +# import os +# import sys +# sys.path.insert(0, os.path.abspath('.')) + + +# -- Project information ----------------------------------------------------- + +project = 'hs-web3' +copyright = '2018, Alexander Krupenkin' +author = 'Alexander Krupenkin' + +# The short X.Y version +version = '0.8' +# The full version, including alpha/beta/rc tags +release = '0.8.0.0' + + +# -- General configuration --------------------------------------------------- + +# If your documentation needs a minimal Sphinx version, state it here. +# +# needs_sphinx = '1.0' + +# Add any Sphinx extension module names here, as strings. They can be +# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom +# ones. +extensions = [ +] + +# Add any paths that contain templates here, relative to this directory. +templates_path = ['_templates'] + +# The suffix(es) of source filenames. +# You can specify multiple suffix as a list of string: +# +# source_suffix = ['.rst', '.md'] +source_suffix = '.rst' + +# The master toctree document. +master_doc = 'index' + +# The language for content autogenerated by Sphinx. Refer to documentation +# for a list of supported languages. +# +# This is also used if you do content translation via gettext catalogs. +# Usually you set "language" from the command line for these cases. +language = None + +# List of patterns, relative to source directory, that match files and +# directories to ignore when looking for source files. +# This pattern also affects html_static_path and html_extra_path . +exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store'] + +# The name of the Pygments (syntax highlighting) style to use. +pygments_style = 'sphinx' + + +# -- Options for HTML output ------------------------------------------------- + +# The theme to use for HTML and HTML Help pages. See the documentation for +# a list of builtin themes. +# +html_theme = 'sphinx_rtd_theme' + +# Theme options are theme-specific and customize the look and feel of a theme +# further. For a list of options available for each theme, see the +# documentation. +# +# html_theme_options = {} + +# Add any paths that contain custom static files (such as style sheets) here, +# relative to this directory. They are copied after the builtin static files, +# so a file named "default.css" will overwrite the builtin "default.css". +html_static_path = ['_static'] + +# Custom sidebar templates, must be a dictionary that maps document names +# to template names. +# +# The default sidebars (for documents that don't match any pattern) are +# defined by theme itself. Builtin themes are using these templates by +# default: ``['localtoc.html', 'relations.html', 'sourcelink.html', +# 'searchbox.html']``. +# +# html_sidebars = {} + + +# -- Options for HTMLHelp output --------------------------------------------- + +# Output file base name for HTML help builder. +htmlhelp_basename = 'hs-web3doc' + + +# -- Options for LaTeX output ------------------------------------------------ + +latex_elements = { + # The paper size ('letterpaper' or 'a4paper'). + # + # 'papersize': 'letterpaper', + + # The font size ('10pt', '11pt' or '12pt'). + # + # 'pointsize': '10pt', + + # Additional stuff for the LaTeX preamble. + # + # 'preamble': '', + + # Latex figure (float) alignment + # + # 'figure_align': 'htbp', +} + +# Grouping the document tree into LaTeX files. List of tuples +# (source start file, target name, title, +# author, documentclass [howto, manual, or own class]). +latex_documents = [ + (master_doc, 'hs-web3.tex', 'hs-web3 Documentation', + 'Alexander Krupenkin', 'manual'), +] + + +# -- Options for manual page output ------------------------------------------ + +# One entry per manual page. List of tuples +# (source start file, name, description, authors, manual section). +man_pages = [ + (master_doc, 'hs-web3', 'hs-web3 Documentation', + [author], 1) +] + + +# -- Options for Texinfo output ---------------------------------------------- + +# Grouping the document tree into Texinfo files. List of tuples +# (source start file, target name, title, author, +# dir menu entry, description, category) +texinfo_documents = [ + (master_doc, 'hs-web3', 'hs-web3 Documentation', + author, 'hs-web3', 'One line description of project.', + 'Miscellaneous'), +] diff --git a/docs/contributing.rst b/docs/contributing.rst new file mode 100644 index 00000000..b31b2f72 --- /dev/null +++ b/docs/contributing.rst @@ -0,0 +1,20 @@ +Contributing +============ + +Did you find a bug? +~~~~~~~~~~~~~~~~~~~ + +* **Ensure the bug was not already reported** by searching on GitHub under `Issues `_. + +* If you're unable to find an open issue addressing the problem, `open a new one `_. Be sure to include a **title and clear description**, as much relevant information as possible. + +Also you can open an issue if you have a proposal for an improvements. + +Did you write a patch that fixes a bug? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +* Open a new GitHub pull request with the patch. + +* Ensure the PR description clearly describes the problem and solution. Include the relevant issue number if applicable. + +Thanks! diff --git a/docs/ens.rst b/docs/ens.rst new file mode 100644 index 00000000..26534a2c --- /dev/null +++ b/docs/ens.rst @@ -0,0 +1,24 @@ +Ethereum Name Service +===================== + +`ENS `_ offers a secure & decentralised way to address resources both on and off the blockchain using simple, human-readable names. + +.. note:: + + Experimental ENS on Ethereum mainnet added in release ``0.8``. + +For resolving addresses from ENS names please use ``resolve`` function from `Network.Ethereum.Ens `_. + +.. code-block:: haskell + + import qualified Network.Ethereum.Ens as Ens + import Network.Ethereum.Web3 + import Lens.Micro ((.~)) + + main = runWeb3 $ withAccount () $ do + alice <- Ens.resolve "aliceaccount.eth" + + withParam (to .~ alice) $ + withParam (value .~ (1 :: Ether)) $ + send () + diff --git a/docs/ethereum_accounts.rst b/docs/ethereum_accounts.rst new file mode 100644 index 00000000..6dbb3a58 --- /dev/null +++ b/docs/ethereum_accounts.rst @@ -0,0 +1,144 @@ +Ethereum accounts +================= + +.. note:: + + `Ethereum whitepaper `_ mention two types of accounts: smart contract and external owned account (EOA). But EOA only can send transaction to network. In this page EOA managing and generalized transaction sending is described. + +**hs-web3** support a few kinds of EOA described in table below. + + ============== ======================================================================= + Type Description + ============== ======================================================================= + Default_ typically first of node accounts list, **should be unlocked** + Personal_ available via ``personal_*`` JSON-RPC, **password required** + PrivateKey_ derived from secp256k1 private key, use JSON-RPC `sendRawTransaction` + ============== ======================================================================= + +.. _Default: http://hackage.haskell.org/package/web3/docs/Network-Ethereum-Account-Default.html +.. _Personal: http://hackage.haskell.org/package/web3/docs/Network-Ethereum-Account-Personal.html +.. _PrivateKey: http://hackage.haskell.org/package/web3/docs/Network-Ethereum-Account-PrivateKey.html + +All of them has an instance for `Account `_ typeclass. + +.. code-block:: haskell + + class MonadTrans t => Account a t | t -> a where + -- | Run computation with given account credentials + withAccount :: JsonRpc m => a -> t m b -> m b + + -- | Send transaction to contract, like a 'write' command + send :: (JsonRpc m, Method args) => args -> t m TxReceipt + + -- | Call constant method of contract, like a 'read' command + call :: (JsonRpc m, Method args, AbiGet result) => args -> t m result + +The ``Account`` is a `multi-parameter typeclass `_ that define most important EOA actions. + +Account managing +~~~~~~~~~~~~~~~~ + +The first parameter of ``Account`` typeclass is an account internal params presended as independent data type. + +.. code-block:: haskell + + -- | Unlockable node managed account params + data Personal = Personal + { personalAddress :: !Address + , personalPassphrase :: !Passphrase + } deriving (Eq, Show) + +In this example ``Personal`` data contains of two params: personal account address and password. For using account credentials ``Account`` typeclass provide special function ``withAccount``. + +.. code-block:: haskell + + -- | Run computation with given account credentials + withAccount :: JsonRpc m => a -> t m b -> m b + +``withAccount`` function takes two arguments: account initialization parameters (some credentials like a password or private key) and computation to run it in given account context. Finally it returns ``JsonRpc`` computation that can be runned using any web3 provider. + +.. code-block:: haskell + + runWeb3 $ do + + -- Run with default account context + withAccount () $ ... + + -- Run with personal account context + withAccount (Personal "0x..." "password") $ ... + + +Transaction sending +~~~~~~~~~~~~~~~~~~~ + + +The second parameter of ``Account`` typeclass is transaction parametrization monad. This monad do one thing - prepare transaction parameters before call. + +.. note:: + + Transaction sending diagram by layer looks like ``provider -> account -> transaction``, provider at low level, account at middle layer and transaction former at high level. + +``withParam`` is a special function, it behaviour is very similar to ``withStateT`` function. It used to set parameters of transaction locally and revert params after out of scope. + +.. code-block:: haskell + + withParam :: Account p (AccountT p) + => (CallParam p -> CallParam p) + -> AccountT p m a + -> AccountT p m a + +The first argument of ``withParam`` function is state transition function, second - the computation to run in context of changed state. ``CallParam`` helps to parametrize transaction sending, `lenses `_ is very useful for this purpose. + +.. code-block:: haskell + + runWeb3 $ + withAccount () $ + withParam (to .~ alice) $ + ... + +Where lens ``to`` is used for setting transaction recipient address. All transaction parametrization lenses presended in table below. + + ==================================================================================================== ====================== + Lens Description + ==================================================================================================== ====================== + `to `_ Recipient address + `value `_ Transaction value + `gasLimit `_ Execution gas limit + `gasPrice `_ Gas price + `block `_ Execution block (for call only) + `account `_ Account credentials + ==================================================================================================== ======================= + +.. note:: + + By default transaction gas limit estimated according to transaction input but it also can be set manually. + +Finally for sending transactions ``Account`` typeclass provide two functions: + +.. code-block:: haskell + + -- | Send transaction to contract, like a 'write' command + send :: (JsonRpc m, Method args) => args -> t m TxReceipt + + -- | Call constant method of contract, like a 'read' command + call :: (JsonRpc m, Method args, AbiGet result) => args -> t m result + +.. note:: + + Functions above can be run in account context only and transaction parameters should be set before. + +Safe transactions +~~~~~~~~~~~~~~~~~ + +Default behaviour of ``send`` function is send transaction and waiting for transaction receipt. It does mean that transaction is already in blockchain when execution flow get back. But finalization in Ethereum is probabilistic. For this reason waiting for some count of confirmation is a good practics for safe transaction sending. + +.. note:: + + Vitalik Buterin `blog post `_ describe how much confirmation is required for high probability of transaction finality. For using this value import ``safeConfirmations`` from ``Network.Ethereum.Account.Safe`` module. + +Module ``Network.Ethereum.Account.Safe`` implements function ``safeSend``. It very similar to ``send`` but take count of transaction confirmation as first argument. + +.. code-block:: haskell + + send = safeSend 0 + diff --git a/docs/ethereum_node_api.rst b/docs/ethereum_node_api.rst new file mode 100644 index 00000000..34484588 --- /dev/null +++ b/docs/ethereum_node_api.rst @@ -0,0 +1,84 @@ +Ethereum node API +================= + +Any Ethereum node can export their `Generic JSON-RPC `_. For connection with node **hs-web3** use internal tiny JSON-RPC client. + +.. note:: + + Tiny client library placed at ``Network.JsonRpc.TinyClient``. It exports special monad ``JsonRpc`` and function ``remote`` to define JSON-RPC methods. When developing tiny client I was inspired `HaXR library `_. + +Providers +~~~~~~~~~ + +To handle connection with Ethereum node some thing named **provider** is required. ``Provider`` data type define the endpoint of Ethereum node API. Module that export this type placed at ``Network.Ethereum.Api.Provider``. + +.. code-block:: haskell + + data Provider = HttpProvider String + +.. note:: + + Currently **hs-web3** support HTTP(S) providers only. + +Another interesting thing in this module is ``Web3`` type. + +.. code-block:: haskell + + newtype Web3 a = ... + instance Monad Web3 + instance JsonRpc Web3 + +As you can see ``Web3`` is monad that can handle JSON-RPC. It's very important because it can be used for any Ethereum node communication. + +.. note:: + + ``Web3`` is a `state monad `_ with ``JsonRpcClient`` type as a state. This is mean that you can modify JSON-RPC server URI in runtime using `MTL lenses `_ for example. + +Finally provider module exports ``runWeb3`` and party functions. + +.. code-block:: haskell + + runWeb3' :: MonadIO m => Provider -> Web3 a -> m (Either Web3Error a) + + runWeb3 :: MonadIO m => Web3 a -> m (Either Web3Error a) + runWeb3 = runWeb3' def + +.. note:: + + Function ``runWeb3`` run default provider at **http://localhost:8545**. + +Lets try to call custom Ethereum node URI with ``runWeb3'`` function using ``ghci``. + +.. code-block:: haskell + + > import Network.Ethereum.Api.Provider + > import qualified Network.Ethereum.Api.Eth as Eth + > runWeb3' (HttpProvider "http://localhost:9545") Eth.blockNumber + +It can be useful to define function with custom Ethereum node endpoint location. + +.. code-block:: haskell + + myNode :: Web3 a -> Either Web3Error a + myNode = runWeb3' (HttpProvider "http://my-host-name:8545") + +API Reference +~~~~~~~~~~~~~ + +Currently implemented the following Ethereum APIs in modules: + + =============== ================ + Method prefix Implementation + =============== ================ + ``eth_*`` `Network.Ethereum.Api.Eth `_ + ``net_*`` `Network.Ethereum.Api.Net `_ + ``web3_*`` `Network.Ethereum.Api.Web3 `_ + ``personal_*`` `Network.Ethereum.Api.Personal `_ + =============== ================ + +All modules use descriptive types according to official Ethereum specification. It placed at `Network.Ethereum.Api.Types `_. + +.. note:: + + See classic API reference at `Hackage web3 page `_. + diff --git a/docs/getting_started.rst b/docs/getting_started.rst new file mode 100644 index 00000000..b94c20ca --- /dev/null +++ b/docs/getting_started.rst @@ -0,0 +1,55 @@ +Getting started +=============== + +.. note:: + **hs-web3** is a Haskell library. Of course you should have some knowledge about Haskell and platform tools like a `cabal` or `stack`. If you have not - `Real World Haskell `_ and `Learn You a Haskell for Great Good `_ is a good point to begin. + +Installation +~~~~~~~~~~~~ + +**Simplest way** is using `Stackage `_ with `Nix `_ integration. + +.. code-block:: bash + + stack install web3 --nix + +Dependencies for building from source without Nix: + +- `zlib `_ +- optional: `solidity `_ + +Quick start +~~~~~~~~~~~ + +Lets import library entrypoint modules using ``ghci``: + +.. code-block:: haskell + + > import Network.Ethereum.Web3 + > import qualified Network.Ethereum.Api.Eth as Eth + +.. note:: + + I recomend to import `Network.Ethereun.Api.Eth` as **qualified**, because it has name similar to their prefix in JSON-RPC API. + +Looks anything in ``Eth`` API: + +.. code-block:: haskell + + > :t Eth.blockNumber + Eth.blockNumber :: JsonRpc m => m Quantity + +To run it use ``runWeb3`` function: + +.. code-block:: haskell + + > :t runWeb3 + runWeb3 :: MonadIO m => Web3 a -> m (Either Web3Error a) + + > runWeb3 Eth.blockNumber + Right 6601059 + +.. note:: + + Function ``runWeb3`` run default provider at **http://localhost:8545**, for using custom providers try to use ``runWeb3'``. + diff --git a/docs/index.rst b/docs/index.rst new file mode 100644 index 00000000..44c4c4e8 --- /dev/null +++ b/docs/index.rst @@ -0,0 +1,24 @@ +Haskell Web3 Documentation +========================== + +**hs-web3** is a Haskell library for interacting with Ethereum. It implements `Generic JSON-RPC `_ client for most popular Ethereum nodes: `parity-ethereum `_ and `go-ethereum `_. + +.. toctree:: + :caption: User documentation + + getting_started + ethereum_node_api + polkadot_node_api + polkadot_storage + polkadot_extrinsic + ethereum_accounts + smart_contracts + ipfs_client_api + ens + +.. toctree:: + :caption: Developer documentation + + contributing + testing + diff --git a/docs/ipfs_client_api.rst b/docs/ipfs_client_api.rst new file mode 100644 index 00000000..0b328765 --- /dev/null +++ b/docs/ipfs_client_api.rst @@ -0,0 +1,69 @@ +Ipfs Client API +================= + +As many Ethereum Dapps use Ipfs for data storage, an `Ipfs Client Api `_ has been included. + +.. note:: + + The api client is placed at ``Network.Ipfs.Api``. ``Network.Ipfs.Api.Ipfs`` exports the api functions. + +Api Type +~~~~~~~~ + +The api type is defined in ``Network.Ipfs.Api.Api``. The client uses the `Servant `_ Library. + +.. code-block:: haskell + + ipfsApi :: Proxy IpfsApi + ipfsApi = Proxy + + _cat :<|> _ls ... :<|> _shutdown = client ipfsApi + +The aeson definitions of the data types returned by the api functions are also present in ``Network.Ipfs.Api.Api``. + +Monad Runner +~~~~~~~~~~~~ + +``Network.Ipfs.Api.Ipfs`` exports ``runIpfs`` monad runner and api functions. + +.. code-block:: haskell + + runIpfs' :: BaseUrl -> Ipfs a -> IO () + + runIpfs :: Ipfs a -> IO () + runIpfs = runIpfs' (BaseUrl Http "localhost" 5001 "/api/v0") + +.. note:: + + As you can see ``runIpfs`` uses the default BaseUrl at **http://localhost:5001/api/v0/** . + +You can create a `BaseUrl `_ instance for any other IPFS Api provider and pass it to **runIpfs'**. + +Example of calling functions (Non-Stream) with runIpfs : + +.. code-block:: haskell + + main = I.runIpfs $ do + ret <- I.cat + +Cid should be of the type Text. + +Call Functions +~~~~~~~~~~~~~~ + +There are three type of call functions: + + ================ ======================================================================= + Type Description + ================ ======================================================================= + call Regular Call function. + multipartCall Call function for ‘multipart/form-data’. + streamCall Call function for Streams. + ================ ======================================================================= + +As streamCall returns IO(), the API functions using it has to be called with **liftIO** (Specified in Function Documentation). + +.. code-block:: haskell + + main = I.runIpfs $ do + ret3 <- liftIO $ I.repoVerify diff --git a/docs/polkadot_extrinsic.rst b/docs/polkadot_extrinsic.rst new file mode 100644 index 00000000..adeadf1a --- /dev/null +++ b/docs/polkadot_extrinsic.rst @@ -0,0 +1,46 @@ +Polkadot Extrinsic +================== + +Extrinsic is a piece of data from external world that proposed to be a part of blockchain. Generally exist two kinds of extrinsics: ``unsigned`` (inherents) and ``signed`` (transactions). + +Lets try to send Polkadot transaction with ``runWeb3'`` function using ``ghci``. + +.. code-block:: haskell + + > import Network.Web3.Provider + > import Network.Polkadot + +The first, let's create new one account. + +.. code-block:: haskell + + > me <- generate :: IO Ed25519 + > multi_signer me + "5D7c97BufUFEqrGGn2nyw5HhgMTzQT2YkBZ33mojWwBijFLQ" + +Where ``Ed25519`` generated and its Base58 encoded address printed out. I've use ``multi_signer`` wrapper because of ``MultiAddress`` format used in Polkadot. + +The next, let's make a call structure that encodes function arguments and parameters required for Polkadot runtime dispatcher. + +.. code-block:: haskell + + > let Right alice = from_ss58check "5GrwvaEF5zXb26Fz9rcQpDWS57CtERHpNehXCPcNoHGKutQY" + > Right myCall <- runWeb3' (WsProvider "127.0.0.1" 9944) $ new_call "Balances" "transfer" (MaId alice, Compact 200000000000000) + > myCall + Call 0 5 (MaId 0xd43593c715fdd31c61141abd04a99fd6822c8558854ccde39a5684e7a56da27d, Compact 200000000000000) + +Where ``alice`` is transfer destination account on chain, ``from_ss58check`` decodes it from Base58 and pack into ``AccountId`` type. It also should be wrapped in call arguments into ``MultiAddress`` type using ``MaId`` constructor. The ``new_call`` function gets module name, function name, arguments tuple and returns encodable structure for Polkadot runtime dispatcher. + +Next step is signing the call and other extrinsic related staff like lifetime, nonce and etc. Fortunately, Haskell Web3 has ``sign_and_send`` function that makes it automatically. + +.. code-block:: haskell + + > Right myTx <- runWeb3' (WsProvider "127.0.0.1" 9944) $ sign_and_send me myCall 0 + > myTx + 0x9034fb2c7e46b5de6e681565a657cefc32fb2aa93c21aad03acc20b79fb31e68 + +The ``sign_and_send`` function gets crypto pair to sign extrinsic, the call structure and tips amount (zero is acceptable in general case). If everything ok then you will get transaction hash as result. + +.. note:: + + More usage details available in `Polkadot example `_ app. diff --git a/docs/polkadot_node_api.rst b/docs/polkadot_node_api.rst new file mode 100644 index 00000000..e7364313 --- /dev/null +++ b/docs/polkadot_node_api.rst @@ -0,0 +1,50 @@ +Polkadot node API +================= + +As same as Ethereum nodes Polkadot node exports HTTP/WebSockets `JSON-RPC` API. For connection with node **hs-web3** use internal tiny JSON-RPC client. + +Lets try to call Polkadot node with ``runWeb3'`` function using ``ghci``. + +.. code-block:: haskell + + > import Network.Web3.Provider + > import qualified Network.Polkadot.Api.System as System + > runWeb3' (WsProvider "127.0.0.1" 9944) $ System.name + Right "Parity Polkadot" + +It can be useful to define function with Polkadot node endpoint location. + +.. code-block:: haskell + + myNode :: Web3 a -> Either Web3Error a + myNode = runWeb3' (Wsprovider "127.0.0.1" 9944) + +API Reference +~~~~~~~~~~~~~ + +Currently implemented the following Polkadot APIs in modules: + + ================== ================ + Method prefix Implementation + ================== ================ + ``account_*`` `Network.Polkadot.Api.Account `_ + ``author_*`` `Network.Polkadot.Api.Author `_ + ``babe_*`` `Network.Polkadot.Api.Babe `_ + ``chain_*`` `Network.Polkadot.Api.Chain `_ + ``childstate_*`` `Network.Polkadot.Api.Childstate `_ + ``contracts_*`` `Network.Polkadot.Api.Contracts `_ + ``engine_*`` `Network.Polkadot.Api.Engine `_ + ``grandpa_*`` `Network.Polkadot.Api.Grandpa `_ + ``offchain_*`` `Network.Polkadot.Api.Offchain `_ + ``payment_*`` `Network.Polkadot.Api.Payment `_ + ``rpc_*`` `Network.Polkadot.Api.Rpc `_ + ``state_*`` `Network.Polkadot.Api.State `_ + ``system_*`` `Network.Polkadot.Api.System `_ + ================== ================ + +All modules use descriptive types located at `Network.Polkadot.Api.Types `_. + +.. note:: + + See classic API reference at `Hackage web3 page `_. + diff --git a/docs/polkadot_storage.rst b/docs/polkadot_storage.rst new file mode 100644 index 00000000..cad7df17 --- /dev/null +++ b/docs/polkadot_storage.rst @@ -0,0 +1,26 @@ +Polkadot Storage +================ + +Blockchains that are built with Substrate expose a remote procedure call (RPC) server +that can be used to query runtime storage. In Haskell Web3 the standard Web3 provider could be used. + +Lets try to query Polkadot storage with ``runWeb3'`` function using ``ghci``. + +.. code-block:: haskell + + > import Network.Web3.Provider + > import Network.Polkadot + > runWeb3' (WsProvider "127.0.0.1" 9944) (query "timestamp" "now" [] :: Web3 (Either String Moment)) + Right (Right 1610689972001) + +The ``query`` function arguments is **section** (or module), **method** and list of arguments (for maps and double maps). + +.. code-block:: haskell + + query :: (JsonRpc m, Decode a) => Text -> Text -> [Argument] -> m a + +Where ``a`` type should be SCALE decodable. + +.. note:: + + More usage details available in `Polkadot example `_ app. diff --git a/docs/smart_contracts.rst b/docs/smart_contracts.rst new file mode 100644 index 00000000..361805c5 --- /dev/null +++ b/docs/smart_contracts.rst @@ -0,0 +1,89 @@ +Smart contracts +=============== + +If Ethereum is a World Computer then smart contract is a program for that. **hs-web3** provide functions and abstractions to compile, deploy and interact with smart contracts. + +.. note:: + + Currently **Solidity** is de facto standard for Ethereum smart contract development. Please read `intro `_ to get more knowledge about Solidity smart contracts. + +Contract ABI +~~~~~~~~~~~~ + +One of the most important thing that Solidity introduce is a `contract Application Binary Interface `_. ABI is a standard for smart contract communication, both from outside the Ethereum and for contract-to-contract interaction. In hs-web3 `Quasiquotation `_ is used to parse contract JSON ABI or load from file. `TemplateHaskell `_ driven generator creates ABI encoding instances and contract method helpers automatically. + +.. code-block:: haskell + + {-# LANGUAGE DataKinds #-} + {-# LANGUAGE DeriveGeneric #-} + {-# LANGUAGE FlexibleContexts #-} + {-# LANGUAGE FlexibleInstances #-} + {-# LANGUAGE MultiParamTypeClasses #-} + {-# LANGUAGE OverloadedStrings #-} + {-# LANGUAGE QuasiQuotes #-} + module ERC20 where + + import Network.Ethereum.Contract.TH + + [abiFrom|ERC20.json|] + +Using Solidity contract ABI generator creates helper functions like a ``transfer`` and ``balanceOf``. + +.. code-block:: haskell + + transfer :: (JsonRpc m, Account a t, Functor (t m)) => Address -> UIntN 256 -> t m TxReceipt + + balanceOf :: (JsonRpc m, Account a t, Functor (t m)) => Address -> t m (UIntN 256) + +.. note:: + + Use ``-ddump-splices`` to see generated code during compilation or in GHCi. + +Helper functions wraps building and sending transaction with given argument and `function selector `_. This behaviour is very similar to `web3.js contract object `_. + +ABI encoding +~~~~~~~~~~~~ + +To build transaction input from Solidity method call special encoding is used. **hs-web3** implements Solidity ABI encoding for `primitive `_ and composed types. Codecs are placed at ``Data.Solidity.Abi.Codec``. + +.. code-block:: haskell + + encode :: (AbiPut a, ByteArray ba) => a -> ba + + decode :: (ByteArrayAccess ba, AbiGet a) => ba -> Either String a + +.. note:: + + When I develop codecs I was inspired by `cereal `_ library. As result ``AbiGet`` and ``AbiPut`` classes are analogue to cereal ``Serialize``. + +Primitive solidity types are placed at ``Data.Solidity.Prim``, this module exports types like an ``Address`` or ``UIntN``. + +.. code-block:: haskell + + > import Data.Solidity.Prim + > import Data.Solidity.Abi.Codec + > encode (42 :: UIntN 128) :: HexString + HexString "0x000000000000000000000000000000000000000000000000000000000000002a" + > encode (42 :: IntN 256, "Hello" :: Text) :: HexString + HexString "0x000000000000000000000000000000000000000000000000000000000000002a0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000548656c6c6f000000000000000000000000000000000000000000000000000000" + +Contract deployment +~~~~~~~~~~~~~~~~~~~ + +To deploy smart contract special function with name ``new`` is used. + +.. code-block:: haskell + + -- | Create new smart contract on blockchain + new :: (Account p t, JsonRpc m, Method a, Monad (t m)) + => a + -- ^ Contract constructor + -> t m (Maybe Address) + -- ^ Address of deployed contract when transaction success + +This function use ``Method`` instance of contract constructor (``*Contract`` data type) to encode transaction input and send it without destination to create new contract. + +.. code-block:: haskell + + Just address <- runWeb3 $ withAccount () $ withParam id $ new SimpleStorageContract + diff --git a/docs/testing.rst b/docs/testing.rst new file mode 100644 index 00000000..7d24687d --- /dev/null +++ b/docs/testing.rst @@ -0,0 +1,12 @@ +Testing +======= + +Testing the **web3** is split up into two suites: **unit** and **live**. + +- The unit suite tests internal library facilities. +- The live tests that the library adequately interacts with a Web3 provider. + +One may simply run ``stack test`` to run both suites, or ``stack test web3:unit`` or ``stack test web3:live`` to run the test suites individually. + +.. note:: + The live suite also requires a Web3 provider with Ethereum capabilities, as well as an unlocked account with ether to send transactions from. diff --git a/examples/TokenInfo.hs b/examples/TokenInfo.hs deleted file mode 100644 index e0f1c885..00000000 --- a/examples/TokenInfo.hs +++ /dev/null @@ -1,29 +0,0 @@ -{-# LANGUAGE OverloadedStrings #-} -module Main where - -import Data.Default (def) -import Data.Text (unpack) -import Text.Printf (printf) - -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 hiding (name) - -import ERC20 - -main :: IO () -main = do - result <- runWeb3 $ do - n <- name tokenCall - s <- symbol tokenCall - d <- decimals tokenCall - return $ printf "Token %s with symbol %s and decimals %d" - (unpack n) (unpack s) (fromIntegral d :: Int) - case result of - Left err -> print err - Right info -> putStrLn info - where - token :: Address - token = "0xA2f4FCb0FDe2dD59f7a1873e121bc5623e3164Eb" - - tokenCall :: Call - tokenCall = def { callTo = Just token } diff --git a/examples/ERC20.hs b/examples/erc20/ERC20.hs similarity index 83% rename from examples/ERC20.hs rename to examples/erc20/ERC20.hs index da17f14d..418f7bf7 100644 --- a/examples/ERC20.hs +++ b/examples/erc20/ERC20.hs @@ -1,5 +1,6 @@ {-# LANGUAGE DataKinds #-} {-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE OverloadedStrings #-} @@ -8,4 +9,4 @@ module ERC20 where import Network.Ethereum.Contract.TH -[abiFrom|examples/ERC20.json|] +[abiFrom|ERC20.json|] diff --git a/examples/ERC20.json b/examples/erc20/ERC20.json similarity index 100% rename from examples/ERC20.json rename to examples/erc20/ERC20.json diff --git a/examples/erc20/Main.hs b/examples/erc20/Main.hs new file mode 100644 index 00000000..1737b90b --- /dev/null +++ b/examples/erc20/Main.hs @@ -0,0 +1,26 @@ +{-# LANGUAGE OverloadedStrings #-} +module Main where + +import Data.Default (def) +import Data.Text (unpack) +import Lens.Micro ((.~)) +import Network.Ethereum hiding (name) +import Network.Ethereum.Account +import Network.Web3 +import Text.Printf (printf) + +import ERC20 + +main :: IO () +main = do + result <- runWeb3 $ + withAccount () $ + withParam (to .~ "0xA2f4FCb0FDe2dD59f7a1873e121bc5623e3164Eb") $ do + n <- name + s <- symbol + d <- decimals + return $ printf "Token %s with symbol %s and decimals %d" + (unpack n) (unpack s) (fromIntegral d :: Int) + case result of + Left err -> error (show err) + Right info -> putStrLn info diff --git a/examples/erc20/example-erc20.cabal b/examples/erc20/example-erc20.cabal new file mode 100644 index 00000000..f5b7cd27 --- /dev/null +++ b/examples/erc20/example-erc20.cabal @@ -0,0 +1,38 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.37.0. +-- +-- see: https://github.com/sol/hpack + +name: example-erc20 +version: 0.0.0.0 +synopsis: ERC20 token example. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2021 +license: Apache-2.0 +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +executable example-erc20 + main-is: Main.hs + other-modules: + ERC20 + Paths_example_erc20 + hs-source-dirs: + ./ + ghc-options: -threaded -rtsopts -with-rtsopts=-N + build-depends: + base + , data-default + , microlens + , text + , web3 + , web3-ethereum + default-language: Haskell2010 diff --git a/examples/erc20/package.yaml b/examples/erc20/package.yaml new file mode 100644 index 00000000..bf5889cc --- /dev/null +++ b/examples/erc20/package.yaml @@ -0,0 +1,26 @@ +name: example-erc20 +version: 0.0.0.0 +synopsis: ERC20 token example. +github: "airalab/hs-web3" +license: Apache-2.0 +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2021" +category: Network + +dependencies: +- base +- text +- web3 +- microlens +- data-default +- web3-ethereum + +executables: + example-erc20: + main: Main.hs + source-dirs: ./ + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/examples/polkadot/Main.hs b/examples/polkadot/Main.hs new file mode 100644 index 00000000..2f6a86e9 --- /dev/null +++ b/examples/polkadot/Main.hs @@ -0,0 +1,46 @@ +{-# LANGUAGE OverloadedStrings #-} +module Main where + +import Control.Monad.IO.Class (liftIO) + +import Network.Polkadot +import qualified Network.Polkadot.Rpc.Chain as Chain +import qualified Network.Polkadot.Rpc.State as State +import qualified Network.Polkadot.Rpc.System as System +import Network.Web3.Provider (Provider (..), runWeb3') + +main :: IO () +main = do + result <- runWeb3' (HttpProvider "http://127.0.0.1:9933") $ do + name <- System.name + liftIO . putStrLn $ "System name: " ++ show name + + best <- Chain.getBlockHash Nothing + liftIO . putStrLn $ "Best hash: " ++ show best + + Right now <- query "timestamp" "now" [] + liftIO . putStrLn $ "Timestamp: " ++ show (now :: Moment) + + Right total <- query "balances" "totalIssuance" [] + liftIO . putStrLn $ "Total amount: " ++ show (total :: Balance) + + let alice = "0xd43593c715fdd31c61141abd04a99fd6822c8558854ccde39a5684e7a56da27d" :: AccountId + Right account <- query "system" "account" [Argument alice] + liftIO . putStrLn $ "Alice account: " ++ show (account :: AccountInfo) + + me <- liftIO generate + liftIO . putStrLn $ "My account: " ++ show (multi_signer (me :: Ed25519)) + + liftIO $ putStrLn "Please send 1000 Unit and press any key" + liftIO getLine + + Right account <- query "system" "account" [Argument (into_account $ multi_signer me)] + liftIO . putStrLn $ "My account: " ++ show (account :: AccountInfo) + + transfer <- new_call "Balances" "transfer" (MaId alice, Compact 200000000000000) + liftIO . putStrLn $ "Sign and send 200 Unit transfer transaction: " ++ show transfer + sign_and_send me transfer 0 + + case result of + Left err -> error (show err) + Right tx_hash -> putStrLn ("Extrinsic sent " ++ show tx_hash) diff --git a/examples/polkadot/example-polkadot.cabal b/examples/polkadot/example-polkadot.cabal new file mode 100644 index 00000000..330010d2 --- /dev/null +++ b/examples/polkadot/example-polkadot.cabal @@ -0,0 +1,36 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.37.0. +-- +-- see: https://github.com/sol/hpack +-- +-- hash: b81d48727b0e6109f04bc46ca049cfcc79d6ab939bdb985c2f325f239afaaa4e + +name: example-polkadot +version: 0.0.0.0 +synopsis: Polkadot API example. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2021 +license: Apache-2.0 +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +executable example-polkadot + main-is: Main.hs + other-modules: + Paths_example_polkadot + hs-source-dirs: + ./ + ghc-options: -threaded -rtsopts -with-rtsopts=-N + build-depends: + base + , web3-polkadot + , web3-provider + default-language: Haskell2010 diff --git a/examples/polkadot/package.yaml b/examples/polkadot/package.yaml new file mode 100644 index 00000000..d7bf097a --- /dev/null +++ b/examples/polkadot/package.yaml @@ -0,0 +1,23 @@ +name: example-polkadot +version: 0.0.0.0 +synopsis: Polkadot API example. +github: "airalab/hs-web3" +license: Apache-2.0 +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2021" +category: Network + +dependencies: +- base +- web3-provider +- web3-polkadot + +executables: + example-polkadot: + main: Main.hs + source-dirs: ./ + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/examples/scale/Main.hs b/examples/scale/Main.hs new file mode 100644 index 00000000..b75c8074 --- /dev/null +++ b/examples/scale/Main.hs @@ -0,0 +1,29 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +module Main where + +import Codec.Scale +import Codec.Scale.Skip +import Data.ByteArray.HexString (HexString) +import Data.Word (Word32) +import qualified GHC.Generics as GHC (Generic) + +data MyTransaction a = Tx + { from :: Word32 + , to :: Word32 + , balance :: Compact Integer + , note :: Skip a + } + deriving (Show, Eq, GHC.Generic, Generic, Encode, Decode) + +main :: IO () +main = do + let alice = 42 + bob = 15 + my_tx = Tx { from = alice + , to = bob + , balance = Compact 1000000 + , note = Skip "Hello!" + } + putStrLn "Encoded transaction:" + print (encode my_tx :: HexString) diff --git a/examples/scale/example-scale.cabal b/examples/scale/example-scale.cabal new file mode 100644 index 00000000..d01e133c --- /dev/null +++ b/examples/scale/example-scale.cabal @@ -0,0 +1,37 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.37.0. +-- +-- see: https://github.com/sol/hpack +-- +-- hash: 238f42572bfe1561436246f28217f679a1f9c3de71d296734e8ba3f056e71681 + +name: example-scale +version: 0.0.0.0 +synopsis: SCALE codec example. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2021 +license: Apache-2.0 +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +executable example-scale + main-is: Main.hs + other-modules: + Paths_example_scale + hs-source-dirs: + ./ + ghc-options: -threaded -rtsopts -with-rtsopts=-N + build-depends: + base + , generics-sop + , memory-hexstring + , scale + default-language: Haskell2010 diff --git a/examples/scale/package.yaml b/examples/scale/package.yaml new file mode 100644 index 00000000..35bc01dd --- /dev/null +++ b/examples/scale/package.yaml @@ -0,0 +1,24 @@ +name: example-scale +version: 0.0.0.0 +synopsis: SCALE codec example. +github: "airalab/hs-web3" +license: Apache-2.0 +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2021" +category: Network + +dependencies: +- base +- scale +- generics-sop +- memory-hexstring + +executables: + example-scale: + main: Main.hs + source-dirs: ./ + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/bignum/LICENSE b/packages/bignum/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/bignum/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/Setup.hs b/packages/bignum/Setup.hs similarity index 100% rename from Setup.hs rename to packages/bignum/Setup.hs diff --git a/packages/bignum/package.yaml b/packages/bignum/package.yaml new file mode 100644 index 00000000..506229e4 --- /dev/null +++ b/packages/bignum/package.yaml @@ -0,0 +1,63 @@ +name: web3-bignum +version: 1.1.0.0 +synopsis: Fixed size big integers for Haskell Web3 library. +description: This package implements codec instances and other helper functions. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- scale >=1.0 && <1.2 +- memory >=0.14 && <0.19 +- memory-hexstring >=1.0 && <1.2 +- cereal >=0.5 && <0.6 +- wide-word >=0.1 && <0.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + dependencies: + - memory-hexstring >=1.0 && <1.2 + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/bignum/src/Data/BigNum.hs b/packages/bignum/src/Data/BigNum.hs new file mode 100644 index 00000000..96f59bf0 --- /dev/null +++ b/packages/bignum/src/Data/BigNum.hs @@ -0,0 +1,141 @@ +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.BigNum +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Big numbers and codecs for Haskell Web3 library. +-- + +module Data.BigNum (Word256, Word128, H160, h160, H256, h256, H512, h512) where + +import Codec.Scale () +import Codec.Scale.Class (Decode (..), Encode (..)) +import Data.ByteArray (ByteArrayAccess, Bytes, + convert) +import qualified Data.ByteArray as A (length) +import Data.ByteArray.HexString.Convert (FromHex (..), ToHex (..), + fromBytes) +import Data.Maybe (fromJust) +import Data.Serialize.Get (getByteString) +import Data.Serialize.Put (putByteString) +import Data.String (IsString (..)) +import Data.WideWord.Word128 (Word128 (..)) +import Data.WideWord.Word256 (Word256 (..)) + +instance Encode Word128 where + put (Word128 l h)= put h >> put l + +instance Decode Word128 where + get = flip Word128 <$> get <*> get + +instance Encode Word256 where + put (Word256 lx hx l h) = do + put h + put l + put hx + put lx + +instance Decode Word256 where + get = do + h <- get + l <- get + hx <- get + lx <- get + return (Word256 lx hx l h) + +-- | 20 byte of data. +newtype H160 = H160 Bytes + deriving (Eq, Ord, ByteArrayAccess) + +-- | Convert any 20 byte array into H160 type, otherwise returns Nothing. +h160 :: ByteArrayAccess a => a -> Maybe H160 +h160 ba + | A.length ba == 20 = Just $ H160 (convert ba) + | otherwise = Nothing + +instance FromHex H160 where + fromHex bs + | A.length bs == 20 = Right $ H160 (convert bs) + | otherwise = Left ("wrong length: " ++ show (A.length bs)) + +instance ToHex H160 where + toHex = fromBytes + +instance Show H160 where + show = show . toHex + +instance IsString H160 where + fromString = either error id . fromHex . fromString + +instance Encode H160 where + put = putByteString . convert + +instance Decode H160 where + get = (fromJust . h160) <$> getByteString 20 + +-- | 32 byte of data. +newtype H256 = H256 Bytes + deriving (Eq, Ord, ByteArrayAccess) + +-- | Convert any 32 byte array into H256 type, otherwise returns Nothing. +h256 :: ByteArrayAccess a => a -> Maybe H256 +h256 ba + | A.length ba == 32 = Just $ H256 (convert ba) + | otherwise = Nothing + +instance FromHex H256 where + fromHex bs + | A.length bs == 32 = Right $ H256 (convert bs) + | otherwise = Left ("wrong length: " ++ show (A.length bs)) + +instance ToHex H256 where + toHex = fromBytes + +instance Show H256 where + show = show . toHex + +instance IsString H256 where + fromString = either error id . fromHex . fromString + +instance Encode H256 where + put = putByteString . convert + +instance Decode H256 where + get = (fromJust . h256) <$> getByteString 32 + +-- | 64 byte of data. +newtype H512 = H512 Bytes + deriving (Eq, Ord, ByteArrayAccess) + +-- | Convert any 64 byte array into H512 type, otherwise returns Nothing. +h512 :: ByteArrayAccess a => a -> Maybe H512 +h512 ba + | A.length ba == 64 = Just $ H512 (convert ba) + | otherwise = Nothing + +instance FromHex H512 where + fromHex bs + | A.length bs == 64 = Right $ H512 (convert bs) + | otherwise = Left ("wrong length: " ++ show (A.length bs)) + +instance ToHex H512 where + toHex = fromBytes + +instance Show H512 where + show = show . toHex + +instance IsString H512 where + fromString = either error id . fromHex . fromString + +instance Encode H512 where + put = putByteString . convert + +instance Decode H512 where + get = (fromJust . h512) <$> getByteString 64 diff --git a/packages/bignum/tests/Data/BigNum/Test/BigNumSpec.hs b/packages/bignum/tests/Data/BigNum/Test/BigNumSpec.hs new file mode 100644 index 00000000..af29ad6e --- /dev/null +++ b/packages/bignum/tests/Data/BigNum/Test/BigNumSpec.hs @@ -0,0 +1,165 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.BigNum.Test.BigNumSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.BigNum.Test.BigNumSpec where + +import Codec.Scale (decode, encode) +import Control.Monad (forM_) +import Data.ByteArray.HexString (HexString) +import Data.WideWord.Word128 (Word128) +import Data.WideWord.Word256 (Word256) +import Test.Hspec + +import Data.BigNum (H160, H256, H512) + +u128_TEST_VECTORS :: [(Word128, HexString)] +u128_TEST_VECTORS = + [ (112009765980327865299926170522124675408, "0x50e91990a464634b4fe24828d64b4454") + , (284084896039402088792232799153441440599, "0x5783434bc168dc9331cef7fcc3c2b8d5") + , (259870372860522542774055759705813848487, "0xa791e84af817d01353bcae32993681c3") + , (12195993515186872808127827346567397926, "0x26025bf77f3914a9da0759c0e7dc2c09") + , (120025979845686107711254958532305515398, "0x867322183592cf181bfd17c7b1294c5a") + , (219406308864564522421661310403439556264, "0xa8f6fcd0af3848558244edc0361e10a5") + , (257335103778365857895651839673319875231, "0x9fe2f88b84b84d90e69d81962ef098c1") + , (68063227844806979300641114110617889264, "0xf0a9ee1480f359800fba8b7a38803433") + , (216514484839331230802109899459159104812, "0x2c9d37bee2fc84f8353ba10f482ce3a2") + , (178182877230765595416853642944570021919, "0x1f587d791c7dacaddc9cfd3b1dc60c86") + , (290335692238486144820126784978954757396, "0x1425c4fd2f1831eac24a9ef4cf9e6cda") + , (165504207802320373299850049582381567447, "0xd78d3e18fb99c252d9f20af572f3827c") + , (47856636672191714454008687982296341606, "0x669c2e67a9bea69ff13aef9d5bda0024") + , (19215563179501177476867447612060366546, "0xd276ae113fdcf62025309b0669c8740e") + , (246485718903164524585854064597022275963, "0x7bf9c3072aaa0ad131067568356c6fb9") + , (197733884573414826455307878816376246254, "0xee4ff5745a481cb00cf2d6d63229c294") + , (149607475627327219754848974470897887087, "0x6f67a69790aa6b881db0546b0a5a8d70") + , (174701307382434508318829001328589289972, "0xf4399c820a79a567d4f390c2773f6e83") + , (72595801292461450864588564249737801167, "0xcfaddd2c4b20d8921f24745d58719d36") + , (68514076502642919617157448984759680837, "0x45bf3cc99096452a982b6990c6548b33") + , (216419667485302883317463919550598457261, "0xada77bf03e963b0fd16727cd6ce9d0a2") + , (116229821064613393178522103562599386123, "0x0bccdb74c7f7a3c2afb443bd9d0c7157") + , (135932484144247690375718666021027537778, "0x72633955ae336d73c58605dbe7a44366") + , (30075132366243141139951812090788233488, "0x10c1c6c0cf467e0fe1630a4a8242a016") + , (110760648836374947274219482463927908576, "0xe0b8c1e1f3221e3cbc6b4b439bb95353") + , (6493109780355214426871710723177871150, "0x2e7712cb1d7b9819004830580787e204") + , (155255127434882774479428817682909336706, "0x8294132da02c8966a7b450e5c50ccd74") + , (249558934561135206340751629864009659619, "0xe3f46e4bfe10c0cbcac4d861704dbfbb") + , (221130490312110890453383188394454522854, "0xe69bb71f38105bc2ff3c3b27ec2e5ca6") + , (330501820625969513409631107753191338114, "0x82f05ac2614f264cae56d056d655a4f8") + , (223256840663930369967277834345880002356, "0x349ff07d428288010a9f53c416b4f5a7") + , (117046551608311569426455411751697532077, "0xad4480fbf4dceacc06bbc6798a580e58") + ] + +u256_TEST_VECTORS :: [(Word256, HexString)] +u256_TEST_VECTORS = + [ (115246322816974817869522522728228591410688, "0x009e4a73c70170d062c7cfaacc68b2ad52010000000000000000000000000000") + , (135938608309138943912299509830613133361152, "0x00003bcac38e0e88ff4be1b553a2d77c8f010000000000000000000000000000") + , (162382544235100656091613459421755842104320, "0x000c62040d9eb5402b77a94756700c33dd010000000000000000000000000000") + , (87401399458010888206718906820085474987520, "0x000e25d50cdf0ebc4288bb79603d81d900010000000000000000000000000000") + , (138984606683918062873256075229427703132672, "0x00b2865449543d0bc4aee7630795657098010000000000000000000000000000") + , (80840810280826333065693090387807395201024, "0x00402505c662fed033657fec8eb9dd91ed000000000000000000000000000000") + , (111243980175912604792124852175079091625472, "0x005e221ba2a0291b64cadf565f41abea46010000000000000000000000000000") + , (68346726659358296375267195304703356056576, "0x00342cd4bdd4aae9d473a64f56bf5cdac8000000000000000000000000000000") + , (106449215354720188380210893871836123739136, "0x00b469f4f9e50e3c9692eca70c247dd338010000000000000000000000000000") + , (78137755955119804750893895610892995805184, "0x0040900a46fc58e6681fea1beb6550a0e5000000000000000000000000000000") + , (37198705638330423439614376452234760232960, "0x002001f5e1b489daa201e473ae1b32516d000000000000000000000000000000") + , (44433624903109480313359576650777141679616, "0x0096d7f1e43651f716e5dc15b5df249482000000000000000000000000000000") + , (148514051583354372738620167945095771152896, "0x0062a572ce8903fc0bb00b5c21e98d71b4010000000000000000000000000000") + , (60014954218248357909848828065675948796928, "0x002cff0f0bf45b444adacc7a76be3b5eb0000000000000000000000000000000") + , (115991051230925873672644713804764031319040, "0x007ca1f34f6509f519e1fe0979e2f7dd54010000000000000000000000000000") + , (128993277087652314984111615353153713316352, "0x00a2db3ff8e4ce7452a7afa42c7fc1137b010000000000000000000000000000") + , (79341042577632633961867710129661883276800, "0x005e51f8c00556a267f89b85cff89029e9000000000000000000000000000000") + , (107155234040248837193602796138479639672832, "0x0038b9433d32cd48b3b6ab8fc264a3e63a010000000000000000000000000000") + , (9692096688234458500324617381072327939072, "0x0014383881662b212547f6856fec857b1c000000000000000000000000000000") + , (153508611663790194252674464693195110905856, "0x0078e84497d0ae7ee3b3c51745310b1fc3010000000000000000000000000000") + , (82797952396630935803342482248562500762624, "0x00fcc41b53fdb9f05f5023d7e0954152f3000000000000000000000000000000") + , (42485067285891128074395084374077297656832, "0x00042093afeaf2b88943f460d85336da7c000000000000000000000000000000") + , (86450357619452627268531966540825354464768, "0x006e167391f2a026579817c9853e050efe000000000000000000000000000000") + , (66917117614349947545091673512474456381440, "0x0058f0bdece2a5fa4d8e9b97800fd8a6c4000000000000000000000000000000") + , (41855199301039963483087569366097332165632, "0x005c7e1023c40c3df8c71c308d2a5a007b000000000000000000000000000000") + , (79447692753915387681092309048730281646080, "0x00184905865a4f806b933431790ccd79e9000000000000000000000000000000") + , (64972869997286725725114985545674517793792, "0x004c362af3a5b3855e591bde0d9727f0be000000000000000000000000000000") + , (142291599105260490990206148836714458533888, "0x00500eb253aef52349907156b8274d28a2010000000000000000000000000000") + , (131059754944904136287166865738657526588416, "0x00246ac6cc16ea922048cd18bea7662681010000000000000000000000000000") + , (86851548177794395407641645798830201528832, "0x00624a9b253533261c8d6a1936bcd73bff000000000000000000000000000000") + , (119121986710264787758595765725140587452416, "0x00187946fbafb3f21928d1c1bf1f6c115e010000000000000000000000000000") + , (75287059147291008379624862024819049134592, "0x007a9e91c390ec87c0b8e9c1e529b03fdd000000000000000000000000000000") + ] + +h160_TEST_VECTORS :: [(H160, HexString)] +h160_TEST_VECTORS = + [ ("0x52908400098527886E0F7030069857D2E4169EE7", "0x52908400098527886E0F7030069857D2E4169EE7") + , ("0x8617E340B3D01FA5F11F306F4090FD50E238070D", "0x8617E340B3D01FA5F11F306F4090FD50E238070D") + , ("0xde709f2102306220921060314715629080e2fb77", "0xde709f2102306220921060314715629080e2fb77") + , ("0x27b1fdb04752bbc536007a920d24acb045561c26", "0x27b1fdb04752bbc536007a920d24acb045561c26") + , ("0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAed", "0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAed") + , ("0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5d359", "0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5d359") + , ("0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6FB", "0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6FB") + , ("0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDb", "0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDb") + ] + +h256_TEST_VECTORS :: [(H256, HexString)] +h256_TEST_VECTORS = + [ ("0xfe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518", "0xfe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518") + , ("0xabeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24", "0xabeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24") + , ("0xf1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33", "0xf1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33") + , ("0xd959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11", "0xd959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11") + , ("0x2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b", "0x2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b") + , ("0xb09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42", "0xb09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42") + , ("0x9afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf75386253", "0x9afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf75386253") + , ("0xebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66", "0xebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66") + , ("0x49f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f5", "0x49f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f5") + , ("0x71b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb30", "0x71b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb30") + , ("0xc850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6", "0xc850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6") + , ("0x0ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c6597", "0x0ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c6597") + , ("0xf8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1ee", "0xf8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1ee") + , ("0xb9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59a", "0xb9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59a") + ] + +h512_TEST_VECTORS :: [(H512, HexString)] +h512_TEST_VECTORS = + [ ("0xfe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518fe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518", "0xfe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518fe700a084ea8882a6661724f3f3277ef5ea9df17cd5291f80c492e537b868518") + , ("0xabeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24abeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24", "0xabeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24abeedc76bd314edcca6c7fedc0414d05a4979bbd8e17fd4f5d300a9afd953b24") + , ("0xf1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33f1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33", "0xf1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33f1555b382428aeadafa3b9cf4bbd4811d1dac92941c1d741078923844e867c33") + , ("0xd959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11d959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11", "0xd959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11d959976b19068248aa287290ae7f1c363fcab571c1775dfa16291ecf97d38e11") + , ("0x2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b", "0x2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b2fd7571b66c46c901984e148071b8fe30a5a65cc4a08c3f98b4a753abce3e40b") + , ("0xb09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42b09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42", "0xb09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42b09d4a38b291296c08a1b369ca898bfe594fa64bcc942ee5ce18511edb9bbd42") + , ("0x9afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf753862539afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf75386253", "0x9afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf753862539afd0350d2b7c8d3972478bf76c9c782d587ff3918524ed5de7753cf75386253") + , ("0xebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66ebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66", "0xebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66ebaf4fcbaa6375fa7b6e5fc96166c34ee774221f2f641fdc1b13300306a54b66") + , ("0x49f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f549f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f5", "0x49f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f549f7d9bda63d100a60e72b3b5df09f7b19bbe4bf7bb8fd6009ab3bf74c38b4f5") + , ("0x71b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb3071b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb30", "0x71b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb3071b4b1615d1c35332d222abd08008c881aa28975e0f4088ba412fcd6b506eb30") + , ("0xc850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6c850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6", "0xc850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6c850252c4c0a14ca0a55bc04077b998139d741ac3ed88db628e02468f3fcc3e6") + , ("0x0ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c65970ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c6597", "0x0ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c65970ae755268da527700201a1b042655f3fde1d9f4bfe990be1998b683d3d5c6597") + , ("0xf8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1eef8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1ee", "0xf8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1eef8caf1ee78b44e90d5dfd99cdcbe0f3b0d45b7d964ce93f60ecfa9af0dc4d1ee") + , ("0xb9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59ab9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59a", "0xb9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59ab9ccbe3823df8602145555f2c6e2e33cfc1cad5c6e053f929c68324a3627d59a") + ] + +spec :: Spec +spec = parallel $ do + describe "SCALE tests" $ do + it "u128 test vectors" $ forM_ u128_TEST_VECTORS $ \(x, l) -> do + encode x `shouldBe` l + decode l `shouldBe` Right x + + it "u256 test vectors" $ forM_ u256_TEST_VECTORS $ \(x, l) -> do + encode x `shouldBe` l + decode l `shouldBe` Right x + + it "H160 test vectors" $ forM_ h160_TEST_VECTORS $ \(x, l) -> do + encode x `shouldBe` l + decode l `shouldBe` Right x + + it "H256 test vectors" $ forM_ h256_TEST_VECTORS $ \(x, l) -> do + encode x `shouldBe` l + decode l `shouldBe` Right x + + it "H512 test vectors" $ forM_ h512_TEST_VECTORS $ \(x, l) -> do + encode x `shouldBe` l + decode l `shouldBe` Right x diff --git a/test/Spec.hs b/packages/bignum/tests/Spec.hs similarity index 100% rename from test/Spec.hs rename to packages/bignum/tests/Spec.hs diff --git a/packages/bignum/web3-bignum.cabal b/packages/bignum/web3-bignum.cabal new file mode 100644 index 00000000..7890355f --- /dev/null +++ b/packages/bignum/web3-bignum.cabal @@ -0,0 +1,64 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-bignum +version: 1.1.0.0 +synopsis: Fixed size big integers for Haskell Web3 library. +description: This package implements codec instances and other helper functions. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Data.BigNum + other-modules: + Paths_web3_bignum + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + base >=4.11 && <4.21 + , cereal ==0.5.* + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , scale >=1.0 && <1.2 + , wide-word ==0.1.* + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Data.BigNum.Test.BigNumSpec + Data.BigNum + Paths_web3_bignum + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + base >=4.11 && <4.21 + , cereal ==0.5.* + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , scale >=1.0 && <1.2 + , wide-word ==0.1.* + default-language: Haskell2010 diff --git a/packages/crypto/LICENSE b/packages/crypto/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/crypto/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/crypto/Setup.hs b/packages/crypto/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/crypto/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/crypto/package.yaml b/packages/crypto/package.yaml new file mode 100644 index 00000000..95a5b4e1 --- /dev/null +++ b/packages/crypto/package.yaml @@ -0,0 +1,76 @@ +name: web3-crypto +version: 1.1.0.0 +synopsis: Cryptograhical primitives for Haskell Web3 library. +description: This package implements Web3 specific cryptography and helper functions. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +extra-source-files: +- src/cbits/xxhash.h +- src/cbits/xxhash.c + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- aeson >=1.2 && <2.3 +- memory >=0.14 && <0.19 +- vector >=0.12 && <0.14 +- containers >=0.6 && <0.8 +- uuid-types >=1.0 && <1.1 +- crypton >=0.30 && <1.1 +- bytestring >=0.10 && <0.13 +- memory-hexstring >=1.0 && <1.2 +- basement >=0.0.16 && < 0.1 +- scientific >=0.3.7 && < 0.4 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + include-dirs: src/cbits + c-sources: src/cbits/xxhash.c + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + include-dirs: src/cbits + c-sources: src/cbits/xxhash.c + dependencies: + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/crypto/src/Crypto/Bip39.hs b/packages/crypto/src/Crypto/Bip39.hs new file mode 100644 index 00000000..1bb81752 --- /dev/null +++ b/packages/crypto/src/Crypto/Bip39.hs @@ -0,0 +1,550 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Bip39 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Mnemonic keys (BIP-39). Only English dictionary. +-- Thanks to Haskoin project . +-- + +module Crypto.Bip39 + ( -- * Mnemonic Sentences + Entropy + , Mnemonic + , Passphrase + , Seed + , toMnemonic + , fromMnemonic + , mnemonicToSeed + ) where + +import Control.Monad (when) +import Crypto.Hash (SHA256 (..), hashWith) +import Crypto.KDF.PBKDF2 (Parameters (..), fastPBKDF2_SHA512) +import Data.Bits (shiftL, shiftR, (.&.), (.|.)) +import qualified Data.ByteArray as BA +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS +import Data.List +import qualified Data.Map.Strict as M +import Data.Maybe +import Data.Text (Text) +import qualified Data.Text as T +import qualified Data.Text.Encoding as E +import Data.Vector (Vector, (!)) +import qualified Data.Vector as V +import Data.Word (Word8) + +-- | Random data used to create a mnemonic sentence. Use a good entropy source. +-- You will get your coins stolen if you don't. You have been warned. +type Entropy = ByteString + +-- | Human-readable mnemonic sentence. +type Mnemonic = Text + +-- | Optional passphrase for mnemnoic sentence. +type Passphrase = Text + +-- | Seed for a private key from a mnemonic sentence. +type Seed = ByteString + +-- | Mnemonic key checksum. +type Checksum = ByteString + +-- | Paremeters for PBKDF2 function. +pbkdfParams :: Parameters +pbkdfParams = Parameters {iterCounts = 2048, outputLength = 64} + +-- | Provide intial 'Entropy' as a 'ByteString' of length multiple of 4 bytes. +-- Output a 'Mnemonic' sentence. +toMnemonic :: Entropy -> Either String Mnemonic +toMnemonic ent = do + when (BS.null ent) $ + Left "toMnemonic: entropy can not be empty" + when (remainder /= 0) $ + Left "toMnemonic: entropy must be multiples of 4 bytes" + when (cs_len > 16) $ + Left "toMnemonic: maximum entropy is 64 bytes (512 bits)" + return ms + where + (cs_len, remainder) = BS.length ent `quotRem` 4 + c = calcCS cs_len ent + indices = bsToIndices $ ent `BS.append` c + ms = T.unwords $ map (wl!) indices + +-- | Revert 'toMnemonic'. Do not use this to generate a 'Seed'. Instead use +-- 'mnemonicToSeed'. This outputs the original 'Entropy' used to generate a +-- 'Mnemonic' sentence. +fromMnemonic :: Mnemonic -> Either String Entropy +fromMnemonic ms = do + when (T.null ms) $ + Left "fromMnemonic: empty mnemonic" + when (word_count > 48) $ + Left $ "fromMnemonic: too many words: " ++ show word_count + when (word_count `mod` 3 /= 0) $ + Left $ "fromMnemonic: wrong number of words:" ++ show word_count + ms_bs <- indicesToBS =<< getIndices ms_words + let (ms_ent, ms_cs) = BS.splitAt (ent_len * 4) ms_bs + ms_cs_num = numCS cs_len ms_cs + ent_cs_num = numCS cs_len $ calcCS cs_len ms_ent + when (ent_cs_num /= ms_cs_num) $ + Left $ "fromMnemonic: checksum failed: " ++ sh ent_cs_num ms_cs_num + return ms_ent + where + ms_words = T.words ms + word_count = length ms_words + (ent_len, cs_len) = (word_count * 11) `quotRem` 32 + sh cs_a cs_b = show cs_a ++ " /= " ++ show cs_b + +-- | Compute 'Checksum'. +calcCS :: Int -> Entropy -> Checksum +calcCS len = getBits len . BA.convert . hashWith SHA256 + +numCS :: Int -> Entropy -> Integer +numCS len = + shiftCS . bsToInteger + where + shiftCS = case 8 - len `mod` 8 of + 8 -> id + x -> flip shiftR x + +-- | Turn an arbitrary sequence of characters into a 512-bit 'Seed'. Use +-- 'mnemonicToSeed' to get a seed from a 'Mnemonic' sentence. Warning: Does not +-- perform NFKD normalization. +anyToSeed :: Passphrase -> Mnemonic -> Seed +anyToSeed pf ms = + fastPBKDF2_SHA512 + pbkdfParams + (E.encodeUtf8 ms) + ("mnemonic" `mappend` E.encodeUtf8 pf) + +-- | Get a 512-bit 'Seed' from a 'Mnemonic' sentence. Will validate checksum. +-- 'Passphrase' can be used to protect the 'Mnemonic'. Use an empty string as +-- 'Passphrase' if none is required. +mnemonicToSeed :: Passphrase -> Mnemonic -> Either String Seed +mnemonicToSeed pf ms = do + ent <- fromMnemonic ms + mnm <- toMnemonic ent + return $ anyToSeed pf mnm + +-- | Get indices of words in word list. +getIndices :: [Text] -> Either String [Int] +getIndices ws + | null n = return $ catMaybes i + | otherwise = Left $ "getIndices: words not found: " ++ show w + where + i = map (`M.lookup` wl') ws + n = elemIndices Nothing i + w = T.unwords $ map (ws !!) n + +-- | Turn a list of 11-bit numbers into a 'ByteString' +indicesToBS :: [Int] -> Either String ByteString +indicesToBS is = do + when lrg $ Left "indicesToBS: index larger or equal than 2048" + return . pad . integerToBS $ foldl' f 0 is `shiftL` shift_width + where + lrg = isJust $ find (>= 2048) is + (q, r) = (length is * 11) `quotRem` 8 + shift_width = + if r == 0 + then 0 + else 8 - r + bl = + if r == 0 + then q + else q + 1 -- length of resulting ByteString + pad bs = BS.append (BS.replicate (bl - BS.length bs) 0x00) bs + f acc x = (acc `shiftL` 11) + fromIntegral x + +-- | Turn a 'ByteString' into a list of 11-bit numbers. +bsToIndices :: ByteString -> [Int] +bsToIndices bs = + reverse . go q $ bsToInteger bs `shiftR` r + where + (q, r) = (BS.length bs * 8) `quotRem` 11 + go 0 _ = [] + go n i = fromIntegral (i `mod` 2048) : go (n - 1) (i `shiftR` 11) + +wl' :: M.Map Text Int +wl' = V.ifoldr' (\i w m -> M.insert w i m) M.empty wl + +-- | Standard English dictionary from BIP-39 specification. +wl :: Vector Text +wl = V.fromListN 2048 + [ "abandon", "ability", "able", "about", "above", "absent" + , "absorb", "abstract", "absurd", "abuse", "access", "accident" + , "account", "accuse", "achieve", "acid", "acoustic", "acquire" + , "across", "act", "action", "actor", "actress", "actual" + , "adapt", "add", "addict", "address", "adjust", "admit" + , "adult", "advance", "advice", "aerobic", "affair", "afford" + , "afraid", "again", "age", "agent", "agree", "ahead" + , "aim", "air", "airport", "aisle", "alarm", "album" + , "alcohol", "alert", "alien", "all", "alley", "allow" + , "almost", "alone", "alpha", "already", "also", "alter" + , "always", "amateur", "amazing", "among", "amount", "amused" + , "analyst", "anchor", "ancient", "anger", "angle", "angry" + , "animal", "ankle", "announce", "annual", "another", "answer" + , "antenna", "antique", "anxiety", "any", "apart", "apology" + , "appear", "apple", "approve", "april", "arch", "arctic" + , "area", "arena", "argue", "arm", "armed", "armor" + , "army", "around", "arrange", "arrest", "arrive", "arrow" + , "art", "artefact", "artist", "artwork", "ask", "aspect" + , "assault", "asset", "assist", "assume", "asthma", "athlete" + , "atom", "attack", "attend", "attitude", "attract", "auction" + , "audit", "august", "aunt", "author", "auto", "autumn" + , "average", "avocado", "avoid", "awake", "aware", "away" + , "awesome", "awful", "awkward", "axis", "baby", "bachelor" + , "bacon", "badge", "bag", "balance", "balcony", "ball" + , "bamboo", "banana", "banner", "bar", "barely", "bargain" + , "barrel", "base", "basic", "basket", "battle", "beach" + , "bean", "beauty", "because", "become", "beef", "before" + , "begin", "behave", "behind", "believe", "below", "belt" + , "bench", "benefit", "best", "betray", "better", "between" + , "beyond", "bicycle", "bid", "bike", "bind", "biology" + , "bird", "birth", "bitter", "black", "blade", "blame" + , "blanket", "blast", "bleak", "bless", "blind", "blood" + , "blossom", "blouse", "blue", "blur", "blush", "board" + , "boat", "body", "boil", "bomb", "bone", "bonus" + , "book", "boost", "border", "boring", "borrow", "boss" + , "bottom", "bounce", "box", "boy", "bracket", "brain" + , "brand", "brass", "brave", "bread", "breeze", "brick" + , "bridge", "brief", "bright", "bring", "brisk", "broccoli" + , "broken", "bronze", "broom", "brother", "brown", "brush" + , "bubble", "buddy", "budget", "buffalo", "build", "bulb" + , "bulk", "bullet", "bundle", "bunker", "burden", "burger" + , "burst", "bus", "business", "busy", "butter", "buyer" + , "buzz", "cabbage", "cabin", "cable", "cactus", "cage" + , "cake", "call", "calm", "camera", "camp", "can" + , "canal", "cancel", "candy", "cannon", "canoe", "canvas" + , "canyon", "capable", "capital", "captain", "car", "carbon" + , "card", "cargo", "carpet", "carry", "cart", "case" + , "cash", "casino", "castle", "casual", "cat", "catalog" + , "catch", "category", "cattle", "caught", "cause", "caution" + , "cave", "ceiling", "celery", "cement", "census", "century" + , "cereal", "certain", "chair", "chalk", "champion", "change" + , "chaos", "chapter", "charge", "chase", "chat", "cheap" + , "check", "cheese", "chef", "cherry", "chest", "chicken" + , "chief", "child", "chimney", "choice", "choose", "chronic" + , "chuckle", "chunk", "churn", "cigar", "cinnamon", "circle" + , "citizen", "city", "civil", "claim", "clap", "clarify" + , "claw", "clay", "clean", "clerk", "clever", "click" + , "client", "cliff", "climb", "clinic", "clip", "clock" + , "clog", "close", "cloth", "cloud", "clown", "club" + , "clump", "cluster", "clutch", "coach", "coast", "coconut" + , "code", "coffee", "coil", "coin", "collect", "color" + , "column", "combine", "come", "comfort", "comic", "common" + , "company", "concert", "conduct", "confirm", "congress", "connect" + , "consider", "control", "convince", "cook", "cool", "copper" + , "copy", "coral", "core", "corn", "correct", "cost" + , "cotton", "couch", "country", "couple", "course", "cousin" + , "cover", "coyote", "crack", "cradle", "craft", "cram" + , "crane", "crash", "crater", "crawl", "crazy", "cream" + , "credit", "creek", "crew", "cricket", "crime", "crisp" + , "critic", "crop", "cross", "crouch", "crowd", "crucial" + , "cruel", "cruise", "crumble", "crunch", "crush", "cry" + , "crystal", "cube", "culture", "cup", "cupboard", "curious" + , "current", "curtain", "curve", "cushion", "custom", "cute" + , "cycle", "dad", "damage", "damp", "dance", "danger" + , "daring", "dash", "daughter", "dawn", "day", "deal" + , "debate", "debris", "decade", "december", "decide", "decline" + , "decorate", "decrease", "deer", "defense", "define", "defy" + , "degree", "delay", "deliver", "demand", "demise", "denial" + , "dentist", "deny", "depart", "depend", "deposit", "depth" + , "deputy", "derive", "describe", "desert", "design", "desk" + , "despair", "destroy", "detail", "detect", "develop", "device" + , "devote", "diagram", "dial", "diamond", "diary", "dice" + , "diesel", "diet", "differ", "digital", "dignity", "dilemma" + , "dinner", "dinosaur", "direct", "dirt", "disagree", "discover" + , "disease", "dish", "dismiss", "disorder", "display", "distance" + , "divert", "divide", "divorce", "dizzy", "doctor", "document" + , "dog", "doll", "dolphin", "domain", "donate", "donkey" + , "donor", "door", "dose", "double", "dove", "draft" + , "dragon", "drama", "drastic", "draw", "dream", "dress" + , "drift", "drill", "drink", "drip", "drive", "drop" + , "drum", "dry", "duck", "dumb", "dune", "during" + , "dust", "dutch", "duty", "dwarf", "dynamic", "eager" + , "eagle", "early", "earn", "earth", "easily", "east" + , "easy", "echo", "ecology", "economy", "edge", "edit" + , "educate", "effort", "egg", "eight", "either", "elbow" + , "elder", "electric", "elegant", "element", "elephant", "elevator" + , "elite", "else", "embark", "embody", "embrace", "emerge" + , "emotion", "employ", "empower", "empty", "enable", "enact" + , "end", "endless", "endorse", "enemy", "energy", "enforce" + , "engage", "engine", "enhance", "enjoy", "enlist", "enough" + , "enrich", "enroll", "ensure", "enter", "entire", "entry" + , "envelope", "episode", "equal", "equip", "era", "erase" + , "erode", "erosion", "error", "erupt", "escape", "essay" + , "essence", "estate", "eternal", "ethics", "evidence", "evil" + , "evoke", "evolve", "exact", "example", "excess", "exchange" + , "excite", "exclude", "excuse", "execute", "exercise", "exhaust" + , "exhibit", "exile", "exist", "exit", "exotic", "expand" + , "expect", "expire", "explain", "expose", "express", "extend" + , "extra", "eye", "eyebrow", "fabric", "face", "faculty" + , "fade", "faint", "faith", "fall", "false", "fame" + , "family", "famous", "fan", "fancy", "fantasy", "farm" + , "fashion", "fat", "fatal", "father", "fatigue", "fault" + , "favorite", "feature", "february", "federal", "fee", "feed" + , "feel", "female", "fence", "festival", "fetch", "fever" + , "few", "fiber", "fiction", "field", "figure", "file" + , "film", "filter", "final", "find", "fine", "finger" + , "finish", "fire", "firm", "first", "fiscal", "fish" + , "fit", "fitness", "fix", "flag", "flame", "flash" + , "flat", "flavor", "flee", "flight", "flip", "float" + , "flock", "floor", "flower", "fluid", "flush", "fly" + , "foam", "focus", "fog", "foil", "fold", "follow" + , "food", "foot", "force", "forest", "forget", "fork" + , "fortune", "forum", "forward", "fossil", "foster", "found" + , "fox", "fragile", "frame", "frequent", "fresh", "friend" + , "fringe", "frog", "front", "frost", "frown", "frozen" + , "fruit", "fuel", "fun", "funny", "furnace", "fury" + , "future", "gadget", "gain", "galaxy", "gallery", "game" + , "gap", "garage", "garbage", "garden", "garlic", "garment" + , "gas", "gasp", "gate", "gather", "gauge", "gaze" + , "general", "genius", "genre", "gentle", "genuine", "gesture" + , "ghost", "giant", "gift", "giggle", "ginger", "giraffe" + , "girl", "give", "glad", "glance", "glare", "glass" + , "glide", "glimpse", "globe", "gloom", "glory", "glove" + , "glow", "glue", "goat", "goddess", "gold", "good" + , "goose", "gorilla", "gospel", "gossip", "govern", "gown" + , "grab", "grace", "grain", "grant", "grape", "grass" + , "gravity", "great", "green", "grid", "grief", "grit" + , "grocery", "group", "grow", "grunt", "guard", "guess" + , "guide", "guilt", "guitar", "gun", "gym", "habit" + , "hair", "half", "hammer", "hamster", "hand", "happy" + , "harbor", "hard", "harsh", "harvest", "hat", "have" + , "hawk", "hazard", "head", "health", "heart", "heavy" + , "hedgehog", "height", "hello", "helmet", "help", "hen" + , "hero", "hidden", "high", "hill", "hint", "hip" + , "hire", "history", "hobby", "hockey", "hold", "hole" + , "holiday", "hollow", "home", "honey", "hood", "hope" + , "horn", "horror", "horse", "hospital", "host", "hotel" + , "hour", "hover", "hub", "huge", "human", "humble" + , "humor", "hundred", "hungry", "hunt", "hurdle", "hurry" + , "hurt", "husband", "hybrid", "ice", "icon", "idea" + , "identify", "idle", "ignore", "ill", "illegal", "illness" + , "image", "imitate", "immense", "immune", "impact", "impose" + , "improve", "impulse", "inch", "include", "income", "increase" + , "index", "indicate", "indoor", "industry", "infant", "inflict" + , "inform", "inhale", "inherit", "initial", "inject", "injury" + , "inmate", "inner", "innocent", "input", "inquiry", "insane" + , "insect", "inside", "inspire", "install", "intact", "interest" + , "into", "invest", "invite", "involve", "iron", "island" + , "isolate", "issue", "item", "ivory", "jacket", "jaguar" + , "jar", "jazz", "jealous", "jeans", "jelly", "jewel" + , "job", "join", "joke", "journey", "joy", "judge" + , "juice", "jump", "jungle", "junior", "junk", "just" + , "kangaroo", "keen", "keep", "ketchup", "key", "kick" + , "kid", "kidney", "kind", "kingdom", "kiss", "kit" + , "kitchen", "kite", "kitten", "kiwi", "knee", "knife" + , "knock", "know", "lab", "label", "labor", "ladder" + , "lady", "lake", "lamp", "language", "laptop", "large" + , "later", "latin", "laugh", "laundry", "lava", "law" + , "lawn", "lawsuit", "layer", "lazy", "leader", "leaf" + , "learn", "leave", "lecture", "left", "leg", "legal" + , "legend", "leisure", "lemon", "lend", "length", "lens" + , "leopard", "lesson", "letter", "level", "liar", "liberty" + , "library", "license", "life", "lift", "light", "like" + , "limb", "limit", "link", "lion", "liquid", "list" + , "little", "live", "lizard", "load", "loan", "lobster" + , "local", "lock", "logic", "lonely", "long", "loop" + , "lottery", "loud", "lounge", "love", "loyal", "lucky" + , "luggage", "lumber", "lunar", "lunch", "luxury", "lyrics" + , "machine", "mad", "magic", "magnet", "maid", "mail" + , "main", "major", "make", "mammal", "man", "manage" + , "mandate", "mango", "mansion", "manual", "maple", "marble" + , "march", "margin", "marine", "market", "marriage", "mask" + , "mass", "master", "match", "material", "math", "matrix" + , "matter", "maximum", "maze", "meadow", "mean", "measure" + , "meat", "mechanic", "medal", "media", "melody", "melt" + , "member", "memory", "mention", "menu", "mercy", "merge" + , "merit", "merry", "mesh", "message", "metal", "method" + , "middle", "midnight", "milk", "million", "mimic", "mind" + , "minimum", "minor", "minute", "miracle", "mirror", "misery" + , "miss", "mistake", "mix", "mixed", "mixture", "mobile" + , "model", "modify", "mom", "moment", "monitor", "monkey" + , "monster", "month", "moon", "moral", "more", "morning" + , "mosquito", "mother", "motion", "motor", "mountain", "mouse" + , "move", "movie", "much", "muffin", "mule", "multiply" + , "muscle", "museum", "mushroom", "music", "must", "mutual" + , "myself", "mystery", "myth", "naive", "name", "napkin" + , "narrow", "nasty", "nation", "nature", "near", "neck" + , "need", "negative", "neglect", "neither", "nephew", "nerve" + , "nest", "net", "network", "neutral", "never", "news" + , "next", "nice", "night", "noble", "noise", "nominee" + , "noodle", "normal", "north", "nose", "notable", "note" + , "nothing", "notice", "novel", "now", "nuclear", "number" + , "nurse", "nut", "oak", "obey", "object", "oblige" + , "obscure", "observe", "obtain", "obvious", "occur", "ocean" + , "october", "odor", "off", "offer", "office", "often" + , "oil", "okay", "old", "olive", "olympic", "omit" + , "once", "one", "onion", "online", "only", "open" + , "opera", "opinion", "oppose", "option", "orange", "orbit" + , "orchard", "order", "ordinary", "organ", "orient", "original" + , "orphan", "ostrich", "other", "outdoor", "outer", "output" + , "outside", "oval", "oven", "over", "own", "owner" + , "oxygen", "oyster", "ozone", "pact", "paddle", "page" + , "pair", "palace", "palm", "panda", "panel", "panic" + , "panther", "paper", "parade", "parent", "park", "parrot" + , "party", "pass", "patch", "path", "patient", "patrol" + , "pattern", "pause", "pave", "payment", "peace", "peanut" + , "pear", "peasant", "pelican", "pen", "penalty", "pencil" + , "people", "pepper", "perfect", "permit", "person", "pet" + , "phone", "photo", "phrase", "physical", "piano", "picnic" + , "picture", "piece", "pig", "pigeon", "pill", "pilot" + , "pink", "pioneer", "pipe", "pistol", "pitch", "pizza" + , "place", "planet", "plastic", "plate", "play", "please" + , "pledge", "pluck", "plug", "plunge", "poem", "poet" + , "point", "polar", "pole", "police", "pond", "pony" + , "pool", "popular", "portion", "position", "possible", "post" + , "potato", "pottery", "poverty", "powder", "power", "practice" + , "praise", "predict", "prefer", "prepare", "present", "pretty" + , "prevent", "price", "pride", "primary", "print", "priority" + , "prison", "private", "prize", "problem", "process", "produce" + , "profit", "program", "project", "promote", "proof", "property" + , "prosper", "protect", "proud", "provide", "public", "pudding" + , "pull", "pulp", "pulse", "pumpkin", "punch", "pupil" + , "puppy", "purchase", "purity", "purpose", "purse", "push" + , "put", "puzzle", "pyramid", "quality", "quantum", "quarter" + , "question", "quick", "quit", "quiz", "quote", "rabbit" + , "raccoon", "race", "rack", "radar", "radio", "rail" + , "rain", "raise", "rally", "ramp", "ranch", "random" + , "range", "rapid", "rare", "rate", "rather", "raven" + , "raw", "razor", "ready", "real", "reason", "rebel" + , "rebuild", "recall", "receive", "recipe", "record", "recycle" + , "reduce", "reflect", "reform", "refuse", "region", "regret" + , "regular", "reject", "relax", "release", "relief", "rely" + , "remain", "remember", "remind", "remove", "render", "renew" + , "rent", "reopen", "repair", "repeat", "replace", "report" + , "require", "rescue", "resemble", "resist", "resource", "response" + , "result", "retire", "retreat", "return", "reunion", "reveal" + , "review", "reward", "rhythm", "rib", "ribbon", "rice" + , "rich", "ride", "ridge", "rifle", "right", "rigid" + , "ring", "riot", "ripple", "risk", "ritual", "rival" + , "river", "road", "roast", "robot", "robust", "rocket" + , "romance", "roof", "rookie", "room", "rose", "rotate" + , "rough", "round", "route", "royal", "rubber", "rude" + , "rug", "rule", "run", "runway", "rural", "sad" + , "saddle", "sadness", "safe", "sail", "salad", "salmon" + , "salon", "salt", "salute", "same", "sample", "sand" + , "satisfy", "satoshi", "sauce", "sausage", "save", "say" + , "scale", "scan", "scare", "scatter", "scene", "scheme" + , "school", "science", "scissors", "scorpion", "scout", "scrap" + , "screen", "script", "scrub", "sea", "search", "season" + , "seat", "second", "secret", "section", "security", "seed" + , "seek", "segment", "select", "sell", "seminar", "senior" + , "sense", "sentence", "series", "service", "session", "settle" + , "setup", "seven", "shadow", "shaft", "shallow", "share" + , "shed", "shell", "sheriff", "shield", "shift", "shine" + , "ship", "shiver", "shock", "shoe", "shoot", "shop" + , "short", "shoulder", "shove", "shrimp", "shrug", "shuffle" + , "shy", "sibling", "sick", "side", "siege", "sight" + , "sign", "silent", "silk", "silly", "silver", "similar" + , "simple", "since", "sing", "siren", "sister", "situate" + , "six", "size", "skate", "sketch", "ski", "skill" + , "skin", "skirt", "skull", "slab", "slam", "sleep" + , "slender", "slice", "slide", "slight", "slim", "slogan" + , "slot", "slow", "slush", "small", "smart", "smile" + , "smoke", "smooth", "snack", "snake", "snap", "sniff" + , "snow", "soap", "soccer", "social", "sock", "soda" + , "soft", "solar", "soldier", "solid", "solution", "solve" + , "someone", "song", "soon", "sorry", "sort", "soul" + , "sound", "soup", "source", "south", "space", "spare" + , "spatial", "spawn", "speak", "special", "speed", "spell" + , "spend", "sphere", "spice", "spider", "spike", "spin" + , "spirit", "split", "spoil", "sponsor", "spoon", "sport" + , "spot", "spray", "spread", "spring", "spy", "square" + , "squeeze", "squirrel", "stable", "stadium", "staff", "stage" + , "stairs", "stamp", "stand", "start", "state", "stay" + , "steak", "steel", "stem", "step", "stereo", "stick" + , "still", "sting", "stock", "stomach", "stone", "stool" + , "story", "stove", "strategy", "street", "strike", "strong" + , "struggle", "student", "stuff", "stumble", "style", "subject" + , "submit", "subway", "success", "such", "sudden", "suffer" + , "sugar", "suggest", "suit", "summer", "sun", "sunny" + , "sunset", "super", "supply", "supreme", "sure", "surface" + , "surge", "surprise", "surround", "survey", "suspect", "sustain" + , "swallow", "swamp", "swap", "swarm", "swear", "sweet" + , "swift", "swim", "swing", "switch", "sword", "symbol" + , "symptom", "syrup", "system", "table", "tackle", "tag" + , "tail", "talent", "talk", "tank", "tape", "target" + , "task", "taste", "tattoo", "taxi", "teach", "team" + , "tell", "ten", "tenant", "tennis", "tent", "term" + , "test", "text", "thank", "that", "theme", "then" + , "theory", "there", "they", "thing", "this", "thought" + , "three", "thrive", "throw", "thumb", "thunder", "ticket" + , "tide", "tiger", "tilt", "timber", "time", "tiny" + , "tip", "tired", "tissue", "title", "toast", "tobacco" + , "today", "toddler", "toe", "together", "toilet", "token" + , "tomato", "tomorrow", "tone", "tongue", "tonight", "tool" + , "tooth", "top", "topic", "topple", "torch", "tornado" + , "tortoise", "toss", "total", "tourist", "toward", "tower" + , "town", "toy", "track", "trade", "traffic", "tragic" + , "train", "transfer", "trap", "trash", "travel", "tray" + , "treat", "tree", "trend", "trial", "tribe", "trick" + , "trigger", "trim", "trip", "trophy", "trouble", "truck" + , "true", "truly", "trumpet", "trust", "truth", "try" + , "tube", "tuition", "tumble", "tuna", "tunnel", "turkey" + , "turn", "turtle", "twelve", "twenty", "twice", "twin" + , "twist", "two", "type", "typical", "ugly", "umbrella" + , "unable", "unaware", "uncle", "uncover", "under", "undo" + , "unfair", "unfold", "unhappy", "uniform", "unique", "unit" + , "universe", "unknown", "unlock", "until", "unusual", "unveil" + , "update", "upgrade", "uphold", "upon", "upper", "upset" + , "urban", "urge", "usage", "use", "used", "useful" + , "useless", "usual", "utility", "vacant", "vacuum", "vague" + , "valid", "valley", "valve", "van", "vanish", "vapor" + , "various", "vast", "vault", "vehicle", "velvet", "vendor" + , "venture", "venue", "verb", "verify", "version", "very" + , "vessel", "veteran", "viable", "vibrant", "vicious", "victory" + , "video", "view", "village", "vintage", "violin", "virtual" + , "virus", "visa", "visit", "visual", "vital", "vivid" + , "vocal", "voice", "void", "volcano", "volume", "vote" + , "voyage", "wage", "wagon", "wait", "walk", "wall" + , "walnut", "want", "warfare", "warm", "warrior", "wash" + , "wasp", "waste", "water", "wave", "way", "wealth" + , "weapon", "wear", "weasel", "weather", "web", "wedding" + , "weekend", "weird", "welcome", "west", "wet", "whale" + , "what", "wheat", "wheel", "when", "where", "whip" + , "whisper", "wide", "width", "wife", "wild", "will" + , "win", "window", "wine", "wing", "wink", "winner" + , "winter", "wire", "wisdom", "wise", "wish", "witness" + , "wolf", "woman", "wonder", "wood", "wool", "word" + , "work", "world", "worry", "worth", "wrap", "wreck" + , "wrestle", "wrist", "write", "wrong", "yard", "year" + , "yellow", "you", "young", "youth", "zebra", "zero" + , "zone", "zoo" + ] + +-- | Decode a big endian 'Integer' from a 'ByteString'. +bsToInteger :: ByteString -> Integer +bsToInteger = BS.foldr f 0 . BS.reverse + where + f w n = toInteger w .|. shiftL n 8 + +-- | Encode an 'Integer' to a 'ByteString' as big endian. +integerToBS :: Integer -> ByteString +integerToBS 0 = BS.pack [0] +integerToBS i + | i > 0 = BS.reverse $ BS.unfoldr f i + | otherwise = error "integerToBS not defined for negative values" + where + f 0 = Nothing + f x = Just (fromInteger x :: Word8, x `shiftR` 8) +-- | Obtain 'Int' bits from beginning of 'ByteString'. Resulting 'ByteString' +-- will be smallest required to hold that many bits, padded with zeroes to the +-- right. +getBits :: Int -> ByteString -> ByteString +getBits b bs + | r == 0 = BS.take q bs + | otherwise = i `BS.snoc` l + where + (q, r) = b `quotRem` 8 + s = BS.take (q + 1) bs + i = BS.init s + l = BS.last s .&. (0xff `shiftL` (8 - r)) -- zero unneeded bits diff --git a/packages/crypto/src/Crypto/Ecdsa/Signature.hs b/packages/crypto/src/Crypto/Ecdsa/Signature.hs new file mode 100644 index 00000000..457dad2a --- /dev/null +++ b/packages/crypto/src/Crypto/Ecdsa/Signature.hs @@ -0,0 +1,103 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Ecdsa.Signature +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Recoverable ECC signature support. +-- + +module Crypto.Ecdsa.Signature + ( + sign + , pack + , unpack + ) where + +import Control.Monad (when) +import Crypto.Hash (SHA256) +import Crypto.Number.Generate (generateBetween) +import Crypto.Number.ModArithmetic (inverse) +import Crypto.Number.Serialize (i2osp, os2ip) +import Crypto.PubKey.ECC.ECDSA (PrivateKey (..)) +import Crypto.PubKey.ECC.Prim (pointMul) +import Crypto.PubKey.ECC.Types (CurveCommon (ecc_g, ecc_n), + Point (..), common_curve) +import Crypto.Random (MonadRandom, withDRG) +import Crypto.Random.HmacDrbg (HmacDrbg, initialize) +import Data.Bits (xor, (.|.)) +import Data.ByteArray (ByteArray, ByteArrayAccess, Bytes, + convert, singleton, takeView, + view) +import qualified Data.ByteArray as BA (length, replicate, unpack) +import Data.Word (Word8) + +import Crypto.Ecdsa.Utils (exportKey) + +-- | Sign arbitrary data by given private key. +-- +-- /WARNING:/ Vulnerable to timing attacks. +sign :: ByteArrayAccess bin + => PrivateKey + -> bin + -> (Integer, Integer, Word8) +sign pk bin = fst $ withDRG hmac_drbg $ ecsign pk (os2ip truncated) + where + hmac_drbg :: HmacDrbg SHA256 + hmac_drbg = initialize $ exportKey pk <> truncated + truncated = convert $ takeView bin 32 :: Bytes + +ecsign :: MonadRandom m + => PrivateKey + -> Integer + -> m (Integer, Integer, Word8) +ecsign pk@(PrivateKey curve d) z = do + k <- generateBetween 0 (n - 1) + case trySign k of + Nothing -> ecsign pk z + Just rsv -> return rsv + where + n = ecc_n (common_curve curve) + g = ecc_g (common_curve curve) + recoveryParam x y r = fromIntegral $ + fromEnum (odd y) .|. if x /= r then 2 else 0 + trySign k = do + (kpX, kpY) <- case pointMul curve k g of + PointO -> Nothing + Point x y -> return (x, y) + let r = kpX `mod` n + kInv <- inverse k n + let s = kInv * (z + r * d) `mod` n + when (r == 0 || s == 0) Nothing + -- Recovery param + let v = recoveryParam kpX kpY r + -- Use complement of s if it > n / 2 + let (s', v') | s > n `div` 2 = (n - s, v `xor` 1) + | otherwise = (s, v) + return (r, s', v' + 27) + +-- | Unpack recoverable signature from byte array. +-- +-- Input array should have 65 byte length. +unpack :: ByteArrayAccess rsv => rsv -> (Integer, Integer, Word8) +unpack vrs = (r, s, v) + where + r = os2ip (view vrs 1 33) + s = os2ip (view vrs 33 65) + v = head (BA.unpack vrs) + +-- | Pack recoverable signature as byte array (65 byte length). +pack :: ByteArray rsv => (Integer, Integer, Word8) -> rsv +pack (r, s, v) = leftPad 32 (i2osp r) <> leftPad 32 (i2osp s) <> singleton v + where + leftPad :: (ByteArray b) => Int -> b -> b + leftPad targetLen bs + | BA.length bs >= targetLen = bs + | otherwise = BA.replicate paddingLen 0 <> bs + where + paddingLen = targetLen - BA.length bs diff --git a/packages/crypto/src/Crypto/Ecdsa/Utils.hs b/packages/crypto/src/Crypto/Ecdsa/Utils.hs new file mode 100644 index 00000000..e89cc1f4 --- /dev/null +++ b/packages/crypto/src/Crypto/Ecdsa/Utils.hs @@ -0,0 +1,53 @@ +-- | +-- Module : Crypto.Ecdsa.Utils +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- ECDSA module helper functions. +-- + +module Crypto.Ecdsa.Utils where + +import Crypto.Number.Serialize (i2osp, os2ip) +import Crypto.PubKey.ECC.ECDSA (PrivateKey (..), PublicKey (..)) +import Crypto.PubKey.ECC.Generate (generateQ) +import Crypto.PubKey.ECC.Types (CurveName (SEC_p256k1), Point (..), + getCurveByName) +import Data.ByteArray (ByteArray, ByteArrayAccess, + singleton) + +-- | Import ECDSA private key from byte array. +-- +-- Input array should have 32 byte length. +importKey :: ByteArrayAccess privateKey => privateKey -> PrivateKey +{-# INLINE importKey #-} +importKey = PrivateKey (getCurveByName SEC_p256k1) . os2ip + +-- | Export private key to byte array (32 byte length). +exportKey :: ByteArray privateKey => PrivateKey -> privateKey +{-# INLINE exportKey #-} +exportKey (PrivateKey _ key) = i2osp key + +-- | Get public key appropriate to private key. +-- +-- /WARNING:/ Vulnerable to timing attacks. +derivePubKey :: PrivateKey -> PublicKey +{-# INLINE derivePubKey #-} +derivePubKey (PrivateKey curve p) = PublicKey curve (generateQ curve p) + +-- | Export public key to byte array (64 byte length). +exportPubKey :: ByteArray publicKey => PublicKey -> publicKey +exportPubKey (PublicKey _ PointO) = mempty +exportPubKey (PublicKey _ (Point x y)) = i2osp x <> i2osp y + +-- | Export compressed public key to byte array (33 byte length). +exportPubKeyCompress :: ByteArray publicKey => PublicKey -> publicKey +exportPubKeyCompress (PublicKey _ PointO) = mempty +exportPubKeyCompress (PublicKey _ (Point x y)) = prefix <> i2osp x + where + prefix | even y = singleton 0x02 + | otherwise = singleton 0x03 diff --git a/packages/crypto/src/Crypto/Ethereum.hs b/packages/crypto/src/Crypto/Ethereum.hs new file mode 100644 index 00000000..ee0dbdb6 --- /dev/null +++ b/packages/crypto/src/Crypto/Ethereum.hs @@ -0,0 +1,31 @@ +-- | +-- Module : Crypto.Ethereum +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum cryptography primitives. +-- + +module Crypto.Ethereum + ( + -- * ECDSA crypto key ops + PrivateKey + , PublicKey + , importKey + , derivePubKey + + -- * Digital Signature Algorithm + , signMessage + + -- * Hash function + , keccak256 + ) where + +import Crypto.Ecdsa.Utils (derivePubKey, importKey) +import Crypto.Ethereum.Signature (signMessage) +import Crypto.Ethereum.Utils (keccak256) +import Crypto.PubKey.ECC.ECDSA (PrivateKey, PublicKey) diff --git a/packages/crypto/src/Crypto/Ethereum/Eip712Signature.hs b/packages/crypto/src/Crypto/Ethereum/Eip712Signature.hs new file mode 100644 index 00000000..3a53808b --- /dev/null +++ b/packages/crypto/src/Crypto/Ethereum/Eip712Signature.hs @@ -0,0 +1,395 @@ +{-# LANGUAGE ImpredicativeTypes #-} +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE TypeApplications #-} + +-- | +-- Module : Crypto.Ethereum.Eip712Signature +-- Copyright : Jin Chui 2025 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me jinchui@pm.me +-- Stability : experimental +-- Portability : portable +-- +-- Ethereum EIP712 Singature implementation. +-- Spec https://eips.ethereum.org/EIPS/eip-712. +-- + +module Crypto.Ethereum.Eip712Signature + ( EIP712Name + , BitWidth (..) + , ByteWidth (..) + , HasWidth (..) + , EIP712FieldType (..) + , EIP712TypedData (..) + , EIP712Struct (..) + , EIP712Field (..) + , EIP712Types + , signTypedData + , signTypedData' + , hashStruct + , encodeType + , encodeData + , typedDataSignHash + ) +where + +import Basement.Types.Word256 (Word256(..)) +import Control.Monad (when) +import Crypto.Ecdsa.Signature (pack, sign) +import Crypto.Ethereum (PrivateKey, keccak256) +import Data.Aeson (Object, (.=)) +import qualified Data.Aeson as Aeson +import Data.Aeson.Key (fromText) +import qualified Data.Aeson.KeyMap as Aeson +import Data.Aeson.Types (object) +import Data.ByteArray (ByteArray, zero) +import qualified Data.ByteArray as BA +import Data.ByteArray.HexString (hexString) +import Data.ByteString (ByteString, toStrict) +import qualified Data.ByteString as BS +import Data.ByteString.Builder (toLazyByteString, word64BE) +import Data.Either (partitionEithers) +import Data.Foldable (toList) +import Data.List (find, intercalate) +import Data.Maybe (mapMaybe) +import Data.Scientific (Scientific, floatingOrInteger) +import Data.Set (Set) +import qualified Data.Set as Set +import Data.String (fromString) +import Data.Text (Text) +import qualified Data.Text as T +import Data.Text.Encoding (encodeUtf8) +import qualified Data.Text.Encoding as TE +import Data.Word (Word8) +import Numeric.Natural (Natural) + +type DefaultByteArray = ByteString + +-- Bit and Byte width constants, used for defining field types + +data BitWidth + = Si8 + | Si16 + | Si24 + | Si32 + | Si40 + | Si48 + | Si56 + | Si64 + | Si72 + | Si80 + | Si88 + | Si96 + | Si104 + | Si112 + | Si120 + | Si128 + | Si136 + | Si144 + | Si152 + | Si160 + | Si168 + | Si176 + | Si184 + | Si192 + | Si200 + | Si208 + | Si216 + | Si224 + | Si232 + | Si240 + | Si248 + | Si256 + deriving (Show, Eq, Bounded, Enum) + +data ByteWidth + = S1 + | S2 + | S3 + | S4 + | S5 + | S6 + | S7 + | S8 + | S9 + | S10 + | S11 + | S12 + | S13 + | S14 + | S15 + | S16 + | S17 + | S18 + | S19 + | S20 + | S21 + | S22 + | S23 + | S24 + | S25 + | S26 + | S27 + | S28 + | S29 + | S30 + | S31 + | S32 + deriving (Show, Eq, Bounded, Enum) + +class HasWidth a where + bytesOf :: a -> Int + +instance HasWidth ByteWidth where + bytesOf a = fromEnum a + 1 + +instance HasWidth BitWidth where + bytesOf a = fromEnum a + 1 + +bitsOf :: (HasWidth a) => a -> Int +bitsOf a = bytesOf a * 8 + +-- EIP712 Data structures + +type EIP712Name = Text + +data EIP712FieldType + = FieldTypeBytesN ByteWidth + | FieldTypeUInt BitWidth + | FieldTypeInt BitWidth + | FieldTypeBool + | FieldTypeAddress + | FieldTypeBytes + | FieldTypeString + | FieldTypeArrayN Natural EIP712FieldType + | FieldTypeArray EIP712FieldType + | FieldTypeStruct EIP712Name + deriving (Show, Eq) + +data EIP712Field = EIP712Field + { eip712FieldName :: EIP712Name + , eip712FieldType :: EIP712FieldType + } + deriving (Show, Eq) + +data EIP712Struct = EIP712Struct + { eip712StructName :: EIP712Name + , eip712StructFields :: [EIP712Field] + } + deriving (Show, Eq) + +type EIP712Types = [EIP712Struct] + +data EIP712TypedData + = EIP712TypedData + { typedDataTypes :: EIP712Types + , typedDataPrimaryType :: EIP712Name + , typedDataDomain :: Object + , typedDataMessage :: Object + } + deriving (Show) + +-- ToJSON serialization + +instance Aeson.ToJSON EIP712Field where + toJSON field = object ["name" .= eip712FieldName field, "type" .= TE.decodeUtf8 (encode $ eip712FieldType field)] + +instance Aeson.ToJSON EIP712TypedData where + toJSON typedData = + object + [ "types" + .= object + [ fromText (eip712StructName s) .= eip712StructFields s + | s <- typedDataTypes typedData + ] + , "primaryType" .= typedDataPrimaryType typedData + , "domain" .= typedDataDomain typedData + , "message" .= typedDataMessage typedData + ] + +-- Custom EIP712 encoding + +class EIP712Encoded a where + encode :: (ByteArray bout) => a -> bout + +instance EIP712Encoded EIP712FieldType where + encode = \case + FieldTypeBytesN sb -> utf8 "bytes" <> toByteArray (bytesOf sb) + FieldTypeUInt sb -> utf8 "uint" <> toByteArray (bitsOf sb) + FieldTypeInt sb -> utf8 "int" <> toByteArray (bitsOf sb) + FieldTypeBool -> utf8 "bool" + FieldTypeAddress -> utf8 "address" + FieldTypeBytes -> utf8 "bytes" + FieldTypeString -> utf8 "string" + FieldTypeArrayN n t -> encode t <> utf8 "[" <> toByteArray n <> utf8 "]" + FieldTypeArray t -> encode t <> utf8 "[]" + FieldTypeStruct name -> utf8 name + +instance EIP712Encoded EIP712Field where + encode EIP712Field{..} = encode eip712FieldType <> utf8 " " <> utf8 eip712FieldName + +-- | Encode a type according to the EIP712 specification (see Definition of `encodeType`) +encodeType :: (ByteArray bout) => EIP712Types -> EIP712Name -> Either String bout +encodeType types typeName = do + struct <- lookupType types typeName + refs <- referencedTypesEncoded struct + let base = encodeUtf8 typeName <> "(" <> fieldsEncoded struct <> ")" + pure $ BA.convert $ base <> refs + where + fieldsEncoded :: EIP712Struct -> BS.ByteString + fieldsEncoded = BS.intercalate "," . fmap encode . eip712StructFields + + referencedTypesEncoded :: EIP712Struct -> Either String ByteString + referencedTypesEncoded = + fmap (BS.concat . toList) + . traverse (encodeType types) + . Set.toList + . referencedTypesNames + + referencedTypesNames :: EIP712Struct -> Set EIP712Name + referencedTypesNames = Set.fromList . mapMaybe (maybeReferenceTypeName . eip712FieldType) . eip712StructFields + + maybeReferenceTypeName :: EIP712FieldType -> Maybe EIP712Name + maybeReferenceTypeName = \case + FieldTypeArray inner -> maybeReferenceTypeName inner + FieldTypeArrayN _ inner -> maybeReferenceTypeName inner + FieldTypeStruct name -> Just name + _ -> Nothing + +-- | Encode data according to the EIP712 specification (see Definition of `encodeData`) +encodeData :: (ByteArray bout) => EIP712Types -> EIP712Name -> Aeson.Object -> Either String bout +encodeData types typeName obj = do + encodedFields <- fieldsAndValues >>= mapM (uncurry encodeValue) + return $ BA.concat encodedFields + where + findValue :: Text -> Either String Aeson.Value + findValue fieldName = case Aeson.lookup (fromString $ T.unpack fieldName) obj of + Just v -> Right v + Nothing -> Left $ fromString $ T.unpack fieldName + + fieldsAndValues :: Either String [(EIP712FieldType, Aeson.Value)] + fieldsAndValues = do + fields <- eip712StructFields <$> lookupType types typeName + let valueOrFieldNameList = fmap (findValue . eip712FieldName) fields + let (missingFields, values) = partitionEithers valueOrFieldNameList + if (not . null) missingFields + then Left $ "missing fields" <> intercalate ", " missingFields + else Right $ zip (fmap eip712FieldType fields) values + + encodeValue :: EIP712FieldType -> Aeson.Value -> Either String BA.Bytes + encodeValue (FieldTypeBytesN s) v = do + encodedBytes <- extractString v >>= hexString . encodeUtf8 + when (BA.length encodedBytes /= bytesOf s) $ Left $ "expected " <> show (bytesOf s) <> "bytes, got " <> show (BA.length encodedBytes) + return $ BA.convert encodedBytes <> zero (32 - bytesOf s) + encodeValue (FieldTypeUInt _) v = do + value <- extractNumber v >>= scientificToWord256 + when (value < 0) $ Left $ "expected unsigned int, got negative value " <> show value + return $ encodeWord256 value + encodeValue (FieldTypeInt _) v = encodeWord256 <$> (extractNumber v >>= scientificToWord256) + encodeValue FieldTypeBool v = encodeWord256 . fromIntegral . fromEnum <$> extractBool v + encodeValue FieldTypeAddress v = do + valueAsHexString <- extractString v >>= hexString . encodeUtf8 + when (BA.length valueAsHexString /= 20) $ Left ("address not valid:" <> show v) + return $ BA.convert $ zero 12 <> valueAsHexString + encodeValue FieldTypeBytes v = do + valueAsHexString <- extractString v >>= hexString . encodeUtf8 + return $ keccak256 valueAsHexString + encodeValue FieldTypeString v = keccak256 . encodeUtf8 <$> extractString v + encodeValue (FieldTypeArrayN _ innerType) v = encodeArray innerType v + encodeValue (FieldTypeArray innerType) v = encodeArray innerType v + encodeValue (FieldTypeStruct innerTypeName) v = do + valueAsObject <- extractObject v + hashStruct types innerTypeName valueAsObject + + encodeArray innerType v = do + valueAsArray <- extractArray v + encodedValues <- traverse (encodeValue innerType) valueAsArray + return $ keccak256 $ BA.concat @BA.Bytes @BA.Bytes $ toList encodedValues + + encodeWord256 (Word256 a3 a2 a1 a0) = BA.convert $ toStrict $ toLazyByteString $ word64BE a3 <> word64BE a2 <> word64BE a1 <> word64BE a0 + + +-- | Compute a hash for the struct according to EIP712 (see Definition of `hashStruct`) +hashStruct :: (ByteArray bout) => EIP712Types -> EIP712Name -> Aeson.Object -> Either String bout +hashStruct types typeName obj = do + encodedData <- encodeData @DefaultByteArray types typeName obj + encodedType <- encodeType @DefaultByteArray types typeName + let typeHash = keccak256 encodedType + return $ keccak256 $ typeHash <> encodedData + +-- | Sign a EIP712 type data, returns encoded version of the signature +signTypedData :: (ByteArray rsv) => PrivateKey -> EIP712TypedData -> Either String rsv +signTypedData key typedData = pack <$> signTypedData' key typedData + +-- | Sign a EIP712 type data, returns (r, s, v) +signTypedData' :: PrivateKey -> EIP712TypedData -> Either String (Integer, Integer, Word8) +signTypedData' key typedData = sign @DefaultByteArray key <$> typedDataSignHash typedData + +-- | Returns the hash that needs to be signed by the private key +typedDataSignHash :: (ByteArray bout) => EIP712TypedData -> Either String bout +typedDataSignHash typedData = do + domainSeparator <- hashStruct (typedDataTypes typedData) "EIP712Domain" (typedDataDomain typedData) + hashStructMessage <- hashStruct (typedDataTypes typedData) (typedDataPrimaryType typedData) (typedDataMessage typedData) + return $ keccak256 @DefaultByteArray (BA.pack [0x19, 0x01] <> domainSeparator <> hashStructMessage) + +-------------------------------------------------------------------------------------------------------- +-- Utility functions for data manipulation +-------------------------------------------------------------------------------------------------------- + +lookupType :: EIP712Types -> EIP712Name -> Either String EIP712Struct +lookupType types typeName = + case find ((== typeName) . eip712StructName) types of + Just struct -> Right struct + Nothing -> + Left $ "EIP712 type not found: " <> show typeName + +describeJsonType :: Aeson.Value -> String +describeJsonType (Aeson.String _) = "string" +describeJsonType (Aeson.Number _) = "number" +describeJsonType (Aeson.Bool _) = "boolean" +describeJsonType (Aeson.Array _) = "array" +describeJsonType (Aeson.Object _) = "object" +describeJsonType Aeson.Null = "null" + +extractError :: String -> Aeson.Value -> Either String b +extractError expected v = Left $ "expected " <> expected <> ", got " <> describeJsonType v + +extractString :: Aeson.Value -> Either String Text +extractString (Aeson.String v) = Right v +extractString v = extractError "string" v + +extractNumber :: Aeson.Value -> Either String Scientific +extractNumber (Aeson.Number v) = Right v +extractNumber v = extractError "number" v + +extractBool :: Aeson.Value -> Either String Bool +extractBool (Aeson.Bool v) = Right v +extractBool v = extractError "bool" v + +extractArray :: Aeson.Value -> Either String Aeson.Array +extractArray (Aeson.Array v) = Right v +extractArray v = extractError "array" v + +extractObject :: Aeson.Value -> Either String Aeson.Object +extractObject (Aeson.Object v) = Right v +extractObject v = extractError "object" v + +scientificToWord256 :: Scientific -> Either String Word256 +scientificToWord256 n = case floatingOrInteger @Double n of + Right r -> Right $ fromInteger r + Left r -> Left $ "Number is not an integer: " <> show r + +-------------------------------------------------------------------------------------------------------- +-- Utility functions for encoding +-------------------------------------------------------------------------------------------------------- + +-- | Generic "to UTF8 bytes" helper +utf8 :: (BA.ByteArray b) => T.Text -> b +utf8 = BA.convert . TE.encodeUtf8 + +-- | Convert a Show-able value to UTF8 bytes +toByteArray :: (Show a, BA.ByteArray b) => a -> b +toByteArray = utf8 . T.pack . show diff --git a/packages/crypto/src/Crypto/Ethereum/Keyfile.hs b/packages/crypto/src/Crypto/Ethereum/Keyfile.hs new file mode 100644 index 00000000..43cca2a1 --- /dev/null +++ b/packages/crypto/src/Crypto/Ethereum/Keyfile.hs @@ -0,0 +1,237 @@ +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Crypto.Ethereum.Keyfile +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Ethereum Secret Storage implementation. +-- Spec https://github.com/ethereum/wiki/wiki/Web3-Secret-Storage-Definition. +-- + +module Crypto.Ethereum.Keyfile + ( + -- * Encrypted Ethereum private key + EncryptedKey(..) + , Cipher(..) + , Kdf(..) + + -- * Secret storage packers + , decrypt + , encrypt + ) where + +import Crypto.Cipher.AES (AES128) +import Crypto.Cipher.Types (IV, cipherInit, ctrCombine, makeIV) +import Crypto.Error (throwCryptoError) +import qualified Crypto.KDF.PBKDF2 as Pbkdf2 (Parameters (..), + fastPBKDF2_SHA256) +import qualified Crypto.KDF.Scrypt as Scrypt (Parameters (..), generate) +import Crypto.Random (MonadRandom (getRandomBytes)) +import Data.Aeson (FromJSON (..), ToJSON (..), Value, + object, withObject, (.:), (.=)) +import Data.Aeson.Types (Parser) +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) +import qualified Data.ByteArray as BA (drop, take, unpack) +import Data.Maybe (fromJust) +import Data.Text (Text) +import Data.UUID.Types (UUID) +import Data.UUID.Types.Internal (buildFromBytes) + +import Crypto.Ethereum.Utils (keccak256) +import Data.ByteArray.HexString (HexString) + +-- | Key derivation function parameters and salt. +data Kdf = Pbkdf2 !Pbkdf2.Parameters !HexString + | Scrypt !Scrypt.Parameters !HexString + +-- | Cipher parameters. +data Cipher = Aes128Ctr + { cipherIv :: !(IV AES128) + , cipherText :: !HexString + } + +-- | Secret Storage representation on memory. +data EncryptedKey = EncryptedKey + { encryptedKeyId :: !UUID + -- ^ Random key ID + , encryptedKeyVersion :: !Int + -- ^ Version (suppoted version 3 only) + , encryptedKeyCipher :: !Cipher + -- ^ Cipher (supported AES-128-CTR only) + , encryptedKeyKdf :: !Kdf + -- ^ Key derivation function + , encryptedKeyMac :: !HexString + -- ^ MAC + } + +instance Eq EncryptedKey where + a == b = encryptedKeyId a == encryptedKeyId b + +instance Show EncryptedKey where + show EncryptedKey{..} = "EncryptedKey " ++ show encryptedKeyId + +instance FromJSON EncryptedKey where + parseJSON = encryptedKeyParser + +instance ToJSON EncryptedKey where + toJSON = encryptedKeyBuilder + +encryptedKeyBuilder :: EncryptedKey -> Value +encryptedKeyBuilder EncryptedKey{..} = object + [ "id" .= encryptedKeyId + , "version" .= encryptedKeyVersion + , "crypto" .= object + [ "cipher" .= cipherName encryptedKeyCipher + , "cipherparams" .= cipherParams encryptedKeyCipher + , "ciphertext" .= cipherText encryptedKeyCipher + , "kdf" .= kdfName encryptedKeyKdf + , "kdfparams" .= kdfParams encryptedKeyKdf + , "mac" .= encryptedKeyMac + ] + ] + where + cipherName :: Cipher -> Text + cipherName Aes128Ctr{..} = "aes-128-ctr" + + cipherParams :: Cipher -> Value + cipherParams Aes128Ctr{..} = object [ "iv" .= (convert cipherIv :: HexString) ] + + kdfName :: Kdf -> Text + kdfName = \case + Pbkdf2 _ _ -> "pbkdf2" + Scrypt _ _ -> "scrypt" + + kdfParams :: Kdf -> Value + kdfParams = \case + Pbkdf2 params salt -> + object [ "salt" .= salt + , "dklen" .= Pbkdf2.outputLength params + , "c" .= Pbkdf2.iterCounts params + ] + Scrypt params salt -> + object [ "salt" .= salt + , "dklen" .= Scrypt.outputLength params + , "p" .= Scrypt.p params + , "r" .= Scrypt.r params + , "n" .= Scrypt.n params + ] + +encryptedKeyParser :: Value -> Parser EncryptedKey +encryptedKeyParser = withObject "EncryptedKey" $ \v -> do + uuid <- v .: "id" + version <- v .: "version" + crypto <- v .: "crypto" + cipher <- parseCipher crypto + kdf <- parseKdf crypto + mac <- withObject "Crypto" (.: "mac") crypto + return $ EncryptedKey uuid version cipher kdf mac + +parseCipher :: Value -> Parser Cipher +parseCipher = withObject "Cipher" $ \v -> do + name <- v .: "cipher" + case name :: Text of + "aes-128-ctr" -> do + params <- v .: "cipherparams" + hexiv <- params .: "iv" + text <- v .: "ciphertext" + case makeIV (hexiv :: HexString) of + Just iv -> return (Aes128Ctr iv text) + Nothing -> fail $ "Unable to make IV from " ++ show hexiv + _ -> fail $ show name ++ " not implemented yet" + +parseKdf :: Value -> Parser Kdf +parseKdf = withObject "Kdf" $ \v -> do + name <- v .: "kdf" + params <- v .: "kdfparams" + dklen <- params .: "dklen" + salt <- params .: "salt" + case name :: Text of + "pbkdf2" -> do + iterations <- params .: "c" + prf <- params .: "prf" + case prf :: Text of + "hmac-sha256" -> return $ Pbkdf2 (Pbkdf2.Parameters iterations dklen) salt + _ -> fail $ show prf ++ " not implemented yet" + "scrypt" -> do + p <- params .: "p" + r <- params .: "r" + n <- params .: "n" + return $ Scrypt (Scrypt.Parameters n r p dklen) salt + _ -> fail $ show name ++ " not implemented yet" + +defaultKdf :: HexString -> Kdf +defaultKdf = Scrypt (Scrypt.Parameters n r p dklen) + where + dklen = 32 + n = 262144 + r = 1 + p = 8 + +deriveKey :: (ByteArrayAccess password, ByteArray ba) => Kdf -> password -> ba +deriveKey kdf password = + case kdf of + Pbkdf2 params salt -> Pbkdf2.fastPBKDF2_SHA256 params password salt + Scrypt params salt -> Scrypt.generate params password salt + + +-- | Decrypt Ethereum private key. +-- +-- Typically Web3 Secret Storage is JSON-encoded. 'EncryptedKey' data type has 'FromJSON' instance +-- to helps decode it from JSON-encoded string or file. +-- +-- @ +-- let decryptJSON pass = flip decrypt pass <=< decode +-- @ +-- +decrypt :: (ByteArrayAccess password, ByteArray privateKey) + => EncryptedKey + -> password + -> Maybe privateKey +decrypt EncryptedKey{..} password + | mac == encryptedKeyMac = Just (convert privateKey) + | otherwise = Nothing + where + privateKey = ctrCombine cipher iv ciphertext + cipher = throwCryptoError $ cipherInit (BA.take 16 derivedKey) :: AES128 + derivedKey = deriveKey encryptedKeyKdf password + ciphertext = cipherText encryptedKeyCipher + mac = keccak256 (BA.drop 16 derivedKey <> ciphertext) + iv = cipherIv encryptedKeyCipher + +-- | Encrypt Ethereum private key. +-- +-- @ +-- let encryptJSON pass key = encode <$> encrypt key pass +-- @ +encrypt :: (ByteArray privateKey, ByteArrayAccess password, MonadRandom m) + => privateKey + -> password + -> m EncryptedKey +encrypt privateKey password = do + kdf <- defaultKdf <$> getRandomBytes 16 + iv <- randomIV + let derivedKey = deriveKey kdf password + cipher = throwCryptoError $ cipherInit (BA.take 16 derivedKey) :: AES128 + ciphertext = ctrCombine cipher iv privateKey + mac = keccak256 (BA.drop 16 derivedKey <> ciphertext) + uuid <- randomUUID + return $ EncryptedKey uuid 3 (Aes128Ctr iv $ convert ciphertext) kdf mac + where + randomUUID = do + uuid <- getRandomBytes 16 + let bs = BA.unpack (uuid :: HexString) + return $ buildFromBytes 4 + (head bs) (bs !! 1) (bs !! 2) (bs !! 3) + (bs !! 4) (bs !! 5) (bs !! 6) (bs !! 7) + (bs !! 8) (bs !! 9) (bs !! 10) (bs !! 11) + (bs !! 12) (bs !! 13) (bs !! 14) (bs !! 15) + randomIV = do + iv <- getRandomBytes 16 + return $ fromJust $ makeIV (iv :: HexString) diff --git a/packages/crypto/src/Crypto/Ethereum/Signature.hs b/packages/crypto/src/Crypto/Ethereum/Signature.hs new file mode 100644 index 00000000..e4358e51 --- /dev/null +++ b/packages/crypto/src/Crypto/Ethereum/Signature.hs @@ -0,0 +1,68 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Ecdsa.Signature +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Recoverable Ethereum signature support. +-- + +module Crypto.Ethereum.Signature + ( + hashMessage + , signMessage + , signTransaction + ) where + +import Crypto.Hash (Digest, Keccak_256 (..), hashWith) +import Crypto.PubKey.ECC.ECDSA (PrivateKey (..)) +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) +import qualified Data.ByteArray as BA (length) +import Data.ByteString.Builder (intDec, toLazyByteString) +import qualified Data.ByteString.Lazy as LBS (toStrict) +import Data.Word (Word8) + +import Crypto.Ecdsa.Signature (pack, sign) + +-- | Make Ethereum standard signature. +-- +-- The message is before enveloped as follows: +-- "\x19Ethereum Signed Message:\n" + message.length + message +-- +-- /WARNING:/ Vulnerable to timing attacks. +signMessage :: (ByteArrayAccess message, ByteArray rsv) + => PrivateKey + -> message + -> rsv +{-# INLINE signMessage #-} +signMessage pk = pack . sign pk . hashMessage + +-- | Ethereum standard hashed message. +-- +-- The data will be UTF-8 HEX decoded and enveloped as follows: +-- "\x19Ethereum Signed Message:\n" + message.length + message and hashed using keccak256. +hashMessage :: ByteArrayAccess message => message -> Digest Keccak_256 +hashMessage msg = hashWith Keccak_256 prefixed + where + len = LBS.toStrict . toLazyByteString . intDec . BA.length + prefixed = "\x19" <> "Ethereum Signed Message:\n" <> len msg <> convert msg + +-- | Sign Ethereum transaction. +-- +-- /WARNING:/ Vulnerable to timing attacks. +signTransaction :: ByteArray ba + => (Maybe (Integer, Integer, Word8) -> ba) + -- ^ Two way transaction packer (unsigned and signed) + -> PrivateKey + -- ^ Private key + -> ba + -- ^ Encoded transaction +signTransaction encode key = encode $ Just signed + where + unsigned = encode Nothing + signed = sign key (hashWith Keccak_256 unsigned) diff --git a/packages/crypto/src/Crypto/Ethereum/Utils.hs b/packages/crypto/src/Crypto/Ethereum/Utils.hs new file mode 100644 index 00000000..8b4462c7 --- /dev/null +++ b/packages/crypto/src/Crypto/Ethereum/Utils.hs @@ -0,0 +1,21 @@ +-- | +-- Module : Crypto.Ethereum.Utils +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Ethereum crypto module helper functions. +-- + +module Crypto.Ethereum.Utils where + +import Crypto.Hash (Keccak_256 (..), hashWith) +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) + +-- | Keccak 256 hash function. +keccak256 :: (ByteArrayAccess bin, ByteArray bout) => bin -> bout +{-# INLINE keccak256 #-} +keccak256 = convert . hashWith Keccak_256 diff --git a/packages/crypto/src/Crypto/Random/HmacDrbg.hs b/packages/crypto/src/Crypto/Random/HmacDrbg.hs new file mode 100644 index 00000000..b03155de --- /dev/null +++ b/packages/crypto/src/Crypto/Random/HmacDrbg.hs @@ -0,0 +1,67 @@ +-- | +-- Module : Crypto.Random.HmacDrbg +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- NIST standardized number-theoretically secure random number generator. +-- https://csrc.nist.gov/csrc/media/events/random-number-generation-workshop-2004/documents/hashblockcipherdrbg.pdf +-- +-- XXX: This algorithm requires reseed after 2^48 iterations. +-- +-- > Inspired by https://github.com/TomMD/DRBG and https://github.com/indutny/hmac-drbg. +-- + +module Crypto.Random.HmacDrbg + ( + HmacDrbg + , initialize + ) where + + +import Crypto.Hash (HashAlgorithm, digestFromByteString, + hashDigestSize) +import Crypto.MAC.HMAC (HMAC (..), hmac) +import Crypto.Random (DRG (..)) +import Data.ByteArray (ByteArray, convert, singleton) +import qualified Data.ByteArray as BA (null, take) +import qualified Data.ByteString as B (replicate) +import Data.Maybe (fromJust) +import Data.Word (Word8) + +-- | HMAC Deterministic Random Bytes Generator. +newtype HmacDrbg a = HmacDrbg (HMAC a, HMAC a) + deriving Eq + +instance HashAlgorithm a => DRG (HmacDrbg a) where + randomBytesGenerate = generate + +update :: (ByteArray bin, HashAlgorithm a) + => bin + -> HmacDrbg a + -> HmacDrbg a +update input | BA.null input = go 0x00 + | otherwise = go 0x01 . go 0x00 + where + go :: HashAlgorithm a => Word8 -> HmacDrbg a -> HmacDrbg a + go c (HmacDrbg (k, v)) = let k' = hmac k (convert v <> singleton c <> input) + v' = hmac k' v + in HmacDrbg (k', v') + +-- | Initialize HMAC-DRBG by seed. +initialize :: (ByteArray seed, HashAlgorithm a) + => seed + -> HmacDrbg a +initialize = flip update $ HmacDrbg (hmac0 undefined 0x00, hmac0 undefined 0x01) + where + hmac0 :: HashAlgorithm a => a -> Word8 -> HMAC a + hmac0 a = HMAC . fromJust . digestFromByteString . B.replicate (hashDigestSize a) + +generate :: (HashAlgorithm a, ByteArray output) => Int -> HmacDrbg a -> (output, HmacDrbg a) +generate reqBytes (HmacDrbg (k, v)) = (output, HmacDrbg (k, vFinal)) + where + getV (u, rest) = let v' = hmac k u in (v', rest <> convert v') + (vFinal, output) = BA.take reqBytes <$> iterate getV (v, mempty) !! reqBytes diff --git a/packages/crypto/src/Data/Digest/Blake2.hs b/packages/crypto/src/Data/Digest/Blake2.hs new file mode 100644 index 00000000..68c587d8 --- /dev/null +++ b/packages/crypto/src/Data/Digest/Blake2.hs @@ -0,0 +1,39 @@ +{-# LANGUAGE DataKinds #-} + +-- | +-- Module : Data.Digest.Blake2 +-- Copyright : Aleksandr Krupenkin 2016-2021 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Cryptonite Blake2b wrappers. +-- + +module Data.Digest.Blake2 where + +import Crypto.Hash (Blake2b, Digest, hash) +import Data.ByteArray (convert) +import Data.ByteString (ByteString) + +-- | Blake2b with 64 bit output. +blake2_64 :: ByteString -> ByteString +{-# INLINE blake2_64 #-} +blake2_64 = convert . (hash :: ByteString -> Digest (Blake2b 64)) + +-- | Blake2b with 128 bit output. +blake2_128 :: ByteString -> ByteString +{-# INLINE blake2_128 #-} +blake2_128 = convert . (hash :: ByteString -> Digest (Blake2b 128)) + +-- | Blake2b with 256 bit output. +blake2_256 :: ByteString -> ByteString +{-# INLINE blake2_256 #-} +blake2_256 = convert . (hash :: ByteString -> Digest (Blake2b 256)) + +-- | Blake2b with 512 bit output. +blake2_512 :: ByteString -> ByteString +{-# INLINE blake2_512 #-} +blake2_512 = convert . (hash :: ByteString -> Digest (Blake2b 512)) diff --git a/packages/crypto/src/Data/Digest/XXHash.hsc b/packages/crypto/src/Data/Digest/XXHash.hsc new file mode 100644 index 00000000..a87e2f7e --- /dev/null +++ b/packages/crypto/src/Data/Digest/XXHash.hsc @@ -0,0 +1,49 @@ +{-# LANGUAGE CPP #-} +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Data.Digest.XXHash +-- Copyright : Aleksandr Krupenkin 2016-2021 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- xxHash C library bindings. +-- +-- Variable bitLength implementation corresponds to polkadot-util: +-- https://github.com/polkadot-js/common/tree/master/packages/util-crypto/src/xxhash +-- + +module Data.Digest.XXHash (xxhash) where + +import Data.ByteString (ByteString, useAsCStringLen) +import Data.ByteString.Builder (toLazyByteString, word64LE) +import Data.ByteString.Lazy (toStrict) +import Foreign +import Foreign.C.String +import Foreign.C.Types +import System.IO.Unsafe (unsafePerformIO) + +#include + +foreign import ccall unsafe "xxhash.h XXH64" + c_XXH64 :: CString -> CSize -> CUInt -> IO Word64 + +xxhash_64 :: CUInt -> ByteString -> Word64 +xxhash_64 seed = unsafePerformIO . flip useAsCStringLen + (\(str, len) -> c_XXH64 str (fromIntegral len) seed) + +-- | Create the xxhash64 and return the result with the specified 'bitLength'. +xxhash :: Integral bitLength + => bitLength + -- ^ Bit lenght of output, will be ceiling to 64 bit. + -> ByteString + -- ^ Input data. + -> ByteString + -- ^ Output hash. +xxhash bitLength input = toStrict . toLazyByteString $ mconcat + [ word64LE (xxhash_64 seed input) | seed <- [0 .. (iterations - 1)]] + where + iterations = ceiling (fromIntegral bitLength / 64) diff --git a/packages/crypto/src/cbits/xxhash.c b/packages/crypto/src/cbits/xxhash.c new file mode 100644 index 00000000..083b039d --- /dev/null +++ b/packages/crypto/src/cbits/xxhash.c @@ -0,0 +1,43 @@ +/* + * xxHash - Extremely Fast Hash algorithm + * Copyright (C) 2012-2021 Yann Collet + * + * BSD 2-Clause License (https://www.opensource.org/licenses/bsd-license.php) + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following disclaimer + * in the documentation and/or other materials provided with the + * distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * You can contact the author at: + * - xxHash homepage: https://www.xxhash.com + * - xxHash source repository: https://github.com/Cyan4973/xxHash + */ + + +/* + * xxhash.c instantiates functions defined in xxhash.h + */ + +#define XXH_STATIC_LINKING_ONLY /* access advanced declarations */ +#define XXH_IMPLEMENTATION /* access definitions */ + +#include "xxhash.h" diff --git a/packages/crypto/src/cbits/xxhash.h b/packages/crypto/src/cbits/xxhash.h new file mode 100644 index 00000000..1b25f35a --- /dev/null +++ b/packages/crypto/src/cbits/xxhash.h @@ -0,0 +1,4766 @@ +/* + * xxHash - Extremely Fast Hash algorithm + * Header File + * Copyright (C) 2012-2021 Yann Collet + * + * BSD 2-Clause License (https://www.opensource.org/licenses/bsd-license.php) + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following disclaimer + * in the documentation and/or other materials provided with the + * distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * You can contact the author at: + * - xxHash homepage: https://www.xxhash.com + * - xxHash source repository: https://github.com/Cyan4973/xxHash + */ + +/* TODO: update */ +/* Notice extracted from xxHash homepage: + +xxHash is an extremely fast hash algorithm, running at RAM speed limits. +It also successfully passes all tests from the SMHasher suite. + +Comparison (single thread, Windows Seven 32 bits, using SMHasher on a Core 2 Duo @3GHz) + +Name Speed Q.Score Author +xxHash 5.4 GB/s 10 +CrapWow 3.2 GB/s 2 Andrew +MumurHash 3a 2.7 GB/s 10 Austin Appleby +SpookyHash 2.0 GB/s 10 Bob Jenkins +SBox 1.4 GB/s 9 Bret Mulvey +Lookup3 1.2 GB/s 9 Bob Jenkins +SuperFastHash 1.2 GB/s 1 Paul Hsieh +CityHash64 1.05 GB/s 10 Pike & Alakuijala +FNV 0.55 GB/s 5 Fowler, Noll, Vo +CRC32 0.43 GB/s 9 +MD5-32 0.33 GB/s 10 Ronald L. Rivest +SHA1-32 0.28 GB/s 10 + +Q.Score is a measure of quality of the hash function. +It depends on successfully passing SMHasher test set. +10 is a perfect score. + +Note: SMHasher's CRC32 implementation is not the fastest one. +Other speed-oriented implementations can be faster, +especially in combination with PCLMUL instruction: +https://fastcompression.blogspot.com/2019/03/presenting-xxh3.html?showComment=1552696407071#c3490092340461170735 + +A 64-bit version, named XXH64, is available since r35. +It offers much better speed, but for 64-bit applications only. +Name Speed on 64 bits Speed on 32 bits +XXH64 13.8 GB/s 1.9 GB/s +XXH32 6.8 GB/s 6.0 GB/s +*/ + +#if defined (__cplusplus) +extern "C" { +#endif + +/* **************************** + * INLINE mode + ******************************/ +/*! + * XXH_INLINE_ALL (and XXH_PRIVATE_API) + * Use these build macros to inline xxhash into the target unit. + * Inlining improves performance on small inputs, especially when the length is + * expressed as a compile-time constant: + * + * https://fastcompression.blogspot.com/2018/03/xxhash-for-small-keys-impressive-power.html + * + * It also keeps xxHash symbols private to the unit, so they are not exported. + * + * Usage: + * #define XXH_INLINE_ALL + * #include "xxhash.h" + * + * Do not compile and link xxhash.o as a separate object, as it is not useful. + */ +#if (defined(XXH_INLINE_ALL) || defined(XXH_PRIVATE_API)) \ + && !defined(XXH_INLINE_ALL_31684351384) + /* this section should be traversed only once */ +# define XXH_INLINE_ALL_31684351384 + /* give access to the advanced API, required to compile implementations */ +# undef XXH_STATIC_LINKING_ONLY /* avoid macro redef */ +# define XXH_STATIC_LINKING_ONLY + /* make all functions private */ +# undef XXH_PUBLIC_API +# if defined(__GNUC__) +# define XXH_PUBLIC_API static __inline __attribute__((unused)) +# elif defined (__cplusplus) || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) +# define XXH_PUBLIC_API static inline +# elif defined(_MSC_VER) +# define XXH_PUBLIC_API static __inline +# else + /* note: this version may generate warnings for unused static functions */ +# define XXH_PUBLIC_API static +# endif + + /* + * This part deals with the special case where a unit wants to inline xxHash, + * but "xxhash.h" has previously been included without XXH_INLINE_ALL, such + * as part of some previously included *.h header file. + * Without further action, the new include would just be ignored, + * and functions would effectively _not_ be inlined (silent failure). + * The following macros solve this situation by prefixing all inlined names, + * avoiding naming collision with previous inclusions. + */ +# ifdef XXH_NAMESPACE +# error "XXH_INLINE_ALL with XXH_NAMESPACE is not supported" + /* + * Note: Alternative: #undef all symbols (it's a pretty large list). + * Without #error: it compiles, but functions are actually not inlined. + */ +# endif +# define XXH_NAMESPACE XXH_INLINE_ + /* + * Some identifiers (enums, type names) are not symbols, but they must + * still be renamed to avoid redeclaration. + * Alternative solution: do not redeclare them. + * However, this requires some #ifdefs, and is a more dispersed action. + * Meanwhile, renaming can be achieved in a single block + */ +# define XXH_IPREF(Id) XXH_INLINE_ ## Id +# define XXH_OK XXH_IPREF(XXH_OK) +# define XXH_ERROR XXH_IPREF(XXH_ERROR) +# define XXH_errorcode XXH_IPREF(XXH_errorcode) +# define XXH32_canonical_t XXH_IPREF(XXH32_canonical_t) +# define XXH64_canonical_t XXH_IPREF(XXH64_canonical_t) +# define XXH128_canonical_t XXH_IPREF(XXH128_canonical_t) +# define XXH32_state_s XXH_IPREF(XXH32_state_s) +# define XXH32_state_t XXH_IPREF(XXH32_state_t) +# define XXH64_state_s XXH_IPREF(XXH64_state_s) +# define XXH64_state_t XXH_IPREF(XXH64_state_t) +# define XXH3_state_s XXH_IPREF(XXH3_state_s) +# define XXH3_state_t XXH_IPREF(XXH3_state_t) +# define XXH128_hash_t XXH_IPREF(XXH128_hash_t) + /* Ensure the header is parsed again, even if it was previously included */ +# undef XXHASH_H_5627135585666179 +# undef XXHASH_H_STATIC_13879238742 +#endif /* XXH_INLINE_ALL || XXH_PRIVATE_API */ + + + +/* **************************************************************** + * Stable API + *****************************************************************/ +#ifndef XXHASH_H_5627135585666179 +#define XXHASH_H_5627135585666179 1 + +/* specific declaration modes for Windows */ +#if !defined(XXH_INLINE_ALL) && !defined(XXH_PRIVATE_API) +# if defined(WIN32) && defined(_MSC_VER) && (defined(XXH_IMPORT) || defined(XXH_EXPORT)) +# ifdef XXH_EXPORT +# define XXH_PUBLIC_API __declspec(dllexport) +# elif XXH_IMPORT +# define XXH_PUBLIC_API __declspec(dllimport) +# endif +# else +# define XXH_PUBLIC_API /* do nothing */ +# endif +#endif + +/*! + * XXH_NAMESPACE, aka Namespace Emulation: + * + * If you want to include _and expose_ xxHash functions from within your own + * library, but also want to avoid symbol collisions with other libraries which + * may also include xxHash, you can use XXH_NAMESPACE to automatically prefix + * any public symbol from xxhash library with the value of XXH_NAMESPACE + * (therefore, avoid empty or numeric values). + * + * Note that no change is required within the calling program as long as it + * includes `xxhash.h`: Regular symbol names will be automatically translated + * by this header. + */ +#ifdef XXH_NAMESPACE +# define XXH_CAT(A,B) A##B +# define XXH_NAME2(A,B) XXH_CAT(A,B) +# define XXH_versionNumber XXH_NAME2(XXH_NAMESPACE, XXH_versionNumber) +/* XXH32 */ +# define XXH32 XXH_NAME2(XXH_NAMESPACE, XXH32) +# define XXH32_createState XXH_NAME2(XXH_NAMESPACE, XXH32_createState) +# define XXH32_freeState XXH_NAME2(XXH_NAMESPACE, XXH32_freeState) +# define XXH32_reset XXH_NAME2(XXH_NAMESPACE, XXH32_reset) +# define XXH32_update XXH_NAME2(XXH_NAMESPACE, XXH32_update) +# define XXH32_digest XXH_NAME2(XXH_NAMESPACE, XXH32_digest) +# define XXH32_copyState XXH_NAME2(XXH_NAMESPACE, XXH32_copyState) +# define XXH32_canonicalFromHash XXH_NAME2(XXH_NAMESPACE, XXH32_canonicalFromHash) +# define XXH32_hashFromCanonical XXH_NAME2(XXH_NAMESPACE, XXH32_hashFromCanonical) +/* XXH64 */ +# define XXH64 XXH_NAME2(XXH_NAMESPACE, XXH64) +# define XXH64_createState XXH_NAME2(XXH_NAMESPACE, XXH64_createState) +# define XXH64_freeState XXH_NAME2(XXH_NAMESPACE, XXH64_freeState) +# define XXH64_reset XXH_NAME2(XXH_NAMESPACE, XXH64_reset) +# define XXH64_update XXH_NAME2(XXH_NAMESPACE, XXH64_update) +# define XXH64_digest XXH_NAME2(XXH_NAMESPACE, XXH64_digest) +# define XXH64_copyState XXH_NAME2(XXH_NAMESPACE, XXH64_copyState) +# define XXH64_canonicalFromHash XXH_NAME2(XXH_NAMESPACE, XXH64_canonicalFromHash) +# define XXH64_hashFromCanonical XXH_NAME2(XXH_NAMESPACE, XXH64_hashFromCanonical) +/* XXH3_64bits */ +# define XXH3_64bits XXH_NAME2(XXH_NAMESPACE, XXH3_64bits) +# define XXH3_64bits_withSecret XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_withSecret) +# define XXH3_64bits_withSeed XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_withSeed) +# define XXH3_createState XXH_NAME2(XXH_NAMESPACE, XXH3_createState) +# define XXH3_freeState XXH_NAME2(XXH_NAMESPACE, XXH3_freeState) +# define XXH3_copyState XXH_NAME2(XXH_NAMESPACE, XXH3_copyState) +# define XXH3_64bits_reset XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_reset) +# define XXH3_64bits_reset_withSeed XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_reset_withSeed) +# define XXH3_64bits_reset_withSecret XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_reset_withSecret) +# define XXH3_64bits_update XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_update) +# define XXH3_64bits_digest XXH_NAME2(XXH_NAMESPACE, XXH3_64bits_digest) +# define XXH3_generateSecret XXH_NAME2(XXH_NAMESPACE, XXH3_generateSecret) +/* XXH3_128bits */ +# define XXH128 XXH_NAME2(XXH_NAMESPACE, XXH128) +# define XXH3_128bits XXH_NAME2(XXH_NAMESPACE, XXH3_128bits) +# define XXH3_128bits_withSeed XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_withSeed) +# define XXH3_128bits_withSecret XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_withSecret) +# define XXH3_128bits_reset XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_reset) +# define XXH3_128bits_reset_withSeed XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_reset_withSeed) +# define XXH3_128bits_reset_withSecret XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_reset_withSecret) +# define XXH3_128bits_update XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_update) +# define XXH3_128bits_digest XXH_NAME2(XXH_NAMESPACE, XXH3_128bits_digest) +# define XXH128_isEqual XXH_NAME2(XXH_NAMESPACE, XXH128_isEqual) +# define XXH128_cmp XXH_NAME2(XXH_NAMESPACE, XXH128_cmp) +# define XXH128_canonicalFromHash XXH_NAME2(XXH_NAMESPACE, XXH128_canonicalFromHash) +# define XXH128_hashFromCanonical XXH_NAME2(XXH_NAMESPACE, XXH128_hashFromCanonical) +#endif + + +/* ************************************* +* Version +***************************************/ +#define XXH_VERSION_MAJOR 0 +#define XXH_VERSION_MINOR 8 +#define XXH_VERSION_RELEASE 0 +#define XXH_VERSION_NUMBER (XXH_VERSION_MAJOR *100*100 + XXH_VERSION_MINOR *100 + XXH_VERSION_RELEASE) +XXH_PUBLIC_API unsigned XXH_versionNumber (void); + + +/* **************************** +* Definitions +******************************/ +#include /* size_t */ +typedef enum { XXH_OK=0, XXH_ERROR } XXH_errorcode; + + +/*-********************************************************************** +* 32-bit hash +************************************************************************/ +#if !defined (__VMS) \ + && (defined (__cplusplus) \ + || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) ) +# include + typedef uint32_t XXH32_hash_t; +#else +# include +# if UINT_MAX == 0xFFFFFFFFUL + typedef unsigned int XXH32_hash_t; +# else +# if ULONG_MAX == 0xFFFFFFFFUL + typedef unsigned long XXH32_hash_t; +# else +# error "unsupported platform: need a 32-bit type" +# endif +# endif +#endif + +/*! + * XXH32(): + * Calculate the 32-bit hash of sequence "length" bytes stored at memory address "input". + * The memory between input & input+length must be valid (allocated and read-accessible). + * "seed" can be used to alter the result predictably. + * Speed on Core 2 Duo @ 3 GHz (single thread, SMHasher benchmark): 5.4 GB/s + * + * Note: XXH3 provides competitive speed for both 32-bit and 64-bit systems, + * and offers true 64/128 bit hash results. It provides a superior level of + * dispersion, and greatly reduces the risks of collisions. + */ +XXH_PUBLIC_API XXH32_hash_t XXH32 (const void* input, size_t length, XXH32_hash_t seed); + +/******* Streaming *******/ + +/* + * Streaming functions generate the xxHash value from an incrememtal input. + * This method is slower than single-call functions, due to state management. + * For small inputs, prefer `XXH32()` and `XXH64()`, which are better optimized. + * + * An XXH state must first be allocated using `XXH*_createState()`. + * + * Start a new hash by initializing the state with a seed using `XXH*_reset()`. + * + * Then, feed the hash state by calling `XXH*_update()` as many times as necessary. + * + * The function returns an error code, with 0 meaning OK, and any other value + * meaning there is an error. + * + * Finally, a hash value can be produced anytime, by using `XXH*_digest()`. + * This function returns the nn-bits hash as an int or long long. + * + * It's still possible to continue inserting input into the hash state after a + * digest, and generate new hash values later on by invoking `XXH*_digest()`. + * + * When done, release the state using `XXH*_freeState()`. + */ + +typedef struct XXH32_state_s XXH32_state_t; /* incomplete type */ +XXH_PUBLIC_API XXH32_state_t* XXH32_createState(void); +XXH_PUBLIC_API XXH_errorcode XXH32_freeState(XXH32_state_t* statePtr); +XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t* dst_state, const XXH32_state_t* src_state); + +XXH_PUBLIC_API XXH_errorcode XXH32_reset (XXH32_state_t* statePtr, XXH32_hash_t seed); +XXH_PUBLIC_API XXH_errorcode XXH32_update (XXH32_state_t* statePtr, const void* input, size_t length); +XXH_PUBLIC_API XXH32_hash_t XXH32_digest (const XXH32_state_t* statePtr); + +/******* Canonical representation *******/ + +/* + * The default return values from XXH functions are unsigned 32 and 64 bit + * integers. + * This the simplest and fastest format for further post-processing. + * + * However, this leaves open the question of what is the order on the byte level, + * since little and big endian conventions will store the same number differently. + * + * The canonical representation settles this issue by mandating big-endian + * convention, the same convention as human-readable numbers (large digits first). + * + * When writing hash values to storage, sending them over a network, or printing + * them, it's highly recommended to use the canonical representation to ensure + * portability across a wider range of systems, present and future. + * + * The following functions allow transformation of hash values to and from + * canonical format. + */ + +typedef struct { unsigned char digest[4]; } XXH32_canonical_t; +XXH_PUBLIC_API void XXH32_canonicalFromHash(XXH32_canonical_t* dst, XXH32_hash_t hash); +XXH_PUBLIC_API XXH32_hash_t XXH32_hashFromCanonical(const XXH32_canonical_t* src); + + +#ifndef XXH_NO_LONG_LONG +/*-********************************************************************** +* 64-bit hash +************************************************************************/ +#if !defined (__VMS) \ + && (defined (__cplusplus) \ + || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) ) +# include + typedef uint64_t XXH64_hash_t; +#else + /* the following type must have a width of 64-bit */ + typedef unsigned long long XXH64_hash_t; +#endif + +/*! + * XXH64(): + * Returns the 64-bit hash of sequence of length @length stored at memory + * address @input. + * @seed can be used to alter the result predictably. + * + * This function usually runs faster on 64-bit systems, but slower on 32-bit + * systems (see benchmark). + * + * Note: XXH3 provides competitive speed for both 32-bit and 64-bit systems, + * and offers true 64/128 bit hash results. It provides a superior level of + * dispersion, and greatly reduces the risks of collisions. + */ +XXH_PUBLIC_API XXH64_hash_t XXH64 (const void* input, size_t length, XXH64_hash_t seed); + +/******* Streaming *******/ +typedef struct XXH64_state_s XXH64_state_t; /* incomplete type */ +XXH_PUBLIC_API XXH64_state_t* XXH64_createState(void); +XXH_PUBLIC_API XXH_errorcode XXH64_freeState(XXH64_state_t* statePtr); +XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t* dst_state, const XXH64_state_t* src_state); + +XXH_PUBLIC_API XXH_errorcode XXH64_reset (XXH64_state_t* statePtr, XXH64_hash_t seed); +XXH_PUBLIC_API XXH_errorcode XXH64_update (XXH64_state_t* statePtr, const void* input, size_t length); +XXH_PUBLIC_API XXH64_hash_t XXH64_digest (const XXH64_state_t* statePtr); + +/******* Canonical representation *******/ +typedef struct { unsigned char digest[sizeof(XXH64_hash_t)]; } XXH64_canonical_t; +XXH_PUBLIC_API void XXH64_canonicalFromHash(XXH64_canonical_t* dst, XXH64_hash_t hash); +XXH_PUBLIC_API XXH64_hash_t XXH64_hashFromCanonical(const XXH64_canonical_t* src); + + +/*-********************************************************************** +* XXH3 64-bit variant +************************************************************************/ + +/* ************************************************************************ + * XXH3 is a new hash algorithm featuring: + * - Improved speed for both small and large inputs + * - True 64-bit and 128-bit outputs + * - SIMD acceleration + * - Improved 32-bit viability + * + * Speed analysis methodology is explained here: + * + * https://fastcompression.blogspot.com/2019/03/presenting-xxh3.html + * + * In general, expect XXH3 to run about ~2x faster on large inputs and >3x + * faster on small ones compared to XXH64, though exact differences depend on + * the platform. + * + * The algorithm is portable: Like XXH32 and XXH64, it generates the same hash + * on all platforms. + * + * It benefits greatly from SIMD and 64-bit arithmetic, but does not require it. + * + * Almost all 32-bit and 64-bit targets that can run XXH32 smoothly can run + * XXH3 at competitive speeds, even if XXH64 runs slowly. Further details are + * explained in the implementation. + * + * Optimized implementations are provided for AVX512, AVX2, SSE2, NEON, POWER8, + * ZVector and scalar targets. This can be controlled with the XXH_VECTOR macro. + * + * XXH3 offers 2 variants, _64bits and _128bits. + * When only 64 bits are needed, prefer calling the _64bits variant, as it + * reduces the amount of mixing, resulting in faster speed on small inputs. + * + * It's also generally simpler to manipulate a scalar return type than a struct. + * + * The 128-bit version adds additional strength, but it is slightly slower. + * + * The XXH3 algorithm is still in development. + * The results it produces may still change in future versions. + * + * Results produced by v0.7.x are not comparable with results from v0.7.y. + * However, the API is completely stable, and it can safely be used for + * ephemeral data (local sessions). + * + * Avoid storing values in long-term storage until the algorithm is finalized. + * XXH3's return values will be officially finalized upon reaching v0.8.0. + * + * After which, return values of XXH3 and XXH128 will no longer change in + * future versions. + * + * The API supports one-shot hashing, streaming mode, and custom secrets. + */ + +/* XXH3_64bits(): + * default 64-bit variant, using default secret and default seed of 0. + * It's the fastest variant. */ +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits(const void* data, size_t len); + +/* + * XXH3_64bits_withSeed(): + * This variant generates a custom secret on the fly + * based on default secret altered using the `seed` value. + * While this operation is decently fast, note that it's not completely free. + * Note: seed==0 produces the same results as XXH3_64bits(). + */ +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_withSeed(const void* data, size_t len, XXH64_hash_t seed); + +/* + * XXH3_64bits_withSecret(): + * It's possible to provide any blob of bytes as a "secret" to generate the hash. + * This makes it more difficult for an external actor to prepare an intentional collision. + * The main condition is that secretSize *must* be large enough (>= XXH3_SECRET_SIZE_MIN). + * However, the quality of produced hash values depends on secret's entropy. + * Technically, the secret must look like a bunch of random bytes. + * Avoid "trivial" or structured data such as repeated sequences or a text document. + * Whenever unsure about the "randomness" of the blob of bytes, + * consider relabelling it as a "custom seed" instead, + * and employ "XXH3_generateSecret()" (see below) + * to generate a high entropy secret derived from the custom seed. + */ +#define XXH3_SECRET_SIZE_MIN 136 +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_withSecret(const void* data, size_t len, const void* secret, size_t secretSize); + + +/******* Streaming *******/ +/* + * Streaming requires state maintenance. + * This operation costs memory and CPU. + * As a consequence, streaming is slower than one-shot hashing. + * For better performance, prefer one-shot functions whenever applicable. + */ +typedef struct XXH3_state_s XXH3_state_t; +XXH_PUBLIC_API XXH3_state_t* XXH3_createState(void); +XXH_PUBLIC_API XXH_errorcode XXH3_freeState(XXH3_state_t* statePtr); +XXH_PUBLIC_API void XXH3_copyState(XXH3_state_t* dst_state, const XXH3_state_t* src_state); + +/* + * XXH3_64bits_reset(): + * Initialize with default parameters. + * digest will be equivalent to `XXH3_64bits()`. + */ +XXH_PUBLIC_API XXH_errorcode XXH3_64bits_reset(XXH3_state_t* statePtr); +/* + * XXH3_64bits_reset_withSeed(): + * Generate a custom secret from `seed`, and store it into `statePtr`. + * digest will be equivalent to `XXH3_64bits_withSeed()`. + */ +XXH_PUBLIC_API XXH_errorcode XXH3_64bits_reset_withSeed(XXH3_state_t* statePtr, XXH64_hash_t seed); +/* + * XXH3_64bits_reset_withSecret(): + * `secret` is referenced, it _must outlive_ the hash streaming session. + * Similar to one-shot API, `secretSize` must be >= `XXH3_SECRET_SIZE_MIN`, + * and the quality of produced hash values depends on secret's entropy + * (secret's content should look like a bunch of random bytes). + * When in doubt about the randomness of a candidate `secret`, + * consider employing `XXH3_generateSecret()` instead (see below). + */ +XXH_PUBLIC_API XXH_errorcode XXH3_64bits_reset_withSecret(XXH3_state_t* statePtr, const void* secret, size_t secretSize); + +XXH_PUBLIC_API XXH_errorcode XXH3_64bits_update (XXH3_state_t* statePtr, const void* input, size_t length); +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_digest (const XXH3_state_t* statePtr); + +/* note : canonical representation of XXH3 is the same as XXH64 + * since they both produce XXH64_hash_t values */ + + +/*-********************************************************************** +* XXH3 128-bit variant +************************************************************************/ + +typedef struct { + XXH64_hash_t low64; + XXH64_hash_t high64; +} XXH128_hash_t; + +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits(const void* data, size_t len); +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_withSeed(const void* data, size_t len, XXH64_hash_t seed); +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_withSecret(const void* data, size_t len, const void* secret, size_t secretSize); + +/******* Streaming *******/ +/* + * Streaming requires state maintenance. + * This operation costs memory and CPU. + * As a consequence, streaming is slower than one-shot hashing. + * For better performance, prefer one-shot functions whenever applicable. + * + * XXH3_128bits uses the same XXH3_state_t as XXH3_64bits(). + * Use already declared XXH3_createState() and XXH3_freeState(). + * + * All reset and streaming functions have same meaning as their 64-bit counterpart. + */ + +XXH_PUBLIC_API XXH_errorcode XXH3_128bits_reset(XXH3_state_t* statePtr); +XXH_PUBLIC_API XXH_errorcode XXH3_128bits_reset_withSeed(XXH3_state_t* statePtr, XXH64_hash_t seed); +XXH_PUBLIC_API XXH_errorcode XXH3_128bits_reset_withSecret(XXH3_state_t* statePtr, const void* secret, size_t secretSize); + +XXH_PUBLIC_API XXH_errorcode XXH3_128bits_update (XXH3_state_t* statePtr, const void* input, size_t length); +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_digest (const XXH3_state_t* statePtr); + +/* Following helper functions make it possible to compare XXH128_hast_t values. + * Since XXH128_hash_t is a structure, this capability is not offered by the language. + * Note: For better performance, these functions can be inlined using XXH_INLINE_ALL */ + +/*! + * XXH128_isEqual(): + * Return: 1 if `h1` and `h2` are equal, 0 if they are not. + */ +XXH_PUBLIC_API int XXH128_isEqual(XXH128_hash_t h1, XXH128_hash_t h2); + +/*! + * XXH128_cmp(): + * + * This comparator is compatible with stdlib's `qsort()`/`bsearch()`. + * + * return: >0 if *h128_1 > *h128_2 + * =0 if *h128_1 == *h128_2 + * <0 if *h128_1 < *h128_2 + */ +XXH_PUBLIC_API int XXH128_cmp(const void* h128_1, const void* h128_2); + + +/******* Canonical representation *******/ +typedef struct { unsigned char digest[sizeof(XXH128_hash_t)]; } XXH128_canonical_t; +XXH_PUBLIC_API void XXH128_canonicalFromHash(XXH128_canonical_t* dst, XXH128_hash_t hash); +XXH_PUBLIC_API XXH128_hash_t XXH128_hashFromCanonical(const XXH128_canonical_t* src); + + +#endif /* XXH_NO_LONG_LONG */ + +#endif /* XXHASH_H_5627135585666179 */ + + + +#if defined(XXH_STATIC_LINKING_ONLY) && !defined(XXHASH_H_STATIC_13879238742) +#define XXHASH_H_STATIC_13879238742 +/* **************************************************************************** + * This section contains declarations which are not guaranteed to remain stable. + * They may change in future versions, becoming incompatible with a different + * version of the library. + * These declarations should only be used with static linking. + * Never use them in association with dynamic linking! + ***************************************************************************** */ + +/* + * These definitions are only present to allow static allocation + * of XXH states, on stack or in a struct, for example. + * Never **ever** access their members directly. + */ + +struct XXH32_state_s { + XXH32_hash_t total_len_32; + XXH32_hash_t large_len; + XXH32_hash_t v1; + XXH32_hash_t v2; + XXH32_hash_t v3; + XXH32_hash_t v4; + XXH32_hash_t mem32[4]; + XXH32_hash_t memsize; + XXH32_hash_t reserved; /* never read nor write, might be removed in a future version */ +}; /* typedef'd to XXH32_state_t */ + + +#ifndef XXH_NO_LONG_LONG /* defined when there is no 64-bit support */ + +struct XXH64_state_s { + XXH64_hash_t total_len; + XXH64_hash_t v1; + XXH64_hash_t v2; + XXH64_hash_t v3; + XXH64_hash_t v4; + XXH64_hash_t mem64[4]; + XXH32_hash_t memsize; + XXH32_hash_t reserved32; /* required for padding anyway */ + XXH64_hash_t reserved64; /* never read nor write, might be removed in a future version */ +}; /* typedef'd to XXH64_state_t */ + +#if defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 201112L) /* C11+ */ +# include +# define XXH_ALIGN(n) alignas(n) +#elif defined(__GNUC__) +# define XXH_ALIGN(n) __attribute__ ((aligned(n))) +#elif defined(_MSC_VER) +# define XXH_ALIGN(n) __declspec(align(n)) +#else +# define XXH_ALIGN(n) /* disabled */ +#endif + +/* Old GCC versions only accept the attribute after the type in structures. */ +#if !(defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 201112L)) /* C11+ */ \ + && defined(__GNUC__) +# define XXH_ALIGN_MEMBER(align, type) type XXH_ALIGN(align) +#else +# define XXH_ALIGN_MEMBER(align, type) XXH_ALIGN(align) type +#endif + +#define XXH3_INTERNALBUFFER_SIZE 256 +#define XXH3_SECRET_DEFAULT_SIZE 192 +struct XXH3_state_s { + XXH_ALIGN_MEMBER(64, XXH64_hash_t acc[8]); + /* used to store a custom secret generated from a seed */ + XXH_ALIGN_MEMBER(64, unsigned char customSecret[XXH3_SECRET_DEFAULT_SIZE]); + XXH_ALIGN_MEMBER(64, unsigned char buffer[XXH3_INTERNALBUFFER_SIZE]); + XXH32_hash_t bufferedSize; + XXH32_hash_t reserved32; + size_t nbStripesSoFar; + XXH64_hash_t totalLen; + size_t nbStripesPerBlock; + size_t secretLimit; + XXH64_hash_t seed; + XXH64_hash_t reserved64; + const unsigned char* extSecret; /* reference to external secret; + * if == NULL, use .customSecret instead */ + /* note: there may be some padding at the end due to alignment on 64 bytes */ +}; /* typedef'd to XXH3_state_t */ + +#undef XXH_ALIGN_MEMBER + +/* When the XXH3_state_t structure is merely emplaced on stack, + * it should be initialized with XXH3_INITSTATE() or a memset() + * in case its first reset uses XXH3_NNbits_reset_withSeed(). + * This init can be omitted if the first reset uses default or _withSecret mode. + * This operation isn't necessary when the state is created with XXH3_createState(). + * Note that this doesn't prepare the state for a streaming operation, + * it's still necessary to use XXH3_NNbits_reset*() afterwards. + */ +#define XXH3_INITSTATE(XXH3_state_ptr) { (XXH3_state_ptr)->seed = 0; } + + +/* === Experimental API === */ +/* Symbols defined below must be considered tied to a specific library version. */ + +/* + * XXH3_generateSecret(): + * + * Derive a high-entropy secret from any user-defined content, named customSeed. + * The generated secret can be used in combination with `*_withSecret()` functions. + * The `_withSecret()` variants are useful to provide a higher level of protection than 64-bit seed, + * as it becomes much more difficult for an external actor to guess how to impact the calculation logic. + * + * The function accepts as input a custom seed of any length and any content, + * and derives from it a high-entropy secret of length XXH3_SECRET_DEFAULT_SIZE + * into an already allocated buffer secretBuffer. + * The generated secret is _always_ XXH_SECRET_DEFAULT_SIZE bytes long. + * + * The generated secret can then be used with any `*_withSecret()` variant. + * Functions `XXH3_128bits_withSecret()`, `XXH3_64bits_withSecret()`, + * `XXH3_128bits_reset_withSecret()` and `XXH3_64bits_reset_withSecret()` + * are part of this list. They all accept a `secret` parameter + * which must be very long for implementation reasons (>= XXH3_SECRET_SIZE_MIN) + * _and_ feature very high entropy (consist of random-looking bytes). + * These conditions can be a high bar to meet, so + * this function can be used to generate a secret of proper quality. + * + * customSeed can be anything. It can have any size, even small ones, + * and its content can be anything, even stupidly "low entropy" source such as a bunch of zeroes. + * The resulting `secret` will nonetheless provide all expected qualities. + * + * Supplying NULL as the customSeed copies the default secret into `secretBuffer`. + * When customSeedSize > 0, supplying NULL as customSeed is undefined behavior. + */ +XXH_PUBLIC_API void XXH3_generateSecret(void* secretBuffer, const void* customSeed, size_t customSeedSize); + + +/* simple short-cut to pre-selected XXH3_128bits variant */ +XXH_PUBLIC_API XXH128_hash_t XXH128(const void* data, size_t len, XXH64_hash_t seed); + + +#endif /* XXH_NO_LONG_LONG */ + + +#if defined(XXH_INLINE_ALL) || defined(XXH_PRIVATE_API) +# define XXH_IMPLEMENTATION +#endif + +#endif /* defined(XXH_STATIC_LINKING_ONLY) && !defined(XXHASH_H_STATIC_13879238742) */ + + +/* ======================================================================== */ +/* ======================================================================== */ +/* ======================================================================== */ + + +/*-********************************************************************** + * xxHash implementation + *-********************************************************************** + * xxHash's implementation used to be hosted inside xxhash.c. + * + * However, inlining requires implementation to be visible to the compiler, + * hence be included alongside the header. + * Previously, implementation was hosted inside xxhash.c, + * which was then #included when inlining was activated. + * This construction created issues with a few build and install systems, + * as it required xxhash.c to be stored in /include directory. + * + * xxHash implementation is now directly integrated within xxhash.h. + * As a consequence, xxhash.c is no longer needed in /include. + * + * xxhash.c is still available and is still useful. + * In a "normal" setup, when xxhash is not inlined, + * xxhash.h only exposes the prototypes and public symbols, + * while xxhash.c can be built into an object file xxhash.o + * which can then be linked into the final binary. + ************************************************************************/ + +#if ( defined(XXH_INLINE_ALL) || defined(XXH_PRIVATE_API) \ + || defined(XXH_IMPLEMENTATION) ) && !defined(XXH_IMPLEM_13a8737387) +# define XXH_IMPLEM_13a8737387 + +/* ************************************* +* Tuning parameters +***************************************/ +/*! + * XXH_FORCE_MEMORY_ACCESS: + * By default, access to unaligned memory is controlled by `memcpy()`, which is + * safe and portable. + * + * Unfortunately, on some target/compiler combinations, the generated assembly + * is sub-optimal. + * + * The below switch allow selection of a different access method + * in the search for improved performance. + * Method 0 (default): + * Use `memcpy()`. Safe and portable. Default. + * Method 1: + * `__attribute__((packed))` statement. It depends on compiler extensions + * and is therefore not portable. + * This method is safe if your compiler supports it, and *generally* as + * fast or faster than `memcpy`. + * Method 2: + * Direct access via cast. This method doesn't depend on the compiler but + * violates the C standard. + * It can generate buggy code on targets which do not support unaligned + * memory accesses. + * But in some circumstances, it's the only known way to get the most + * performance (example: GCC + ARMv6) + * Method 3: + * Byteshift. This can generate the best code on old compilers which don't + * inline small `memcpy()` calls, and it might also be faster on big-endian + * systems which lack a native byteswap instruction. + * See https://stackoverflow.com/a/32095106/646947 for details. + * Prefer these methods in priority order (0 > 1 > 2 > 3) + */ +#ifndef XXH_FORCE_MEMORY_ACCESS /* can be defined externally, on command line for example */ +# if !defined(__clang__) && defined(__GNUC__) && defined(__ARM_FEATURE_UNALIGNED) && defined(__ARM_ARCH) && (__ARM_ARCH == 6) +# define XXH_FORCE_MEMORY_ACCESS 2 +# elif !defined(__clang__) && ((defined(__INTEL_COMPILER) && !defined(_WIN32)) || \ + (defined(__GNUC__) && (defined(__ARM_ARCH) && __ARM_ARCH >= 7))) +# define XXH_FORCE_MEMORY_ACCESS 1 +# endif +#endif + +/*! + * XXH_ACCEPT_NULL_INPUT_POINTER: + * If the input pointer is NULL, xxHash's default behavior is to dereference it, + * triggering a segfault. + * When this macro is enabled, xxHash actively checks the input for a null pointer. + * If it is, the result for null input pointers is the same as a zero-length input. + */ +#ifndef XXH_ACCEPT_NULL_INPUT_POINTER /* can be defined externally */ +# define XXH_ACCEPT_NULL_INPUT_POINTER 0 +#endif + +/*! + * XXH_FORCE_ALIGN_CHECK: + * This is an important performance trick + * for architectures without decent unaligned memory access performance. + * It checks for input alignment, and when conditions are met, + * uses a "fast path" employing direct 32-bit/64-bit read, + * resulting in _dramatically faster_ read speed. + * + * The check costs one initial branch per hash, which is generally negligible, but not zero. + * Moreover, it's not useful to generate binary for an additional code path + * if memory access uses same instruction for both aligned and unaligned adresses. + * + * In these cases, the alignment check can be removed by setting this macro to 0. + * Then the code will always use unaligned memory access. + * Align check is automatically disabled on x86, x64 & arm64, + * which are platforms known to offer good unaligned memory accesses performance. + * + * This option does not affect XXH3 (only XXH32 and XXH64). + */ +#ifndef XXH_FORCE_ALIGN_CHECK /* can be defined externally */ +# if defined(__i386) || defined(__x86_64__) || defined(__aarch64__) \ + || defined(_M_IX86) || defined(_M_X64) || defined(_M_ARM64) /* visual */ +# define XXH_FORCE_ALIGN_CHECK 0 +# else +# define XXH_FORCE_ALIGN_CHECK 1 +# endif +#endif + +/*! + * XXH_NO_INLINE_HINTS: + * + * By default, xxHash tries to force the compiler to inline almost all internal + * functions. + * + * This can usually improve performance due to reduced jumping and improved + * constant folding, but significantly increases the size of the binary which + * might not be favorable. + * + * Additionally, sometimes the forced inlining can be detrimental to performance, + * depending on the architecture. + * + * XXH_NO_INLINE_HINTS marks all internal functions as static, giving the + * compiler full control on whether to inline or not. + * + * When not optimizing (-O0), optimizing for size (-Os, -Oz), or using + * -fno-inline with GCC or Clang, this will automatically be defined. + */ +#ifndef XXH_NO_INLINE_HINTS +# if defined(__OPTIMIZE_SIZE__) /* -Os, -Oz */ \ + || defined(__NO_INLINE__) /* -O0, -fno-inline */ +# define XXH_NO_INLINE_HINTS 1 +# else +# define XXH_NO_INLINE_HINTS 0 +# endif +#endif + +/*! + * XXH_REROLL: + * Whether to reroll XXH32_finalize, and XXH64_finalize, + * instead of using an unrolled jump table/if statement loop. + * + * This is automatically defined on -Os/-Oz on GCC and Clang. + */ +#ifndef XXH_REROLL +# if defined(__OPTIMIZE_SIZE__) +# define XXH_REROLL 1 +# else +# define XXH_REROLL 0 +# endif +#endif + + +/* ************************************* +* Includes & Memory related functions +***************************************/ +/*! + * Modify the local functions below should you wish to use + * different memory routines for malloc() and free() + */ +#include + +static void* XXH_malloc(size_t s) { return malloc(s); } +static void XXH_free(void* p) { free(p); } + +/*! and for memcpy() */ +#include +static void* XXH_memcpy(void* dest, const void* src, size_t size) +{ + return memcpy(dest,src,size); +} + +#include /* ULLONG_MAX */ + + +/* ************************************* +* Compiler Specific Options +***************************************/ +#ifdef _MSC_VER /* Visual Studio warning fix */ +# pragma warning(disable : 4127) /* disable: C4127: conditional expression is constant */ +#endif + +#if XXH_NO_INLINE_HINTS /* disable inlining hints */ +# if defined(__GNUC__) +# define XXH_FORCE_INLINE static __attribute__((unused)) +# else +# define XXH_FORCE_INLINE static +# endif +# define XXH_NO_INLINE static +/* enable inlining hints */ +#elif defined(_MSC_VER) /* Visual Studio */ +# define XXH_FORCE_INLINE static __forceinline +# define XXH_NO_INLINE static __declspec(noinline) +#elif defined(__GNUC__) +# define XXH_FORCE_INLINE static __inline__ __attribute__((always_inline, unused)) +# define XXH_NO_INLINE static __attribute__((noinline)) +#elif defined (__cplusplus) \ + || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L)) /* C99 */ +# define XXH_FORCE_INLINE static inline +# define XXH_NO_INLINE static +#else +# define XXH_FORCE_INLINE static +# define XXH_NO_INLINE static +#endif + + + +/* ************************************* +* Debug +***************************************/ +/* + * XXH_DEBUGLEVEL is expected to be defined externally, typically via the + * compiler's command line options. The value must be a number. + */ +#ifndef XXH_DEBUGLEVEL +# ifdef DEBUGLEVEL /* backwards compat */ +# define XXH_DEBUGLEVEL DEBUGLEVEL +# else +# define XXH_DEBUGLEVEL 0 +# endif +#endif + +#if (XXH_DEBUGLEVEL>=1) +# include /* note: can still be disabled with NDEBUG */ +# define XXH_ASSERT(c) assert(c) +#else +# define XXH_ASSERT(c) ((void)0) +#endif + +/* note: use after variable declarations */ +#define XXH_STATIC_ASSERT(c) do { enum { XXH_sa = 1/(int)(!!(c)) }; } while (0) + + +/* ************************************* +* Basic Types +***************************************/ +#if !defined (__VMS) \ + && (defined (__cplusplus) \ + || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) ) +# include + typedef uint8_t xxh_u8; +#else + typedef unsigned char xxh_u8; +#endif +typedef XXH32_hash_t xxh_u32; + +#ifdef XXH_OLD_NAMES +# define BYTE xxh_u8 +# define U8 xxh_u8 +# define U32 xxh_u32 +#endif + +/* *** Memory access *** */ + +#if (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==3)) +/* + * Manual byteshift. Best for old compilers which don't inline memcpy. + * We actually directly use XXH_readLE32 and XXH_readBE32. + */ +#elif (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==2)) + +/* + * Force direct memory access. Only works on CPU which support unaligned memory + * access in hardware. + */ +static xxh_u32 XXH_read32(const void* memPtr) { return *(const xxh_u32*) memPtr; } + +#elif (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==1)) + +/* + * __pack instructions are safer but compiler specific, hence potentially + * problematic for some compilers. + * + * Currently only defined for GCC and ICC. + */ +#ifdef XXH_OLD_NAMES +typedef union { xxh_u32 u32; } __attribute__((packed)) unalign; +#endif +static xxh_u32 XXH_read32(const void* ptr) +{ + typedef union { xxh_u32 u32; } __attribute__((packed)) xxh_unalign; + return ((const xxh_unalign*)ptr)->u32; +} + +#else + +/* + * Portable and safe solution. Generally efficient. + * see: https://stackoverflow.com/a/32095106/646947 + */ +static xxh_u32 XXH_read32(const void* memPtr) +{ + xxh_u32 val; + memcpy(&val, memPtr, sizeof(val)); + return val; +} + +#endif /* XXH_FORCE_DIRECT_MEMORY_ACCESS */ + + +/* *** Endianess *** */ +typedef enum { XXH_bigEndian=0, XXH_littleEndian=1 } XXH_endianess; + +/*! + * XXH_CPU_LITTLE_ENDIAN: + * Defined to 1 if the target is little endian, or 0 if it is big endian. + * It can be defined externally, for example on the compiler command line. + * + * If it is not defined, a runtime check (which is usually constant folded) + * is used instead. + */ +#ifndef XXH_CPU_LITTLE_ENDIAN +/* + * Try to detect endianness automatically, to avoid the nonstandard behavior + * in `XXH_isLittleEndian()` + */ +# if defined(_WIN32) /* Windows is always little endian */ \ + || defined(__LITTLE_ENDIAN__) \ + || (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__) +# define XXH_CPU_LITTLE_ENDIAN 1 +# elif defined(__BIG_ENDIAN__) \ + || (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__) +# define XXH_CPU_LITTLE_ENDIAN 0 +# else +/* + * runtime test, presumed to simplify to a constant by compiler + */ +static int XXH_isLittleEndian(void) +{ + /* + * Portable and well-defined behavior. + * Don't use static: it is detrimental to performance. + */ + const union { xxh_u32 u; xxh_u8 c[4]; } one = { 1 }; + return one.c[0]; +} +# define XXH_CPU_LITTLE_ENDIAN XXH_isLittleEndian() +# endif +#endif + + + + +/* **************************************** +* Compiler-specific Functions and Macros +******************************************/ +#define XXH_GCC_VERSION (__GNUC__ * 100 + __GNUC_MINOR__) + +#ifdef __has_builtin +# define XXH_HAS_BUILTIN(x) __has_builtin(x) +#else +# define XXH_HAS_BUILTIN(x) 0 +#endif + +#if !defined(NO_CLANG_BUILTIN) && XXH_HAS_BUILTIN(__builtin_rotateleft32) \ + && XXH_HAS_BUILTIN(__builtin_rotateleft64) +# define XXH_rotl32 __builtin_rotateleft32 +# define XXH_rotl64 __builtin_rotateleft64 +/* Note: although _rotl exists for minGW (GCC under windows), performance seems poor */ +#elif defined(_MSC_VER) +# define XXH_rotl32(x,r) _rotl(x,r) +# define XXH_rotl64(x,r) _rotl64(x,r) +#else +# define XXH_rotl32(x,r) (((x) << (r)) | ((x) >> (32 - (r)))) +# define XXH_rotl64(x,r) (((x) << (r)) | ((x) >> (64 - (r)))) +#endif + +#if defined(_MSC_VER) /* Visual Studio */ +# define XXH_swap32 _byteswap_ulong +#elif XXH_GCC_VERSION >= 403 +# define XXH_swap32 __builtin_bswap32 +#else +static xxh_u32 XXH_swap32 (xxh_u32 x) +{ + return ((x << 24) & 0xff000000 ) | + ((x << 8) & 0x00ff0000 ) | + ((x >> 8) & 0x0000ff00 ) | + ((x >> 24) & 0x000000ff ); +} +#endif + + +/* *************************** +* Memory reads +*****************************/ +typedef enum { XXH_aligned, XXH_unaligned } XXH_alignment; + +/* + * XXH_FORCE_MEMORY_ACCESS==3 is an endian-independent byteshift load. + * + * This is ideal for older compilers which don't inline memcpy. + */ +#if (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==3)) + +XXH_FORCE_INLINE xxh_u32 XXH_readLE32(const void* memPtr) +{ + const xxh_u8* bytePtr = (const xxh_u8 *)memPtr; + return bytePtr[0] + | ((xxh_u32)bytePtr[1] << 8) + | ((xxh_u32)bytePtr[2] << 16) + | ((xxh_u32)bytePtr[3] << 24); +} + +XXH_FORCE_INLINE xxh_u32 XXH_readBE32(const void* memPtr) +{ + const xxh_u8* bytePtr = (const xxh_u8 *)memPtr; + return bytePtr[3] + | ((xxh_u32)bytePtr[2] << 8) + | ((xxh_u32)bytePtr[1] << 16) + | ((xxh_u32)bytePtr[0] << 24); +} + +#else +XXH_FORCE_INLINE xxh_u32 XXH_readLE32(const void* ptr) +{ + return XXH_CPU_LITTLE_ENDIAN ? XXH_read32(ptr) : XXH_swap32(XXH_read32(ptr)); +} + +static xxh_u32 XXH_readBE32(const void* ptr) +{ + return XXH_CPU_LITTLE_ENDIAN ? XXH_swap32(XXH_read32(ptr)) : XXH_read32(ptr); +} +#endif + +XXH_FORCE_INLINE xxh_u32 +XXH_readLE32_align(const void* ptr, XXH_alignment align) +{ + if (align==XXH_unaligned) { + return XXH_readLE32(ptr); + } else { + return XXH_CPU_LITTLE_ENDIAN ? *(const xxh_u32*)ptr : XXH_swap32(*(const xxh_u32*)ptr); + } +} + + +/* ************************************* +* Misc +***************************************/ +XXH_PUBLIC_API unsigned XXH_versionNumber (void) { return XXH_VERSION_NUMBER; } + + +/* ******************************************************************* +* 32-bit hash functions +*********************************************************************/ +static const xxh_u32 XXH_PRIME32_1 = 0x9E3779B1U; /* 0b10011110001101110111100110110001 */ +static const xxh_u32 XXH_PRIME32_2 = 0x85EBCA77U; /* 0b10000101111010111100101001110111 */ +static const xxh_u32 XXH_PRIME32_3 = 0xC2B2AE3DU; /* 0b11000010101100101010111000111101 */ +static const xxh_u32 XXH_PRIME32_4 = 0x27D4EB2FU; /* 0b00100111110101001110101100101111 */ +static const xxh_u32 XXH_PRIME32_5 = 0x165667B1U; /* 0b00010110010101100110011110110001 */ + +#ifdef XXH_OLD_NAMES +# define PRIME32_1 XXH_PRIME32_1 +# define PRIME32_2 XXH_PRIME32_2 +# define PRIME32_3 XXH_PRIME32_3 +# define PRIME32_4 XXH_PRIME32_4 +# define PRIME32_5 XXH_PRIME32_5 +#endif + +static xxh_u32 XXH32_round(xxh_u32 acc, xxh_u32 input) +{ + acc += input * XXH_PRIME32_2; + acc = XXH_rotl32(acc, 13); + acc *= XXH_PRIME32_1; +#if defined(__GNUC__) && defined(__SSE4_1__) && !defined(XXH_ENABLE_AUTOVECTORIZE) + /* + * UGLY HACK: + * This inline assembly hack forces acc into a normal register. This is the + * only thing that prevents GCC and Clang from autovectorizing the XXH32 + * loop (pragmas and attributes don't work for some resason) without globally + * disabling SSE4.1. + * + * The reason we want to avoid vectorization is because despite working on + * 4 integers at a time, there are multiple factors slowing XXH32 down on + * SSE4: + * - There's a ridiculous amount of lag from pmulld (10 cycles of latency on + * newer chips!) making it slightly slower to multiply four integers at + * once compared to four integers independently. Even when pmulld was + * fastest, Sandy/Ivy Bridge, it is still not worth it to go into SSE + * just to multiply unless doing a long operation. + * + * - Four instructions are required to rotate, + * movqda tmp, v // not required with VEX encoding + * pslld tmp, 13 // tmp <<= 13 + * psrld v, 19 // x >>= 19 + * por v, tmp // x |= tmp + * compared to one for scalar: + * roll v, 13 // reliably fast across the board + * shldl v, v, 13 // Sandy Bridge and later prefer this for some reason + * + * - Instruction level parallelism is actually more beneficial here because + * the SIMD actually serializes this operation: While v1 is rotating, v2 + * can load data, while v3 can multiply. SSE forces them to operate + * together. + * + * How this hack works: + * __asm__("" // Declare an assembly block but don't declare any instructions + * : // However, as an Input/Output Operand, + * "+r" // constrain a read/write operand (+) as a general purpose register (r). + * (acc) // and set acc as the operand + * ); + * + * Because of the 'r', the compiler has promised that seed will be in a + * general purpose register and the '+' says that it will be 'read/write', + * so it has to assume it has changed. It is like volatile without all the + * loads and stores. + * + * Since the argument has to be in a normal register (not an SSE register), + * each time XXH32_round is called, it is impossible to vectorize. + */ + __asm__("" : "+r" (acc)); +#endif + return acc; +} + +/* mix all bits */ +static xxh_u32 XXH32_avalanche(xxh_u32 h32) +{ + h32 ^= h32 >> 15; + h32 *= XXH_PRIME32_2; + h32 ^= h32 >> 13; + h32 *= XXH_PRIME32_3; + h32 ^= h32 >> 16; + return(h32); +} + +#define XXH_get32bits(p) XXH_readLE32_align(p, align) + +static xxh_u32 +XXH32_finalize(xxh_u32 h32, const xxh_u8* ptr, size_t len, XXH_alignment align) +{ +#define XXH_PROCESS1 do { \ + h32 += (*ptr++) * XXH_PRIME32_5; \ + h32 = XXH_rotl32(h32, 11) * XXH_PRIME32_1; \ +} while (0) + +#define XXH_PROCESS4 do { \ + h32 += XXH_get32bits(ptr) * XXH_PRIME32_3; \ + ptr += 4; \ + h32 = XXH_rotl32(h32, 17) * XXH_PRIME32_4; \ +} while (0) + + /* Compact rerolled version */ + if (XXH_REROLL) { + len &= 15; + while (len >= 4) { + XXH_PROCESS4; + len -= 4; + } + while (len > 0) { + XXH_PROCESS1; + --len; + } + return XXH32_avalanche(h32); + } else { + switch(len&15) /* or switch(bEnd - p) */ { + case 12: XXH_PROCESS4; + /* fallthrough */ + case 8: XXH_PROCESS4; + /* fallthrough */ + case 4: XXH_PROCESS4; + return XXH32_avalanche(h32); + + case 13: XXH_PROCESS4; + /* fallthrough */ + case 9: XXH_PROCESS4; + /* fallthrough */ + case 5: XXH_PROCESS4; + XXH_PROCESS1; + return XXH32_avalanche(h32); + + case 14: XXH_PROCESS4; + /* fallthrough */ + case 10: XXH_PROCESS4; + /* fallthrough */ + case 6: XXH_PROCESS4; + XXH_PROCESS1; + XXH_PROCESS1; + return XXH32_avalanche(h32); + + case 15: XXH_PROCESS4; + /* fallthrough */ + case 11: XXH_PROCESS4; + /* fallthrough */ + case 7: XXH_PROCESS4; + /* fallthrough */ + case 3: XXH_PROCESS1; + /* fallthrough */ + case 2: XXH_PROCESS1; + /* fallthrough */ + case 1: XXH_PROCESS1; + /* fallthrough */ + case 0: return XXH32_avalanche(h32); + } + XXH_ASSERT(0); + return h32; /* reaching this point is deemed impossible */ + } +} + +#ifdef XXH_OLD_NAMES +# define PROCESS1 XXH_PROCESS1 +# define PROCESS4 XXH_PROCESS4 +#else +# undef XXH_PROCESS1 +# undef XXH_PROCESS4 +#endif + +XXH_FORCE_INLINE xxh_u32 +XXH32_endian_align(const xxh_u8* input, size_t len, xxh_u32 seed, XXH_alignment align) +{ + const xxh_u8* bEnd = input + len; + xxh_u32 h32; + +#if defined(XXH_ACCEPT_NULL_INPUT_POINTER) && (XXH_ACCEPT_NULL_INPUT_POINTER>=1) + if (input==NULL) { + len=0; + bEnd=input=(const xxh_u8*)(size_t)16; + } +#endif + + if (len>=16) { + const xxh_u8* const limit = bEnd - 15; + xxh_u32 v1 = seed + XXH_PRIME32_1 + XXH_PRIME32_2; + xxh_u32 v2 = seed + XXH_PRIME32_2; + xxh_u32 v3 = seed + 0; + xxh_u32 v4 = seed - XXH_PRIME32_1; + + do { + v1 = XXH32_round(v1, XXH_get32bits(input)); input += 4; + v2 = XXH32_round(v2, XXH_get32bits(input)); input += 4; + v3 = XXH32_round(v3, XXH_get32bits(input)); input += 4; + v4 = XXH32_round(v4, XXH_get32bits(input)); input += 4; + } while (input < limit); + + h32 = XXH_rotl32(v1, 1) + XXH_rotl32(v2, 7) + + XXH_rotl32(v3, 12) + XXH_rotl32(v4, 18); + } else { + h32 = seed + XXH_PRIME32_5; + } + + h32 += (xxh_u32)len; + + return XXH32_finalize(h32, input, len&15, align); +} + + +XXH_PUBLIC_API XXH32_hash_t XXH32 (const void* input, size_t len, XXH32_hash_t seed) +{ +#if 0 + /* Simple version, good for code maintenance, but unfortunately slow for small inputs */ + XXH32_state_t state; + XXH32_reset(&state, seed); + XXH32_update(&state, (const xxh_u8*)input, len); + return XXH32_digest(&state); + +#else + + if (XXH_FORCE_ALIGN_CHECK) { + if ((((size_t)input) & 3) == 0) { /* Input is 4-bytes aligned, leverage the speed benefit */ + return XXH32_endian_align((const xxh_u8*)input, len, seed, XXH_aligned); + } } + + return XXH32_endian_align((const xxh_u8*)input, len, seed, XXH_unaligned); +#endif +} + + + +/******* Hash streaming *******/ + +XXH_PUBLIC_API XXH32_state_t* XXH32_createState(void) +{ + return (XXH32_state_t*)XXH_malloc(sizeof(XXH32_state_t)); +} +XXH_PUBLIC_API XXH_errorcode XXH32_freeState(XXH32_state_t* statePtr) +{ + XXH_free(statePtr); + return XXH_OK; +} + +XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t* dstState, const XXH32_state_t* srcState) +{ + memcpy(dstState, srcState, sizeof(*dstState)); +} + +XXH_PUBLIC_API XXH_errorcode XXH32_reset(XXH32_state_t* statePtr, XXH32_hash_t seed) +{ + XXH32_state_t state; /* using a local state to memcpy() in order to avoid strict-aliasing warnings */ + memset(&state, 0, sizeof(state)); + state.v1 = seed + XXH_PRIME32_1 + XXH_PRIME32_2; + state.v2 = seed + XXH_PRIME32_2; + state.v3 = seed + 0; + state.v4 = seed - XXH_PRIME32_1; + /* do not write into reserved, planned to be removed in a future version */ + memcpy(statePtr, &state, sizeof(state) - sizeof(state.reserved)); + return XXH_OK; +} + + +XXH_PUBLIC_API XXH_errorcode +XXH32_update(XXH32_state_t* state, const void* input, size_t len) +{ + if (input==NULL) +#if defined(XXH_ACCEPT_NULL_INPUT_POINTER) && (XXH_ACCEPT_NULL_INPUT_POINTER>=1) + return XXH_OK; +#else + return XXH_ERROR; +#endif + + { const xxh_u8* p = (const xxh_u8*)input; + const xxh_u8* const bEnd = p + len; + + state->total_len_32 += (XXH32_hash_t)len; + state->large_len |= (XXH32_hash_t)((len>=16) | (state->total_len_32>=16)); + + if (state->memsize + len < 16) { /* fill in tmp buffer */ + XXH_memcpy((xxh_u8*)(state->mem32) + state->memsize, input, len); + state->memsize += (XXH32_hash_t)len; + return XXH_OK; + } + + if (state->memsize) { /* some data left from previous update */ + XXH_memcpy((xxh_u8*)(state->mem32) + state->memsize, input, 16-state->memsize); + { const xxh_u32* p32 = state->mem32; + state->v1 = XXH32_round(state->v1, XXH_readLE32(p32)); p32++; + state->v2 = XXH32_round(state->v2, XXH_readLE32(p32)); p32++; + state->v3 = XXH32_round(state->v3, XXH_readLE32(p32)); p32++; + state->v4 = XXH32_round(state->v4, XXH_readLE32(p32)); + } + p += 16-state->memsize; + state->memsize = 0; + } + + if (p <= bEnd-16) { + const xxh_u8* const limit = bEnd - 16; + xxh_u32 v1 = state->v1; + xxh_u32 v2 = state->v2; + xxh_u32 v3 = state->v3; + xxh_u32 v4 = state->v4; + + do { + v1 = XXH32_round(v1, XXH_readLE32(p)); p+=4; + v2 = XXH32_round(v2, XXH_readLE32(p)); p+=4; + v3 = XXH32_round(v3, XXH_readLE32(p)); p+=4; + v4 = XXH32_round(v4, XXH_readLE32(p)); p+=4; + } while (p<=limit); + + state->v1 = v1; + state->v2 = v2; + state->v3 = v3; + state->v4 = v4; + } + + if (p < bEnd) { + XXH_memcpy(state->mem32, p, (size_t)(bEnd-p)); + state->memsize = (unsigned)(bEnd-p); + } + } + + return XXH_OK; +} + + +XXH_PUBLIC_API XXH32_hash_t XXH32_digest (const XXH32_state_t* state) +{ + xxh_u32 h32; + + if (state->large_len) { + h32 = XXH_rotl32(state->v1, 1) + + XXH_rotl32(state->v2, 7) + + XXH_rotl32(state->v3, 12) + + XXH_rotl32(state->v4, 18); + } else { + h32 = state->v3 /* == seed */ + XXH_PRIME32_5; + } + + h32 += state->total_len_32; + + return XXH32_finalize(h32, (const xxh_u8*)state->mem32, state->memsize, XXH_aligned); +} + + +/******* Canonical representation *******/ + +/* + * The default return values from XXH functions are unsigned 32 and 64 bit + * integers. + * + * The canonical representation uses big endian convention, the same convention + * as human-readable numbers (large digits first). + * + * This way, hash values can be written into a file or buffer, remaining + * comparable across different systems. + * + * The following functions allow transformation of hash values to and from their + * canonical format. + */ +XXH_PUBLIC_API void XXH32_canonicalFromHash(XXH32_canonical_t* dst, XXH32_hash_t hash) +{ + XXH_STATIC_ASSERT(sizeof(XXH32_canonical_t) == sizeof(XXH32_hash_t)); + if (XXH_CPU_LITTLE_ENDIAN) hash = XXH_swap32(hash); + memcpy(dst, &hash, sizeof(*dst)); +} + +XXH_PUBLIC_API XXH32_hash_t XXH32_hashFromCanonical(const XXH32_canonical_t* src) +{ + return XXH_readBE32(src); +} + + +#ifndef XXH_NO_LONG_LONG + +/* ******************************************************************* +* 64-bit hash functions +*********************************************************************/ + +/******* Memory access *******/ + +typedef XXH64_hash_t xxh_u64; + +#ifdef XXH_OLD_NAMES +# define U64 xxh_u64 +#endif + +/*! + * XXH_REROLL_XXH64: + * Whether to reroll the XXH64_finalize() loop. + * + * Just like XXH32, we can unroll the XXH64_finalize() loop. This can be a + * performance gain on 64-bit hosts, as only one jump is required. + * + * However, on 32-bit hosts, because arithmetic needs to be done with two 32-bit + * registers, and 64-bit arithmetic needs to be simulated, it isn't beneficial + * to unroll. The code becomes ridiculously large (the largest function in the + * binary on i386!), and rerolling it saves anywhere from 3kB to 20kB. It is + * also slightly faster because it fits into cache better and is more likely + * to be inlined by the compiler. + * + * If XXH_REROLL is defined, this is ignored and the loop is always rerolled. + */ +#ifndef XXH_REROLL_XXH64 +# if (defined(__ILP32__) || defined(_ILP32)) /* ILP32 is often defined on 32-bit GCC family */ \ + || !(defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) /* x86-64 */ \ + || defined(_M_ARM64) || defined(__aarch64__) || defined(__arm64__) /* aarch64 */ \ + || defined(__PPC64__) || defined(__PPC64LE__) || defined(__ppc64__) || defined(__powerpc64__) /* ppc64 */ \ + || defined(__mips64__) || defined(__mips64)) /* mips64 */ \ + || (!defined(SIZE_MAX) || SIZE_MAX < ULLONG_MAX) /* check limits */ +# define XXH_REROLL_XXH64 1 +# else +# define XXH_REROLL_XXH64 0 +# endif +#endif /* !defined(XXH_REROLL_XXH64) */ + +#if (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==3)) +/* + * Manual byteshift. Best for old compilers which don't inline memcpy. + * We actually directly use XXH_readLE64 and XXH_readBE64. + */ +#elif (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==2)) + +/* Force direct memory access. Only works on CPU which support unaligned memory access in hardware */ +static xxh_u64 XXH_read64(const void* memPtr) { return *(const xxh_u64*) memPtr; } + +#elif (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==1)) + +/* + * __pack instructions are safer, but compiler specific, hence potentially + * problematic for some compilers. + * + * Currently only defined for GCC and ICC. + */ +#ifdef XXH_OLD_NAMES +typedef union { xxh_u32 u32; xxh_u64 u64; } __attribute__((packed)) unalign64; +#endif +static xxh_u64 XXH_read64(const void* ptr) +{ + typedef union { xxh_u32 u32; xxh_u64 u64; } __attribute__((packed)) xxh_unalign64; + return ((const xxh_unalign64*)ptr)->u64; +} + +#else + +/* + * Portable and safe solution. Generally efficient. + * see: https://stackoverflow.com/a/32095106/646947 + */ +static xxh_u64 XXH_read64(const void* memPtr) +{ + xxh_u64 val; + memcpy(&val, memPtr, sizeof(val)); + return val; +} + +#endif /* XXH_FORCE_DIRECT_MEMORY_ACCESS */ + +#if defined(_MSC_VER) /* Visual Studio */ +# define XXH_swap64 _byteswap_uint64 +#elif XXH_GCC_VERSION >= 403 +# define XXH_swap64 __builtin_bswap64 +#else +static xxh_u64 XXH_swap64 (xxh_u64 x) +{ + return ((x << 56) & 0xff00000000000000ULL) | + ((x << 40) & 0x00ff000000000000ULL) | + ((x << 24) & 0x0000ff0000000000ULL) | + ((x << 8) & 0x000000ff00000000ULL) | + ((x >> 8) & 0x00000000ff000000ULL) | + ((x >> 24) & 0x0000000000ff0000ULL) | + ((x >> 40) & 0x000000000000ff00ULL) | + ((x >> 56) & 0x00000000000000ffULL); +} +#endif + + +/* XXH_FORCE_MEMORY_ACCESS==3 is an endian-independent byteshift load. */ +#if (defined(XXH_FORCE_MEMORY_ACCESS) && (XXH_FORCE_MEMORY_ACCESS==3)) + +XXH_FORCE_INLINE xxh_u64 XXH_readLE64(const void* memPtr) +{ + const xxh_u8* bytePtr = (const xxh_u8 *)memPtr; + return bytePtr[0] + | ((xxh_u64)bytePtr[1] << 8) + | ((xxh_u64)bytePtr[2] << 16) + | ((xxh_u64)bytePtr[3] << 24) + | ((xxh_u64)bytePtr[4] << 32) + | ((xxh_u64)bytePtr[5] << 40) + | ((xxh_u64)bytePtr[6] << 48) + | ((xxh_u64)bytePtr[7] << 56); +} + +XXH_FORCE_INLINE xxh_u64 XXH_readBE64(const void* memPtr) +{ + const xxh_u8* bytePtr = (const xxh_u8 *)memPtr; + return bytePtr[7] + | ((xxh_u64)bytePtr[6] << 8) + | ((xxh_u64)bytePtr[5] << 16) + | ((xxh_u64)bytePtr[4] << 24) + | ((xxh_u64)bytePtr[3] << 32) + | ((xxh_u64)bytePtr[2] << 40) + | ((xxh_u64)bytePtr[1] << 48) + | ((xxh_u64)bytePtr[0] << 56); +} + +#else +XXH_FORCE_INLINE xxh_u64 XXH_readLE64(const void* ptr) +{ + return XXH_CPU_LITTLE_ENDIAN ? XXH_read64(ptr) : XXH_swap64(XXH_read64(ptr)); +} + +static xxh_u64 XXH_readBE64(const void* ptr) +{ + return XXH_CPU_LITTLE_ENDIAN ? XXH_swap64(XXH_read64(ptr)) : XXH_read64(ptr); +} +#endif + +XXH_FORCE_INLINE xxh_u64 +XXH_readLE64_align(const void* ptr, XXH_alignment align) +{ + if (align==XXH_unaligned) + return XXH_readLE64(ptr); + else + return XXH_CPU_LITTLE_ENDIAN ? *(const xxh_u64*)ptr : XXH_swap64(*(const xxh_u64*)ptr); +} + + +/******* xxh64 *******/ + +static const xxh_u64 XXH_PRIME64_1 = 0x9E3779B185EBCA87ULL; /* 0b1001111000110111011110011011000110000101111010111100101010000111 */ +static const xxh_u64 XXH_PRIME64_2 = 0xC2B2AE3D27D4EB4FULL; /* 0b1100001010110010101011100011110100100111110101001110101101001111 */ +static const xxh_u64 XXH_PRIME64_3 = 0x165667B19E3779F9ULL; /* 0b0001011001010110011001111011000110011110001101110111100111111001 */ +static const xxh_u64 XXH_PRIME64_4 = 0x85EBCA77C2B2AE63ULL; /* 0b1000010111101011110010100111011111000010101100101010111001100011 */ +static const xxh_u64 XXH_PRIME64_5 = 0x27D4EB2F165667C5ULL; /* 0b0010011111010100111010110010111100010110010101100110011111000101 */ + +#ifdef XXH_OLD_NAMES +# define PRIME64_1 XXH_PRIME64_1 +# define PRIME64_2 XXH_PRIME64_2 +# define PRIME64_3 XXH_PRIME64_3 +# define PRIME64_4 XXH_PRIME64_4 +# define PRIME64_5 XXH_PRIME64_5 +#endif + +static xxh_u64 XXH64_round(xxh_u64 acc, xxh_u64 input) +{ + acc += input * XXH_PRIME64_2; + acc = XXH_rotl64(acc, 31); + acc *= XXH_PRIME64_1; + return acc; +} + +static xxh_u64 XXH64_mergeRound(xxh_u64 acc, xxh_u64 val) +{ + val = XXH64_round(0, val); + acc ^= val; + acc = acc * XXH_PRIME64_1 + XXH_PRIME64_4; + return acc; +} + +static xxh_u64 XXH64_avalanche(xxh_u64 h64) +{ + h64 ^= h64 >> 33; + h64 *= XXH_PRIME64_2; + h64 ^= h64 >> 29; + h64 *= XXH_PRIME64_3; + h64 ^= h64 >> 32; + return h64; +} + + +#define XXH_get64bits(p) XXH_readLE64_align(p, align) + +static xxh_u64 +XXH64_finalize(xxh_u64 h64, const xxh_u8* ptr, size_t len, XXH_alignment align) +{ +#define XXH_PROCESS1_64 do { \ + h64 ^= (*ptr++) * XXH_PRIME64_5; \ + h64 = XXH_rotl64(h64, 11) * XXH_PRIME64_1; \ +} while (0) + +#define XXH_PROCESS4_64 do { \ + h64 ^= (xxh_u64)(XXH_get32bits(ptr)) * XXH_PRIME64_1; \ + ptr += 4; \ + h64 = XXH_rotl64(h64, 23) * XXH_PRIME64_2 + XXH_PRIME64_3; \ +} while (0) + +#define XXH_PROCESS8_64 do { \ + xxh_u64 const k1 = XXH64_round(0, XXH_get64bits(ptr)); \ + ptr += 8; \ + h64 ^= k1; \ + h64 = XXH_rotl64(h64,27) * XXH_PRIME64_1 + XXH_PRIME64_4; \ +} while (0) + + /* Rerolled version for 32-bit targets is faster and much smaller. */ + if (XXH_REROLL || XXH_REROLL_XXH64) { + len &= 31; + while (len >= 8) { + XXH_PROCESS8_64; + len -= 8; + } + if (len >= 4) { + XXH_PROCESS4_64; + len -= 4; + } + while (len > 0) { + XXH_PROCESS1_64; + --len; + } + return XXH64_avalanche(h64); + } else { + switch(len & 31) { + case 24: XXH_PROCESS8_64; + /* fallthrough */ + case 16: XXH_PROCESS8_64; + /* fallthrough */ + case 8: XXH_PROCESS8_64; + return XXH64_avalanche(h64); + + case 28: XXH_PROCESS8_64; + /* fallthrough */ + case 20: XXH_PROCESS8_64; + /* fallthrough */ + case 12: XXH_PROCESS8_64; + /* fallthrough */ + case 4: XXH_PROCESS4_64; + return XXH64_avalanche(h64); + + case 25: XXH_PROCESS8_64; + /* fallthrough */ + case 17: XXH_PROCESS8_64; + /* fallthrough */ + case 9: XXH_PROCESS8_64; + XXH_PROCESS1_64; + return XXH64_avalanche(h64); + + case 29: XXH_PROCESS8_64; + /* fallthrough */ + case 21: XXH_PROCESS8_64; + /* fallthrough */ + case 13: XXH_PROCESS8_64; + /* fallthrough */ + case 5: XXH_PROCESS4_64; + XXH_PROCESS1_64; + return XXH64_avalanche(h64); + + case 26: XXH_PROCESS8_64; + /* fallthrough */ + case 18: XXH_PROCESS8_64; + /* fallthrough */ + case 10: XXH_PROCESS8_64; + XXH_PROCESS1_64; + XXH_PROCESS1_64; + return XXH64_avalanche(h64); + + case 30: XXH_PROCESS8_64; + /* fallthrough */ + case 22: XXH_PROCESS8_64; + /* fallthrough */ + case 14: XXH_PROCESS8_64; + /* fallthrough */ + case 6: XXH_PROCESS4_64; + XXH_PROCESS1_64; + XXH_PROCESS1_64; + return XXH64_avalanche(h64); + + case 27: XXH_PROCESS8_64; + /* fallthrough */ + case 19: XXH_PROCESS8_64; + /* fallthrough */ + case 11: XXH_PROCESS8_64; + XXH_PROCESS1_64; + XXH_PROCESS1_64; + XXH_PROCESS1_64; + return XXH64_avalanche(h64); + + case 31: XXH_PROCESS8_64; + /* fallthrough */ + case 23: XXH_PROCESS8_64; + /* fallthrough */ + case 15: XXH_PROCESS8_64; + /* fallthrough */ + case 7: XXH_PROCESS4_64; + /* fallthrough */ + case 3: XXH_PROCESS1_64; + /* fallthrough */ + case 2: XXH_PROCESS1_64; + /* fallthrough */ + case 1: XXH_PROCESS1_64; + /* fallthrough */ + case 0: return XXH64_avalanche(h64); + } + } + /* impossible to reach */ + XXH_ASSERT(0); + return 0; /* unreachable, but some compilers complain without it */ +} + +#ifdef XXH_OLD_NAMES +# define PROCESS1_64 XXH_PROCESS1_64 +# define PROCESS4_64 XXH_PROCESS4_64 +# define PROCESS8_64 XXH_PROCESS8_64 +#else +# undef XXH_PROCESS1_64 +# undef XXH_PROCESS4_64 +# undef XXH_PROCESS8_64 +#endif + +XXH_FORCE_INLINE xxh_u64 +XXH64_endian_align(const xxh_u8* input, size_t len, xxh_u64 seed, XXH_alignment align) +{ + const xxh_u8* bEnd = input + len; + xxh_u64 h64; + +#if defined(XXH_ACCEPT_NULL_INPUT_POINTER) && (XXH_ACCEPT_NULL_INPUT_POINTER>=1) + if (input==NULL) { + len=0; + bEnd=input=(const xxh_u8*)(size_t)32; + } +#endif + + if (len>=32) { + const xxh_u8* const limit = bEnd - 32; + xxh_u64 v1 = seed + XXH_PRIME64_1 + XXH_PRIME64_2; + xxh_u64 v2 = seed + XXH_PRIME64_2; + xxh_u64 v3 = seed + 0; + xxh_u64 v4 = seed - XXH_PRIME64_1; + + do { + v1 = XXH64_round(v1, XXH_get64bits(input)); input+=8; + v2 = XXH64_round(v2, XXH_get64bits(input)); input+=8; + v3 = XXH64_round(v3, XXH_get64bits(input)); input+=8; + v4 = XXH64_round(v4, XXH_get64bits(input)); input+=8; + } while (input<=limit); + + h64 = XXH_rotl64(v1, 1) + XXH_rotl64(v2, 7) + XXH_rotl64(v3, 12) + XXH_rotl64(v4, 18); + h64 = XXH64_mergeRound(h64, v1); + h64 = XXH64_mergeRound(h64, v2); + h64 = XXH64_mergeRound(h64, v3); + h64 = XXH64_mergeRound(h64, v4); + + } else { + h64 = seed + XXH_PRIME64_5; + } + + h64 += (xxh_u64) len; + + return XXH64_finalize(h64, input, len, align); +} + + +XXH_PUBLIC_API XXH64_hash_t XXH64 (const void* input, size_t len, XXH64_hash_t seed) +{ +#if 0 + /* Simple version, good for code maintenance, but unfortunately slow for small inputs */ + XXH64_state_t state; + XXH64_reset(&state, seed); + XXH64_update(&state, (const xxh_u8*)input, len); + return XXH64_digest(&state); + +#else + + if (XXH_FORCE_ALIGN_CHECK) { + if ((((size_t)input) & 7)==0) { /* Input is aligned, let's leverage the speed advantage */ + return XXH64_endian_align((const xxh_u8*)input, len, seed, XXH_aligned); + } } + + return XXH64_endian_align((const xxh_u8*)input, len, seed, XXH_unaligned); + +#endif +} + +/******* Hash Streaming *******/ + +XXH_PUBLIC_API XXH64_state_t* XXH64_createState(void) +{ + return (XXH64_state_t*)XXH_malloc(sizeof(XXH64_state_t)); +} +XXH_PUBLIC_API XXH_errorcode XXH64_freeState(XXH64_state_t* statePtr) +{ + XXH_free(statePtr); + return XXH_OK; +} + +XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t* dstState, const XXH64_state_t* srcState) +{ + memcpy(dstState, srcState, sizeof(*dstState)); +} + +XXH_PUBLIC_API XXH_errorcode XXH64_reset(XXH64_state_t* statePtr, XXH64_hash_t seed) +{ + XXH64_state_t state; /* use a local state to memcpy() in order to avoid strict-aliasing warnings */ + memset(&state, 0, sizeof(state)); + state.v1 = seed + XXH_PRIME64_1 + XXH_PRIME64_2; + state.v2 = seed + XXH_PRIME64_2; + state.v3 = seed + 0; + state.v4 = seed - XXH_PRIME64_1; + /* do not write into reserved64, might be removed in a future version */ + memcpy(statePtr, &state, sizeof(state) - sizeof(state.reserved64)); + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH64_update (XXH64_state_t* state, const void* input, size_t len) +{ + if (input==NULL) +#if defined(XXH_ACCEPT_NULL_INPUT_POINTER) && (XXH_ACCEPT_NULL_INPUT_POINTER>=1) + return XXH_OK; +#else + return XXH_ERROR; +#endif + + { const xxh_u8* p = (const xxh_u8*)input; + const xxh_u8* const bEnd = p + len; + + state->total_len += len; + + if (state->memsize + len < 32) { /* fill in tmp buffer */ + XXH_memcpy(((xxh_u8*)state->mem64) + state->memsize, input, len); + state->memsize += (xxh_u32)len; + return XXH_OK; + } + + if (state->memsize) { /* tmp buffer is full */ + XXH_memcpy(((xxh_u8*)state->mem64) + state->memsize, input, 32-state->memsize); + state->v1 = XXH64_round(state->v1, XXH_readLE64(state->mem64+0)); + state->v2 = XXH64_round(state->v2, XXH_readLE64(state->mem64+1)); + state->v3 = XXH64_round(state->v3, XXH_readLE64(state->mem64+2)); + state->v4 = XXH64_round(state->v4, XXH_readLE64(state->mem64+3)); + p += 32-state->memsize; + state->memsize = 0; + } + + if (p+32 <= bEnd) { + const xxh_u8* const limit = bEnd - 32; + xxh_u64 v1 = state->v1; + xxh_u64 v2 = state->v2; + xxh_u64 v3 = state->v3; + xxh_u64 v4 = state->v4; + + do { + v1 = XXH64_round(v1, XXH_readLE64(p)); p+=8; + v2 = XXH64_round(v2, XXH_readLE64(p)); p+=8; + v3 = XXH64_round(v3, XXH_readLE64(p)); p+=8; + v4 = XXH64_round(v4, XXH_readLE64(p)); p+=8; + } while (p<=limit); + + state->v1 = v1; + state->v2 = v2; + state->v3 = v3; + state->v4 = v4; + } + + if (p < bEnd) { + XXH_memcpy(state->mem64, p, (size_t)(bEnd-p)); + state->memsize = (unsigned)(bEnd-p); + } + } + + return XXH_OK; +} + + +XXH_PUBLIC_API XXH64_hash_t XXH64_digest (const XXH64_state_t* state) +{ + xxh_u64 h64; + + if (state->total_len >= 32) { + xxh_u64 const v1 = state->v1; + xxh_u64 const v2 = state->v2; + xxh_u64 const v3 = state->v3; + xxh_u64 const v4 = state->v4; + + h64 = XXH_rotl64(v1, 1) + XXH_rotl64(v2, 7) + XXH_rotl64(v3, 12) + XXH_rotl64(v4, 18); + h64 = XXH64_mergeRound(h64, v1); + h64 = XXH64_mergeRound(h64, v2); + h64 = XXH64_mergeRound(h64, v3); + h64 = XXH64_mergeRound(h64, v4); + } else { + h64 = state->v3 /*seed*/ + XXH_PRIME64_5; + } + + h64 += (xxh_u64) state->total_len; + + return XXH64_finalize(h64, (const xxh_u8*)state->mem64, (size_t)state->total_len, XXH_aligned); +} + + +/******* Canonical representation *******/ + +XXH_PUBLIC_API void XXH64_canonicalFromHash(XXH64_canonical_t* dst, XXH64_hash_t hash) +{ + XXH_STATIC_ASSERT(sizeof(XXH64_canonical_t) == sizeof(XXH64_hash_t)); + if (XXH_CPU_LITTLE_ENDIAN) hash = XXH_swap64(hash); + memcpy(dst, &hash, sizeof(*dst)); +} + +XXH_PUBLIC_API XXH64_hash_t XXH64_hashFromCanonical(const XXH64_canonical_t* src) +{ + return XXH_readBE64(src); +} + + + +/* ********************************************************************* +* XXH3 +* New generation hash designed for speed on small keys and vectorization +************************************************************************ */ + +/* === Compiler specifics === */ + +#if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L /* >= C99 */ +# define XXH_RESTRICT restrict +#else +/* Note: it might be useful to define __restrict or __restrict__ for some C++ compilers */ +# define XXH_RESTRICT /* disable */ +#endif + +#if (defined(__GNUC__) && (__GNUC__ >= 3)) \ + || (defined(__INTEL_COMPILER) && (__INTEL_COMPILER >= 800)) \ + || defined(__clang__) +# define XXH_likely(x) __builtin_expect(x, 1) +# define XXH_unlikely(x) __builtin_expect(x, 0) +#else +# define XXH_likely(x) (x) +# define XXH_unlikely(x) (x) +#endif + +#if defined(__GNUC__) +# if defined(__AVX2__) +# include +# elif defined(__SSE2__) +# include +# elif defined(__ARM_NEON__) || defined(__ARM_NEON) +# define inline __inline__ /* circumvent a clang bug */ +# include +# undef inline +# endif +#elif defined(_MSC_VER) +# include +#endif + +/* + * One goal of XXH3 is to make it fast on both 32-bit and 64-bit, while + * remaining a true 64-bit/128-bit hash function. + * + * This is done by prioritizing a subset of 64-bit operations that can be + * emulated without too many steps on the average 32-bit machine. + * + * For example, these two lines seem similar, and run equally fast on 64-bit: + * + * xxh_u64 x; + * x ^= (x >> 47); // good + * x ^= (x >> 13); // bad + * + * However, to a 32-bit machine, there is a major difference. + * + * x ^= (x >> 47) looks like this: + * + * x.lo ^= (x.hi >> (47 - 32)); + * + * while x ^= (x >> 13) looks like this: + * + * // note: funnel shifts are not usually cheap. + * x.lo ^= (x.lo >> 13) | (x.hi << (32 - 13)); + * x.hi ^= (x.hi >> 13); + * + * The first one is significantly faster than the second, simply because the + * shift is larger than 32. This means: + * - All the bits we need are in the upper 32 bits, so we can ignore the lower + * 32 bits in the shift. + * - The shift result will always fit in the lower 32 bits, and therefore, + * we can ignore the upper 32 bits in the xor. + * + * Thanks to this optimization, XXH3 only requires these features to be efficient: + * + * - Usable unaligned access + * - A 32-bit or 64-bit ALU + * - If 32-bit, a decent ADC instruction + * - A 32 or 64-bit multiply with a 64-bit result + * - For the 128-bit variant, a decent byteswap helps short inputs. + * + * The first two are already required by XXH32, and almost all 32-bit and 64-bit + * platforms which can run XXH32 can run XXH3 efficiently. + * + * Thumb-1, the classic 16-bit only subset of ARM's instruction set, is one + * notable exception. + * + * First of all, Thumb-1 lacks support for the UMULL instruction which + * performs the important long multiply. This means numerous __aeabi_lmul + * calls. + * + * Second of all, the 8 functional registers are just not enough. + * Setup for __aeabi_lmul, byteshift loads, pointers, and all arithmetic need + * Lo registers, and this shuffling results in thousands more MOVs than A32. + * + * A32 and T32 don't have this limitation. They can access all 14 registers, + * do a 32->64 multiply with UMULL, and the flexible operand allowing free + * shifts is helpful, too. + * + * Therefore, we do a quick sanity check. + * + * If compiling Thumb-1 for a target which supports ARM instructions, we will + * emit a warning, as it is not a "sane" platform to compile for. + * + * Usually, if this happens, it is because of an accident and you probably need + * to specify -march, as you likely meant to compile for a newer architecture. + * + * Credit: large sections of the vectorial and asm source code paths + * have been contributed by @easyaspi314 + */ +#if defined(__thumb__) && !defined(__thumb2__) && defined(__ARM_ARCH_ISA_ARM) +# warning "XXH3 is highly inefficient without ARM or Thumb-2." +#endif + +/* ========================================== + * Vectorization detection + * ========================================== */ +#define XXH_SCALAR 0 /* Portable scalar version */ +#define XXH_SSE2 1 /* SSE2 for Pentium 4 and all x86_64 */ +#define XXH_AVX2 2 /* AVX2 for Haswell and Bulldozer */ +#define XXH_AVX512 3 /* AVX512 for Skylake and Icelake */ +#define XXH_NEON 4 /* NEON for most ARMv7-A and all AArch64 */ +#define XXH_VSX 5 /* VSX and ZVector for POWER8/z13 */ + +#ifndef XXH_VECTOR /* can be defined on command line */ +# if defined(__AVX512F__) +# define XXH_VECTOR XXH_AVX512 +# elif defined(__AVX2__) +# define XXH_VECTOR XXH_AVX2 +# elif defined(__SSE2__) || defined(_M_AMD64) || defined(_M_X64) || (defined(_M_IX86_FP) && (_M_IX86_FP == 2)) +# define XXH_VECTOR XXH_SSE2 +# elif defined(__GNUC__) /* msvc support maybe later */ \ + && (defined(__ARM_NEON__) || defined(__ARM_NEON)) \ + && (defined(__LITTLE_ENDIAN__) /* We only support little endian NEON */ \ + || (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)) +# define XXH_VECTOR XXH_NEON +# elif (defined(__PPC64__) && defined(__POWER8_VECTOR__)) \ + || (defined(__s390x__) && defined(__VEC__)) \ + && defined(__GNUC__) /* TODO: IBM XL */ +# define XXH_VECTOR XXH_VSX +# else +# define XXH_VECTOR XXH_SCALAR +# endif +#endif + +/* + * Controls the alignment of the accumulator, + * for compatibility with aligned vector loads, which are usually faster. + */ +#ifndef XXH_ACC_ALIGN +# if defined(XXH_X86DISPATCH) +# define XXH_ACC_ALIGN 64 /* for compatibility with avx512 */ +# elif XXH_VECTOR == XXH_SCALAR /* scalar */ +# define XXH_ACC_ALIGN 8 +# elif XXH_VECTOR == XXH_SSE2 /* sse2 */ +# define XXH_ACC_ALIGN 16 +# elif XXH_VECTOR == XXH_AVX2 /* avx2 */ +# define XXH_ACC_ALIGN 32 +# elif XXH_VECTOR == XXH_NEON /* neon */ +# define XXH_ACC_ALIGN 16 +# elif XXH_VECTOR == XXH_VSX /* vsx */ +# define XXH_ACC_ALIGN 16 +# elif XXH_VECTOR == XXH_AVX512 /* avx512 */ +# define XXH_ACC_ALIGN 64 +# endif +#endif + +#if defined(XXH_X86DISPATCH) || XXH_VECTOR == XXH_SSE2 \ + || XXH_VECTOR == XXH_AVX2 || XXH_VECTOR == XXH_AVX512 +# define XXH_SEC_ALIGN XXH_ACC_ALIGN +#else +# define XXH_SEC_ALIGN 8 +#endif + +/* + * UGLY HACK: + * GCC usually generates the best code with -O3 for xxHash. + * + * However, when targeting AVX2, it is overzealous in its unrolling resulting + * in code roughly 3/4 the speed of Clang. + * + * There are other issues, such as GCC splitting _mm256_loadu_si256 into + * _mm_loadu_si128 + _mm256_inserti128_si256. This is an optimization which + * only applies to Sandy and Ivy Bridge... which don't even support AVX2. + * + * That is why when compiling the AVX2 version, it is recommended to use either + * -O2 -mavx2 -march=haswell + * or + * -O2 -mavx2 -mno-avx256-split-unaligned-load + * for decent performance, or to use Clang instead. + * + * Fortunately, we can control the first one with a pragma that forces GCC into + * -O2, but the other one we can't control without "failed to inline always + * inline function due to target mismatch" warnings. + */ +#if XXH_VECTOR == XXH_AVX2 /* AVX2 */ \ + && defined(__GNUC__) && !defined(__clang__) /* GCC, not Clang */ \ + && defined(__OPTIMIZE__) && !defined(__OPTIMIZE_SIZE__) /* respect -O0 and -Os */ +# pragma GCC push_options +# pragma GCC optimize("-O2") +#endif + + +#if XXH_VECTOR == XXH_NEON +/* + * NEON's setup for vmlal_u32 is a little more complicated than it is on + * SSE2, AVX2, and VSX. + * + * While PMULUDQ and VMULEUW both perform a mask, VMLAL.U32 performs an upcast. + * + * To do the same operation, the 128-bit 'Q' register needs to be split into + * two 64-bit 'D' registers, performing this operation:: + * + * [ a | b ] + * | '---------. .--------' | + * | x | + * | .---------' '--------. | + * [ a & 0xFFFFFFFF | b & 0xFFFFFFFF ],[ a >> 32 | b >> 32 ] + * + * Due to significant changes in aarch64, the fastest method for aarch64 is + * completely different than the fastest method for ARMv7-A. + * + * ARMv7-A treats D registers as unions overlaying Q registers, so modifying + * D11 will modify the high half of Q5. This is similar to how modifying AH + * will only affect bits 8-15 of AX on x86. + * + * VZIP takes two registers, and puts even lanes in one register and odd lanes + * in the other. + * + * On ARMv7-A, this strangely modifies both parameters in place instead of + * taking the usual 3-operand form. + * + * Therefore, if we want to do this, we can simply use a D-form VZIP.32 on the + * lower and upper halves of the Q register to end up with the high and low + * halves where we want - all in one instruction. + * + * vzip.32 d10, d11 @ d10 = { d10[0], d11[0] }; d11 = { d10[1], d11[1] } + * + * Unfortunately we need inline assembly for this: Instructions modifying two + * registers at once is not possible in GCC or Clang's IR, and they have to + * create a copy. + * + * aarch64 requires a different approach. + * + * In order to make it easier to write a decent compiler for aarch64, many + * quirks were removed, such as conditional execution. + * + * NEON was also affected by this. + * + * aarch64 cannot access the high bits of a Q-form register, and writes to a + * D-form register zero the high bits, similar to how writes to W-form scalar + * registers (or DWORD registers on x86_64) work. + * + * The formerly free vget_high intrinsics now require a vext (with a few + * exceptions) + * + * Additionally, VZIP was replaced by ZIP1 and ZIP2, which are the equivalent + * of PUNPCKL* and PUNPCKH* in SSE, respectively, in order to only modify one + * operand. + * + * The equivalent of the VZIP.32 on the lower and upper halves would be this + * mess: + * + * ext v2.4s, v0.4s, v0.4s, #2 // v2 = { v0[2], v0[3], v0[0], v0[1] } + * zip1 v1.2s, v0.2s, v2.2s // v1 = { v0[0], v2[0] } + * zip2 v0.2s, v0.2s, v1.2s // v0 = { v0[1], v2[1] } + * + * Instead, we use a literal downcast, vmovn_u64 (XTN), and vshrn_n_u64 (SHRN): + * + * shrn v1.2s, v0.2d, #32 // v1 = (uint32x2_t)(v0 >> 32); + * xtn v0.2s, v0.2d // v0 = (uint32x2_t)(v0 & 0xFFFFFFFF); + * + * This is available on ARMv7-A, but is less efficient than a single VZIP.32. + */ + +/* + * Function-like macro: + * void XXH_SPLIT_IN_PLACE(uint64x2_t &in, uint32x2_t &outLo, uint32x2_t &outHi) + * { + * outLo = (uint32x2_t)(in & 0xFFFFFFFF); + * outHi = (uint32x2_t)(in >> 32); + * in = UNDEFINED; + * } + */ +# if !defined(XXH_NO_VZIP_HACK) /* define to disable */ \ + && defined(__GNUC__) \ + && !defined(__aarch64__) && !defined(__arm64__) +# define XXH_SPLIT_IN_PLACE(in, outLo, outHi) \ + do { \ + /* Undocumented GCC/Clang operand modifier: %e0 = lower D half, %f0 = upper D half */ \ + /* https://github.com/gcc-mirror/gcc/blob/38cf91e5/gcc/config/arm/arm.c#L22486 */ \ + /* https://github.com/llvm-mirror/llvm/blob/2c4ca683/lib/Target/ARM/ARMAsmPrinter.cpp#L399 */ \ + __asm__("vzip.32 %e0, %f0" : "+w" (in)); \ + (outLo) = vget_low_u32 (vreinterpretq_u32_u64(in)); \ + (outHi) = vget_high_u32(vreinterpretq_u32_u64(in)); \ + } while (0) +# else +# define XXH_SPLIT_IN_PLACE(in, outLo, outHi) \ + do { \ + (outLo) = vmovn_u64 (in); \ + (outHi) = vshrn_n_u64 ((in), 32); \ + } while (0) +# endif +#endif /* XXH_VECTOR == XXH_NEON */ + +/* + * VSX and Z Vector helpers. + * + * This is very messy, and any pull requests to clean this up are welcome. + * + * There are a lot of problems with supporting VSX and s390x, due to + * inconsistent intrinsics, spotty coverage, and multiple endiannesses. + */ +#if XXH_VECTOR == XXH_VSX +# if defined(__s390x__) +# include +# else +/* gcc's altivec.h can have the unwanted consequence to unconditionally + * #define bool, vector, and pixel keywords, + * with bad consequences for programs already using these keywords for other purposes. + * The paragraph defining these macros is skipped when __APPLE_ALTIVEC__ is defined. + * __APPLE_ALTIVEC__ is _generally_ defined automatically by the compiler, + * but it seems that, in some cases, it isn't. + * Force the build macro to be defined, so that keywords are not altered. + */ +# if defined(__GNUC__) && !defined(__APPLE_ALTIVEC__) +# define __APPLE_ALTIVEC__ +# endif +# include +# endif + +typedef __vector unsigned long long xxh_u64x2; +typedef __vector unsigned char xxh_u8x16; +typedef __vector unsigned xxh_u32x4; + +# ifndef XXH_VSX_BE +# if defined(__BIG_ENDIAN__) \ + || (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__) +# define XXH_VSX_BE 1 +# elif defined(__VEC_ELEMENT_REG_ORDER__) && __VEC_ELEMENT_REG_ORDER__ == __ORDER_BIG_ENDIAN__ +# warning "-maltivec=be is not recommended. Please use native endianness." +# define XXH_VSX_BE 1 +# else +# define XXH_VSX_BE 0 +# endif +# endif /* !defined(XXH_VSX_BE) */ + +# if XXH_VSX_BE +/* A wrapper for POWER9's vec_revb. */ +# if defined(__POWER9_VECTOR__) || (defined(__clang__) && defined(__s390x__)) +# define XXH_vec_revb vec_revb +# else +XXH_FORCE_INLINE xxh_u64x2 XXH_vec_revb(xxh_u64x2 val) +{ + xxh_u8x16 const vByteSwap = { 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00, + 0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x09, 0x08 }; + return vec_perm(val, val, vByteSwap); +} +# endif +# endif /* XXH_VSX_BE */ + +/* + * Performs an unaligned load and byte swaps it on big endian. + */ +XXH_FORCE_INLINE xxh_u64x2 XXH_vec_loadu(const void *ptr) +{ + xxh_u64x2 ret; + memcpy(&ret, ptr, sizeof(xxh_u64x2)); +# if XXH_VSX_BE + ret = XXH_vec_revb(ret); +# endif + return ret; +} + +/* + * vec_mulo and vec_mule are very problematic intrinsics on PowerPC + * + * These intrinsics weren't added until GCC 8, despite existing for a while, + * and they are endian dependent. Also, their meaning swap depending on version. + * */ +# if defined(__s390x__) + /* s390x is always big endian, no issue on this platform */ +# define XXH_vec_mulo vec_mulo +# define XXH_vec_mule vec_mule +# elif defined(__clang__) && XXH_HAS_BUILTIN(__builtin_altivec_vmuleuw) +/* Clang has a better way to control this, we can just use the builtin which doesn't swap. */ +# define XXH_vec_mulo __builtin_altivec_vmulouw +# define XXH_vec_mule __builtin_altivec_vmuleuw +# else +/* gcc needs inline assembly */ +/* Adapted from https://github.com/google/highwayhash/blob/master/highwayhash/hh_vsx.h. */ +XXH_FORCE_INLINE xxh_u64x2 XXH_vec_mulo(xxh_u32x4 a, xxh_u32x4 b) +{ + xxh_u64x2 result; + __asm__("vmulouw %0, %1, %2" : "=v" (result) : "v" (a), "v" (b)); + return result; +} +XXH_FORCE_INLINE xxh_u64x2 XXH_vec_mule(xxh_u32x4 a, xxh_u32x4 b) +{ + xxh_u64x2 result; + __asm__("vmuleuw %0, %1, %2" : "=v" (result) : "v" (a), "v" (b)); + return result; +} +# endif /* XXH_vec_mulo, XXH_vec_mule */ +#endif /* XXH_VECTOR == XXH_VSX */ + + +/* prefetch + * can be disabled, by declaring XXH_NO_PREFETCH build macro */ +#if defined(XXH_NO_PREFETCH) +# define XXH_PREFETCH(ptr) (void)(ptr) /* disabled */ +#else +# if defined(_MSC_VER) && (defined(_M_X64) || defined(_M_I86)) /* _mm_prefetch() is not defined outside of x86/x64 */ +# include /* https://msdn.microsoft.com/fr-fr/library/84szxsww(v=vs.90).aspx */ +# define XXH_PREFETCH(ptr) _mm_prefetch((const char*)(ptr), _MM_HINT_T0) +# elif defined(__GNUC__) && ( (__GNUC__ >= 4) || ( (__GNUC__ == 3) && (__GNUC_MINOR__ >= 1) ) ) +# define XXH_PREFETCH(ptr) __builtin_prefetch((ptr), 0 /* rw==read */, 3 /* locality */) +# else +# define XXH_PREFETCH(ptr) (void)(ptr) /* disabled */ +# endif +#endif /* XXH_NO_PREFETCH */ + + +/* ========================================== + * XXH3 default settings + * ========================================== */ + +#define XXH_SECRET_DEFAULT_SIZE 192 /* minimum XXH3_SECRET_SIZE_MIN */ + +#if (XXH_SECRET_DEFAULT_SIZE < XXH3_SECRET_SIZE_MIN) +# error "default keyset is not large enough" +#endif + +/* Pseudorandom secret taken directly from FARSH */ +XXH_ALIGN(64) static const xxh_u8 XXH3_kSecret[XXH_SECRET_DEFAULT_SIZE] = { + 0xb8, 0xfe, 0x6c, 0x39, 0x23, 0xa4, 0x4b, 0xbe, 0x7c, 0x01, 0x81, 0x2c, 0xf7, 0x21, 0xad, 0x1c, + 0xde, 0xd4, 0x6d, 0xe9, 0x83, 0x90, 0x97, 0xdb, 0x72, 0x40, 0xa4, 0xa4, 0xb7, 0xb3, 0x67, 0x1f, + 0xcb, 0x79, 0xe6, 0x4e, 0xcc, 0xc0, 0xe5, 0x78, 0x82, 0x5a, 0xd0, 0x7d, 0xcc, 0xff, 0x72, 0x21, + 0xb8, 0x08, 0x46, 0x74, 0xf7, 0x43, 0x24, 0x8e, 0xe0, 0x35, 0x90, 0xe6, 0x81, 0x3a, 0x26, 0x4c, + 0x3c, 0x28, 0x52, 0xbb, 0x91, 0xc3, 0x00, 0xcb, 0x88, 0xd0, 0x65, 0x8b, 0x1b, 0x53, 0x2e, 0xa3, + 0x71, 0x64, 0x48, 0x97, 0xa2, 0x0d, 0xf9, 0x4e, 0x38, 0x19, 0xef, 0x46, 0xa9, 0xde, 0xac, 0xd8, + 0xa8, 0xfa, 0x76, 0x3f, 0xe3, 0x9c, 0x34, 0x3f, 0xf9, 0xdc, 0xbb, 0xc7, 0xc7, 0x0b, 0x4f, 0x1d, + 0x8a, 0x51, 0xe0, 0x4b, 0xcd, 0xb4, 0x59, 0x31, 0xc8, 0x9f, 0x7e, 0xc9, 0xd9, 0x78, 0x73, 0x64, + 0xea, 0xc5, 0xac, 0x83, 0x34, 0xd3, 0xeb, 0xc3, 0xc5, 0x81, 0xa0, 0xff, 0xfa, 0x13, 0x63, 0xeb, + 0x17, 0x0d, 0xdd, 0x51, 0xb7, 0xf0, 0xda, 0x49, 0xd3, 0x16, 0x55, 0x26, 0x29, 0xd4, 0x68, 0x9e, + 0x2b, 0x16, 0xbe, 0x58, 0x7d, 0x47, 0xa1, 0xfc, 0x8f, 0xf8, 0xb8, 0xd1, 0x7a, 0xd0, 0x31, 0xce, + 0x45, 0xcb, 0x3a, 0x8f, 0x95, 0x16, 0x04, 0x28, 0xaf, 0xd7, 0xfb, 0xca, 0xbb, 0x4b, 0x40, 0x7e, +}; + + +#ifdef XXH_OLD_NAMES +# define kSecret XXH3_kSecret +#endif + +/* + * Calculates a 32-bit to 64-bit long multiply. + * + * Wraps __emulu on MSVC x86 because it tends to call __allmul when it doesn't + * need to (but it shouldn't need to anyways, it is about 7 instructions to do + * a 64x64 multiply...). Since we know that this will _always_ emit MULL, we + * use that instead of the normal method. + * + * If you are compiling for platforms like Thumb-1 and don't have a better option, + * you may also want to write your own long multiply routine here. + * + * XXH_FORCE_INLINE xxh_u64 XXH_mult32to64(xxh_u64 x, xxh_u64 y) + * { + * return (x & 0xFFFFFFFF) * (y & 0xFFFFFFFF); + * } + */ +#if defined(_MSC_VER) && defined(_M_IX86) +# include +# define XXH_mult32to64(x, y) __emulu((unsigned)(x), (unsigned)(y)) +#else +/* + * Downcast + upcast is usually better than masking on older compilers like + * GCC 4.2 (especially 32-bit ones), all without affecting newer compilers. + * + * The other method, (x & 0xFFFFFFFF) * (y & 0xFFFFFFFF), will AND both operands + * and perform a full 64x64 multiply -- entirely redundant on 32-bit. + */ +# define XXH_mult32to64(x, y) ((xxh_u64)(xxh_u32)(x) * (xxh_u64)(xxh_u32)(y)) +#endif + +/* + * Calculates a 64->128-bit long multiply. + * + * Uses __uint128_t and _umul128 if available, otherwise uses a scalar version. + */ +static XXH128_hash_t +XXH_mult64to128(xxh_u64 lhs, xxh_u64 rhs) +{ + /* + * GCC/Clang __uint128_t method. + * + * On most 64-bit targets, GCC and Clang define a __uint128_t type. + * This is usually the best way as it usually uses a native long 64-bit + * multiply, such as MULQ on x86_64 or MUL + UMULH on aarch64. + * + * Usually. + * + * Despite being a 32-bit platform, Clang (and emscripten) define this type + * despite not having the arithmetic for it. This results in a laggy + * compiler builtin call which calculates a full 128-bit multiply. + * In that case it is best to use the portable one. + * https://github.com/Cyan4973/xxHash/issues/211#issuecomment-515575677 + */ +#if defined(__GNUC__) && !defined(__wasm__) \ + && defined(__SIZEOF_INT128__) \ + || (defined(_INTEGRAL_MAX_BITS) && _INTEGRAL_MAX_BITS >= 128) + + __uint128_t const product = (__uint128_t)lhs * (__uint128_t)rhs; + XXH128_hash_t r128; + r128.low64 = (xxh_u64)(product); + r128.high64 = (xxh_u64)(product >> 64); + return r128; + + /* + * MSVC for x64's _umul128 method. + * + * xxh_u64 _umul128(xxh_u64 Multiplier, xxh_u64 Multiplicand, xxh_u64 *HighProduct); + * + * This compiles to single operand MUL on x64. + */ +#elif defined(_M_X64) || defined(_M_IA64) + +#ifndef _MSC_VER +# pragma intrinsic(_umul128) +#endif + xxh_u64 product_high; + xxh_u64 const product_low = _umul128(lhs, rhs, &product_high); + XXH128_hash_t r128; + r128.low64 = product_low; + r128.high64 = product_high; + return r128; + +#else + /* + * Portable scalar method. Optimized for 32-bit and 64-bit ALUs. + * + * This is a fast and simple grade school multiply, which is shown below + * with base 10 arithmetic instead of base 0x100000000. + * + * 9 3 // D2 lhs = 93 + * x 7 5 // D2 rhs = 75 + * ---------- + * 1 5 // D2 lo_lo = (93 % 10) * (75 % 10) = 15 + * 4 5 | // D2 hi_lo = (93 / 10) * (75 % 10) = 45 + * 2 1 | // D2 lo_hi = (93 % 10) * (75 / 10) = 21 + * + 6 3 | | // D2 hi_hi = (93 / 10) * (75 / 10) = 63 + * --------- + * 2 7 | // D2 cross = (15 / 10) + (45 % 10) + 21 = 27 + * + 6 7 | | // D2 upper = (27 / 10) + (45 / 10) + 63 = 67 + * --------- + * 6 9 7 5 // D4 res = (27 * 10) + (15 % 10) + (67 * 100) = 6975 + * + * The reasons for adding the products like this are: + * 1. It avoids manual carry tracking. Just like how + * (9 * 9) + 9 + 9 = 99, the same applies with this for UINT64_MAX. + * This avoids a lot of complexity. + * + * 2. It hints for, and on Clang, compiles to, the powerful UMAAL + * instruction available in ARM's Digital Signal Processing extension + * in 32-bit ARMv6 and later, which is shown below: + * + * void UMAAL(xxh_u32 *RdLo, xxh_u32 *RdHi, xxh_u32 Rn, xxh_u32 Rm) + * { + * xxh_u64 product = (xxh_u64)*RdLo * (xxh_u64)*RdHi + Rn + Rm; + * *RdLo = (xxh_u32)(product & 0xFFFFFFFF); + * *RdHi = (xxh_u32)(product >> 32); + * } + * + * This instruction was designed for efficient long multiplication, and + * allows this to be calculated in only 4 instructions at speeds + * comparable to some 64-bit ALUs. + * + * 3. It isn't terrible on other platforms. Usually this will be a couple + * of 32-bit ADD/ADCs. + */ + + /* First calculate all of the cross products. */ + xxh_u64 const lo_lo = XXH_mult32to64(lhs & 0xFFFFFFFF, rhs & 0xFFFFFFFF); + xxh_u64 const hi_lo = XXH_mult32to64(lhs >> 32, rhs & 0xFFFFFFFF); + xxh_u64 const lo_hi = XXH_mult32to64(lhs & 0xFFFFFFFF, rhs >> 32); + xxh_u64 const hi_hi = XXH_mult32to64(lhs >> 32, rhs >> 32); + + /* Now add the products together. These will never overflow. */ + xxh_u64 const cross = (lo_lo >> 32) + (hi_lo & 0xFFFFFFFF) + lo_hi; + xxh_u64 const upper = (hi_lo >> 32) + (cross >> 32) + hi_hi; + xxh_u64 const lower = (cross << 32) | (lo_lo & 0xFFFFFFFF); + + XXH128_hash_t r128; + r128.low64 = lower; + r128.high64 = upper; + return r128; +#endif +} + +/* + * Does a 64-bit to 128-bit multiply, then XOR folds it. + * + * The reason for the separate function is to prevent passing too many structs + * around by value. This will hopefully inline the multiply, but we don't force it. + */ +static xxh_u64 +XXH3_mul128_fold64(xxh_u64 lhs, xxh_u64 rhs) +{ + XXH128_hash_t product = XXH_mult64to128(lhs, rhs); + return product.low64 ^ product.high64; +} + +/* Seems to produce slightly better code on GCC for some reason. */ +XXH_FORCE_INLINE xxh_u64 XXH_xorshift64(xxh_u64 v64, int shift) +{ + XXH_ASSERT(0 <= shift && shift < 64); + return v64 ^ (v64 >> shift); +} + +/* + * This is a fast avalanche stage, + * suitable when input bits are already partially mixed + */ +static XXH64_hash_t XXH3_avalanche(xxh_u64 h64) +{ + h64 = XXH_xorshift64(h64, 37); + h64 *= 0x165667919E3779F9ULL; + h64 = XXH_xorshift64(h64, 32); + return h64; +} + +/* + * This is a stronger avalanche, + * inspired by Pelle Evensen's rrmxmx + * preferable when input has not been previously mixed + */ +static XXH64_hash_t XXH3_rrmxmx(xxh_u64 h64, xxh_u64 len) +{ + /* this mix is inspired by Pelle Evensen's rrmxmx */ + h64 ^= XXH_rotl64(h64, 49) ^ XXH_rotl64(h64, 24); + h64 *= 0x9FB21C651E98DF25ULL; + h64 ^= (h64 >> 35) + len ; + h64 *= 0x9FB21C651E98DF25ULL; + return XXH_xorshift64(h64, 28); +} + + +/* ========================================== + * Short keys + * ========================================== + * One of the shortcomings of XXH32 and XXH64 was that their performance was + * sub-optimal on short lengths. It used an iterative algorithm which strongly + * favored lengths that were a multiple of 4 or 8. + * + * Instead of iterating over individual inputs, we use a set of single shot + * functions which piece together a range of lengths and operate in constant time. + * + * Additionally, the number of multiplies has been significantly reduced. This + * reduces latency, especially when emulating 64-bit multiplies on 32-bit. + * + * Depending on the platform, this may or may not be faster than XXH32, but it + * is almost guaranteed to be faster than XXH64. + */ + +/* + * At very short lengths, there isn't enough input to fully hide secrets, or use + * the entire secret. + * + * There is also only a limited amount of mixing we can do before significantly + * impacting performance. + * + * Therefore, we use different sections of the secret and always mix two secret + * samples with an XOR. This should have no effect on performance on the + * seedless or withSeed variants because everything _should_ be constant folded + * by modern compilers. + * + * The XOR mixing hides individual parts of the secret and increases entropy. + * + * This adds an extra layer of strength for custom secrets. + */ +XXH_FORCE_INLINE XXH64_hash_t +XXH3_len_1to3_64b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(input != NULL); + XXH_ASSERT(1 <= len && len <= 3); + XXH_ASSERT(secret != NULL); + /* + * len = 1: combined = { input[0], 0x01, input[0], input[0] } + * len = 2: combined = { input[1], 0x02, input[0], input[1] } + * len = 3: combined = { input[2], 0x03, input[0], input[1] } + */ + { xxh_u8 const c1 = input[0]; + xxh_u8 const c2 = input[len >> 1]; + xxh_u8 const c3 = input[len - 1]; + xxh_u32 const combined = ((xxh_u32)c1 << 16) | ((xxh_u32)c2 << 24) + | ((xxh_u32)c3 << 0) | ((xxh_u32)len << 8); + xxh_u64 const bitflip = (XXH_readLE32(secret) ^ XXH_readLE32(secret+4)) + seed; + xxh_u64 const keyed = (xxh_u64)combined ^ bitflip; + return XXH64_avalanche(keyed); + } +} + +XXH_FORCE_INLINE XXH64_hash_t +XXH3_len_4to8_64b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(input != NULL); + XXH_ASSERT(secret != NULL); + XXH_ASSERT(4 <= len && len < 8); + seed ^= (xxh_u64)XXH_swap32((xxh_u32)seed) << 32; + { xxh_u32 const input1 = XXH_readLE32(input); + xxh_u32 const input2 = XXH_readLE32(input + len - 4); + xxh_u64 const bitflip = (XXH_readLE64(secret+8) ^ XXH_readLE64(secret+16)) - seed; + xxh_u64 const input64 = input2 + (((xxh_u64)input1) << 32); + xxh_u64 const keyed = input64 ^ bitflip; + return XXH3_rrmxmx(keyed, len); + } +} + +XXH_FORCE_INLINE XXH64_hash_t +XXH3_len_9to16_64b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(input != NULL); + XXH_ASSERT(secret != NULL); + XXH_ASSERT(8 <= len && len <= 16); + { xxh_u64 const bitflip1 = (XXH_readLE64(secret+24) ^ XXH_readLE64(secret+32)) + seed; + xxh_u64 const bitflip2 = (XXH_readLE64(secret+40) ^ XXH_readLE64(secret+48)) - seed; + xxh_u64 const input_lo = XXH_readLE64(input) ^ bitflip1; + xxh_u64 const input_hi = XXH_readLE64(input + len - 8) ^ bitflip2; + xxh_u64 const acc = len + + XXH_swap64(input_lo) + input_hi + + XXH3_mul128_fold64(input_lo, input_hi); + return XXH3_avalanche(acc); + } +} + +XXH_FORCE_INLINE XXH64_hash_t +XXH3_len_0to16_64b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(len <= 16); + { if (XXH_likely(len > 8)) return XXH3_len_9to16_64b(input, len, secret, seed); + if (XXH_likely(len >= 4)) return XXH3_len_4to8_64b(input, len, secret, seed); + if (len) return XXH3_len_1to3_64b(input, len, secret, seed); + return XXH64_avalanche(seed ^ (XXH_readLE64(secret+56) ^ XXH_readLE64(secret+64))); + } +} + +/* + * DISCLAIMER: There are known *seed-dependent* multicollisions here due to + * multiplication by zero, affecting hashes of lengths 17 to 240. + * + * However, they are very unlikely. + * + * Keep this in mind when using the unseeded XXH3_64bits() variant: As with all + * unseeded non-cryptographic hashes, it does not attempt to defend itself + * against specially crafted inputs, only random inputs. + * + * Compared to classic UMAC where a 1 in 2^31 chance of 4 consecutive bytes + * cancelling out the secret is taken an arbitrary number of times (addressed + * in XXH3_accumulate_512), this collision is very unlikely with random inputs + * and/or proper seeding: + * + * This only has a 1 in 2^63 chance of 8 consecutive bytes cancelling out, in a + * function that is only called up to 16 times per hash with up to 240 bytes of + * input. + * + * This is not too bad for a non-cryptographic hash function, especially with + * only 64 bit outputs. + * + * The 128-bit variant (which trades some speed for strength) is NOT affected + * by this, although it is always a good idea to use a proper seed if you care + * about strength. + */ +XXH_FORCE_INLINE xxh_u64 XXH3_mix16B(const xxh_u8* XXH_RESTRICT input, + const xxh_u8* XXH_RESTRICT secret, xxh_u64 seed64) +{ +#if defined(__GNUC__) && !defined(__clang__) /* GCC, not Clang */ \ + && defined(__i386__) && defined(__SSE2__) /* x86 + SSE2 */ \ + && !defined(XXH_ENABLE_AUTOVECTORIZE) /* Define to disable like XXH32 hack */ + /* + * UGLY HACK: + * GCC for x86 tends to autovectorize the 128-bit multiply, resulting in + * slower code. + * + * By forcing seed64 into a register, we disrupt the cost model and + * cause it to scalarize. See `XXH32_round()` + * + * FIXME: Clang's output is still _much_ faster -- On an AMD Ryzen 3600, + * XXH3_64bits @ len=240 runs at 4.6 GB/s with Clang 9, but 3.3 GB/s on + * GCC 9.2, despite both emitting scalar code. + * + * GCC generates much better scalar code than Clang for the rest of XXH3, + * which is why finding a more optimal codepath is an interest. + */ + __asm__ ("" : "+r" (seed64)); +#endif + { xxh_u64 const input_lo = XXH_readLE64(input); + xxh_u64 const input_hi = XXH_readLE64(input+8); + return XXH3_mul128_fold64( + input_lo ^ (XXH_readLE64(secret) + seed64), + input_hi ^ (XXH_readLE64(secret+8) - seed64) + ); + } +} + +/* For mid range keys, XXH3 uses a Mum-hash variant. */ +XXH_FORCE_INLINE XXH64_hash_t +XXH3_len_17to128_64b(const xxh_u8* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH64_hash_t seed) +{ + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); (void)secretSize; + XXH_ASSERT(16 < len && len <= 128); + + { xxh_u64 acc = len * XXH_PRIME64_1; + if (len > 32) { + if (len > 64) { + if (len > 96) { + acc += XXH3_mix16B(input+48, secret+96, seed); + acc += XXH3_mix16B(input+len-64, secret+112, seed); + } + acc += XXH3_mix16B(input+32, secret+64, seed); + acc += XXH3_mix16B(input+len-48, secret+80, seed); + } + acc += XXH3_mix16B(input+16, secret+32, seed); + acc += XXH3_mix16B(input+len-32, secret+48, seed); + } + acc += XXH3_mix16B(input+0, secret+0, seed); + acc += XXH3_mix16B(input+len-16, secret+16, seed); + + return XXH3_avalanche(acc); + } +} + +#define XXH3_MIDSIZE_MAX 240 + +XXH_NO_INLINE XXH64_hash_t +XXH3_len_129to240_64b(const xxh_u8* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH64_hash_t seed) +{ + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); (void)secretSize; + XXH_ASSERT(128 < len && len <= XXH3_MIDSIZE_MAX); + + #define XXH3_MIDSIZE_STARTOFFSET 3 + #define XXH3_MIDSIZE_LASTOFFSET 17 + + { xxh_u64 acc = len * XXH_PRIME64_1; + int const nbRounds = (int)len / 16; + int i; + for (i=0; i<8; i++) { + acc += XXH3_mix16B(input+(16*i), secret+(16*i), seed); + } + acc = XXH3_avalanche(acc); + XXH_ASSERT(nbRounds >= 8); +#if defined(__clang__) /* Clang */ \ + && (defined(__ARM_NEON) || defined(__ARM_NEON__)) /* NEON */ \ + && !defined(XXH_ENABLE_AUTOVECTORIZE) /* Define to disable */ + /* + * UGLY HACK: + * Clang for ARMv7-A tries to vectorize this loop, similar to GCC x86. + * In everywhere else, it uses scalar code. + * + * For 64->128-bit multiplies, even if the NEON was 100% optimal, it + * would still be slower than UMAAL (see XXH_mult64to128). + * + * Unfortunately, Clang doesn't handle the long multiplies properly and + * converts them to the nonexistent "vmulq_u64" intrinsic, which is then + * scalarized into an ugly mess of VMOV.32 instructions. + * + * This mess is difficult to avoid without turning autovectorization + * off completely, but they are usually relatively minor and/or not + * worth it to fix. + * + * This loop is the easiest to fix, as unlike XXH32, this pragma + * _actually works_ because it is a loop vectorization instead of an + * SLP vectorization. + */ + #pragma clang loop vectorize(disable) +#endif + for (i=8 ; i < nbRounds; i++) { + acc += XXH3_mix16B(input+(16*i), secret+(16*(i-8)) + XXH3_MIDSIZE_STARTOFFSET, seed); + } + /* last bytes */ + acc += XXH3_mix16B(input + len - 16, secret + XXH3_SECRET_SIZE_MIN - XXH3_MIDSIZE_LASTOFFSET, seed); + return XXH3_avalanche(acc); + } +} + + +/* ======= Long Keys ======= */ + +#define XXH_STRIPE_LEN 64 +#define XXH_SECRET_CONSUME_RATE 8 /* nb of secret bytes consumed at each accumulation */ +#define XXH_ACC_NB (XXH_STRIPE_LEN / sizeof(xxh_u64)) + +#ifdef XXH_OLD_NAMES +# define STRIPE_LEN XXH_STRIPE_LEN +# define ACC_NB XXH_ACC_NB +#endif + +XXH_FORCE_INLINE void XXH_writeLE64(void* dst, xxh_u64 v64) +{ + if (!XXH_CPU_LITTLE_ENDIAN) v64 = XXH_swap64(v64); + memcpy(dst, &v64, sizeof(v64)); +} + +/* Several intrinsic functions below are supposed to accept __int64 as argument, + * as documented in https://software.intel.com/sites/landingpage/IntrinsicsGuide/ . + * However, several environments do not define __int64 type, + * requiring a workaround. + */ +#if !defined (__VMS) \ + && (defined (__cplusplus) \ + || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) ) + typedef int64_t xxh_i64; +#else + /* the following type must have a width of 64-bit */ + typedef long long xxh_i64; +#endif + +/* + * XXH3_accumulate_512 is the tightest loop for long inputs, and it is the most optimized. + * + * It is a hardened version of UMAC, based off of FARSH's implementation. + * + * This was chosen because it adapts quite well to 32-bit, 64-bit, and SIMD + * implementations, and it is ridiculously fast. + * + * We harden it by mixing the original input to the accumulators as well as the product. + * + * This means that in the (relatively likely) case of a multiply by zero, the + * original input is preserved. + * + * On 128-bit inputs, we swap 64-bit pairs when we add the input to improve + * cross-pollination, as otherwise the upper and lower halves would be + * essentially independent. + * + * This doesn't matter on 64-bit hashes since they all get merged together in + * the end, so we skip the extra step. + * + * Both XXH3_64bits and XXH3_128bits use this subroutine. + */ + +#if (XXH_VECTOR == XXH_AVX512) || defined(XXH_X86DISPATCH) + +#ifndef XXH_TARGET_AVX512 +# define XXH_TARGET_AVX512 /* disable attribute target */ +#endif + +XXH_FORCE_INLINE XXH_TARGET_AVX512 void +XXH3_accumulate_512_avx512(void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + XXH_ALIGN(64) __m512i* const xacc = (__m512i *) acc; + XXH_ASSERT((((size_t)acc) & 63) == 0); + XXH_STATIC_ASSERT(XXH_STRIPE_LEN == sizeof(__m512i)); + + { + /* data_vec = input[0]; */ + __m512i const data_vec = _mm512_loadu_si512 (input); + /* key_vec = secret[0]; */ + __m512i const key_vec = _mm512_loadu_si512 (secret); + /* data_key = data_vec ^ key_vec; */ + __m512i const data_key = _mm512_xor_si512 (data_vec, key_vec); + /* data_key_lo = data_key >> 32; */ + __m512i const data_key_lo = _mm512_shuffle_epi32 (data_key, (_MM_PERM_ENUM)_MM_SHUFFLE(0, 3, 0, 1)); + /* product = (data_key & 0xffffffff) * (data_key_lo & 0xffffffff); */ + __m512i const product = _mm512_mul_epu32 (data_key, data_key_lo); + /* xacc[0] += swap(data_vec); */ + __m512i const data_swap = _mm512_shuffle_epi32(data_vec, (_MM_PERM_ENUM)_MM_SHUFFLE(1, 0, 3, 2)); + __m512i const sum = _mm512_add_epi64(*xacc, data_swap); + /* xacc[0] += product; */ + *xacc = _mm512_add_epi64(product, sum); + } +} + +/* + * XXH3_scrambleAcc: Scrambles the accumulators to improve mixing. + * + * Multiplication isn't perfect, as explained by Google in HighwayHash: + * + * // Multiplication mixes/scrambles bytes 0-7 of the 64-bit result to + * // varying degrees. In descending order of goodness, bytes + * // 3 4 2 5 1 6 0 7 have quality 228 224 164 160 100 96 36 32. + * // As expected, the upper and lower bytes are much worse. + * + * Source: https://github.com/google/highwayhash/blob/0aaf66b/highwayhash/hh_avx2.h#L291 + * + * Since our algorithm uses a pseudorandom secret to add some variance into the + * mix, we don't need to (or want to) mix as often or as much as HighwayHash does. + * + * This isn't as tight as XXH3_accumulate, but still written in SIMD to avoid + * extraction. + * + * Both XXH3_64bits and XXH3_128bits use this subroutine. + */ + +XXH_FORCE_INLINE XXH_TARGET_AVX512 void +XXH3_scrambleAcc_avx512(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 63) == 0); + XXH_STATIC_ASSERT(XXH_STRIPE_LEN == sizeof(__m512i)); + { XXH_ALIGN(64) __m512i* const xacc = (__m512i*) acc; + const __m512i prime32 = _mm512_set1_epi32((int)XXH_PRIME32_1); + + /* xacc[0] ^= (xacc[0] >> 47) */ + __m512i const acc_vec = *xacc; + __m512i const shifted = _mm512_srli_epi64 (acc_vec, 47); + __m512i const data_vec = _mm512_xor_si512 (acc_vec, shifted); + /* xacc[0] ^= secret; */ + __m512i const key_vec = _mm512_loadu_si512 (secret); + __m512i const data_key = _mm512_xor_si512 (data_vec, key_vec); + + /* xacc[0] *= XXH_PRIME32_1; */ + __m512i const data_key_hi = _mm512_shuffle_epi32 (data_key, (_MM_PERM_ENUM)_MM_SHUFFLE(0, 3, 0, 1)); + __m512i const prod_lo = _mm512_mul_epu32 (data_key, prime32); + __m512i const prod_hi = _mm512_mul_epu32 (data_key_hi, prime32); + *xacc = _mm512_add_epi64(prod_lo, _mm512_slli_epi64(prod_hi, 32)); + } +} + +XXH_FORCE_INLINE XXH_TARGET_AVX512 void +XXH3_initCustomSecret_avx512(void* XXH_RESTRICT customSecret, xxh_u64 seed64) +{ + XXH_STATIC_ASSERT((XXH_SECRET_DEFAULT_SIZE & 63) == 0); + XXH_STATIC_ASSERT(XXH_SEC_ALIGN == 64); + XXH_ASSERT(((size_t)customSecret & 63) == 0); + (void)(&XXH_writeLE64); + { int const nbRounds = XXH_SECRET_DEFAULT_SIZE / sizeof(__m512i); + __m512i const seed = _mm512_mask_set1_epi64(_mm512_set1_epi64((xxh_i64)seed64), 0xAA, -(xxh_i64)seed64); + + XXH_ALIGN(64) const __m512i* const src = (const __m512i*) XXH3_kSecret; + XXH_ALIGN(64) __m512i* const dest = ( __m512i*) customSecret; + int i; + for (i=0; i < nbRounds; ++i) { + /* GCC has a bug, _mm512_stream_load_si512 accepts 'void*', not 'void const*', + * this will warn "discards ‘const’ qualifier". */ + union { + XXH_ALIGN(64) const __m512i* cp; + XXH_ALIGN(64) void* p; + } remote_const_void; + remote_const_void.cp = src + i; + dest[i] = _mm512_add_epi64(_mm512_stream_load_si512(remote_const_void.p), seed); + } } +} + +#endif + +#if (XXH_VECTOR == XXH_AVX2) || defined(XXH_X86DISPATCH) + +#ifndef XXH_TARGET_AVX2 +# define XXH_TARGET_AVX2 /* disable attribute target */ +#endif + +XXH_FORCE_INLINE XXH_TARGET_AVX2 void +XXH3_accumulate_512_avx2( void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 31) == 0); + { XXH_ALIGN(32) __m256i* const xacc = (__m256i *) acc; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm256_loadu_si256 requires a const __m256i * pointer for some reason. */ + const __m256i* const xinput = (const __m256i *) input; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm256_loadu_si256 requires a const __m256i * pointer for some reason. */ + const __m256i* const xsecret = (const __m256i *) secret; + + size_t i; + for (i=0; i < XXH_STRIPE_LEN/sizeof(__m256i); i++) { + /* data_vec = xinput[i]; */ + __m256i const data_vec = _mm256_loadu_si256 (xinput+i); + /* key_vec = xsecret[i]; */ + __m256i const key_vec = _mm256_loadu_si256 (xsecret+i); + /* data_key = data_vec ^ key_vec; */ + __m256i const data_key = _mm256_xor_si256 (data_vec, key_vec); + /* data_key_lo = data_key >> 32; */ + __m256i const data_key_lo = _mm256_shuffle_epi32 (data_key, _MM_SHUFFLE(0, 3, 0, 1)); + /* product = (data_key & 0xffffffff) * (data_key_lo & 0xffffffff); */ + __m256i const product = _mm256_mul_epu32 (data_key, data_key_lo); + /* xacc[i] += swap(data_vec); */ + __m256i const data_swap = _mm256_shuffle_epi32(data_vec, _MM_SHUFFLE(1, 0, 3, 2)); + __m256i const sum = _mm256_add_epi64(xacc[i], data_swap); + /* xacc[i] += product; */ + xacc[i] = _mm256_add_epi64(product, sum); + } } +} + +XXH_FORCE_INLINE XXH_TARGET_AVX2 void +XXH3_scrambleAcc_avx2(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 31) == 0); + { XXH_ALIGN(32) __m256i* const xacc = (__m256i*) acc; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm256_loadu_si256 requires a const __m256i * pointer for some reason. */ + const __m256i* const xsecret = (const __m256i *) secret; + const __m256i prime32 = _mm256_set1_epi32((int)XXH_PRIME32_1); + + size_t i; + for (i=0; i < XXH_STRIPE_LEN/sizeof(__m256i); i++) { + /* xacc[i] ^= (xacc[i] >> 47) */ + __m256i const acc_vec = xacc[i]; + __m256i const shifted = _mm256_srli_epi64 (acc_vec, 47); + __m256i const data_vec = _mm256_xor_si256 (acc_vec, shifted); + /* xacc[i] ^= xsecret; */ + __m256i const key_vec = _mm256_loadu_si256 (xsecret+i); + __m256i const data_key = _mm256_xor_si256 (data_vec, key_vec); + + /* xacc[i] *= XXH_PRIME32_1; */ + __m256i const data_key_hi = _mm256_shuffle_epi32 (data_key, _MM_SHUFFLE(0, 3, 0, 1)); + __m256i const prod_lo = _mm256_mul_epu32 (data_key, prime32); + __m256i const prod_hi = _mm256_mul_epu32 (data_key_hi, prime32); + xacc[i] = _mm256_add_epi64(prod_lo, _mm256_slli_epi64(prod_hi, 32)); + } + } +} + +XXH_FORCE_INLINE XXH_TARGET_AVX2 void XXH3_initCustomSecret_avx2(void* XXH_RESTRICT customSecret, xxh_u64 seed64) +{ + XXH_STATIC_ASSERT((XXH_SECRET_DEFAULT_SIZE & 31) == 0); + XXH_STATIC_ASSERT((XXH_SECRET_DEFAULT_SIZE / sizeof(__m256i)) == 6); + XXH_STATIC_ASSERT(XXH_SEC_ALIGN <= 64); + (void)(&XXH_writeLE64); + XXH_PREFETCH(customSecret); + { __m256i const seed = _mm256_set_epi64x(-(xxh_i64)seed64, (xxh_i64)seed64, -(xxh_i64)seed64, (xxh_i64)seed64); + + XXH_ALIGN(64) const __m256i* const src = (const __m256i*) XXH3_kSecret; + XXH_ALIGN(64) __m256i* dest = ( __m256i*) customSecret; + +# if defined(__GNUC__) || defined(__clang__) + /* + * On GCC & Clang, marking 'dest' as modified will cause the compiler: + * - do not extract the secret from sse registers in the internal loop + * - use less common registers, and avoid pushing these reg into stack + * The asm hack causes Clang to assume that XXH3_kSecretPtr aliases with + * customSecret, and on aarch64, this prevented LDP from merging two + * loads together for free. Putting the loads together before the stores + * properly generates LDP. + */ + __asm__("" : "+r" (dest)); +# endif + + /* GCC -O2 need unroll loop manually */ + dest[0] = _mm256_add_epi64(_mm256_stream_load_si256(src+0), seed); + dest[1] = _mm256_add_epi64(_mm256_stream_load_si256(src+1), seed); + dest[2] = _mm256_add_epi64(_mm256_stream_load_si256(src+2), seed); + dest[3] = _mm256_add_epi64(_mm256_stream_load_si256(src+3), seed); + dest[4] = _mm256_add_epi64(_mm256_stream_load_si256(src+4), seed); + dest[5] = _mm256_add_epi64(_mm256_stream_load_si256(src+5), seed); + } +} + +#endif + +#if (XXH_VECTOR == XXH_SSE2) || defined(XXH_X86DISPATCH) + +#ifndef XXH_TARGET_SSE2 +# define XXH_TARGET_SSE2 /* disable attribute target */ +#endif + +XXH_FORCE_INLINE XXH_TARGET_SSE2 void +XXH3_accumulate_512_sse2( void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + /* SSE2 is just a half-scale version of the AVX2 version. */ + XXH_ASSERT((((size_t)acc) & 15) == 0); + { XXH_ALIGN(16) __m128i* const xacc = (__m128i *) acc; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm_loadu_si128 requires a const __m128i * pointer for some reason. */ + const __m128i* const xinput = (const __m128i *) input; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm_loadu_si128 requires a const __m128i * pointer for some reason. */ + const __m128i* const xsecret = (const __m128i *) secret; + + size_t i; + for (i=0; i < XXH_STRIPE_LEN/sizeof(__m128i); i++) { + /* data_vec = xinput[i]; */ + __m128i const data_vec = _mm_loadu_si128 (xinput+i); + /* key_vec = xsecret[i]; */ + __m128i const key_vec = _mm_loadu_si128 (xsecret+i); + /* data_key = data_vec ^ key_vec; */ + __m128i const data_key = _mm_xor_si128 (data_vec, key_vec); + /* data_key_lo = data_key >> 32; */ + __m128i const data_key_lo = _mm_shuffle_epi32 (data_key, _MM_SHUFFLE(0, 3, 0, 1)); + /* product = (data_key & 0xffffffff) * (data_key_lo & 0xffffffff); */ + __m128i const product = _mm_mul_epu32 (data_key, data_key_lo); + /* xacc[i] += swap(data_vec); */ + __m128i const data_swap = _mm_shuffle_epi32(data_vec, _MM_SHUFFLE(1,0,3,2)); + __m128i const sum = _mm_add_epi64(xacc[i], data_swap); + /* xacc[i] += product; */ + xacc[i] = _mm_add_epi64(product, sum); + } } +} + +XXH_FORCE_INLINE XXH_TARGET_SSE2 void +XXH3_scrambleAcc_sse2(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 15) == 0); + { XXH_ALIGN(16) __m128i* const xacc = (__m128i*) acc; + /* Unaligned. This is mainly for pointer arithmetic, and because + * _mm_loadu_si128 requires a const __m128i * pointer for some reason. */ + const __m128i* const xsecret = (const __m128i *) secret; + const __m128i prime32 = _mm_set1_epi32((int)XXH_PRIME32_1); + + size_t i; + for (i=0; i < XXH_STRIPE_LEN/sizeof(__m128i); i++) { + /* xacc[i] ^= (xacc[i] >> 47) */ + __m128i const acc_vec = xacc[i]; + __m128i const shifted = _mm_srli_epi64 (acc_vec, 47); + __m128i const data_vec = _mm_xor_si128 (acc_vec, shifted); + /* xacc[i] ^= xsecret[i]; */ + __m128i const key_vec = _mm_loadu_si128 (xsecret+i); + __m128i const data_key = _mm_xor_si128 (data_vec, key_vec); + + /* xacc[i] *= XXH_PRIME32_1; */ + __m128i const data_key_hi = _mm_shuffle_epi32 (data_key, _MM_SHUFFLE(0, 3, 0, 1)); + __m128i const prod_lo = _mm_mul_epu32 (data_key, prime32); + __m128i const prod_hi = _mm_mul_epu32 (data_key_hi, prime32); + xacc[i] = _mm_add_epi64(prod_lo, _mm_slli_epi64(prod_hi, 32)); + } + } +} + +XXH_FORCE_INLINE XXH_TARGET_SSE2 void XXH3_initCustomSecret_sse2(void* XXH_RESTRICT customSecret, xxh_u64 seed64) +{ + XXH_STATIC_ASSERT((XXH_SECRET_DEFAULT_SIZE & 15) == 0); + (void)(&XXH_writeLE64); + { int const nbRounds = XXH_SECRET_DEFAULT_SIZE / sizeof(__m128i); + +# if defined(_MSC_VER) && defined(_M_IX86) && _MSC_VER < 1900 + // MSVC 32bit mode does not support _mm_set_epi64x before 2015 + XXH_ALIGN(16) const xxh_i64 seed64x2[2] = { (xxh_i64)seed64, -(xxh_i64)seed64 }; + __m128i const seed = _mm_load_si128((__m128i const*)seed64x2); +# else + __m128i const seed = _mm_set_epi64x(-(xxh_i64)seed64, (xxh_i64)seed64); +# endif + int i; + + XXH_ALIGN(64) const float* const src = (float const*) XXH3_kSecret; + XXH_ALIGN(XXH_SEC_ALIGN) __m128i* dest = (__m128i*) customSecret; +# if defined(__GNUC__) || defined(__clang__) + /* + * On GCC & Clang, marking 'dest' as modified will cause the compiler: + * - do not extract the secret from sse registers in the internal loop + * - use less common registers, and avoid pushing these reg into stack + */ + __asm__("" : "+r" (dest)); +# endif + + for (i=0; i < nbRounds; ++i) { + dest[i] = _mm_add_epi64(_mm_castps_si128(_mm_load_ps(src+i*4)), seed); + } } +} + +#endif + +#if (XXH_VECTOR == XXH_NEON) + +XXH_FORCE_INLINE void +XXH3_accumulate_512_neon( void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 15) == 0); + { + XXH_ALIGN(16) uint64x2_t* const xacc = (uint64x2_t *) acc; + /* We don't use a uint32x4_t pointer because it causes bus errors on ARMv7. */ + uint8_t const* const xinput = (const uint8_t *) input; + uint8_t const* const xsecret = (const uint8_t *) secret; + + size_t i; + for (i=0; i < XXH_STRIPE_LEN / sizeof(uint64x2_t); i++) { + /* data_vec = xinput[i]; */ + uint8x16_t data_vec = vld1q_u8(xinput + (i * 16)); + /* key_vec = xsecret[i]; */ + uint8x16_t key_vec = vld1q_u8(xsecret + (i * 16)); + uint64x2_t data_key; + uint32x2_t data_key_lo, data_key_hi; + /* xacc[i] += swap(data_vec); */ + uint64x2_t const data64 = vreinterpretq_u64_u8(data_vec); + uint64x2_t const swapped = vextq_u64(data64, data64, 1); + xacc[i] = vaddq_u64 (xacc[i], swapped); + /* data_key = data_vec ^ key_vec; */ + data_key = vreinterpretq_u64_u8(veorq_u8(data_vec, key_vec)); + /* data_key_lo = (uint32x2_t) (data_key & 0xFFFFFFFF); + * data_key_hi = (uint32x2_t) (data_key >> 32); + * data_key = UNDEFINED; */ + XXH_SPLIT_IN_PLACE(data_key, data_key_lo, data_key_hi); + /* xacc[i] += (uint64x2_t) data_key_lo * (uint64x2_t) data_key_hi; */ + xacc[i] = vmlal_u32 (xacc[i], data_key_lo, data_key_hi); + + } + } +} + +XXH_FORCE_INLINE void +XXH3_scrambleAcc_neon(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 15) == 0); + + { uint64x2_t* xacc = (uint64x2_t*) acc; + uint8_t const* xsecret = (uint8_t const*) secret; + uint32x2_t prime = vdup_n_u32 (XXH_PRIME32_1); + + size_t i; + for (i=0; i < XXH_STRIPE_LEN/sizeof(uint64x2_t); i++) { + /* xacc[i] ^= (xacc[i] >> 47); */ + uint64x2_t acc_vec = xacc[i]; + uint64x2_t shifted = vshrq_n_u64 (acc_vec, 47); + uint64x2_t data_vec = veorq_u64 (acc_vec, shifted); + + /* xacc[i] ^= xsecret[i]; */ + uint8x16_t key_vec = vld1q_u8(xsecret + (i * 16)); + uint64x2_t data_key = veorq_u64(data_vec, vreinterpretq_u64_u8(key_vec)); + + /* xacc[i] *= XXH_PRIME32_1 */ + uint32x2_t data_key_lo, data_key_hi; + /* data_key_lo = (uint32x2_t) (xacc[i] & 0xFFFFFFFF); + * data_key_hi = (uint32x2_t) (xacc[i] >> 32); + * xacc[i] = UNDEFINED; */ + XXH_SPLIT_IN_PLACE(data_key, data_key_lo, data_key_hi); + { /* + * prod_hi = (data_key >> 32) * XXH_PRIME32_1; + * + * Avoid vmul_u32 + vshll_n_u32 since Clang 6 and 7 will + * incorrectly "optimize" this: + * tmp = vmul_u32(vmovn_u64(a), vmovn_u64(b)); + * shifted = vshll_n_u32(tmp, 32); + * to this: + * tmp = "vmulq_u64"(a, b); // no such thing! + * shifted = vshlq_n_u64(tmp, 32); + * + * However, unlike SSE, Clang lacks a 64-bit multiply routine + * for NEON, and it scalarizes two 64-bit multiplies instead. + * + * vmull_u32 has the same timing as vmul_u32, and it avoids + * this bug completely. + * See https://bugs.llvm.org/show_bug.cgi?id=39967 + */ + uint64x2_t prod_hi = vmull_u32 (data_key_hi, prime); + /* xacc[i] = prod_hi << 32; */ + xacc[i] = vshlq_n_u64(prod_hi, 32); + /* xacc[i] += (prod_hi & 0xFFFFFFFF) * XXH_PRIME32_1; */ + xacc[i] = vmlal_u32(xacc[i], data_key_lo, prime); + } + } } +} + +#endif + +#if (XXH_VECTOR == XXH_VSX) + +XXH_FORCE_INLINE void +XXH3_accumulate_512_vsx( void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + xxh_u64x2* const xacc = (xxh_u64x2*) acc; /* presumed aligned */ + xxh_u64x2 const* const xinput = (xxh_u64x2 const*) input; /* no alignment restriction */ + xxh_u64x2 const* const xsecret = (xxh_u64x2 const*) secret; /* no alignment restriction */ + xxh_u64x2 const v32 = { 32, 32 }; + size_t i; + for (i = 0; i < XXH_STRIPE_LEN / sizeof(xxh_u64x2); i++) { + /* data_vec = xinput[i]; */ + xxh_u64x2 const data_vec = XXH_vec_loadu(xinput + i); + /* key_vec = xsecret[i]; */ + xxh_u64x2 const key_vec = XXH_vec_loadu(xsecret + i); + xxh_u64x2 const data_key = data_vec ^ key_vec; + /* shuffled = (data_key << 32) | (data_key >> 32); */ + xxh_u32x4 const shuffled = (xxh_u32x4)vec_rl(data_key, v32); + /* product = ((xxh_u64x2)data_key & 0xFFFFFFFF) * ((xxh_u64x2)shuffled & 0xFFFFFFFF); */ + xxh_u64x2 const product = XXH_vec_mulo((xxh_u32x4)data_key, shuffled); + xacc[i] += product; + + /* swap high and low halves */ +#ifdef __s390x__ + xacc[i] += vec_permi(data_vec, data_vec, 2); +#else + xacc[i] += vec_xxpermdi(data_vec, data_vec, 2); +#endif + } +} + +XXH_FORCE_INLINE void +XXH3_scrambleAcc_vsx(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ASSERT((((size_t)acc) & 15) == 0); + + { xxh_u64x2* const xacc = (xxh_u64x2*) acc; + const xxh_u64x2* const xsecret = (const xxh_u64x2*) secret; + /* constants */ + xxh_u64x2 const v32 = { 32, 32 }; + xxh_u64x2 const v47 = { 47, 47 }; + xxh_u32x4 const prime = { XXH_PRIME32_1, XXH_PRIME32_1, XXH_PRIME32_1, XXH_PRIME32_1 }; + size_t i; + for (i = 0; i < XXH_STRIPE_LEN / sizeof(xxh_u64x2); i++) { + /* xacc[i] ^= (xacc[i] >> 47); */ + xxh_u64x2 const acc_vec = xacc[i]; + xxh_u64x2 const data_vec = acc_vec ^ (acc_vec >> v47); + + /* xacc[i] ^= xsecret[i]; */ + xxh_u64x2 const key_vec = XXH_vec_loadu(xsecret + i); + xxh_u64x2 const data_key = data_vec ^ key_vec; + + /* xacc[i] *= XXH_PRIME32_1 */ + /* prod_lo = ((xxh_u64x2)data_key & 0xFFFFFFFF) * ((xxh_u64x2)prime & 0xFFFFFFFF); */ + xxh_u64x2 const prod_even = XXH_vec_mule((xxh_u32x4)data_key, prime); + /* prod_hi = ((xxh_u64x2)data_key >> 32) * ((xxh_u64x2)prime >> 32); */ + xxh_u64x2 const prod_odd = XXH_vec_mulo((xxh_u32x4)data_key, prime); + xacc[i] = prod_odd + (prod_even << v32); + } } +} + +#endif + +/* scalar variants - universal */ + +XXH_FORCE_INLINE void +XXH3_accumulate_512_scalar(void* XXH_RESTRICT acc, + const void* XXH_RESTRICT input, + const void* XXH_RESTRICT secret) +{ + XXH_ALIGN(XXH_ACC_ALIGN) xxh_u64* const xacc = (xxh_u64*) acc; /* presumed aligned */ + const xxh_u8* const xinput = (const xxh_u8*) input; /* no alignment restriction */ + const xxh_u8* const xsecret = (const xxh_u8*) secret; /* no alignment restriction */ + size_t i; + XXH_ASSERT(((size_t)acc & (XXH_ACC_ALIGN-1)) == 0); + for (i=0; i < XXH_ACC_NB; i++) { + xxh_u64 const data_val = XXH_readLE64(xinput + 8*i); + xxh_u64 const data_key = data_val ^ XXH_readLE64(xsecret + i*8); + xacc[i ^ 1] += data_val; /* swap adjacent lanes */ + xacc[i] += XXH_mult32to64(data_key & 0xFFFFFFFF, data_key >> 32); + } +} + +XXH_FORCE_INLINE void +XXH3_scrambleAcc_scalar(void* XXH_RESTRICT acc, const void* XXH_RESTRICT secret) +{ + XXH_ALIGN(XXH_ACC_ALIGN) xxh_u64* const xacc = (xxh_u64*) acc; /* presumed aligned */ + const xxh_u8* const xsecret = (const xxh_u8*) secret; /* no alignment restriction */ + size_t i; + XXH_ASSERT((((size_t)acc) & (XXH_ACC_ALIGN-1)) == 0); + for (i=0; i < XXH_ACC_NB; i++) { + xxh_u64 const key64 = XXH_readLE64(xsecret + 8*i); + xxh_u64 acc64 = xacc[i]; + acc64 = XXH_xorshift64(acc64, 47); + acc64 ^= key64; + acc64 *= XXH_PRIME32_1; + xacc[i] = acc64; + } +} + +XXH_FORCE_INLINE void +XXH3_initCustomSecret_scalar(void* XXH_RESTRICT customSecret, xxh_u64 seed64) +{ + /* + * We need a separate pointer for the hack below, + * which requires a non-const pointer. + * Any decent compiler will optimize this out otherwise. + */ + const xxh_u8* kSecretPtr = XXH3_kSecret; + XXH_STATIC_ASSERT((XXH_SECRET_DEFAULT_SIZE & 15) == 0); + +#if defined(__clang__) && defined(__aarch64__) + /* + * UGLY HACK: + * Clang generates a bunch of MOV/MOVK pairs for aarch64, and they are + * placed sequentially, in order, at the top of the unrolled loop. + * + * While MOVK is great for generating constants (2 cycles for a 64-bit + * constant compared to 4 cycles for LDR), long MOVK chains stall the + * integer pipelines: + * I L S + * MOVK + * MOVK + * MOVK + * MOVK + * ADD + * SUB STR + * STR + * By forcing loads from memory (as the asm line causes Clang to assume + * that XXH3_kSecretPtr has been changed), the pipelines are used more + * efficiently: + * I L S + * LDR + * ADD LDR + * SUB STR + * STR + * XXH3_64bits_withSeed, len == 256, Snapdragon 835 + * without hack: 2654.4 MB/s + * with hack: 3202.9 MB/s + */ + __asm__("" : "+r" (kSecretPtr)); +#endif + /* + * Note: in debug mode, this overrides the asm optimization + * and Clang will emit MOVK chains again. + */ + XXH_ASSERT(kSecretPtr == XXH3_kSecret); + + { int const nbRounds = XXH_SECRET_DEFAULT_SIZE / 16; + int i; + for (i=0; i < nbRounds; i++) { + /* + * The asm hack causes Clang to assume that kSecretPtr aliases with + * customSecret, and on aarch64, this prevented LDP from merging two + * loads together for free. Putting the loads together before the stores + * properly generates LDP. + */ + xxh_u64 lo = XXH_readLE64(kSecretPtr + 16*i) + seed64; + xxh_u64 hi = XXH_readLE64(kSecretPtr + 16*i + 8) - seed64; + XXH_writeLE64((xxh_u8*)customSecret + 16*i, lo); + XXH_writeLE64((xxh_u8*)customSecret + 16*i + 8, hi); + } } +} + + +typedef void (*XXH3_f_accumulate_512)(void* XXH_RESTRICT, const void*, const void*); +typedef void (*XXH3_f_scrambleAcc)(void* XXH_RESTRICT, const void*); +typedef void (*XXH3_f_initCustomSecret)(void* XXH_RESTRICT, xxh_u64); + + +#if (XXH_VECTOR == XXH_AVX512) + +#define XXH3_accumulate_512 XXH3_accumulate_512_avx512 +#define XXH3_scrambleAcc XXH3_scrambleAcc_avx512 +#define XXH3_initCustomSecret XXH3_initCustomSecret_avx512 + +#elif (XXH_VECTOR == XXH_AVX2) + +#define XXH3_accumulate_512 XXH3_accumulate_512_avx2 +#define XXH3_scrambleAcc XXH3_scrambleAcc_avx2 +#define XXH3_initCustomSecret XXH3_initCustomSecret_avx2 + +#elif (XXH_VECTOR == XXH_SSE2) + +#define XXH3_accumulate_512 XXH3_accumulate_512_sse2 +#define XXH3_scrambleAcc XXH3_scrambleAcc_sse2 +#define XXH3_initCustomSecret XXH3_initCustomSecret_sse2 + +#elif (XXH_VECTOR == XXH_NEON) + +#define XXH3_accumulate_512 XXH3_accumulate_512_neon +#define XXH3_scrambleAcc XXH3_scrambleAcc_neon +#define XXH3_initCustomSecret XXH3_initCustomSecret_scalar + +#elif (XXH_VECTOR == XXH_VSX) + +#define XXH3_accumulate_512 XXH3_accumulate_512_vsx +#define XXH3_scrambleAcc XXH3_scrambleAcc_vsx +#define XXH3_initCustomSecret XXH3_initCustomSecret_scalar + +#else /* scalar */ + +#define XXH3_accumulate_512 XXH3_accumulate_512_scalar +#define XXH3_scrambleAcc XXH3_scrambleAcc_scalar +#define XXH3_initCustomSecret XXH3_initCustomSecret_scalar + +#endif + + + +#ifndef XXH_PREFETCH_DIST +# ifdef __clang__ +# define XXH_PREFETCH_DIST 320 +# else +# if (XXH_VECTOR == XXH_AVX512) +# define XXH_PREFETCH_DIST 512 +# else +# define XXH_PREFETCH_DIST 384 +# endif +# endif /* __clang__ */ +#endif /* XXH_PREFETCH_DIST */ + +/* + * XXH3_accumulate() + * Loops over XXH3_accumulate_512(). + * Assumption: nbStripes will not overflow the secret size + */ +XXH_FORCE_INLINE void +XXH3_accumulate( xxh_u64* XXH_RESTRICT acc, + const xxh_u8* XXH_RESTRICT input, + const xxh_u8* XXH_RESTRICT secret, + size_t nbStripes, + XXH3_f_accumulate_512 f_acc512) +{ + size_t n; + for (n = 0; n < nbStripes; n++ ) { + const xxh_u8* const in = input + n*XXH_STRIPE_LEN; + XXH_PREFETCH(in + XXH_PREFETCH_DIST); + f_acc512(acc, + in, + secret + n*XXH_SECRET_CONSUME_RATE); + } +} + +XXH_FORCE_INLINE void +XXH3_hashLong_internal_loop(xxh_u64* XXH_RESTRICT acc, + const xxh_u8* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble) +{ + size_t const nbStripesPerBlock = (secretSize - XXH_STRIPE_LEN) / XXH_SECRET_CONSUME_RATE; + size_t const block_len = XXH_STRIPE_LEN * nbStripesPerBlock; + size_t const nb_blocks = (len - 1) / block_len; + + size_t n; + + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); + + for (n = 0; n < nb_blocks; n++) { + XXH3_accumulate(acc, input + n*block_len, secret, nbStripesPerBlock, f_acc512); + f_scramble(acc, secret + secretSize - XXH_STRIPE_LEN); + } + + /* last partial block */ + XXH_ASSERT(len > XXH_STRIPE_LEN); + { size_t const nbStripes = ((len - 1) - (block_len * nb_blocks)) / XXH_STRIPE_LEN; + XXH_ASSERT(nbStripes <= (secretSize / XXH_SECRET_CONSUME_RATE)); + XXH3_accumulate(acc, input + nb_blocks*block_len, secret, nbStripes, f_acc512); + + /* last stripe */ + { const xxh_u8* const p = input + len - XXH_STRIPE_LEN; +#define XXH_SECRET_LASTACC_START 7 /* not aligned on 8, last secret is different from acc & scrambler */ + f_acc512(acc, p, secret + secretSize - XXH_STRIPE_LEN - XXH_SECRET_LASTACC_START); + } } +} + +XXH_FORCE_INLINE xxh_u64 +XXH3_mix2Accs(const xxh_u64* XXH_RESTRICT acc, const xxh_u8* XXH_RESTRICT secret) +{ + return XXH3_mul128_fold64( + acc[0] ^ XXH_readLE64(secret), + acc[1] ^ XXH_readLE64(secret+8) ); +} + +static XXH64_hash_t +XXH3_mergeAccs(const xxh_u64* XXH_RESTRICT acc, const xxh_u8* XXH_RESTRICT secret, xxh_u64 start) +{ + xxh_u64 result64 = start; + size_t i = 0; + + for (i = 0; i < 4; i++) { + result64 += XXH3_mix2Accs(acc+2*i, secret + 16*i); +#if defined(__clang__) /* Clang */ \ + && (defined(__arm__) || defined(__thumb__)) /* ARMv7 */ \ + && (defined(__ARM_NEON) || defined(__ARM_NEON__)) /* NEON */ \ + && !defined(XXH_ENABLE_AUTOVECTORIZE) /* Define to disable */ + /* + * UGLY HACK: + * Prevent autovectorization on Clang ARMv7-a. Exact same problem as + * the one in XXH3_len_129to240_64b. Speeds up shorter keys > 240b. + * XXH3_64bits, len == 256, Snapdragon 835: + * without hack: 2063.7 MB/s + * with hack: 2560.7 MB/s + */ + __asm__("" : "+r" (result64)); +#endif + } + + return XXH3_avalanche(result64); +} + +#define XXH3_INIT_ACC { XXH_PRIME32_3, XXH_PRIME64_1, XXH_PRIME64_2, XXH_PRIME64_3, \ + XXH_PRIME64_4, XXH_PRIME32_2, XXH_PRIME64_5, XXH_PRIME32_1 } + +XXH_FORCE_INLINE XXH64_hash_t +XXH3_hashLong_64b_internal(const void* XXH_RESTRICT input, size_t len, + const void* XXH_RESTRICT secret, size_t secretSize, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble) +{ + XXH_ALIGN(XXH_ACC_ALIGN) xxh_u64 acc[XXH_ACC_NB] = XXH3_INIT_ACC; + + XXH3_hashLong_internal_loop(acc, (const xxh_u8*)input, len, (const xxh_u8*)secret, secretSize, f_acc512, f_scramble); + + /* converge into final hash */ + XXH_STATIC_ASSERT(sizeof(acc) == 64); + /* do not align on 8, so that the secret is different from the accumulator */ +#define XXH_SECRET_MERGEACCS_START 11 + XXH_ASSERT(secretSize >= sizeof(acc) + XXH_SECRET_MERGEACCS_START); + return XXH3_mergeAccs(acc, (const xxh_u8*)secret + XXH_SECRET_MERGEACCS_START, (xxh_u64)len * XXH_PRIME64_1); +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + */ +XXH_NO_INLINE XXH64_hash_t +XXH3_hashLong_64b_withSecret(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, const xxh_u8* XXH_RESTRICT secret, size_t secretLen) +{ + (void)seed64; + return XXH3_hashLong_64b_internal(input, len, secret, secretLen, XXH3_accumulate_512, XXH3_scrambleAcc); +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + * Since the function is not inlined, the compiler may not be able to understand that, + * in some scenarios, its `secret` argument is actually a compile time constant. + * This variant enforces that the compiler can detect that, + * and uses this opportunity to streamline the generated code for better performance. + */ +XXH_NO_INLINE XXH64_hash_t +XXH3_hashLong_64b_default(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, const xxh_u8* XXH_RESTRICT secret, size_t secretLen) +{ + (void)seed64; (void)secret; (void)secretLen; + return XXH3_hashLong_64b_internal(input, len, XXH3_kSecret, sizeof(XXH3_kSecret), XXH3_accumulate_512, XXH3_scrambleAcc); +} + +/* + * XXH3_hashLong_64b_withSeed(): + * Generate a custom key based on alteration of default XXH3_kSecret with the seed, + * and then use this key for long mode hashing. + * + * This operation is decently fast but nonetheless costs a little bit of time. + * Try to avoid it whenever possible (typically when seed==0). + * + * It's important for performance that XXH3_hashLong is not inlined. Not sure + * why (uop cache maybe?), but the difference is large and easily measurable. + */ +XXH_FORCE_INLINE XXH64_hash_t +XXH3_hashLong_64b_withSeed_internal(const void* input, size_t len, + XXH64_hash_t seed, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble, + XXH3_f_initCustomSecret f_initSec) +{ + if (seed == 0) + return XXH3_hashLong_64b_internal(input, len, + XXH3_kSecret, sizeof(XXH3_kSecret), + f_acc512, f_scramble); + { XXH_ALIGN(XXH_SEC_ALIGN) xxh_u8 secret[XXH_SECRET_DEFAULT_SIZE]; + f_initSec(secret, seed); + return XXH3_hashLong_64b_internal(input, len, secret, sizeof(secret), + f_acc512, f_scramble); + } +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + */ +XXH_NO_INLINE XXH64_hash_t +XXH3_hashLong_64b_withSeed(const void* input, size_t len, + XXH64_hash_t seed, const xxh_u8* secret, size_t secretLen) +{ + (void)secret; (void)secretLen; + return XXH3_hashLong_64b_withSeed_internal(input, len, seed, + XXH3_accumulate_512, XXH3_scrambleAcc, XXH3_initCustomSecret); +} + + +typedef XXH64_hash_t (*XXH3_hashLong64_f)(const void* XXH_RESTRICT, size_t, + XXH64_hash_t, const xxh_u8* XXH_RESTRICT, size_t); + +XXH_FORCE_INLINE XXH64_hash_t +XXH3_64bits_internal(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, const void* XXH_RESTRICT secret, size_t secretLen, + XXH3_hashLong64_f f_hashLong) +{ + XXH_ASSERT(secretLen >= XXH3_SECRET_SIZE_MIN); + /* + * If an action is to be taken if `secretLen` condition is not respected, + * it should be done here. + * For now, it's a contract pre-condition. + * Adding a check and a branch here would cost performance at every hash. + * Also, note that function signature doesn't offer room to return an error. + */ + if (len <= 16) + return XXH3_len_0to16_64b((const xxh_u8*)input, len, (const xxh_u8*)secret, seed64); + if (len <= 128) + return XXH3_len_17to128_64b((const xxh_u8*)input, len, (const xxh_u8*)secret, secretLen, seed64); + if (len <= XXH3_MIDSIZE_MAX) + return XXH3_len_129to240_64b((const xxh_u8*)input, len, (const xxh_u8*)secret, secretLen, seed64); + return f_hashLong(input, len, seed64, (const xxh_u8*)secret, secretLen); +} + + +/* === Public entry point === */ + +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits(const void* input, size_t len) +{ + return XXH3_64bits_internal(input, len, 0, XXH3_kSecret, sizeof(XXH3_kSecret), XXH3_hashLong_64b_default); +} + +XXH_PUBLIC_API XXH64_hash_t +XXH3_64bits_withSecret(const void* input, size_t len, const void* secret, size_t secretSize) +{ + return XXH3_64bits_internal(input, len, 0, secret, secretSize, XXH3_hashLong_64b_withSecret); +} + +XXH_PUBLIC_API XXH64_hash_t +XXH3_64bits_withSeed(const void* input, size_t len, XXH64_hash_t seed) +{ + return XXH3_64bits_internal(input, len, seed, XXH3_kSecret, sizeof(XXH3_kSecret), XXH3_hashLong_64b_withSeed); +} + + +/* === XXH3 streaming === */ + +/* + * Malloc's a pointer that is always aligned to align. + * + * This must be freed with `XXH_alignedFree()`. + * + * malloc typically guarantees 16 byte alignment on 64-bit systems and 8 byte + * alignment on 32-bit. This isn't enough for the 32 byte aligned loads in AVX2 + * or on 32-bit, the 16 byte aligned loads in SSE2 and NEON. + * + * This underalignment previously caused a rather obvious crash which went + * completely unnoticed due to XXH3_createState() not actually being tested. + * Credit to RedSpah for noticing this bug. + * + * The alignment is done manually: Functions like posix_memalign or _mm_malloc + * are avoided: To maintain portability, we would have to write a fallback + * like this anyways, and besides, testing for the existence of library + * functions without relying on external build tools is impossible. + * + * The method is simple: Overallocate, manually align, and store the offset + * to the original behind the returned pointer. + * + * Align must be a power of 2 and 8 <= align <= 128. + */ +static void* XXH_alignedMalloc(size_t s, size_t align) +{ + XXH_ASSERT(align <= 128 && align >= 8); /* range check */ + XXH_ASSERT((align & (align-1)) == 0); /* power of 2 */ + XXH_ASSERT(s != 0 && s < (s + align)); /* empty/overflow */ + { /* Overallocate to make room for manual realignment and an offset byte */ + xxh_u8* base = (xxh_u8*)XXH_malloc(s + align); + if (base != NULL) { + /* + * Get the offset needed to align this pointer. + * + * Even if the returned pointer is aligned, there will always be + * at least one byte to store the offset to the original pointer. + */ + size_t offset = align - ((size_t)base & (align - 1)); /* base % align */ + /* Add the offset for the now-aligned pointer */ + xxh_u8* ptr = base + offset; + + XXH_ASSERT((size_t)ptr % align == 0); + + /* Store the offset immediately before the returned pointer. */ + ptr[-1] = (xxh_u8)offset; + return ptr; + } + return NULL; + } +} +/* + * Frees an aligned pointer allocated by XXH_alignedMalloc(). Don't pass + * normal malloc'd pointers, XXH_alignedMalloc has a specific data layout. + */ +static void XXH_alignedFree(void* p) +{ + if (p != NULL) { + xxh_u8* ptr = (xxh_u8*)p; + /* Get the offset byte we added in XXH_malloc. */ + xxh_u8 offset = ptr[-1]; + /* Free the original malloc'd pointer */ + xxh_u8* base = ptr - offset; + XXH_free(base); + } +} +XXH_PUBLIC_API XXH3_state_t* XXH3_createState(void) +{ + XXH3_state_t* const state = (XXH3_state_t*)XXH_alignedMalloc(sizeof(XXH3_state_t), 64); + if (state==NULL) return NULL; + XXH3_INITSTATE(state); + return state; +} + +XXH_PUBLIC_API XXH_errorcode XXH3_freeState(XXH3_state_t* statePtr) +{ + XXH_alignedFree(statePtr); + return XXH_OK; +} + +XXH_PUBLIC_API void +XXH3_copyState(XXH3_state_t* dst_state, const XXH3_state_t* src_state) +{ + memcpy(dst_state, src_state, sizeof(*dst_state)); +} + +static void +XXH3_64bits_reset_internal(XXH3_state_t* statePtr, + XXH64_hash_t seed, + const void* secret, size_t secretSize) +{ + size_t const initStart = offsetof(XXH3_state_t, bufferedSize); + size_t const initLength = offsetof(XXH3_state_t, nbStripesPerBlock) - initStart; + XXH_ASSERT(offsetof(XXH3_state_t, nbStripesPerBlock) > initStart); + XXH_ASSERT(statePtr != NULL); + /* set members from bufferedSize to nbStripesPerBlock (excluded) to 0 */ + memset((char*)statePtr + initStart, 0, initLength); + statePtr->acc[0] = XXH_PRIME32_3; + statePtr->acc[1] = XXH_PRIME64_1; + statePtr->acc[2] = XXH_PRIME64_2; + statePtr->acc[3] = XXH_PRIME64_3; + statePtr->acc[4] = XXH_PRIME64_4; + statePtr->acc[5] = XXH_PRIME32_2; + statePtr->acc[6] = XXH_PRIME64_5; + statePtr->acc[7] = XXH_PRIME32_1; + statePtr->seed = seed; + statePtr->extSecret = (const unsigned char*)secret; + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); + statePtr->secretLimit = secretSize - XXH_STRIPE_LEN; + statePtr->nbStripesPerBlock = statePtr->secretLimit / XXH_SECRET_CONSUME_RATE; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_64bits_reset(XXH3_state_t* statePtr) +{ + if (statePtr == NULL) return XXH_ERROR; + XXH3_64bits_reset_internal(statePtr, 0, XXH3_kSecret, XXH_SECRET_DEFAULT_SIZE); + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_64bits_reset_withSecret(XXH3_state_t* statePtr, const void* secret, size_t secretSize) +{ + if (statePtr == NULL) return XXH_ERROR; + XXH3_64bits_reset_internal(statePtr, 0, secret, secretSize); + if (secret == NULL) return XXH_ERROR; + if (secretSize < XXH3_SECRET_SIZE_MIN) return XXH_ERROR; + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_64bits_reset_withSeed(XXH3_state_t* statePtr, XXH64_hash_t seed) +{ + if (statePtr == NULL) return XXH_ERROR; + if (seed==0) return XXH3_64bits_reset(statePtr); + if (seed != statePtr->seed) XXH3_initCustomSecret(statePtr->customSecret, seed); + XXH3_64bits_reset_internal(statePtr, seed, NULL, XXH_SECRET_DEFAULT_SIZE); + return XXH_OK; +} + +/* Note : when XXH3_consumeStripes() is invoked, + * there must be a guarantee that at least one more byte must be consumed from input + * so that the function can blindly consume all stripes using the "normal" secret segment */ +XXH_FORCE_INLINE void +XXH3_consumeStripes(xxh_u64* XXH_RESTRICT acc, + size_t* XXH_RESTRICT nbStripesSoFarPtr, size_t nbStripesPerBlock, + const xxh_u8* XXH_RESTRICT input, size_t nbStripes, + const xxh_u8* XXH_RESTRICT secret, size_t secretLimit, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble) +{ + XXH_ASSERT(nbStripes <= nbStripesPerBlock); /* can handle max 1 scramble per invocation */ + XXH_ASSERT(*nbStripesSoFarPtr < nbStripesPerBlock); + if (nbStripesPerBlock - *nbStripesSoFarPtr <= nbStripes) { + /* need a scrambling operation */ + size_t const nbStripesToEndofBlock = nbStripesPerBlock - *nbStripesSoFarPtr; + size_t const nbStripesAfterBlock = nbStripes - nbStripesToEndofBlock; + XXH3_accumulate(acc, input, secret + nbStripesSoFarPtr[0] * XXH_SECRET_CONSUME_RATE, nbStripesToEndofBlock, f_acc512); + f_scramble(acc, secret + secretLimit); + XXH3_accumulate(acc, input + nbStripesToEndofBlock * XXH_STRIPE_LEN, secret, nbStripesAfterBlock, f_acc512); + *nbStripesSoFarPtr = nbStripesAfterBlock; + } else { + XXH3_accumulate(acc, input, secret + nbStripesSoFarPtr[0] * XXH_SECRET_CONSUME_RATE, nbStripes, f_acc512); + *nbStripesSoFarPtr += nbStripes; + } +} + +/* + * Both XXH3_64bits_update and XXH3_128bits_update use this routine. + */ +XXH_FORCE_INLINE XXH_errorcode +XXH3_update(XXH3_state_t* state, + const xxh_u8* input, size_t len, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble) +{ + if (input==NULL) +#if defined(XXH_ACCEPT_NULL_INPUT_POINTER) && (XXH_ACCEPT_NULL_INPUT_POINTER>=1) + return XXH_OK; +#else + return XXH_ERROR; +#endif + + { const xxh_u8* const bEnd = input + len; + const unsigned char* const secret = (state->extSecret == NULL) ? state->customSecret : state->extSecret; + + state->totalLen += len; + + if (state->bufferedSize + len <= XXH3_INTERNALBUFFER_SIZE) { /* fill in tmp buffer */ + XXH_memcpy(state->buffer + state->bufferedSize, input, len); + state->bufferedSize += (XXH32_hash_t)len; + return XXH_OK; + } + /* total input is now > XXH3_INTERNALBUFFER_SIZE */ + + #define XXH3_INTERNALBUFFER_STRIPES (XXH3_INTERNALBUFFER_SIZE / XXH_STRIPE_LEN) + XXH_STATIC_ASSERT(XXH3_INTERNALBUFFER_SIZE % XXH_STRIPE_LEN == 0); /* clean multiple */ + + /* + * Internal buffer is partially filled (always, except at beginning) + * Complete it, then consume it. + */ + if (state->bufferedSize) { + size_t const loadSize = XXH3_INTERNALBUFFER_SIZE - state->bufferedSize; + XXH_memcpy(state->buffer + state->bufferedSize, input, loadSize); + input += loadSize; + XXH3_consumeStripes(state->acc, + &state->nbStripesSoFar, state->nbStripesPerBlock, + state->buffer, XXH3_INTERNALBUFFER_STRIPES, + secret, state->secretLimit, + f_acc512, f_scramble); + state->bufferedSize = 0; + } + XXH_ASSERT(input < bEnd); + + /* Consume input by a multiple of internal buffer size */ + if (input+XXH3_INTERNALBUFFER_SIZE < bEnd) { + const xxh_u8* const limit = bEnd - XXH3_INTERNALBUFFER_SIZE; + do { + XXH3_consumeStripes(state->acc, + &state->nbStripesSoFar, state->nbStripesPerBlock, + input, XXH3_INTERNALBUFFER_STRIPES, + secret, state->secretLimit, + f_acc512, f_scramble); + input += XXH3_INTERNALBUFFER_SIZE; + } while (inputbuffer + sizeof(state->buffer) - XXH_STRIPE_LEN, input - XXH_STRIPE_LEN, XXH_STRIPE_LEN); + } + XXH_ASSERT(input < bEnd); + + /* Some remaining input (always) : buffer it */ + XXH_memcpy(state->buffer, input, (size_t)(bEnd-input)); + state->bufferedSize = (XXH32_hash_t)(bEnd-input); + } + + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_64bits_update(XXH3_state_t* state, const void* input, size_t len) +{ + return XXH3_update(state, (const xxh_u8*)input, len, + XXH3_accumulate_512, XXH3_scrambleAcc); +} + + +XXH_FORCE_INLINE void +XXH3_digest_long (XXH64_hash_t* acc, + const XXH3_state_t* state, + const unsigned char* secret) +{ + /* + * Digest on a local copy. This way, the state remains unaltered, and it can + * continue ingesting more input afterwards. + */ + memcpy(acc, state->acc, sizeof(state->acc)); + if (state->bufferedSize >= XXH_STRIPE_LEN) { + size_t const nbStripes = (state->bufferedSize - 1) / XXH_STRIPE_LEN; + size_t nbStripesSoFar = state->nbStripesSoFar; + XXH3_consumeStripes(acc, + &nbStripesSoFar, state->nbStripesPerBlock, + state->buffer, nbStripes, + secret, state->secretLimit, + XXH3_accumulate_512, XXH3_scrambleAcc); + /* last stripe */ + XXH3_accumulate_512(acc, + state->buffer + state->bufferedSize - XXH_STRIPE_LEN, + secret + state->secretLimit - XXH_SECRET_LASTACC_START); + } else { /* bufferedSize < XXH_STRIPE_LEN */ + xxh_u8 lastStripe[XXH_STRIPE_LEN]; + size_t const catchupSize = XXH_STRIPE_LEN - state->bufferedSize; + XXH_ASSERT(state->bufferedSize > 0); /* there is always some input buffered */ + memcpy(lastStripe, state->buffer + sizeof(state->buffer) - catchupSize, catchupSize); + memcpy(lastStripe + catchupSize, state->buffer, state->bufferedSize); + XXH3_accumulate_512(acc, + lastStripe, + secret + state->secretLimit - XXH_SECRET_LASTACC_START); + } +} + +XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_digest (const XXH3_state_t* state) +{ + const unsigned char* const secret = (state->extSecret == NULL) ? state->customSecret : state->extSecret; + if (state->totalLen > XXH3_MIDSIZE_MAX) { + XXH_ALIGN(XXH_ACC_ALIGN) XXH64_hash_t acc[XXH_ACC_NB]; + XXH3_digest_long(acc, state, secret); + return XXH3_mergeAccs(acc, + secret + XXH_SECRET_MERGEACCS_START, + (xxh_u64)state->totalLen * XXH_PRIME64_1); + } + /* totalLen <= XXH3_MIDSIZE_MAX: digesting a short input */ + if (state->seed) + return XXH3_64bits_withSeed(state->buffer, (size_t)state->totalLen, state->seed); + return XXH3_64bits_withSecret(state->buffer, (size_t)(state->totalLen), + secret, state->secretLimit + XXH_STRIPE_LEN); +} + + +#define XXH_MIN(x, y) (((x) > (y)) ? (y) : (x)) + +XXH_PUBLIC_API void +XXH3_generateSecret(void* secretBuffer, const void* customSeed, size_t customSeedSize) +{ + XXH_ASSERT(secretBuffer != NULL); + if (customSeedSize == 0) { + memcpy(secretBuffer, XXH3_kSecret, XXH_SECRET_DEFAULT_SIZE); + return; + } + XXH_ASSERT(customSeed != NULL); + + { size_t const segmentSize = sizeof(XXH128_hash_t); + size_t const nbSegments = XXH_SECRET_DEFAULT_SIZE / segmentSize; + XXH128_canonical_t scrambler; + XXH64_hash_t seeds[12]; + size_t segnb; + XXH_ASSERT(nbSegments == 12); + XXH_ASSERT(segmentSize * nbSegments == XXH_SECRET_DEFAULT_SIZE); /* exact multiple */ + XXH128_canonicalFromHash(&scrambler, XXH128(customSeed, customSeedSize, 0)); + + /* + * Copy customSeed to seeds[], truncating or repeating as necessary. + */ + { size_t toFill = XXH_MIN(customSeedSize, sizeof(seeds)); + size_t filled = toFill; + memcpy(seeds, customSeed, toFill); + while (filled < sizeof(seeds)) { + toFill = XXH_MIN(filled, sizeof(seeds) - filled); + memcpy((char*)seeds + filled, seeds, toFill); + filled += toFill; + } } + + /* generate secret */ + memcpy(secretBuffer, &scrambler, sizeof(scrambler)); + for (segnb=1; segnb < nbSegments; segnb++) { + size_t const segmentStart = segnb * segmentSize; + XXH128_canonical_t segment; + XXH128_canonicalFromHash(&segment, + XXH128(&scrambler, sizeof(scrambler), XXH_readLE64(seeds + segnb) + segnb) ); + memcpy((char*)secretBuffer + segmentStart, &segment, sizeof(segment)); + } } +} + + +/* ========================================== + * XXH3 128 bits (a.k.a XXH128) + * ========================================== + * XXH3's 128-bit variant has better mixing and strength than the 64-bit variant, + * even without counting the significantly larger output size. + * + * For example, extra steps are taken to avoid the seed-dependent collisions + * in 17-240 byte inputs (See XXH3_mix16B and XXH128_mix32B). + * + * This strength naturally comes at the cost of some speed, especially on short + * lengths. Note that longer hashes are about as fast as the 64-bit version + * due to it using only a slight modification of the 64-bit loop. + * + * XXH128 is also more oriented towards 64-bit machines. It is still extremely + * fast for a _128-bit_ hash on 32-bit (it usually clears XXH64). + */ + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_len_1to3_128b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + /* A doubled version of 1to3_64b with different constants. */ + XXH_ASSERT(input != NULL); + XXH_ASSERT(1 <= len && len <= 3); + XXH_ASSERT(secret != NULL); + /* + * len = 1: combinedl = { input[0], 0x01, input[0], input[0] } + * len = 2: combinedl = { input[1], 0x02, input[0], input[1] } + * len = 3: combinedl = { input[2], 0x03, input[0], input[1] } + */ + { xxh_u8 const c1 = input[0]; + xxh_u8 const c2 = input[len >> 1]; + xxh_u8 const c3 = input[len - 1]; + xxh_u32 const combinedl = ((xxh_u32)c1 <<16) | ((xxh_u32)c2 << 24) + | ((xxh_u32)c3 << 0) | ((xxh_u32)len << 8); + xxh_u32 const combinedh = XXH_rotl32(XXH_swap32(combinedl), 13); + xxh_u64 const bitflipl = (XXH_readLE32(secret) ^ XXH_readLE32(secret+4)) + seed; + xxh_u64 const bitfliph = (XXH_readLE32(secret+8) ^ XXH_readLE32(secret+12)) - seed; + xxh_u64 const keyed_lo = (xxh_u64)combinedl ^ bitflipl; + xxh_u64 const keyed_hi = (xxh_u64)combinedh ^ bitfliph; + XXH128_hash_t h128; + h128.low64 = XXH64_avalanche(keyed_lo); + h128.high64 = XXH64_avalanche(keyed_hi); + return h128; + } +} + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_len_4to8_128b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(input != NULL); + XXH_ASSERT(secret != NULL); + XXH_ASSERT(4 <= len && len <= 8); + seed ^= (xxh_u64)XXH_swap32((xxh_u32)seed) << 32; + { xxh_u32 const input_lo = XXH_readLE32(input); + xxh_u32 const input_hi = XXH_readLE32(input + len - 4); + xxh_u64 const input_64 = input_lo + ((xxh_u64)input_hi << 32); + xxh_u64 const bitflip = (XXH_readLE64(secret+16) ^ XXH_readLE64(secret+24)) + seed; + xxh_u64 const keyed = input_64 ^ bitflip; + + /* Shift len to the left to ensure it is even, this avoids even multiplies. */ + XXH128_hash_t m128 = XXH_mult64to128(keyed, XXH_PRIME64_1 + (len << 2)); + + m128.high64 += (m128.low64 << 1); + m128.low64 ^= (m128.high64 >> 3); + + m128.low64 = XXH_xorshift64(m128.low64, 35); + m128.low64 *= 0x9FB21C651E98DF25ULL; + m128.low64 = XXH_xorshift64(m128.low64, 28); + m128.high64 = XXH3_avalanche(m128.high64); + return m128; + } +} + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_len_9to16_128b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(input != NULL); + XXH_ASSERT(secret != NULL); + XXH_ASSERT(9 <= len && len <= 16); + { xxh_u64 const bitflipl = (XXH_readLE64(secret+32) ^ XXH_readLE64(secret+40)) - seed; + xxh_u64 const bitfliph = (XXH_readLE64(secret+48) ^ XXH_readLE64(secret+56)) + seed; + xxh_u64 const input_lo = XXH_readLE64(input); + xxh_u64 input_hi = XXH_readLE64(input + len - 8); + XXH128_hash_t m128 = XXH_mult64to128(input_lo ^ input_hi ^ bitflipl, XXH_PRIME64_1); + /* + * Put len in the middle of m128 to ensure that the length gets mixed to + * both the low and high bits in the 128x64 multiply below. + */ + m128.low64 += (xxh_u64)(len - 1) << 54; + input_hi ^= bitfliph; + /* + * Add the high 32 bits of input_hi to the high 32 bits of m128, then + * add the long product of the low 32 bits of input_hi and XXH_PRIME32_2 to + * the high 64 bits of m128. + * + * The best approach to this operation is different on 32-bit and 64-bit. + */ + if (sizeof(void *) < sizeof(xxh_u64)) { /* 32-bit */ + /* + * 32-bit optimized version, which is more readable. + * + * On 32-bit, it removes an ADC and delays a dependency between the two + * halves of m128.high64, but it generates an extra mask on 64-bit. + */ + m128.high64 += (input_hi & 0xFFFFFFFF00000000ULL) + XXH_mult32to64((xxh_u32)input_hi, XXH_PRIME32_2); + } else { + /* + * 64-bit optimized (albeit more confusing) version. + * + * Uses some properties of addition and multiplication to remove the mask: + * + * Let: + * a = input_hi.lo = (input_hi & 0x00000000FFFFFFFF) + * b = input_hi.hi = (input_hi & 0xFFFFFFFF00000000) + * c = XXH_PRIME32_2 + * + * a + (b * c) + * Inverse Property: x + y - x == y + * a + (b * (1 + c - 1)) + * Distributive Property: x * (y + z) == (x * y) + (x * z) + * a + (b * 1) + (b * (c - 1)) + * Identity Property: x * 1 == x + * a + b + (b * (c - 1)) + * + * Substitute a, b, and c: + * input_hi.hi + input_hi.lo + ((xxh_u64)input_hi.lo * (XXH_PRIME32_2 - 1)) + * + * Since input_hi.hi + input_hi.lo == input_hi, we get this: + * input_hi + ((xxh_u64)input_hi.lo * (XXH_PRIME32_2 - 1)) + */ + m128.high64 += input_hi + XXH_mult32to64((xxh_u32)input_hi, XXH_PRIME32_2 - 1); + } + /* m128 ^= XXH_swap64(m128 >> 64); */ + m128.low64 ^= XXH_swap64(m128.high64); + + { /* 128x64 multiply: h128 = m128 * XXH_PRIME64_2; */ + XXH128_hash_t h128 = XXH_mult64to128(m128.low64, XXH_PRIME64_2); + h128.high64 += m128.high64 * XXH_PRIME64_2; + + h128.low64 = XXH3_avalanche(h128.low64); + h128.high64 = XXH3_avalanche(h128.high64); + return h128; + } } +} + +/* + * Assumption: `secret` size is >= XXH3_SECRET_SIZE_MIN + */ +XXH_FORCE_INLINE XXH128_hash_t +XXH3_len_0to16_128b(const xxh_u8* input, size_t len, const xxh_u8* secret, XXH64_hash_t seed) +{ + XXH_ASSERT(len <= 16); + { if (len > 8) return XXH3_len_9to16_128b(input, len, secret, seed); + if (len >= 4) return XXH3_len_4to8_128b(input, len, secret, seed); + if (len) return XXH3_len_1to3_128b(input, len, secret, seed); + { XXH128_hash_t h128; + xxh_u64 const bitflipl = XXH_readLE64(secret+64) ^ XXH_readLE64(secret+72); + xxh_u64 const bitfliph = XXH_readLE64(secret+80) ^ XXH_readLE64(secret+88); + h128.low64 = XXH64_avalanche(seed ^ bitflipl); + h128.high64 = XXH64_avalanche( seed ^ bitfliph); + return h128; + } } +} + +/* + * A bit slower than XXH3_mix16B, but handles multiply by zero better. + */ +XXH_FORCE_INLINE XXH128_hash_t +XXH128_mix32B(XXH128_hash_t acc, const xxh_u8* input_1, const xxh_u8* input_2, + const xxh_u8* secret, XXH64_hash_t seed) +{ + acc.low64 += XXH3_mix16B (input_1, secret+0, seed); + acc.low64 ^= XXH_readLE64(input_2) + XXH_readLE64(input_2 + 8); + acc.high64 += XXH3_mix16B (input_2, secret+16, seed); + acc.high64 ^= XXH_readLE64(input_1) + XXH_readLE64(input_1 + 8); + return acc; +} + + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_len_17to128_128b(const xxh_u8* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH64_hash_t seed) +{ + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); (void)secretSize; + XXH_ASSERT(16 < len && len <= 128); + + { XXH128_hash_t acc; + acc.low64 = len * XXH_PRIME64_1; + acc.high64 = 0; + if (len > 32) { + if (len > 64) { + if (len > 96) { + acc = XXH128_mix32B(acc, input+48, input+len-64, secret+96, seed); + } + acc = XXH128_mix32B(acc, input+32, input+len-48, secret+64, seed); + } + acc = XXH128_mix32B(acc, input+16, input+len-32, secret+32, seed); + } + acc = XXH128_mix32B(acc, input, input+len-16, secret, seed); + { XXH128_hash_t h128; + h128.low64 = acc.low64 + acc.high64; + h128.high64 = (acc.low64 * XXH_PRIME64_1) + + (acc.high64 * XXH_PRIME64_4) + + ((len - seed) * XXH_PRIME64_2); + h128.low64 = XXH3_avalanche(h128.low64); + h128.high64 = (XXH64_hash_t)0 - XXH3_avalanche(h128.high64); + return h128; + } + } +} + +XXH_NO_INLINE XXH128_hash_t +XXH3_len_129to240_128b(const xxh_u8* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH64_hash_t seed) +{ + XXH_ASSERT(secretSize >= XXH3_SECRET_SIZE_MIN); (void)secretSize; + XXH_ASSERT(128 < len && len <= XXH3_MIDSIZE_MAX); + + { XXH128_hash_t acc; + int const nbRounds = (int)len / 32; + int i; + acc.low64 = len * XXH_PRIME64_1; + acc.high64 = 0; + for (i=0; i<4; i++) { + acc = XXH128_mix32B(acc, + input + (32 * i), + input + (32 * i) + 16, + secret + (32 * i), + seed); + } + acc.low64 = XXH3_avalanche(acc.low64); + acc.high64 = XXH3_avalanche(acc.high64); + XXH_ASSERT(nbRounds >= 4); + for (i=4 ; i < nbRounds; i++) { + acc = XXH128_mix32B(acc, + input + (32 * i), + input + (32 * i) + 16, + secret + XXH3_MIDSIZE_STARTOFFSET + (32 * (i - 4)), + seed); + } + /* last bytes */ + acc = XXH128_mix32B(acc, + input + len - 16, + input + len - 32, + secret + XXH3_SECRET_SIZE_MIN - XXH3_MIDSIZE_LASTOFFSET - 16, + 0ULL - seed); + + { XXH128_hash_t h128; + h128.low64 = acc.low64 + acc.high64; + h128.high64 = (acc.low64 * XXH_PRIME64_1) + + (acc.high64 * XXH_PRIME64_4) + + ((len - seed) * XXH_PRIME64_2); + h128.low64 = XXH3_avalanche(h128.low64); + h128.high64 = (XXH64_hash_t)0 - XXH3_avalanche(h128.high64); + return h128; + } + } +} + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_hashLong_128b_internal(const void* XXH_RESTRICT input, size_t len, + const xxh_u8* XXH_RESTRICT secret, size_t secretSize, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble) +{ + XXH_ALIGN(XXH_ACC_ALIGN) xxh_u64 acc[XXH_ACC_NB] = XXH3_INIT_ACC; + + XXH3_hashLong_internal_loop(acc, (const xxh_u8*)input, len, secret, secretSize, f_acc512, f_scramble); + + /* converge into final hash */ + XXH_STATIC_ASSERT(sizeof(acc) == 64); + XXH_ASSERT(secretSize >= sizeof(acc) + XXH_SECRET_MERGEACCS_START); + { XXH128_hash_t h128; + h128.low64 = XXH3_mergeAccs(acc, + secret + XXH_SECRET_MERGEACCS_START, + (xxh_u64)len * XXH_PRIME64_1); + h128.high64 = XXH3_mergeAccs(acc, + secret + secretSize + - sizeof(acc) - XXH_SECRET_MERGEACCS_START, + ~((xxh_u64)len * XXH_PRIME64_2)); + return h128; + } +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + */ +XXH_NO_INLINE XXH128_hash_t +XXH3_hashLong_128b_default(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, + const void* XXH_RESTRICT secret, size_t secretLen) +{ + (void)seed64; (void)secret; (void)secretLen; + return XXH3_hashLong_128b_internal(input, len, XXH3_kSecret, sizeof(XXH3_kSecret), + XXH3_accumulate_512, XXH3_scrambleAcc); +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + */ +XXH_NO_INLINE XXH128_hash_t +XXH3_hashLong_128b_withSecret(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, + const void* XXH_RESTRICT secret, size_t secretLen) +{ + (void)seed64; + return XXH3_hashLong_128b_internal(input, len, (const xxh_u8*)secret, secretLen, + XXH3_accumulate_512, XXH3_scrambleAcc); +} + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_hashLong_128b_withSeed_internal(const void* XXH_RESTRICT input, size_t len, + XXH64_hash_t seed64, + XXH3_f_accumulate_512 f_acc512, + XXH3_f_scrambleAcc f_scramble, + XXH3_f_initCustomSecret f_initSec) +{ + if (seed64 == 0) + return XXH3_hashLong_128b_internal(input, len, + XXH3_kSecret, sizeof(XXH3_kSecret), + f_acc512, f_scramble); + { XXH_ALIGN(XXH_SEC_ALIGN) xxh_u8 secret[XXH_SECRET_DEFAULT_SIZE]; + f_initSec(secret, seed64); + return XXH3_hashLong_128b_internal(input, len, (const xxh_u8*)secret, sizeof(secret), + f_acc512, f_scramble); + } +} + +/* + * It's important for performance that XXH3_hashLong is not inlined. + */ +XXH_NO_INLINE XXH128_hash_t +XXH3_hashLong_128b_withSeed(const void* input, size_t len, + XXH64_hash_t seed64, const void* XXH_RESTRICT secret, size_t secretLen) +{ + (void)secret; (void)secretLen; + return XXH3_hashLong_128b_withSeed_internal(input, len, seed64, + XXH3_accumulate_512, XXH3_scrambleAcc, XXH3_initCustomSecret); +} + +typedef XXH128_hash_t (*XXH3_hashLong128_f)(const void* XXH_RESTRICT, size_t, + XXH64_hash_t, const void* XXH_RESTRICT, size_t); + +XXH_FORCE_INLINE XXH128_hash_t +XXH3_128bits_internal(const void* input, size_t len, + XXH64_hash_t seed64, const void* XXH_RESTRICT secret, size_t secretLen, + XXH3_hashLong128_f f_hl128) +{ + XXH_ASSERT(secretLen >= XXH3_SECRET_SIZE_MIN); + /* + * If an action is to be taken if `secret` conditions are not respected, + * it should be done here. + * For now, it's a contract pre-condition. + * Adding a check and a branch here would cost performance at every hash. + */ + if (len <= 16) + return XXH3_len_0to16_128b((const xxh_u8*)input, len, (const xxh_u8*)secret, seed64); + if (len <= 128) + return XXH3_len_17to128_128b((const xxh_u8*)input, len, (const xxh_u8*)secret, secretLen, seed64); + if (len <= XXH3_MIDSIZE_MAX) + return XXH3_len_129to240_128b((const xxh_u8*)input, len, (const xxh_u8*)secret, secretLen, seed64); + return f_hl128(input, len, seed64, secret, secretLen); +} + + +/* === Public XXH128 API === */ + +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits(const void* input, size_t len) +{ + return XXH3_128bits_internal(input, len, 0, + XXH3_kSecret, sizeof(XXH3_kSecret), + XXH3_hashLong_128b_default); +} + +XXH_PUBLIC_API XXH128_hash_t +XXH3_128bits_withSecret(const void* input, size_t len, const void* secret, size_t secretSize) +{ + return XXH3_128bits_internal(input, len, 0, + (const xxh_u8*)secret, secretSize, + XXH3_hashLong_128b_withSecret); +} + +XXH_PUBLIC_API XXH128_hash_t +XXH3_128bits_withSeed(const void* input, size_t len, XXH64_hash_t seed) +{ + return XXH3_128bits_internal(input, len, seed, + XXH3_kSecret, sizeof(XXH3_kSecret), + XXH3_hashLong_128b_withSeed); +} + +XXH_PUBLIC_API XXH128_hash_t +XXH128(const void* input, size_t len, XXH64_hash_t seed) +{ + return XXH3_128bits_withSeed(input, len, seed); +} + + +/* === XXH3 128-bit streaming === */ + +/* + * All the functions are actually the same as for 64-bit streaming variant. + * The only difference is the finalizatiom routine. + */ + +static void +XXH3_128bits_reset_internal(XXH3_state_t* statePtr, + XXH64_hash_t seed, + const void* secret, size_t secretSize) +{ + XXH3_64bits_reset_internal(statePtr, seed, secret, secretSize); +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_128bits_reset(XXH3_state_t* statePtr) +{ + if (statePtr == NULL) return XXH_ERROR; + XXH3_128bits_reset_internal(statePtr, 0, XXH3_kSecret, XXH_SECRET_DEFAULT_SIZE); + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_128bits_reset_withSecret(XXH3_state_t* statePtr, const void* secret, size_t secretSize) +{ + if (statePtr == NULL) return XXH_ERROR; + XXH3_128bits_reset_internal(statePtr, 0, secret, secretSize); + if (secret == NULL) return XXH_ERROR; + if (secretSize < XXH3_SECRET_SIZE_MIN) return XXH_ERROR; + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_128bits_reset_withSeed(XXH3_state_t* statePtr, XXH64_hash_t seed) +{ + if (statePtr == NULL) return XXH_ERROR; + if (seed==0) return XXH3_128bits_reset(statePtr); + if (seed != statePtr->seed) XXH3_initCustomSecret(statePtr->customSecret, seed); + XXH3_128bits_reset_internal(statePtr, seed, NULL, XXH_SECRET_DEFAULT_SIZE); + return XXH_OK; +} + +XXH_PUBLIC_API XXH_errorcode +XXH3_128bits_update(XXH3_state_t* state, const void* input, size_t len) +{ + return XXH3_update(state, (const xxh_u8*)input, len, + XXH3_accumulate_512, XXH3_scrambleAcc); +} + +XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_digest (const XXH3_state_t* state) +{ + const unsigned char* const secret = (state->extSecret == NULL) ? state->customSecret : state->extSecret; + if (state->totalLen > XXH3_MIDSIZE_MAX) { + XXH_ALIGN(XXH_ACC_ALIGN) XXH64_hash_t acc[XXH_ACC_NB]; + XXH3_digest_long(acc, state, secret); + XXH_ASSERT(state->secretLimit + XXH_STRIPE_LEN >= sizeof(acc) + XXH_SECRET_MERGEACCS_START); + { XXH128_hash_t h128; + h128.low64 = XXH3_mergeAccs(acc, + secret + XXH_SECRET_MERGEACCS_START, + (xxh_u64)state->totalLen * XXH_PRIME64_1); + h128.high64 = XXH3_mergeAccs(acc, + secret + state->secretLimit + XXH_STRIPE_LEN + - sizeof(acc) - XXH_SECRET_MERGEACCS_START, + ~((xxh_u64)state->totalLen * XXH_PRIME64_2)); + return h128; + } + } + /* len <= XXH3_MIDSIZE_MAX : short code */ + if (state->seed) + return XXH3_128bits_withSeed(state->buffer, (size_t)state->totalLen, state->seed); + return XXH3_128bits_withSecret(state->buffer, (size_t)(state->totalLen), + secret, state->secretLimit + XXH_STRIPE_LEN); +} + +/* 128-bit utility functions */ + +#include /* memcmp, memcpy */ + +/* return : 1 is equal, 0 if different */ +XXH_PUBLIC_API int XXH128_isEqual(XXH128_hash_t h1, XXH128_hash_t h2) +{ + /* note : XXH128_hash_t is compact, it has no padding byte */ + return !(memcmp(&h1, &h2, sizeof(h1))); +} + +/* This prototype is compatible with stdlib's qsort(). + * return : >0 if *h128_1 > *h128_2 + * <0 if *h128_1 < *h128_2 + * =0 if *h128_1 == *h128_2 */ +XXH_PUBLIC_API int XXH128_cmp(const void* h128_1, const void* h128_2) +{ + XXH128_hash_t const h1 = *(const XXH128_hash_t*)h128_1; + XXH128_hash_t const h2 = *(const XXH128_hash_t*)h128_2; + int const hcmp = (h1.high64 > h2.high64) - (h2.high64 > h1.high64); + /* note : bets that, in most cases, hash values are different */ + if (hcmp) return hcmp; + return (h1.low64 > h2.low64) - (h2.low64 > h1.low64); +} + + +/*====== Canonical representation ======*/ +XXH_PUBLIC_API void +XXH128_canonicalFromHash(XXH128_canonical_t* dst, XXH128_hash_t hash) +{ + XXH_STATIC_ASSERT(sizeof(XXH128_canonical_t) == sizeof(XXH128_hash_t)); + if (XXH_CPU_LITTLE_ENDIAN) { + hash.high64 = XXH_swap64(hash.high64); + hash.low64 = XXH_swap64(hash.low64); + } + memcpy(dst, &hash.high64, sizeof(hash.high64)); + memcpy((char*)dst + sizeof(hash.high64), &hash.low64, sizeof(hash.low64)); +} + +XXH_PUBLIC_API XXH128_hash_t +XXH128_hashFromCanonical(const XXH128_canonical_t* src) +{ + XXH128_hash_t h; + h.high64 = XXH_readBE64(src); + h.low64 = XXH_readBE64(src->digest + 8); + return h; +} + +/* Pop our optimization override from above */ +#if XXH_VECTOR == XXH_AVX2 /* AVX2 */ \ + && defined(__GNUC__) && !defined(__clang__) /* GCC, not Clang */ \ + && defined(__OPTIMIZE__) && !defined(__OPTIMIZE_SIZE__) /* respect -O0 and -Os */ +# pragma GCC pop_options +#endif + +#endif /* XXH_NO_LONG_LONG */ + + +#endif /* XXH_IMPLEMENTATION */ + + +#if defined (__cplusplus) +} +#endif diff --git a/packages/crypto/tests/Crypto/Ethereum/Test/EIP712SignatureSpec.hs b/packages/crypto/tests/Crypto/Ethereum/Test/EIP712SignatureSpec.hs new file mode 100644 index 00000000..cead1dc4 --- /dev/null +++ b/packages/crypto/tests/Crypto/Ethereum/Test/EIP712SignatureSpec.hs @@ -0,0 +1,220 @@ +{-# LANGUAGE ImpredicativeTypes #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE TypeApplications #-} + +-- | +-- Module : Crypto.Ethereum.Test.EIP712SignatureSpec +-- Copyright : Jin Chui 2025 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me jinchui@pm.me +-- Stability : experimental +-- Portability : unportable +-- + +module Crypto.Ethereum.Test.EIP712SignatureSpec (spec) where + +import Crypto.Ethereum.Eip712Signature +import Crypto.Ethereum.Utils (keccak256) +import Data.Aeson (toJSON) +import qualified Data.Aeson as Aeson +import qualified Data.Aeson.KeyMap as Aeson +import qualified Data.ByteArray.Encoding as BAE +import Data.ByteString (ByteString) +import Data.Either (fromRight) +import Test.Hspec + +encodeTypeConcrete :: EIP712Types -> EIP712Name -> Either String ByteString +encodeTypeConcrete = encodeType + +keccak256Concrete :: ByteString -> ByteString +keccak256Concrete = keccak256 + +hexEncode :: ByteString -> ByteString +hexEncode = BAE.convertToBase BAE.Base16 + +encodeDataConcrete :: EIP712Types -> EIP712Name -> Aeson.Object -> Either String ByteString +encodeDataConcrete = encodeData + +hashStructConcrete :: EIP712Types -> EIP712Name -> Aeson.Object -> Either String ByteString +hashStructConcrete = hashStruct + +mailTypes :: EIP712Types +mailTypes = + [ EIP712Struct + { eip712StructName = "Mail" + , eip712StructFields = + [ EIP712Field "from" (FieldTypeStruct "Person") + , EIP712Field "to" (FieldTypeStruct "Person") + , EIP712Field "contents" FieldTypeString + ] + } + , EIP712Struct + { eip712StructName = "Person" + , eip712StructFields = + [ EIP712Field "name" FieldTypeString + , EIP712Field "wallet" FieldTypeAddress + ] + } + , EIP712Struct + { eip712StructName = "EIP712Domain" + , eip712StructFields = + [ EIP712Field "name" FieldTypeString + , EIP712Field "version" FieldTypeString + , EIP712Field "chainId" (FieldTypeUInt Si256) + , EIP712Field "verifyingContract" FieldTypeAddress + ] + } + ] + +nestedArrayTypes :: EIP712Types +nestedArrayTypes = + [ EIP712Struct + { eip712StructName = "foo" + , eip712StructFields = + [ EIP712Field "a" (FieldTypeArray (FieldTypeArray (FieldTypeUInt Si256))) + , EIP712Field "b" FieldTypeString + ] + } + ] + +safeTxType :: EIP712Struct +safeTxType = + EIP712Struct + { eip712StructName = "SafeTx" + , eip712StructFields = + [ EIP712Field "to" FieldTypeAddress + , EIP712Field "value" (FieldTypeUInt Si256) + , EIP712Field "data" FieldTypeBytes + , EIP712Field "operation" (FieldTypeUInt Si8) + , EIP712Field "safeTxGas" (FieldTypeUInt Si256) + , EIP712Field "baseGas" (FieldTypeUInt Si256) + , EIP712Field "gasPrice" (FieldTypeUInt Si256) + , EIP712Field "gasToken" FieldTypeAddress + , EIP712Field "refundReceiver" FieldTypeAddress + , EIP712Field "nonce" (FieldTypeUInt Si256) + ] + } + +expectedEncodedSafeTxType :: ByteString +expectedEncodedSafeTxType = "SafeTx(\ + \address to,\ + \uint256 value,\ + \bytes data,\ + \uint8 operation,\ + \uint256 safeTxGas,\ + \uint256 baseGas,\ + \uint256 gasPrice,\ + \address gasToken,\ + \address refundReceiver,\ + \uint256 nonce)" + +safeDomainType :: EIP712Struct +safeDomainType = + EIP712Struct + { eip712StructName = "EIP712Domain" + , eip712StructFields = + [ EIP712Field "chainId" (FieldTypeUInt Si256) + , EIP712Field "verifyingContract" FieldTypeAddress + ] + } + +safeDomain :: Aeson.KeyMap Aeson.Value +safeDomain = + Aeson.fromList + [("chainId", toJSON @Int 8453), ("verifyingContract", toJSON @String "0xCD2a3d9F938E13CD947Ec05AbC7FE734Df8DD826")] + +expectedEncodedSafeDomain :: ByteString +expectedEncodedSafeDomain = "0000000000000000000000000000000000000000000000000000000000002105\ + \000000000000000000000000cd2a3d9f938e13cd947ec05abc7fe734df8dd826" + +safeMessage :: Aeson.KeyMap Aeson.Value +safeMessage = + Aeson.fromList + [ ("to",toJSON @String "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" ) + , ("value", toJSON @Integer 0 ) + , ("data", toJSON @String "0x0b89085a01a3b67d2231c6a136f9c8eea75d7d479a83a127356f8540ee15af010c22b846886e98aeffc1f1166d4b3586") + , ("operation", toJSON @Integer 0) + , ("safeTxGas", toJSON @Integer 0) + , ("baseGas", toJSON @Integer 0) + , ("gasPrice", toJSON @Integer 0) + , ("gasToken", toJSON @String "0x0000000000000000000000000000000000000000") + , ("refundReceiver", toJSON @String "0x0000000000000000000000000000000000000000") + , ("nonce", toJSON (37 :: Integer)) + ] + +expectedEncodedSafeMessage :: ByteString +expectedEncodedSafeMessage = "000000000000000000000000aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \059c15417e7e213ad30596d872d2e906e4feafd54fa0c9ac864b421ab1ba5adb\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000000\ + \0000000000000000000000000000000000000000000000000000000000000025" + +safeTxTypedData :: EIP712TypedData +safeTxTypedData = EIP712TypedData + { typedDataTypes = [safeTxType, safeDomainType] + , typedDataPrimaryType = "SafeTx" + , typedDataDomain = safeDomain + , typedDataMessage = safeMessage + } + + +spec :: Spec +spec = do + describe "encodeType" $ do + it "simple types should be encoding properly" $ do + let eip712structs = mailTypes + encodeTypeConcrete eip712structs "Person" `shouldBe` Right "Person(string name,address wallet)" + encodeTypeConcrete eip712structs "Mail" + `shouldBe` Right "Mail(Person from,Person to,string contents)Person(string name,address wallet)" + encodeTypeConcrete eip712structs "EIP712Domain" + `shouldBe` Right "EIP712Domain(string name,string version,uint256 chainId,address verifyingContract)" + it "should work for Safe transactions" $ do + + encodeTypeConcrete [safeDomainType] "EIP712Domain" `shouldBe` Right "EIP712Domain(uint256 chainId,address verifyingContract)" + hexEncode . keccak256Concrete <$> encodeTypeConcrete [safeDomainType] "EIP712Domain" + `shouldBe` Right "47e79534a245952e8b16893a336b85a3d9ea9fa8c573f3d803afb92a79469218" + hexEncode <$> hashStruct [safeDomainType] "EIP712Domain" safeDomain + `shouldBe` Right "b3a3e869527602e68d877d9edcc629823648c73a3b10ee1e23cf4ab81b599cf5" + + it "should work for safe transaction" $ encodeTypeConcrete [safeTxType] "SafeTx" + `shouldBe` Right expectedEncodedSafeTxType + + describe "encodeData" $ do + it "should encode simple data" $ do + let eip712structs = mailTypes + let typeName = "Person" + let message = + Aeson.fromList + [("name", toJSON ("Cow" :: String)), ("wallet", toJSON ("0xCD2a3d9F938E13CD947Ec05AbC7FE734Df8DD826" :: String))] + let encodedDataOrError = encodeDataConcrete eip712structs typeName message + let expectedEncodedData = "8c1d2bd5348394761719da11ec67eedae9502d137e8940fee8ecd6f641ee1648\ + \000000000000000000000000cd2a3d9f938e13cd947ec05abc7fe734df8dd826" + hexEncode <$> encodedDataOrError `shouldBe` Right expectedEncodedData + hashStructConcrete eip712structs "Person" message + `shouldBe` Right (keccak256Concrete $ keccak256Concrete "Person(string name,address wallet)" <> fromRight undefined encodedDataOrError) + + it "should encode nested arrays" $ do + let message = + Aeson.fromList + [ ("a", toJSON [[35 :: Int, 36], [37]]) + , ("b", toJSON ("hello" :: String)) + ] + encodeTypeConcrete nestedArrayTypes "foo" `shouldBe` Right "foo(uint256[][] a,string b)" + let expectedDataEncoded = "fa5ffe3a0504d850bc7c9eeda1cf960b596b73f4dc0272a6fa89dace08e32029\ + \1c8aff950685c2ed4bc3174f3472287b56d9517b9c948127319a09a7a36deac8" + hexEncode <$> encodeDataConcrete nestedArrayTypes "foo" message `shouldBe` Right expectedDataEncoded + it "should encode Safe domain" $ + (hexEncode <$> encodeDataConcrete [safeDomainType] "EIP712Domain" safeDomain) `shouldBe` Right expectedEncodedSafeDomain + + it "should encode Safe transaction" $ + (hexEncode <$> encodeDataConcrete [safeTxType] "SafeTx" safeMessage) `shouldBe` Right expectedEncodedSafeMessage + + + describe "typedDataSignHash" $ it "encode properly a safe transaction" $ do + hexEncode <$> typedDataSignHash safeTxTypedData `shouldBe` Right "cd3b59061dd8a7060486fb14e75e2f066a19a6e93f6888dbf83c77fbfeb8874b" diff --git a/packages/crypto/tests/Crypto/Ethereum/Test/KeyfileSpec.hs b/packages/crypto/tests/Crypto/Ethereum/Test/KeyfileSpec.hs new file mode 100644 index 00000000..113f7c68 --- /dev/null +++ b/packages/crypto/tests/Crypto/Ethereum/Test/KeyfileSpec.hs @@ -0,0 +1,110 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Ethereum.Test.KeyfileSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Crypto.Ethereum.Test.KeyfileSpec where + +import Data.Aeson (eitherDecode) +import Data.ByteString (ByteString) +import qualified Data.ByteString.Lazy as L (ByteString) +import Data.UUID.Types (UUID) +import Test.Hspec + +import Crypto.Ethereum.Keyfile +import Data.ByteArray.HexString (HexString) + +pbkdf2_test_keyfile :: L.ByteString +pbkdf2_test_keyfile = "\ +\{\ +\ \"crypto\" : {\ +\ \"cipher\" : \"aes-128-ctr\",\ +\ \"cipherparams\" : {\ +\ \"iv\" : \"6087dab2f9fdbbfaddc31a909735c1e6\"\ +\ },\ +\ \"ciphertext\" : \"5318b4d5bcd28de64ee5559e671353e16f075ecae9f99c7a79a38af5f869aa46\",\ +\ \"kdf\" : \"pbkdf2\",\ +\ \"kdfparams\" : {\ +\ \"c\" : 262144,\ +\ \"dklen\" : 32,\ +\ \"prf\" : \"hmac-sha256\",\ +\ \"salt\" : \"ae3cd4e7013836a3df6bd7241b12db061dbe2c6785853cce422d148a624ce0bd\"\ +\ },\ +\ \"mac\" : \"517ead924a9d0dc3124507e3393d175ce3ff7c1e96529c6c555ce9e51205e9b2\"\ +\ },\ +\ \"id\" : \"3198bc9c-6672-5ab3-d995-4942343ae5b6\",\ +\ \"version\" : 3\ +\}" + +scrypt_test_keyfile :: L.ByteString +scrypt_test_keyfile = "\ +\{\ +\ \"crypto\" : {\ +\ \"cipher\" : \"aes-128-ctr\",\ +\ \"cipherparams\" : {\ +\ \"iv\" : \"83dbcc02d8ccb40e466191a123791e0e\"\ +\ },\ +\ \"ciphertext\" : \"d172bf743a674da9cdad04534d56926ef8358534d458fffccd4e6ad2fbde479c\",\ +\ \"kdf\" : \"scrypt\",\ +\ \"kdfparams\" : {\ +\ \"dklen\" : 32,\ +\ \"n\" : 262144,\ +\ \"r\" : 1,\ +\ \"p\" : 8,\ +\ \"salt\" : \"ab0c7876052600dd703518d6fc3fe8984592145b591fc8fb5c6d43190334ba19\"\ +\ },\ +\ \"mac\" : \"2103ac29920d71da29f15d75b4a16dbe95cfd7ff8faea1056c33131d846e3097\"\ +\ },\ +\ \"id\" : \"3198bc9c-6672-5ab3-d995-4942343ae5b6\",\ +\ \"version\" : 3\ +\}" + +test_uuid :: UUID +test_uuid = read "3198bc9c-6672-5ab3-d995-4942343ae5b6" + +test_pbkdf2_mac :: HexString +test_pbkdf2_mac = "517ead924a9d0dc3124507e3393d175ce3ff7c1e96529c6c555ce9e51205e9b2" + +test_scrypt_mac :: HexString +test_scrypt_mac = "2103ac29920d71da29f15d75b4a16dbe95cfd7ff8faea1056c33131d846e3097" + +test_password :: ByteString +test_password = "testpassword" + +test_private :: HexString +test_private = "7a28b5ba57c53603b0b07b56bba752f7784bf506fa95edc395f5cf6c7514fe9d" + +spec :: Spec +spec = parallel $ do + describe "AES-128-CTR and PBKDF2-SHA-256" $ do + it "can decode keyfile" $ + case eitherDecode pbkdf2_test_keyfile of + Left e -> error e + Right ekey -> do + encryptedKeyId ekey `shouldBe` test_uuid + encryptedKeyMac ekey `shouldBe` test_pbkdf2_mac + + it "can decrypt keyfile" $ do + case eitherDecode pbkdf2_test_keyfile of + Left e -> error e + Right ekey -> decrypt ekey test_password `shouldBe` Just test_private + + describe "AES-128-CTR and Scrypt" $ do + it "can decode keyfile" $ + case eitherDecode scrypt_test_keyfile of + Left e -> error e + Right ekey -> do + encryptedKeyId ekey `shouldBe` test_uuid + encryptedKeyMac ekey `shouldBe` test_scrypt_mac + + it "can decrypt keyfile" $ + case eitherDecode scrypt_test_keyfile of + Left e -> error e + Right ekey -> decrypt ekey test_password `shouldBe` Just test_private diff --git a/packages/crypto/tests/Crypto/Ethereum/Test/SignatureSpec.hs b/packages/crypto/tests/Crypto/Ethereum/Test/SignatureSpec.hs new file mode 100644 index 00000000..6b227bb9 --- /dev/null +++ b/packages/crypto/tests/Crypto/Ethereum/Test/SignatureSpec.hs @@ -0,0 +1,48 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Ethereum.Test.SignatureSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Crypto.Ethereum.Test.SignatureSpec where + +import Crypto.Ecdsa.Utils (importKey) +import Crypto.Ethereum.Signature (hashMessage, signMessage) +import Data.ByteArray (convert) +import Data.ByteArray.HexString (HexString) +import Data.Foldable (for_) +import Test.Hspec + +test_vector :: [(HexString, HexString, HexString)] +test_vector = [ + ("0xa8510b592963f52d2d8b3413ab5822111c68d45370f6104a869fe6e72c58952fe6b420115a9dfadaae2956ad761db2f113", "0x5cc3704a552b40515909a220d3cb91e850d4d6c6c0180424e433d00400612ed6", "0x3477bfac3621680c30cf3ad59da9288bc53e46773af4911592c6f3b2ba9029861fac19b0fa0cc543731133346eb817cd7f3aa4cabac5e613919567bc9704af861c"), + ("0x5680f1d195bbe2b0f1601a039ad23a6ad488c1f0949a68e84bffe398ad", "0xcaf03f0aa6862758e526dd76782a4afa7ad48533f00f8f9e8731d4a6b1656d9f", "0x659263cb4d54c653e5ef41550f959e15a71b01f19bce88750c8c3cad8ab293d12138db412f471df6c67575d49e9c25b6973a3405396a3e6985a3f391efee74751c"), + ("0x487f9a", "0xa13bf6fdb2e2a5790f4a80d822180c7851b227d16c1893de2359dc98b1e27756", "0x143da940f9e144218979074cfde306d0697b3ddaec4c5e464a5aa093733f957776ba158ec4492a6cdc9951c6e0c1b10040916cb503ad240ed3b76677f9ac4ad41c"), + ("0x958c2c5bafc5eb97004774f4c9b56aaecd37c06befac0042a93c67", "0x496b49cc02b63f927f2669a32dece10876e1a33dc0bd684f7643f849ecbe7c73", "0x34e768e959b89d305f16f796d0ff2da4e5923d6a6f33ba66b29471953e10be1a183743fb764f806ca8d97ad29dad94115d0368f374d5e085348267cc1c5bce411b"), + ("0x02e2", "0x0425c9ac326acac4b93ff871f22c1dfe69c05038c2ac5b9eadb7e09743baa603", "0xbf52108b598a02aeeea1f9ee84947300985953edcfd07351f038bfe0de4c62df5cf467caaa7a33c3c4ebdf4aeaf05b1f4674f6b82b27e87fbf8d2a0980e68f1d1b"), + ("0x74391586ff29f0638d7f7971640cefac3bfa3865ec5310e15a", "0x104432a31597e399f3f0f34e70b52a062feeb65aa3ad5383d2d7b90b0ab50126", "0x78c81fff1acdd1773badea5f35b0149e14b3dffe8de0e554b0edd80526acd55f1fc315b96afe5964df24f28b756f5651a6a52b2b9e0ffc87cda2a4a8f448a8951c"), + ("0xd3ba712ef9dd8f8b37d805a9d1c2b5ee92db66dda0fd8582d55cec1b2519d18dfff2333e29081e80544af7244f2f22", "0x330ee59f080c59252218d1245029d8689b48b021dcf2c438938264bbc61d05af", "0xcf96a0f05e40d05ebcedbff0af522a68e6c846e63b44245a1208592ddf03cc12136ad522656f08fd838c55ff78e093d387d23b30b88a57e467636e63c786e04e1c"), + ("0x1e99da3e7bb02e1f239bbf0b2ea113848673dd52da24c87f2f40", "0x52c58101fe861f9292fb6ad3df74551b5fb3feca9983b108645a5a9354bfbe99", "0x8eebcef599eb67e9379e7d6b074123628c1a65f1b754647704eb003fa61aff0a0e5c79fb022970fea80409e20a12bd4b8e1a79a787394a547fbc93c2d3c1e2dc1c"), + ("0x1e973d1b5b158acc7d710099700c793e702b215a1fa534317d5c44406000fc727c", "0x1280413acfcd88a97b759e72e60069a1dc4f0a595e815aad9a1a83fa73f81af2", "0x7a77a37f2f4378dab5a0ba7f55b858a2a116f885f2eeab30dcd0b6d1f7286fbb7cbdccbd52721ce68fbcf2448a2f450a6bc6bc7f0027906259821bb3800133181b"), + ("0x95da865540bd1336402a325a0435a920768f47d4b1ec0d89e0063f811872d1cb6423b5f4a4b931c9f41b216def", "0x0d537e54120ea923621225e3114b91a568a1abe7b7315b642017cad28cfad40b", "0xe04196529154ab89ceb598654f7d1ae178ecdcf73395aa8e8abb9200b504c39c58a93a6e502aaaddc2cbd712b436e9c9fb1010323927835ac54a7a77f11957f91c"), + ("0x5f6f0fb4805de6c07057", "0x2fe8fc66c90cca91bb502d4ab3d9ecec1621ee1d3c3e5837d98fbd1e08484980", "0x5f1760725b719a0f4f06078868511b397d87b7e3a76aa95671ac774587b5d68a000894b31c26288e67190910b7589b36d3ce7d182b8dc4b903e06284ea61fc811b"), + ("0x64ee1efda1b47bd975f7b14737", "0x8bd280c92fdf874ed9cf46616a2da0ce383c3c9c93daa599844168e6883f527d", "0x00f47d9633245b095ba5f9fa8e4f71a02bff785469f0dd1a3b146578d84061c17a4283bea20c54c2c27e8975e51311d6556acd9c19a783cccc0934d4c7592ba61b") + ] + +test_key :: HexString +test_key = "29461542faa1acbc968bcb332115e0537c023f8df416317602ca5d15ca12d02d" + +spec :: Spec +spec = parallel $ do + describe "Ethereum ECDSA" $ do + it "can hash Ethereum prefixed message" $ for_ test_vector $ \(msg, msgHash, _) -> + convert (hashMessage msg) `shouldBe` msgHash + + it "can sign Ethereum prefixed message" $ for_ test_vector $ \(msg, _, msgSig) -> + signMessage (importKey test_key) msg `shouldBe` msgSig diff --git a/packages/crypto/tests/Crypto/Random/Test/HmacDrbgSpec.hs b/packages/crypto/tests/Crypto/Random/Test/HmacDrbgSpec.hs new file mode 100644 index 00000000..5faabe59 --- /dev/null +++ b/packages/crypto/tests/Crypto/Random/Test/HmacDrbgSpec.hs @@ -0,0 +1,36 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Crypto.Random.Test.HmacDrbgSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Inspired by https://github.com/indutny/hmac-drbg +-- + +module Crypto.Random.Test.HmacDrbgSpec where + +import Crypto.Hash.Algorithms (SHA256) +import Crypto.Random (randomBytesGenerate) +import Data.ByteString (ByteString) +import Test.Hspec + +import Crypto.Random.HmacDrbg +import Data.ByteArray.HexString (HexString) + +spec :: Spec +spec = parallel $ do + describe "HMAC-DRBG-SHA256" $ do + it "indutny/hmac-drbg test vectors" $ do + let doDrbg :: ByteString -> HexString + doDrbg seed = fst (randomBytesGenerate 32 (initialize seed) :: (HexString, HmacDrbg SHA256)) + + doDrbg "totally random0123456789secret noncemy drbg" + `shouldBe` "018ec5f8e08c41e5ac974eb129ac297c5388ee1864324fa13d9b15cf98d9a157" + + doDrbg "totally random0123456789secret nonce" + `shouldBe` "ed5d61ecf0ef38258e62f03bbb49f19f2cd07ba5145a840d83b134d5963b3633" diff --git a/packages/crypto/tests/Data/Digest/Test/Blake2Spec.hs b/packages/crypto/tests/Data/Digest/Test/Blake2Spec.hs new file mode 100644 index 00000000..18cdf9f7 --- /dev/null +++ b/packages/crypto/tests/Data/Digest/Test/Blake2Spec.hs @@ -0,0 +1,38 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.Digest.Test.Blake2Spec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.Digest.Test.Blake2Spec where + +import Data.ByteArray (convert) +import Data.ByteArray.HexString (HexString) +import Test.Hspec + +import Data.Digest.Blake2 + +spec :: Spec +spec = parallel $ do + describe "Variable lenght Blake2" $ do + it "64-bit output (Blake2b 64)" $ + let hash = convert (blake2_64 "abc") :: HexString + in hash `shouldBe` "0xd8bb14d833d59559" + + it "128-bit output (Blake2b 128)" $ + let hash = convert (blake2_128 "abc") :: HexString + in hash `shouldBe` "0xcf4ab791c62b8d2b2109c90275287816" + + it "256-bit output (Blake2b 256)" $ + let hash = convert (blake2_256 "abc") :: HexString + in hash `shouldBe` "0xbddd813c634239723171ef3fee98579b94964e3bb1cb3e427262c8c068d52319" + + it "512-bit output (Blake2b 512)" $ + let hash = convert (blake2_512 "abc") :: HexString + in hash `shouldBe` "0xba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923" diff --git a/packages/crypto/tests/Data/Digest/Test/XXHashSpec.hs b/packages/crypto/tests/Data/Digest/Test/XXHashSpec.hs new file mode 100644 index 00000000..44595a13 --- /dev/null +++ b/packages/crypto/tests/Data/Digest/Test/XXHashSpec.hs @@ -0,0 +1,43 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.Digest.Test.XXHashSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.Digest.Test.XXHashSpec where + +import Data.ByteArray (convert) +import Test.Hspec + +import Data.ByteArray.HexString (HexString) +import Data.Digest.XXHash (xxhash) + +spec :: Spec +spec = parallel $ do + describe "Variable lenght Twox" $ do + it "64-bit output (Twox64)" $ do + let hash = convert (xxhash 32 "abc") :: HexString + hash `shouldBe` "0x990977adf52cbc44" + + let hash' = convert (xxhash 64 "abc") :: HexString + hash' `shouldBe` "0x990977adf52cbc44" + + it "128-bit output (Twox128)" $ do + let hash = convert (xxhash 65 "abc") :: HexString + hash `shouldBe` "0x990977adf52cbc440889329981caa9be" + + let hash' = convert (xxhash 128 "abc") :: HexString + hash' `shouldBe` "0x990977adf52cbc440889329981caa9be" + + it "256-bit output (Twox256)" $ do + let hash = convert (xxhash 255 "abc") :: HexString + hash `shouldBe` "0x990977adf52cbc440889329981caa9bef7da5770b2b8a05303b75d95360dd62b" + + let hash' = convert (xxhash 256 "abc") :: HexString + hash' `shouldBe` "0x990977adf52cbc440889329981caa9bef7da5770b2b8a05303b75d95360dd62b" diff --git a/unit/Spec.hs b/packages/crypto/tests/Spec.hs similarity index 100% rename from unit/Spec.hs rename to packages/crypto/tests/Spec.hs diff --git a/packages/crypto/web3-crypto.cabal b/packages/crypto/web3-crypto.cabal new file mode 100644 index 00000000..a5684f7f --- /dev/null +++ b/packages/crypto/web3-crypto.cabal @@ -0,0 +1,112 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-crypto +version: 1.1.0.0 +synopsis: Cryptograhical primitives for Haskell Web3 library. +description: This package implements Web3 specific cryptography and helper functions. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple +extra-source-files: + src/cbits/xxhash.h + src/cbits/xxhash.c + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Crypto.Bip39 + Crypto.Ecdsa.Signature + Crypto.Ecdsa.Utils + Crypto.Ethereum + Crypto.Ethereum.Eip712Signature + Crypto.Ethereum.Keyfile + Crypto.Ethereum.Signature + Crypto.Ethereum.Utils + Crypto.Random.HmacDrbg + Data.Digest.Blake2 + Data.Digest.XXHash + other-modules: + Paths_web3_crypto + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + include-dirs: + src/cbits + c-sources: + src/cbits/xxhash.c + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , basement >=0.0.16 && <0.1 + , bytestring >=0.10 && <0.13 + , containers >=0.6 && <0.8 + , crypton >=0.30 && <1.1 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , scientific >=0.3.7 && <0.4 + , text >=1.2 && <2.2 + , uuid-types ==1.0.* + , vector >=0.12 && <0.14 + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Crypto.Ethereum.Test.EIP712SignatureSpec + Crypto.Ethereum.Test.KeyfileSpec + Crypto.Ethereum.Test.SignatureSpec + Crypto.Random.Test.HmacDrbgSpec + Data.Digest.Test.Blake2Spec + Data.Digest.Test.XXHashSpec + Crypto.Bip39 + Crypto.Ecdsa.Signature + Crypto.Ecdsa.Utils + Crypto.Ethereum + Crypto.Ethereum.Eip712Signature + Crypto.Ethereum.Keyfile + Crypto.Ethereum.Signature + Crypto.Ethereum.Utils + Crypto.Random.HmacDrbg + Data.Digest.Blake2 + Data.Digest.XXHash + Paths_web3_crypto + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + include-dirs: + src/cbits + c-sources: + src/cbits/xxhash.c + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , basement >=0.0.16 && <0.1 + , bytestring >=0.10 && <0.13 + , containers >=0.6 && <0.8 + , crypton >=0.30 && <1.1 + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , scientific >=0.3.7 && <0.4 + , text >=1.2 && <2.2 + , uuid-types ==1.0.* + , vector >=0.12 && <0.14 + default-language: Haskell2010 diff --git a/packages/ethereum/LICENSE b/packages/ethereum/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/ethereum/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/ethereum/Setup.hs b/packages/ethereum/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/ethereum/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/ethereum/package.yaml b/packages/ethereum/package.yaml new file mode 100644 index 00000000..f315ebb7 --- /dev/null +++ b/packages/ethereum/package.yaml @@ -0,0 +1,82 @@ +name: web3-ethereum +version: 1.1.0.1 +synopsis: Ethereum support for Haskell Web3 library. +description: Client library for Third Generation of Web. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- vinyl >=0.5 && <0.15 +- aeson >=1.2 && <2.3 +- aeson-casing >=0.2 && <0.3 +- tagged >=0.8 && <0.9 +- memory >=0.14 && <0.19 +- relapse >=1.0 && <1.1 +- OneTuple >=0.2 && <0.5 +- machines >=0.6 && <0.8 +- microlens >=0.4 && <0.5 +- bytestring >=0.10 && <0.13 +- exceptions >=0.8 && <0.11 +- generics-sop >=0.3 && <0.6 +- data-default >=0.7 && <0.9 +- transformers >=0.5 && <0.7 +- microlens-aeson >=2.2 && <2.6 +- template-haskell >=2.11 && <2.23 +- mtl >=2.2 && <2.4 +- web3-crypto >=1.0 && <1.2 +- web3-solidity >=1.0 && <1.2 +- memory-hexstring >=1.0 && <1.2 +- jsonrpc-tinyclient >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + +data-files: +- tests/contracts/*.json + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + dependencies: + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/ethereum/src/Network/Ethereum.hs b/packages/ethereum/src/Network/Ethereum.hs new file mode 100644 index 00000000..0237f942 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum.hs @@ -0,0 +1,32 @@ +-- | +-- Module : Network.Ethereum +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum is a global, open-source platform for decentralized applications. +-- + +module Network.Ethereum + ( + -- * Basic transaction sending + module Account + + -- * Basic EVM event listening + , EventAction(..) + , event + + -- * Primitive Solidity data types + , module Prim + + -- * Metric unit system + , module Unit + ) where + +import Data.Solidity.Prim as Prim +import Network.Ethereum.Account as Account +import Network.Ethereum.Contract.Event (EventAction (..), event) +import Network.Ethereum.Unit as Unit diff --git a/packages/ethereum/src/Network/Ethereum/Account.hs b/packages/ethereum/src/Network/Ethereum/Account.hs new file mode 100644 index 00000000..754cf7a8 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account.hs @@ -0,0 +1,56 @@ +-- | +-- Module : Network.Ethereum.Account +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- In Etereun there are two types of accounts: +-- * Externally owned account (EOAs): an account controlled by a private key, and if you own +-- the private key associated with the EOA you have the ability to send ether and messages from it. +-- * Contract: an account that has its own code, and is controlled by code. +-- +-- This module exports different kinds of EOAs: default, node managed and local. Node managed accounts +-- use 'Personal' JSON-RPC API for signing transactions. Local account sign transaction locally and +-- use 'sendRawTransaction' method to export transaction to Ethereum network. +-- + +module Network.Ethereum.Account + ( + -- * The @Account@ type + Account(..) + + -- * Default node account + , DefaultAccount + + -- * Unlockable node account + , PersonalAccount + , Personal(..) + + -- * Local key account + , LocalKeyAccount + , LocalKey(..) + + -- * Transaction parameterization function and lenses + , withParam + , to + , value + , gasLimit + , gasPrice + , block + , account + , timeout + + ) where + +import Network.Ethereum.Account.Class (Account (..)) +import Network.Ethereum.Account.Default (DefaultAccount) +import Network.Ethereum.Account.Internal (account, block, gasLimit, + gasPrice, timeout, to, + value, withParam) +import Network.Ethereum.Account.LocalKey (LocalKey (..), + LocalKeyAccount) +import Network.Ethereum.Account.Personal (Personal (..), + PersonalAccount) diff --git a/packages/ethereum/src/Network/Ethereum/Account/Class.hs b/packages/ethereum/src/Network/Ethereum/Account/Class.hs new file mode 100644 index 00000000..e7c8f917 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/Class.hs @@ -0,0 +1,56 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FunctionalDependencies #-} + +-- | +-- Module : Network.Ethereum.Account.Class +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum external owned account abstraction. +-- + +module Network.Ethereum.Account.Class where + +import Control.Monad.Trans (MonadTrans) + +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Abi (AbiGet) +import Network.Ethereum.Api.Types (TxReceipt) +import Network.Ethereum.Contract.Method (Method) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Account is needed for sending transactions to blockchain +-- +-- Typically account is provided by node. In this case node manage accounts: +-- encrypt and decrypt private keys, manipulate files etc. In other case web3 +-- can derive account from private key and send to node already signed transactions. +-- +class MonadTrans t => Account a t | t -> a where + + -- | Run computation with given account credentials + withAccount :: JsonRpc m + => a + -- ^ Account params (like a password or private key) + -> t m b + -- ^ Computation that use account for sending transactions + -> m b + -- ^ Json-rpc monad + + -- | Send transaction to contract, like a 'write' command + send :: (JsonRpc m, Method args) + => args + -- ^ Contract method arguments + -> t m (Either HexString TxReceipt) + -- ^ Receipt of the sent transaction, or transaction hash in case of a timeout + + -- | Call constant method of contract, like a 'read' command + call :: (JsonRpc m, Method args, AbiGet result) + => args + -- ^ Contact method arguments + -> t m result + -- ^ Decoded result of method call + diff --git a/packages/ethereum/src/Network/Ethereum/Account/Default.hs b/packages/ethereum/src/Network/Ethereum/Account/Default.hs new file mode 100644 index 00000000..4c197e9b --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/Default.hs @@ -0,0 +1,74 @@ +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Ethereum.Account.Default +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Default node managed account (typically the first of accounts list). +-- + +module Network.Ethereum.Account.Default where + +import Control.Exception (TypeError (..)) +import Control.Monad.Catch (throwM) +import Control.Monad.State.Strict (get, runStateT) +import Control.Monad.Trans (MonadTrans (..)) +import qualified Data.ByteArray as BA (convert) +import Data.Maybe (listToMaybe) +import Data.Proxy (Proxy (..)) + +import Data.Solidity.Abi.Codec (decode, encode) +import Network.Ethereum.Account.Class (Account (..)) +import Network.Ethereum.Account.Internal (AccountT (..), + CallParam (..), + defaultCallParam, getCall, + getReceipt) +import qualified Network.Ethereum.Api.Eth as Eth (accounts, call, + estimateGas, + sendTransaction) +import Network.Ethereum.Api.Types (Call (callData, callFrom, callGas)) +import Network.Ethereum.Contract.Method (Method (..)) + +type DefaultAccount = AccountT () + +instance Account () DefaultAccount where + withAccount _ = + fmap fst . flip runStateT (defaultCallParam ()) . runAccountT + + send (args :: a) = do + c <- getCall + timeout <- _timeout <$> get + lift $ do + accounts <- Eth.accounts + let dat = selector (Proxy :: Proxy a) <> encode args + params = c { callData = Just $ BA.convert dat + , callFrom = listToMaybe accounts } + + params' <- case callGas params of + Just _ -> return params + Nothing -> do + gasLimit <- Eth.estimateGas params + return $ params { callGas = Just gasLimit } + + getReceipt timeout =<< Eth.sendTransaction params' + + call (args :: a) = do + c <- getCall + CallParam{..} <- get + res <- lift $ do + accounts <- Eth.accounts + let dat = selector (Proxy :: Proxy a) <> encode args + params = c { callData = Just $ BA.convert dat + , callFrom = listToMaybe accounts } + Eth.call params _block + case decode res of + Right r -> return r + Left e -> lift (throwM $ TypeError e) diff --git a/packages/ethereum/src/Network/Ethereum/Account/Internal.hs b/packages/ethereum/src/Network/Ethereum/Account/Internal.hs new file mode 100644 index 00000000..36b0ed10 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/Internal.hs @@ -0,0 +1,141 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Network.Ethereum.Account.Internal +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Internal types and functions of 'Account' module. +-- + +module Network.Ethereum.Account.Internal where + +import Control.Concurrent (threadDelay) +import Control.Monad.IO.Class (liftIO) +import Control.Monad.State.Strict (MonadState (..), StateT (..), + withStateT) +import Control.Monad.Trans (MonadTrans (..)) +import Data.Default (Default (..)) +import Data.Either (fromRight) +import Data.Maybe (fromMaybe) +import Lens.Micro (Lens', lens) + +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Prim (Address) +import Network.Ethereum.Account.Class (Account) +import qualified Network.Ethereum.Api.Eth as Eth (getTransactionReceipt) +import Network.Ethereum.Api.Types (Call (..), + DefaultBlock (Latest), + TxReceipt) +import Network.Ethereum.Unit (Unit (..)) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Account is needed to send transactions to blockchain + +-- | Transaction parametrization data type +data CallParam p = CallParam + { _to :: Maybe Address + -- ^ Transaction recepient + , _value :: Integer + -- ^ Transaction value + , _gasLimit :: Maybe Integer + -- ^ Transaction gas limit + , _gasPrice :: Maybe Integer + -- ^ Transaction gas price + , _block :: DefaultBlock + -- ^ Call block number + , _account :: p + -- ^ Account params to sign transaction + , _timeout :: Maybe Int + -- ^ Transaction timeout in microseconds + } deriving Eq + +-- | Transaction recipient lens +to :: Lens' (CallParam p) Address +to = lens (fromMaybe def . _to) $ \a b -> a { _to = Just b } + +-- | Transaction value lens +value :: Unit value => Lens' (CallParam p) value +value = lens (fromWei . _value) $ \a b -> a { _value = toWei b } + +-- | Transaction gas limit lens +gasLimit :: Lens' (CallParam p) Integer +gasLimit = lens (fromMaybe def . _gasLimit) $ \a b -> a { _gasLimit = Just b } + +-- | Transaction gas price lens +gasPrice :: Unit gasprice => Lens' (CallParam p) gasprice +gasPrice = lens (fromWei . fromMaybe def . _gasPrice) $ \a b -> a { _gasPrice = Just (toWei b) } + +-- | Call execution block lens +block :: Lens' (CallParam p) DefaultBlock +block = lens _block $ \a b -> a { _block = b } + +-- | EOA params lens +account :: Lens' (CallParam p) p +account = lens _account $ \a b -> a { _account = b } + +-- | Transaction timeout lens +timeout :: Lens' (CallParam p) (Maybe Int) +timeout = lens _timeout $ \a b -> a { _timeout = b } + +-- | Monad transformer for sending parametrized transactions from account +newtype AccountT p m a = AccountT + { runAccountT :: StateT (CallParam p) m a } + deriving (Functor, Applicative, Monad, MonadTrans) + +instance Monad m => MonadState (CallParam p) (AccountT p m) where + get = AccountT get + put = AccountT . put + +-- | @withParam@ is very similar to @withStateT@ function, it's used +-- to set parameters of transaction locally and revert params after out of scope. +-- +-- @ +-- withAccount () $ +-- withParam (to .~ tokenAddress) $ +-- transfer alice 42 +-- @ +withParam :: Account p (AccountT p) + => (CallParam p -> CallParam p) + -> AccountT p m a + -> AccountT p m a +{-# INLINE withParam #-} +withParam f m = AccountT $ withStateT f $ runAccountT m + +defaultCallParam :: a -> CallParam a +{-# INLINE defaultCallParam #-} +defaultCallParam acc = CallParam def 0 Nothing Nothing Latest acc Nothing + +getCall :: MonadState (CallParam p) m => m Call +getCall = do + CallParam{..} <- get + return $ def { callTo = _to + , callValue = Just $ fromInteger _value + , callGas = fromInteger <$> _gasLimit + , callGasPrice = fromInteger <$> _gasPrice + } + +getReceipt :: JsonRpc m => Maybe Int -> HexString -> m (Either HexString TxReceipt) +getReceipt mbtimeout tx = do + mbreceipt <- Eth.getTransactionReceipt tx + case mbreceipt of + Just receipt -> return $ Right receipt + Nothing -> case mbtimeout of + Just us + | us > 0 -> retry $ Just $ us - 100000 + | otherwise -> return $ Left tx + Nothing -> retry Nothing + where + retry mbtimeout' = do + liftIO $ threadDelay 100000 + getReceipt mbtimeout' tx + +getReceipt' :: JsonRpc m => HexString -> m TxReceipt +getReceipt' = fmap (fromRight undefined) . getReceipt Nothing diff --git a/packages/ethereum/src/Network/Ethereum/Account/LocalKey.hs b/packages/ethereum/src/Network/Ethereum/Account/LocalKey.hs new file mode 100644 index 00000000..11a9e021 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/LocalKey.hs @@ -0,0 +1,97 @@ +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Ethereum.Account.LocalKey +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- Roy Blankman 2018 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Using ECC for singing transactions locally, e.g. out of Ethereum node. +-- Transaction will send using 'eth_sendRawTransacion' JSON-RPC method. +-- + +module Network.Ethereum.Account.LocalKey where + +import Control.Exception (TypeError (..)) +import Control.Monad.Catch (throwM) +import Control.Monad.State.Strict (get, runStateT) +import Control.Monad.Trans (lift) +import Crypto.Ethereum (PrivateKey) +import Data.ByteArray (convert) +import Data.ByteString (empty) +import Data.Default (Default (..)) +import Data.Proxy (Proxy (..)) + +import Crypto.Ethereum (derivePubKey, importKey) +import Crypto.Ethereum.Signature (signTransaction) +import Data.Solidity.Abi.Codec (decode, encode) +import Data.Solidity.Prim.Address (fromPubKey) +import Network.Ethereum.Account.Class (Account (..)) +import Network.Ethereum.Account.Internal (AccountT (..), + CallParam (..), + defaultCallParam, getCall, + getReceipt) +import qualified Network.Ethereum.Api.Eth as Eth (call, estimateGas, + getTransactionCount, + sendRawTransaction) +import Network.Ethereum.Api.Types (Call (..)) +import Network.Ethereum.Chain (foundation) +import Network.Ethereum.Contract.Method (selector) +import Network.Ethereum.Transaction (encodeTransaction) + +-- | Local EOA params +data LocalKey = LocalKey + { localKeyPrivate :: !PrivateKey + , localKeyChainId :: !Integer + } + deriving (Eq, Show) + +instance Default LocalKey where + def = LocalKey (importKey empty) foundation + +type LocalKeyAccount = AccountT LocalKey + +instance Account LocalKey LocalKeyAccount where + withAccount a = + fmap fst . flip runStateT (defaultCallParam a) . runAccountT + + send (args :: a) = do + CallParam{..} <- get + c <- getCall + + let dat = selector (Proxy :: Proxy a) <> encode args + address = fromPubKey (derivePubKey $ localKeyPrivate _account) + + nonce <- lift $ Eth.getTransactionCount address _block + let params = c { callFrom = Just address + , callNonce = Just nonce + , callData = Just $ convert dat } + + params' <- case callGas params of + Just _ -> return params + Nothing -> do + gasLimit <- lift $ Eth.estimateGas params + return $ params { callGas = Just gasLimit } + + let packer = encodeTransaction params' (localKeyChainId _account) + signed = signTransaction packer (localKeyPrivate _account) + lift $ getReceipt _timeout =<< Eth.sendRawTransaction signed + + call (args :: a) = do + CallParam{..} <- get + c <- getCall + let dat = selector (Proxy :: Proxy a) <> encode args + address = fromPubKey (derivePubKey $ localKeyPrivate _account) + params = c { callFrom = Just address, callData = Just $ convert dat } + + res <- lift $ Eth.call params _block + case decode res of + Right r -> return r + Left e -> lift (throwM $ TypeError e) diff --git a/packages/ethereum/src/Network/Ethereum/Account/Personal.hs b/packages/ethereum/src/Network/Ethereum/Account/Personal.hs new file mode 100644 index 00000000..62bf58c9 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/Personal.hs @@ -0,0 +1,85 @@ +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Ethereum.Account.Personal +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Node managed unlockable account. Typically to send transaction from this account +-- password is required. +-- + +module Network.Ethereum.Account.Personal where + +import Control.Exception (TypeError (..)) +import Control.Monad.Catch (throwM) +import Control.Monad.State.Strict (get, runStateT) +import Control.Monad.Trans (lift) +import qualified Data.ByteArray as BA (convert) +import Data.Default (Default (..)) +import Data.Proxy (Proxy (..)) + +import Data.Solidity.Abi.Codec (decode, encode) +import Data.Solidity.Prim.Address (Address) +import Network.Ethereum.Account.Class (Account (..)) +import Network.Ethereum.Account.Internal (AccountT (..), + CallParam (..), + defaultCallParam, getCall, + getReceipt) +import qualified Network.Ethereum.Api.Eth as Eth (call, estimateGas) +import Network.Ethereum.Api.Personal (Passphrase) +import qualified Network.Ethereum.Api.Personal as Personal (sendTransaction) +import Network.Ethereum.Api.Types (Call (callData, callFrom, callGas)) +import Network.Ethereum.Contract.Method (selector) + +-- | Unlockable node managed account params +data Personal = Personal + { personalAddress :: !Address + , personalPassphrase :: !Passphrase + } + deriving (Eq, Show) + +instance Default Personal where + def = Personal def "" + +type PersonalAccount = AccountT Personal + +instance Account Personal PersonalAccount where + withAccount a = + fmap fst . flip runStateT (defaultCallParam a) . runAccountT + + send (args :: a) = do + CallParam{..} <- get + c <- getCall + lift $ do + let dat = selector (Proxy :: Proxy a) <> encode args + params = c { callFrom = Just $ personalAddress _account + , callData = Just $ BA.convert dat } + + params' <- case callGas params of + Just _ -> return params + Nothing -> do + gasLimit <- Eth.estimateGas params + return $ params { callGas = Just gasLimit } + + getReceipt _timeout =<< Personal.sendTransaction params' (personalPassphrase _account) + + call (args :: a) = do + s <- get + case s of + CallParam _ _ _ _ block (Personal address _) _ -> do + c <- getCall + let dat = selector (Proxy :: Proxy a) <> encode args + params = c { callFrom = Just address, callData = Just $ BA.convert dat } + res <- lift $ Eth.call params block + case decode res of + Right r -> return r + Left e -> lift (throwM $ TypeError e) diff --git a/packages/ethereum/src/Network/Ethereum/Account/Safe.hs b/packages/ethereum/src/Network/Ethereum/Account/Safe.hs new file mode 100644 index 00000000..7856bd02 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Account/Safe.hs @@ -0,0 +1,55 @@ +{-# LANGUAGE FlexibleContexts #-} + +-- | +-- Module : Network.Ethereum.Account.Safe +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Safe sending of Ethereum transaction. +-- + +module Network.Ethereum.Account.Safe where + +import Control.Concurrent (threadDelay) +import Control.Monad.IO.Class (liftIO) +import Control.Monad.Trans (lift) +import Data.ByteArray.HexString (HexString) + +import Network.Ethereum.Account.Class (Account (send)) +import qualified Network.Ethereum.Api.Eth as Eth +import Network.Ethereum.Api.Types (TxReceipt (receiptBlockNumber)) +import Network.Ethereum.Contract.Method (Method) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Safe version of 'send' function of 'Account' typeclass +-- Waiting for some blocks of transaction confirmation before return +safeSend :: (Account p t, JsonRpc m, Method args, Monad (t m)) + => Integer + -- ^ Confirmation in blocks + -> args + -- ^ Contract method arguments + -> t m (Either HexString TxReceipt) + -- ^ Receipt of the sent transaction, or transaction data in case of a timeout +safeSend b a = lift . withReceipt waiting =<< send a + where + withReceipt f receiptOrTx = + case receiptOrTx of + Left tx -> return $ Left tx + Right receipt -> Right <$> f receipt + + waiting receipt = do + current <- Eth.blockNumber + if current - receiptBlockNumber receipt >= fromInteger b + then return receipt + else do liftIO $ threadDelay 1000000 + waiting receipt + +-- | Count block confirmation to keep secure +-- According to Vitalik post +-- https://blog.ethereum.org/2015/09/14/on-slow-and-fast-block-times/ +safeConfirmations :: Integer +safeConfirmations = 10 diff --git a/src/Network/Ethereum/Web3/Eth.hs b/packages/ethereum/src/Network/Ethereum/Api/Eth.hs similarity index 64% rename from src/Network/Ethereum/Web3/Eth.hs rename to packages/ethereum/src/Network/Ethereum/Api/Eth.hs index 40f9df0e..7806e2aa 100644 --- a/src/Network/Ethereum/Web3/Eth.hs +++ b/packages/ethereum/src/Network/Ethereum/Api/Eth.hs @@ -1,10 +1,10 @@ -{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE OverloadedStrings #-} -- | -- Module : Network.Ethereum.Web3.Eth --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental @@ -13,222 +13,244 @@ -- Ethereum node JSON-RPC API methods with `eth_` prefix. -- -module Network.Ethereum.Web3.Eth where - -import Data.Text (Text) -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.ABI.Prim.Bytes (Bytes, BytesN) -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Block, Call, Change, - DefaultBlock, Filter, Hash, - Quantity, SyncingState, - Transaction, TxReceipt) -import Network.JsonRpc.TinyClient (remote) +module Network.Ethereum.Api.Eth where + +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Prim.Address (Address) +import Data.Text (Text) +import Network.Ethereum.Api.Types + ( Block + , BlockT + , Call + , Change + , DefaultBlock + , FeeHistory + , Filter + , Quantity + , SyncingState + , Transaction + , TxReceipt + ) +import Network.JsonRpc.TinyClient (JsonRpc(..)) -- | Returns the current ethereum protocol version. -protocolVersion :: Web3 Text +protocolVersion :: JsonRpc m => m Text {-# INLINE protocolVersion #-} protocolVersion = remote "eth_protocolVersion" -- | Returns an object with data about the sync status or false. -syncing :: Web3 SyncingState +syncing :: JsonRpc m => m SyncingState {-# INLINE syncing #-} syncing = remote "eth_syncing" -- | Returns the client coinbase address. -coinbase :: Web3 Address +coinbase :: JsonRpc m => m Address {-# INLINE coinbase #-} coinbase = remote "eth_coinbase" -- | Returns true if client is actively mining new blocks. -mining :: Web3 Bool +mining :: JsonRpc m => m Bool {-# INLINE mining #-} mining = remote "eth_mining" -- | Returns the number of hashes per second that the node is mining with. -hashrate :: Web3 Quantity +hashrate :: JsonRpc m => m Quantity {-# INLINE hashrate #-} hashrate = remote "eth_hashrate" -- | Returns the value from a storage position at a given address. -getStorageAt :: Address -> Quantity -> DefaultBlock -> Web3 (BytesN 32) +getStorageAt :: JsonRpc m => Address -> Quantity -> DefaultBlock -> m HexString {-# INLINE getStorageAt #-} getStorageAt = remote "eth_getStorageAt" -- | Returns the number of transactions sent from an address. -getTransactionCount :: Address -> DefaultBlock -> Web3 Quantity +getTransactionCount :: JsonRpc m => Address -> DefaultBlock -> m Quantity {-# INLINE getTransactionCount #-} getTransactionCount = remote "eth_getTransactionCount" -- | Returns the number of transactions in a block from a block matching the given block hash. -getBlockTransactionCountByHash :: Hash -> Web3 Quantity +getBlockTransactionCountByHash :: JsonRpc m => HexString -> m Quantity {-# INLINE getBlockTransactionCountByHash #-} getBlockTransactionCountByHash = remote "eth_getBlockTransactionCountByHash" -- | Returns the number of transactions in a block matching the -- given block number. -getBlockTransactionCountByNumber :: Quantity -> Web3 Quantity +getBlockTransactionCountByNumber :: JsonRpc m => Quantity -> m Quantity {-# INLINE getBlockTransactionCountByNumber #-} getBlockTransactionCountByNumber = remote "eth_getBlockTransactionCountByNumber" -- | Returns the number of uncles in a block from a block matching the given -- block hash. -getUncleCountByBlockHash :: Hash -> Web3 Quantity +getUncleCountByBlockHash :: JsonRpc m => HexString -> m Quantity {-# INLINE getUncleCountByBlockHash #-} getUncleCountByBlockHash = remote "eth_getUncleCountByBlockHash" -- | Returns the number of uncles in a block from a block matching the given -- block number. -getUncleCountByBlockNumber :: Quantity -> Web3 Quantity +getUncleCountByBlockNumber :: JsonRpc m => Quantity -> m Quantity {-# INLINE getUncleCountByBlockNumber #-} getUncleCountByBlockNumber = remote "eth_getUncleCountByBlockNumber" -- | Returns code at a given address. -getCode :: Address -> DefaultBlock -> Web3 Bytes +getCode :: JsonRpc m => Address -> DefaultBlock -> m HexString {-# INLINE getCode #-} getCode = remote "eth_getCode" -- | Returns an Ethereum specific signature with: -- sign(keccak256("\x19Ethereum Signed Message:\n" + len(message) + message))). -sign :: Address -> Bytes -> Web3 Bytes +sign :: JsonRpc m => Address -> HexString -> m HexString {-# INLINE sign #-} sign = remote "eth_sign" -- | Creates new message call transaction or a contract creation, -- if the data field contains code. -sendTransaction :: Call -> Web3 Hash +sendTransaction :: JsonRpc m => Call -> m HexString {-# INLINE sendTransaction #-} sendTransaction = remote "eth_sendTransaction" -- | Creates new message call transaction or a contract creation for signed -- transactions. -sendRawTransaction :: Bytes -> Web3 Hash +sendRawTransaction :: JsonRpc m => HexString -> m HexString {-# INLINE sendRawTransaction #-} sendRawTransaction = remote "eth_sendRawTransaction" -- | Returns the balance of the account of given address. -getBalance :: Address -> DefaultBlock -> Web3 Quantity +getBalance :: JsonRpc m => Address -> DefaultBlock -> m Quantity {-# INLINE getBalance #-} getBalance = remote "eth_getBalance" -- | Creates a filter object, based on filter options, to notify when the -- state changes (logs). To check if the state has changed, call -- 'getFilterChanges'. -newFilter :: Filter e -> Web3 Quantity +newFilter :: JsonRpc m => Filter e -> m Quantity {-# INLINE newFilter #-} newFilter = remote "eth_newFilter" -- | Polling method for a filter, which returns an array of logs which -- occurred since last poll. -getFilterChanges :: Quantity -> Web3 [Change] +getFilterChanges :: JsonRpc m => Quantity -> m [Change] {-# INLINE getFilterChanges #-} getFilterChanges = remote "eth_getFilterChanges" -- | Uninstalls a filter with given id. -- Should always be called when watch is no longer needed. -uninstallFilter :: Quantity -> Web3 Bool +uninstallFilter :: JsonRpc m => Quantity -> m Bool {-# INLINE uninstallFilter #-} uninstallFilter = remote "eth_uninstallFilter" -- | Returns an array of all logs matching a given filter object. -getLogs :: Filter e -> Web3 [Change] +getLogs :: JsonRpc m => Filter e -> m [Change] {-# INLINE getLogs #-} getLogs = remote "eth_getLogs" -- | Executes a new message call immediately without creating a -- transaction on the block chain. -call :: Call -> DefaultBlock -> Web3 Bytes +call :: JsonRpc m => Call -> DefaultBlock -> m HexString {-# INLINE call #-} call = remote "eth_call" -- | Makes a call or transaction, which won't be added to the blockchain and -- returns the used gas, which can be used for estimating the used gas. -estimateGas :: Call -> Web3 Quantity +estimateGas :: JsonRpc m => Call -> m Quantity {-# INLINE estimateGas #-} estimateGas = remote "eth_estimateGas" +-- | Returns transaction base fee per gas and effective priority fee per gas for the requested/supported block range. +feeHistory :: (JsonRpc m) => Quantity -> DefaultBlock -> [Double] -> m FeeHistory +feeHistory = remote "eth_feeHistory" + +-- | Returns information about a block by hash with only hashes of the transactions in it. +getBlockByHashLite :: JsonRpc m => HexString -> m (Maybe (BlockT HexString)) +{-# INLINE getBlockByHashLite #-} +getBlockByHashLite = flip (remote "eth_getBlockByHash") False + +-- | Returns information about a block by block number with only hashes of the transactions in it. +getBlockByNumberLite :: JsonRpc m => Quantity -> m (Maybe (BlockT HexString)) +{-# INLINE getBlockByNumberLite #-} +getBlockByNumberLite = flip (remote "eth_getBlockByNumber") False + -- | Returns information about a block by hash. -getBlockByHash :: Hash -> Web3 Block +getBlockByHash :: JsonRpc m => HexString -> m (Maybe Block) {-# INLINE getBlockByHash #-} getBlockByHash = flip (remote "eth_getBlockByHash") True -- | Returns information about a block by block number. -getBlockByNumber :: Quantity -> Web3 Block +getBlockByNumber :: JsonRpc m => Quantity -> m (Maybe Block) {-# INLINE getBlockByNumber #-} getBlockByNumber = flip (remote "eth_getBlockByNumber") True -- | Returns the information about a transaction requested by transaction hash. -getTransactionByHash :: Hash -> Web3 (Maybe Transaction) +getTransactionByHash :: JsonRpc m => HexString -> m (Maybe Transaction) {-# INLINE getTransactionByHash #-} getTransactionByHash = remote "eth_getTransactionByHash" -- | Returns information about a transaction by block hash and transaction index position. -getTransactionByBlockHashAndIndex :: Hash -> Quantity -> Web3 (Maybe Transaction) +getTransactionByBlockHashAndIndex :: JsonRpc m => HexString -> Quantity -> m (Maybe Transaction) {-# INLINE getTransactionByBlockHashAndIndex #-} getTransactionByBlockHashAndIndex = remote "eth_getTransactionByBlockHashAndIndex" -- | Returns information about a transaction by block number and transaction -- index position. -getTransactionByBlockNumberAndIndex :: DefaultBlock -> Quantity -> Web3 (Maybe Transaction) +getTransactionByBlockNumberAndIndex :: JsonRpc m => DefaultBlock -> Quantity -> m (Maybe Transaction) {-# INLINE getTransactionByBlockNumberAndIndex #-} getTransactionByBlockNumberAndIndex = remote "eth_getTransactionByBlockNumberAndIndex" -- | Returns the receipt of a transaction by transaction hash. -getTransactionReceipt :: Hash -> Web3 (Maybe TxReceipt) +getTransactionReceipt :: JsonRpc m => HexString -> m (Maybe TxReceipt) {-# INLINE getTransactionReceipt #-} getTransactionReceipt = remote "eth_getTransactionReceipt" -- | Returns a list of addresses owned by client. -accounts :: Web3 [Address] +accounts :: JsonRpc m => m [Address] {-# INLINE accounts #-} accounts = remote "eth_accounts" -- | Creates a filter in the node, to notify when a new block arrives. -newBlockFilter :: Web3 Quantity +newBlockFilter :: JsonRpc m => m Quantity {-# INLINE newBlockFilter #-} newBlockFilter = remote "eth_newBlockFilter" -- | Polling method for a block filter, which returns an array of block hashes -- occurred since last poll. -getBlockFilterChanges :: Quantity -> Web3 [Hash] +getBlockFilterChanges :: JsonRpc m => Quantity -> m [HexString] {-# INLINE getBlockFilterChanges #-} getBlockFilterChanges = remote "eth_getFilterChanges" -- | Returns the number of most recent block. -blockNumber :: Web3 Quantity +blockNumber :: JsonRpc m => m Quantity {-# INLINE blockNumber #-} blockNumber = remote "eth_blockNumber" -- | Returns the current price per gas in wei. -gasPrice :: Web3 Quantity +gasPrice :: JsonRpc m => m Quantity {-# INLINE gasPrice #-} gasPrice = remote "eth_gasPrice" -- | Returns information about a uncle of a block by hash and uncle index -- position. -getUncleByBlockHashAndIndex :: Hash -> Quantity -> Web3 Block +getUncleByBlockHashAndIndex :: JsonRpc m => HexString -> Quantity -> m Block {-# INLINE getUncleByBlockHashAndIndex #-} getUncleByBlockHashAndIndex = remote "eth_getUncleByBlockHashAndIndex" -- | Returns information about a uncle of a block by number and uncle index -- position. -getUncleByBlockNumberAndIndex :: DefaultBlock -> Quantity -> Web3 Block +getUncleByBlockNumberAndIndex :: JsonRpc m => DefaultBlock -> Quantity -> m Block {-# INLINE getUncleByBlockNumberAndIndex #-} getUncleByBlockNumberAndIndex = remote "eth_getUncleByBlockNumberAndIndex" -- | Creates a filter in the node, to notify when new pending transactions arrive. To check if the state has changed, call getFilterChanges. Returns a FilterId. -newPendingTransactionFilter :: Web3 Quantity +newPendingTransactionFilter :: JsonRpc m => m Quantity {-# INLINE newPendingTransactionFilter #-} newPendingTransactionFilter = remote "eth_newPendingTransactionFilter" -- | Returns an array of all logs matching filter with given id. -getFilterLogs :: Quantity -> Web3 [Change] +getFilterLogs :: JsonRpc m => Quantity -> m [Change] {-# INLINE getFilterLogs #-} getFilterLogs = remote "eth_getFilterLogs" -- | Returns the hash of the current block, the seedHash, and the boundary -- condition to be met ("target"). -getWork :: Web3 [Bytes] +getWork :: JsonRpc m => m [HexString] {-# INLINE getWork #-} getWork = remote "eth_getWork" @@ -237,7 +259,7 @@ getWork = remote "eth_getWork" -- 1. DATA, 8 Bytes - The nonce found (64 bits) -- 2. DATA, 32 Bytes - The header's pow-hash (256 bits) -- 3. DATA, 32 Bytes - The mix digest (256 bits) -submitWork :: BytesN 8 -> BytesN 32 -> BytesN 32 -> Web3 Bool +submitWork :: JsonRpc m => HexString -> HexString -> HexString -> m Bool {-# INLINE submitWork #-} submitWork = remote "eth_submitWork" @@ -245,6 +267,11 @@ submitWork = remote "eth_submitWork" -- Parameters: -- 1. Hashrate, a hexadecimal string representation (32 bytes) of the hash rate -- 2. ID, String - A random hexadecimal(32 bytes) ID identifying the client -submitHashrate :: BytesN 32 -> BytesN 32 -> Web3 Bool +submitHashrate :: JsonRpc m => HexString -> HexString -> m Bool {-# INLINE submitHashrate #-} submitHashrate = remote "eth_submitHashrate" + +-- | Returns the chain ID of the current network. +chainId :: JsonRpc m => m Quantity +{-# INLINE chainId #-} +chainId = remote "eth_chainId" diff --git a/src/Network/Ethereum/Web3/Net.hs b/packages/ethereum/src/Network/Ethereum/Api/Net.hs similarity index 54% rename from src/Network/Ethereum/Web3/Net.hs rename to packages/ethereum/src/Network/Ethereum/Api/Net.hs index 8959b1f3..afbde9d3 100644 --- a/src/Network/Ethereum/Web3/Net.hs +++ b/packages/ethereum/src/Network/Ethereum/Api/Net.hs @@ -1,9 +1,10 @@ +{-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE OverloadedStrings #-} -- | --- Module : Network.Ethereum.Web3.Net --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 +-- Module : Network.Ethereum.Api.Net +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental @@ -12,24 +13,23 @@ -- Ethereum node JSON-RPC API methods with `net_` prefix. -- -module Network.Ethereum.Web3.Net where +module Network.Ethereum.Api.Net where -import Data.Text (Text) -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Quantity) -import Network.JsonRpc.TinyClient (remote) +import Data.Text (Text) +import Network.Ethereum.Api.Types (Quantity) +import Network.JsonRpc.TinyClient (JsonRpc (..)) -- | Returns the current network id. -version :: Web3 Text +version :: JsonRpc m => m Text {-# INLINE version #-} version = remote "net_version" -- | Returns true if client is actively listening for network connections. -listening :: Web3 Bool +listening :: JsonRpc m => m Bool {-# INLINE listening #-} listening = remote "net_listening" -- | Returns number of peers currently connected to the client. -peerCount :: Web3 Quantity +peerCount :: JsonRpc m => m Quantity {-# INLINE peerCount #-} peerCount = remote "net_peerCount" diff --git a/src/Network/Ethereum/Web3/Personal.hs b/packages/ethereum/src/Network/Ethereum/Api/Personal.hs similarity index 72% rename from src/Network/Ethereum/Web3/Personal.hs rename to packages/ethereum/src/Network/Ethereum/Api/Personal.hs index f8f96cd1..9e05a7e3 100644 --- a/src/Network/Ethereum/Web3/Personal.hs +++ b/packages/ethereum/src/Network/Ethereum/Api/Personal.hs @@ -1,10 +1,10 @@ -{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE OverloadedStrings #-} -- | --- Module : Network.Ethereum.Web3.Personal +-- Module : Network.Ethereum.Api.Personal -- Copyright : Keagan McClelland 2018 --- License : BSD3 +-- License : Apache-2.0 -- -- Maintainer : keagan.mcclelland@gmail.com -- Stability : experimental @@ -13,14 +13,15 @@ -- Ethereum node JSON-RPC API methods with `personal_` prefix. -- -module Network.Ethereum.Web3.Personal where +module Network.Ethereum.Api.Personal where -import Data.Text (Text) -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.ABI.Prim.Bytes (Bytes, BytesN) -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Call, Hash) -import Network.JsonRpc.TinyClient (remote) +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Prim.Address (Address) +import Data.Text (Text) +import Network.Ethereum.Api.Types (Call) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +type Passphrase = Text -- | Imports the given unencrypted private key (hex string) into the key store, encrypting it with the passphrase. -- @@ -31,23 +32,23 @@ import Network.JsonRpc.TinyClient (remote) -- 2. passphrase -- -- Returns: address of new account -importRawKey :: BytesN 32 -> Text -> Web3 Address +importRawKey :: JsonRpc m => HexString -> Passphrase -> m Address {-# INLINE importRawKey #-} importRawKey = remote "personal_importRawKey" -- | Returns all the Ethereum account addresses of all keys in the key store. -listAccounts :: Web3 [Address] +listAccounts :: JsonRpc m => m [Address] {-# INLINE listAccounts #-} listAccounts = remote "personal_listAccounts" -- | Removes the private key with given address from memory. The account can no longer be used to send transactions. -lockAccount :: Address -> Web3 Bool +lockAccount :: JsonRpc m => Address -> m Bool {-# INLINE lockAccount #-} lockAccount = remote "personal_lockAccount" -- | Generates a new private key and stores it in the key store directory. The key file is encrypted with the given -- passphrase. Returns the address of the new account. -newAccount :: Text -> Web3 Address +newAccount :: JsonRpc m => Passphrase -> m Address {-# INLINE newAccount #-} newAccount = remote "personal_newAccount" @@ -56,7 +57,7 @@ newAccount = remote "personal_newAccount" -- The unencrypted key will be held in memory until it is locked again -- -- The account can be used with eth_sign and eth_sendTransaction while it is unlocked. -unlockAccount :: Address -> Text -> Web3 Bool +unlockAccount :: JsonRpc m => Address -> Passphrase -> m Bool {-# INLINE unlockAccount #-} unlockAccount = remote "personal_unlockAccount" @@ -65,7 +66,7 @@ unlockAccount = remote "personal_unlockAccount" -- The transaction is the same argument as for eth_sendTransaction and contains the from address. If the passphrase can -- be used to decrypt the private key belonging to the transaction 'callFrom', the transaction is verified, signed and -- send onto the network. The account is not unlocked globally in the node and cannot be used in other RPC calls. -sendTransaction :: Call -> Text -> Web3 Hash +sendTransaction :: JsonRpc m => Call -> Passphrase -> m HexString {-# INLINE sendTransaction #-} sendTransaction = remote "personal_sendTransaction" @@ -74,7 +75,7 @@ sendTransaction = remote "personal_sendTransaction" -- sign(keccak256("\x19Ethereum Signed Message:\n" + len(message) + message))). -- -- when given a passphrase to decrypt the account's private key -sign :: Bytes -> Address -> Text -> Web3 Bytes +sign :: JsonRpc m => HexString -> Address -> Passphrase -> m HexString {-# INLINE sign #-} sign = remote "personal_sign" @@ -87,6 +88,6 @@ sign = remote "personal_sign" -- 2. signature: DATA, 65 bytes -- -- Returns: Address -ecRecover :: Bytes -> Bytes -> Web3 Address +ecRecover :: JsonRpc m => HexString -> HexString -> m Address {-# INLINE ecRecover #-} ecRecover = remote "personal_ecRecover" diff --git a/packages/ethereum/src/Network/Ethereum/Api/Types.hs b/packages/ethereum/src/Network/Ethereum/Api/Types.hs new file mode 100644 index 00000000..08133cb0 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Api/Types.hs @@ -0,0 +1,372 @@ +{-# LANGUAGE DeriveDataTypeable #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Ethereum.Api.Types +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Ethereum generic JSON-RPC types. +-- + +module Network.Ethereum.Api.Types where + +import Data.Aeson (FromJSON (..), + Options (fieldLabelModifier, omitNothingFields), + ToJSON (..), Value (Bool, String), + defaultOptions, object, (.=)) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Default (Default (..)) +import Data.Solidity.Prim.Address (Address) +import Data.String (IsString (..)) +import qualified Data.Text as T (pack) +import qualified Data.Text.Lazy.Builder as B (toLazyText) +import qualified Data.Text.Lazy.Builder.Int as B (hexadecimal) +import qualified Data.Text.Read as R (decimal, hexadecimal) +import Data.Word (Word8) +import GHC.Generics (Generic) +import Lens.Micro (_head, over) + +-- | Should be viewed as type to representing QUANTITY in Web3 JSON RPC docs +-- +-- When encoding QUANTITIES (integers, numbers): encode as hex, prefix with "0x", +-- the most compact representation (slight exception: zero should be represented as "0x0"). +-- Examples: +-- +-- 0x41 (65 in decimal) +-- 0x400 (1024 in decimal) +-- WRONG: 0x (should always have at least one digit - zero is "0x0") +-- WRONG: 0x0400 (no leading zeroes allowed) +-- WRONG: ff (must be prefixed 0x) +newtype Quantity = Quantity { unQuantity :: Integer } + deriving (Num, Real, Integral, Enum, Eq, Ord, Generic) + +instance Show Quantity where + show = show . unQuantity + +instance IsString Quantity where + fromString ('0' : 'x' : hex) = + case R.hexadecimal (T.pack hex) of + Right (x, "") -> Quantity x + _ -> error ("Quantity " ++ show hex ++ " is not valid hex") + fromString num = + case R.decimal (T.pack num) of + Right (x, "") -> Quantity x + _ -> error ("Quantity " ++ show num ++ " is not valid decimal") + +instance ToJSON Quantity where + toJSON (Quantity x) = + let hexValue = B.toLazyText (B.hexadecimal x) + in toJSON ("0x" <> hexValue) + +instance FromJSON Quantity where + parseJSON (String v) = + case R.hexadecimal v of + Right (x, "") -> return (Quantity x) + _ -> fail $ "Quantity " ++ show v <> " is not valid hex" + parseJSON _ = fail "Quantity should be a JSON String" + +-- | Type representing a Byte in Web3 JSON RPC docs ("#/components/schemas/byte") +-- +-- The encoding is similar to Quantity, encoding as hex string. +newtype Byte = Byte { unByte :: Word8 } + deriving (Num, Real, Integral, Enum, Eq, Ord, Generic) + +instance Show Byte where + show = show . unByte + +instance IsString Byte where + fromString ('0' : 'x' : hex) = + case R.hexadecimal (T.pack hex) of + Right (x, "") + | toInteger (minBound :: Word8) <= x && x <= toInteger (maxBound :: Word8) -> Byte (fromInteger x) + | otherwise -> error ("Byte " ++ show hex ++ "is not within bounds") + _ -> error ("Byte " ++ show hex ++ " is not valid hex") + + fromString num = + case R.decimal (T.pack num) of + Right (x, "") + | toInteger (minBound :: Word8) <= x && x <= toInteger (maxBound :: Word8) -> Byte (fromInteger x) + | otherwise -> error ("Byte " ++ show num ++ "is not within bounds") + _ -> error ("Byte " ++ show num ++ " is not valid decimal") + +instance ToJSON Byte where + toJSON (Byte x) = + let hexValue = B.toLazyText (B.hexadecimal x) + in toJSON ("0x" <> hexValue) + +instance FromJSON Byte where + parseJSON (String v) = + case R.hexadecimal v of + Right (x, "") -> return (Byte x) + _ -> fail $ "Byte " ++ show v <> " is not valid hex" + parseJSON _ = fail "Byte should be a JSON String" + + +-- | An object with sync status data. +data SyncActive = SyncActive + { syncStartingBlock :: !Quantity + -- ^ QUANTITY - The block at which the import started (will only be reset, after the sync reached his head). + , syncCurrentBlock :: !Quantity + -- ^ QUANTITY - The current block, same as eth_blockNumber. + , syncHighestBlock :: !Quantity + -- ^ QUANTITY - The estimated highest block. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 4 }) ''SyncActive) + +-- | Sync state pulled by low-level call 'eth_syncing'. +data SyncingState = Syncing SyncActive + | NotSyncing + deriving (Eq, Generic, Show) + +instance FromJSON SyncingState where + parseJSON (Bool _) = pure NotSyncing + parseJSON v = Syncing <$> parseJSON v + +-- | Changes pulled by low-level call 'eth_getFilterChanges', 'eth_getLogs', +-- and 'eth_getFilterLogs' +data Change = Change + { changeLogIndex :: !(Maybe Quantity) + -- ^ QUANTITY - integer of the log index position in the block. null when its pending log. + , changeTransactionIndex :: !(Maybe Quantity) + -- ^ QUANTITY - integer of the transactions index position log was created from. null when its pending log. + , changeTransactionHash :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - hash of the transactions this log was created from. null when its pending log. + , changeBlockHash :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - hash of the block where this log was in. null when its pending. null when its pending log. + , changeBlockNumber :: !(Maybe Quantity) + -- ^ QUANTITY - the block number where this log was in. null when its pending. null when its pending log. + , changeAddress :: !Address + -- ^ DATA, 20 Bytes - address from which this log originated. + , changeData :: !HexString + -- ^ DATA - contains one or more 32 Bytes non-indexed arguments of the log. + , changeTopics :: ![HexString] + -- ^ Array of DATA - Array of 0 to 4 32 Bytes DATA of indexed log arguments. + } + deriving (Eq, Show, Generic) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''Change) + +-- | The contract call params. +data Call = Call + { callFrom :: !(Maybe Address) + -- ^ DATA, 20 Bytes - The address the transaction is send from. + , callTo :: !(Maybe Address) + -- ^ DATA, 20 Bytes - (optional when creating new contract) The address the transaction is directed to. + , callGas :: !(Maybe Quantity) + -- ^ QUANTITY - (optional, default: 3000000) Integer of the gas provided for the transaction execution. It will return unused gas. + , callGasPrice :: !(Maybe Quantity) + -- ^ QUANTITY - (optional, default: To-Be-Determined) Integer of the gasPrice used for each paid gas. + , callValue :: !(Maybe Quantity) + -- ^ QUANTITY - (optional) Integer of the value sent with this transaction. + , callData :: !(Maybe HexString) + -- ^ DATA - The compiled code of a contract OR the hash of the invoked method signature and encoded parameters. + , callNonce :: !(Maybe Quantity) + -- ^ QUANTITY - (optional) Integer of a nonce. This allows to overwrite your own pending transactions that use the same nonce. + } + deriving (Eq, Show, Generic) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 4 + , omitNothingFields = True }) ''Call) + +instance Default Call where + def = Call Nothing Nothing (Just 3000000) Nothing (Just 0) Nothing Nothing + +-- | The state of blockchain for contract call. +data DefaultBlock = BlockWithNumber Quantity + | Earliest + | Latest + | Pending + deriving (Eq, Show, Generic) + +instance ToJSON DefaultBlock where + toJSON (BlockWithNumber bn) = toJSON bn + toJSON parameter = toJSON . over _head toLower . show $ parameter + +-- | Low-level event filter data structure. +data Filter e = Filter + { filterAddress :: !(Maybe [Address]) + -- ^ DATA|Array, 20 Bytes - (optional) Contract address or a list of addresses from which logs should originate. + , filterFromBlock :: !DefaultBlock + -- ^ QUANTITY|TAG - (optional, default: "latest") Integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions. + , filterToBlock :: !DefaultBlock + -- ^ QUANTITY|TAG - (optional, default: "latest") Integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions. + , filterTopics :: !(Maybe [Maybe HexString]) + -- ^ Array of DATA, - (optional) Array of 32 Bytes DATA topics. Topics are order-dependent. Each topic can also be an array of DATA with "or" options. + } + deriving (Eq, Show, Generic) + +instance ToJSON (Filter e) where + toJSON f = object [ "address" .= filterAddress f + , "fromBlock" .= filterFromBlock f + , "toBlock" .= filterToBlock f + , "topics" .= filterTopics f ] + +instance Ord DefaultBlock where + compare Pending Pending = EQ + compare Latest Latest = EQ + compare Earliest Earliest = EQ + compare (BlockWithNumber a) (BlockWithNumber b) = compare a b + compare _ Pending = LT + compare Pending Latest = GT + compare _ Latest = LT + compare Earliest _ = LT + compare a b = case compare b a of + LT -> GT + GT -> LT + EQ -> EQ + +-- | The Receipt of a Transaction +data TxReceipt = TxReceipt + { receiptType :: !(Maybe Byte) + -- ^ BYTE - type of the transaction 0x00 for legacy transactions, 0x01 EIP-2930, 0x02 EIP-1559 + , receiptTransactionHash :: !HexString + -- ^ DATA, 32 Bytes - hash of the transaction. + , receiptTransactionIndex :: !Quantity + -- ^ QUANTITY - index of the transaction. + , receiptBlockHash :: !HexString + -- ^ DATA, 32 Bytes - hash of the block where this transaction was in. + , receiptBlockNumber :: !Quantity + -- ^ QUANTITY - block number where this transaction was in. + , receiptFrom :: !Address + -- ^ DATA, 20 Bytes - the address of the sender + , receiptTo :: !(Maybe Address) + -- ^ DATA, 20 Bytes - The address of the receiver. null when the transaction is a contract creation transaction. + , receiptCumulativeGasUsed :: !Quantity + -- ^ QUANTITY - The total amount of gas used when this transaction was executed in the block. + , receiptGasUsed :: !Quantity + -- ^ QUANTITY - The amount of gas used by this specific transaction alone. + , receiptBlobGasUsed :: !(Maybe Quantity) + -- ^ QUANTITY - The amount of blob gas used for this specific transaction. Only specified for blob transactions as defined by EIP-4844. + , receiptContractAddress :: !(Maybe Address) + -- ^ DATA, 20 Bytes - The contract address created, if the transaction was a contract creation, otherwise null. + , receiptLogs :: ![Change] + -- ^ Array - Array of log objects, which this transaction generated. + , receiptLogsBloom :: !HexString + -- ^ DATA, 256 Bytes - Bloom filter for light clients to quickly retrieve related logs. + , receiptRoot :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - The post-transaction state root. Only specified for transactions included before the Byzantium upgrade. + , receiptStatus :: !(Maybe Quantity) + -- ^ QUANTITY either 1 (success) or 0 (failure) + , receiptEffectiveGasPrice :: !Quantity + -- ^ QUANTITY - The actual value per gas deducted from the sender's account. Before EIP-1559, this is equal to the transaction's gas price. After, it is equal to baseFeePerGas + min(maxFeePerGas - baseFeePerGas, maxPriorityFeePerGas). + , blobGasPrice :: !(Maybe Quantity) + -- ^ QUANTITY - The actual value per gas deducted from the sender's account for blob gas. Only specified for blob transactions as defined by EIP-4844. + } + deriving (Show, Generic) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''TxReceipt) + +-- | Transaction information. +data Transaction = Transaction + { txHash :: !HexString + -- ^ DATA, 32 Bytes - hash of the transaction. + , txNonce :: !Quantity + -- ^ QUANTITY - the number of transactions made by the sender prior to this one. + , txBlockHash :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - hash of the block where this transaction was in. null when its pending. + , txBlockNumber :: !(Maybe Quantity) + -- ^ QUANTITY - block number where this transaction was in. null when its pending. + , txTransactionIndex :: !(Maybe Quantity) + -- ^ QUANTITY - integer of the transactions index position in the block. null when its pending. + , txFrom :: !Address + -- ^ DATA, 20 Bytes - address of the sender. + , txTo :: !(Maybe Address) + -- ^ DATA, 20 Bytes - address of the receiver. null when its a contract creation transaction. + , txValue :: !Quantity + -- ^ QUANTITY - value transferred in Wei. + , txGasPrice :: !Quantity + -- ^ QUANTITY - gas price provided by the sender in Wei. + , txGas :: !Quantity + -- ^ QUANTITY - gas provided by the sender. + , txInput :: !HexString + -- ^ DATA - the data send along with the transaction. + } + deriving (Eq, Show, Generic) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 2 }) ''Transaction) + +-- | Block information with full transactions. +type Block = BlockT Transaction + +-- | Block information. +-- It is parameterized by the type of transactions stored in the block because +-- sometimes only TX hashes may be stored. +data BlockT tx = Block + { blockNumber :: !(Maybe Quantity) + -- ^ QUANTITY - the block number. null when its pending block. + , blockHash :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - hash of the block. null when its pending block. + , blockParentHash :: !HexString + -- ^ DATA, 32 Bytes - hash of the parent block. + , blockNonce :: !(Maybe HexString) + -- ^ DATA, 8 Bytes - hash of the generated proof-of-work. null when its pending block. + , blockSha3Uncles :: !HexString + -- ^ DATA, 32 Bytes - SHA3 of the uncles data in the block. + , blockLogsBloom :: !(Maybe HexString) + -- ^ DATA, 256 Bytes - the bloom filter for the logs of the block. null when its pending block. + , blockTransactionsRoot :: !HexString + -- ^ DATA, 32 Bytes - the root of the transaction trie of the block. + , blockStateRoot :: !HexString + -- ^ DATA, 32 Bytes - the root of the final state trie of the block. + , blockReceiptsRoot :: !(Maybe HexString) + -- ^ DATA, 32 Bytes - the root of the receipts trie of the block. + , blockMiner :: !Address + -- ^ DATA, 20 Bytes - the address of the beneficiary to whom the mining rewards were given. + , blockDifficulty :: !(Maybe Quantity) + -- ^ QUANTITY - integer of the difficulty for this block. + , blockExtraData :: !HexString + -- ^ DATA - the "extra data" field of this block. + , blockSize :: !Quantity + -- ^ QUANTITY - integer the size of this block in bytes. + , blockGasLimit :: !Quantity + -- ^ QUANTITY - the maximum gas allowed in this block. + , blockGasUsed :: !Quantity + -- ^ QUANTITY - the total used gas by all transactions in this block. + , blockTimestamp :: !Quantity + -- ^ QUANTITY - the unix timestamp for when the block was collated. + , blockTransactions :: ![tx] + -- ^ Array of transaction objects. + , blockUncles :: ![HexString] + -- ^ Array - Array of uncle hashes. + } + deriving (Show, Generic) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''BlockT) + +-- | Fee History information +data FeeHistory + = FeeHistory + { feeHistoryBaseFeePerBlobGas :: [Quantity] + -- ^ array of block base fees per blob gas. + , feeHistoryBaseFeePerGas :: [Quantity] + -- ^ Array of block base fees per gas. + , feeHistoryBlobGasUsedRatio :: [Rational] + -- ^ Array of block base fees per blob gas. + , feeHistoryGasUsedRatio :: [Rational] + -- ^ Array of block gas used ratios. + , feeHistoryOldestBlock :: Quantity + -- ^ QUANTITY - lowest number block of returned range. + , feeHistoryReward :: [[Quantity]] + -- ^ Two-dimensional array of effective priority fees per gas at the requested block percentiles. + } + deriving (Generic, Show) + +$(deriveJSON defaultOptions{fieldLabelModifier = over _head toLower . drop 10} ''FeeHistory) diff --git a/packages/ethereum/src/Network/Ethereum/Api/Web3.hs b/packages/ethereum/src/Network/Ethereum/Api/Web3.hs new file mode 100644 index 00000000..1a0b6f3a --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Api/Web3.hs @@ -0,0 +1,30 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Ethereum.Api.Web3 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unknown +-- +-- Ethereum node JSON-RPC API methods with `web3_` prefix. +-- + +module Network.Ethereum.Api.Web3 where + +import Data.ByteArray.HexString (HexString) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Returns current node version string. +clientVersion :: JsonRpc m => m Text +{-# INLINE clientVersion #-} +clientVersion = remote "web3_clientVersion" + +-- | Returns Keccak-256 (not the standardized SHA3-256) of the given data. +sha3 :: JsonRpc m => HexString -> m HexString +{-# INLINE sha3 #-} +sha3 = remote "web3_sha3" diff --git a/packages/ethereum/src/Network/Ethereum/Chain.hs b/packages/ethereum/src/Network/Ethereum/Chain.hs new file mode 100644 index 00000000..6993fa5e --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Chain.hs @@ -0,0 +1,37 @@ +-- | +-- Module : Network.Ethereum.Chain +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum chain IDs. +-- + +module Network.Ethereum.Chain where + +-- | Ethereum mainnet CHAIN_ID from EIP155 +foundation :: Integer +foundation = 1 + +-- | Ethereum testnet CHAIN_ID from EIP155 +ropsten :: Integer +ropsten = 3 + +-- | Rokenby CHAIN_ID from EIP155 +rikenby :: Integer +rikenby = 4 + +-- | Kovan CHAIN_ID from EIP155 +kovan :: Integer +kovan = 42 + +-- | Ethereum Classic mainnet CHAIN_ID from EIP155 +classic :: Integer +classic = 61 + +-- | Ethereum Classic testnet CHAIN_ID from EIP155 +classicTestnet :: Integer +classicTestnet = 62 diff --git a/packages/ethereum/src/Network/Ethereum/Contract.hs b/packages/ethereum/src/Network/Ethereum/Contract.hs new file mode 100644 index 00000000..c021fff3 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Contract.hs @@ -0,0 +1,54 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Ethereum.Contract +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Smart contract type class and utils. A contract in the sense of Solidity +-- is a collection of code (its functions) and data (its state) that resides +-- at a specific address on the Ethereum blockchain. +-- + +module Network.Ethereum.Contract where + +import Data.Proxy (Proxy) +import Data.Text (Text) + +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Prim.Address (Address) +import Network.Ethereum.Account.Class (Account) +import Network.Ethereum.Account.Safe (safeConfirmations, safeSend) +import Network.Ethereum.Api.Types (receiptContractAddress) +import Network.Ethereum.Contract.Method (Method) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Contract description type clase +class Contract a where + -- | Contract Solidity ABI + -- https://solidity.readthedocs.io/en/latest/abi-spec.html + abi :: Proxy a -> Text + + -- | Contract bytecode as hex string + bytecode :: Proxy a -> HexString + +-- | Create new smart contract on blockchain +new :: (Account p t, JsonRpc m, Method a, Monad (t m)) + => a + -- ^ Contract constructor + -> t m (Either HexString (Maybe Address)) + -- ^ Address of deployed contract when transaction success; + -- transaction hash in case of a timeout +new = fmap (mapRight receiptContractAddress) . safeSend safeConfirmations + where + mapRight f e = + case e of + Left x -> Left x + Right y -> Right $ f y diff --git a/packages/ethereum/src/Network/Ethereum/Contract/Event.hs b/packages/ethereum/src/Network/Ethereum/Contract/Event.hs new file mode 100644 index 00000000..cbd20455 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Contract/Event.hs @@ -0,0 +1,22 @@ +-- | +-- Module : Network.Ethereum.Contract.Event +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum contract event support. +-- + +module Network.Ethereum.Contract.Event + ( + module Network.Ethereum.Contract.Event.Common + , module Network.Ethereum.Contract.Event.SingleFilter + , module Network.Ethereum.Contract.Event.MultiFilter + ) where + +import Network.Ethereum.Contract.Event.Common +import Network.Ethereum.Contract.Event.MultiFilter +import Network.Ethereum.Contract.Event.SingleFilter diff --git a/packages/ethereum/src/Network/Ethereum/Contract/Event/Common.hs b/packages/ethereum/src/Network/Ethereum/Contract/Event/Common.hs new file mode 100644 index 00000000..4c24e4f2 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Contract/Event/Common.hs @@ -0,0 +1,83 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE GADTs #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE UndecidableInstances #-} + +-- | +-- Module : Network.Ethereum.Contract.Event.Common +-- Copyright : FOAM team 2018 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Common event manipulation functions. +-- + +module Network.Ethereum.Contract.Event.Common where + +import Control.Concurrent (threadDelay) +import Control.Exception (Exception, throwIO) +import Control.Monad.IO.Class (liftIO) +import Data.Either (lefts, rights) + +import Data.Solidity.Event (DecodeEvent (..)) +import qualified Network.Ethereum.Api.Eth as Eth +import Network.Ethereum.Api.Types (Change (..), DefaultBlock (..), + Filter (..), Quantity) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Event callback control response +data EventAction = ContinueEvent + | TerminateEvent + deriving (Show, Eq) + + +data FilterChange a = FilterChange + { filterChangeRawChange :: Change + , filterChangeEvent :: a + } + +data EventParseFailure = EventParseFailure String + deriving (Show) + +instance Exception EventParseFailure + +mkFilterChanges :: DecodeEvent i ni e + => [Change] + -> IO [FilterChange e] +mkFilterChanges changes = + let eChanges = map (\c@Change{..} -> FilterChange c <$> decodeEvent changeTopics changeData) changes + ls = lefts eChanges + rs = rights eChanges + in if ls /= [] then throwIO (EventParseFailure $ show ls) else pure rs + + +data FilterStreamState e = FilterStreamState + { fssCurrentBlock :: Quantity + , fssInitialFilter :: Filter e + , fssWindowSize :: Integer + } + + +-- | Coerce a 'DefaultBlock' into a numerical block number. +mkBlockNumber :: JsonRpc m => DefaultBlock -> m Quantity +mkBlockNumber bm = case bm of + BlockWithNumber bn -> return bn + Earliest -> return 0 + _ -> Eth.blockNumber + + +pollTillBlockProgress :: JsonRpc m => Quantity -> m Quantity +pollTillBlockProgress currentBlock = do + bn <- Eth.blockNumber + if currentBlock >= bn + then do + liftIO $ threadDelay 3000000 + pollTillBlockProgress currentBlock + else pure bn diff --git a/src/Network/Ethereum/Contract/Event/MultiFilter.hs b/packages/ethereum/src/Network/Ethereum/Contract/Event/MultiFilter.hs similarity index 71% rename from src/Network/Ethereum/Contract/Event/MultiFilter.hs rename to packages/ethereum/src/Network/Ethereum/Contract/Event/MultiFilter.hs index 7328d599..3ce056a4 100644 --- a/src/Network/Ethereum/Contract/Event/MultiFilter.hs +++ b/packages/ethereum/src/Network/Ethereum/Contract/Event/MultiFilter.hs @@ -1,42 +1,52 @@ +{-# LANGUAGE CPP #-} {-# LANGUAGE DataKinds #-} {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE FunctionalDependencies #-} {-# LANGUAGE GADTs #-} {-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE RankNTypes #-} {-# LANGUAGE RecordWildCards #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE TypeApplications #-} -{-# LANGUAGE TypeFamilies #-} {-# LANGUAGE TypeFamilyDependencies #-} {-# LANGUAGE TypeOperators #-} {-# LANGUAGE UndecidableInstances #-} - -module Network.Ethereum.Contract.Event.MultiFilter -- * MultiEventMonitors - ( MultiFilter(..) - , minStartBlock - , minEndBlock - , modifyMultiFilter - -- * With geth filters - , multiEvent - , multiEvent' - , multiEventMany' - - -- * Without geth filters - , multiEventNoFilter - , multiEventNoFilter' - , multiEventManyNoFilter' - - -- * ReExports - , Handlers - , Handler(..) - , Rec(..) - ) where +-- | +-- Module : Network.Ethereum.Contract.Event.MultiFilter +-- Copyright : FOAM team 2018 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Parallel multiple event filters. +-- + +module Network.Ethereum.Contract.Event.MultiFilter + ( + -- * The @MultiFilter@ type + MultiFilter(..) + , minStartBlock + , minEndBlock + , modifyMultiFilter + + -- * With geth filters + , multiEvent + , multiEventMany + + -- * Without geth filters + , multiEventNoFilter + , multiEventManyNoFilter + + -- * Re-exports + , Handlers + , Handler(..) + , Rec(..) + ) where import Control.Concurrent (threadDelay) -import Control.Concurrent.Async (Async) import Control.Monad (forM, void, when) import Control.Monad.IO.Class (MonadIO (..)) import Control.Monad.Trans.Class (lift) @@ -50,20 +60,31 @@ import Data.Machine (MachineT, asParts, import Data.Machine.Plan (PlanT, stop, yield) import Data.Maybe (catMaybes, fromJust, listToMaybe) -import Data.Monoid ((<>)) +import Data.Tagged (Tagged (..)) +import Data.Vinyl (Rec ((:&), RNil), + RecApplicative) +import Data.Vinyl.CoRec (CoRec (..), Field, + FoldRec, Handler (H), + Handlers, coRecToRec, + firstField, match, + onField) +import Data.Vinyl.Functor (Compose (..), + Identity (..)) +#if MIN_VERSION_vinyl(0,10,0) +import Data.Vinyl (RPureConstrained) +#else import Data.Proxy (Proxy (..)) -import Data.Tagged -import Data.Vinyl -import Data.Vinyl.CoRec -import Data.Vinyl.Functor -import Data.Vinyl.TypeLevel -import Network.Ethereum.ABI.Event (DecodeEvent (..)) -import Network.Ethereum.Contract.Event.Common -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Provider (Web3, forkWeb3) -import Network.Ethereum.Web3.Types (Change (..), +import Data.Vinyl.TypeLevel (AllAllSat) +#endif + +import Data.Solidity.Event (DecodeEvent (..)) +import qualified Network.Ethereum.Api.Eth as Eth +import Network.Ethereum.Api.Types (Change (..), DefaultBlock (..), Filter (..), Quantity) +import Network.JsonRpc.TinyClient (JsonRpc(..)) +import Network.Ethereum.Contract.Event.Common + -------------------------------------------------------------------------------- -- | MultiFilters -------------------------------------------------------------------------------- @@ -91,32 +112,25 @@ modifyMultiFilter -> MultiFilter es -> MultiFilter es modifyMultiFilter _ NilFilters = NilFilters -modifyMultiFilter h (f :? fs) = (h f :? modifyMultiFilter h fs) +modifyMultiFilter h (f :? fs) = h f :? modifyMultiFilter h fs multiEvent :: ( PollFilters es , QueryAllLogs es - , MapHandlers Web3 es (WithChange es) - , AllAllSat '[HasLogIndex] (WithChange es) - , RecApplicative (WithChange es) - ) - => MultiFilter es - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 (Async ()) -multiEvent fltrs = forkWeb3 . multiEvent' fltrs - -multiEvent' - :: ( PollFilters es - , QueryAllLogs es - , MapHandlers Web3 es (WithChange es) + , MapHandlers m es (WithChange es) +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilter es - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 () -multiEvent' fltrs = multiEventMany' fltrs 0 + -> Handlers es (ReaderT Change m EventAction) + -> m () +multiEvent fltrs = multiEventMany fltrs 0 data MultiFilterStreamState es = MultiFilterStreamState { mfssCurrentBlock :: Quantity @@ -125,18 +139,23 @@ data MultiFilterStreamState es = } -multiEventMany' +multiEventMany :: ( PollFilters es , QueryAllLogs es - , MapHandlers Web3 es (WithChange es) + , MapHandlers m es (WithChange es) +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilter es -> Integer - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 () -multiEventMany' fltrs window handlers = do + -> Handlers es (ReaderT Change m EventAction) + -> m () +multiEventMany fltrs window handlers = do start <- mkBlockNumber $ minStartBlock fltrs let initState = MultiFilterStreamState { mfssCurrentBlock = start @@ -157,15 +176,18 @@ multiEventMany' fltrs window handlers = do let pollTo = minEndBlock fltrs' void $ reduceMultiEventStream (pollMultiFilter fIds pollTo) handlers -multiFilterStream - :: MultiFilterStreamState es - -> MachineT Web3 k (MultiFilter es) +multiFilterStream :: JsonRpc m + => MultiFilterStreamState es + -> MachineT m k (MultiFilter es) multiFilterStream initialPlan = do unfoldPlan initialPlan $ \s -> do end <- lift . mkBlockNumber . minEndBlock . mfssInitialMultiFilter $ initialPlan filterPlan end s where - filterPlan :: Quantity -> MultiFilterStreamState es -> PlanT k (MultiFilter es) Web3 (MultiFilterStreamState es) + filterPlan :: JsonRpc m + => Quantity + -> MultiFilterStreamState es + -> PlanT k (MultiFilter es) m (MultiFilterStreamState es) filterPlan end initialState@MultiFilterStreamState{..} = do if mfssCurrentBlock > end then stop @@ -191,7 +213,7 @@ type family WithChange (es :: [*]) = (es' :: [*]) | es' -> es where WithChange (e : es) = FilterChange e : WithChange es class QueryAllLogs (es :: [*]) where - queryAllLogs :: MultiFilter es -> Web3 [Field (WithChange es)] + queryAllLogs :: JsonRpc m => MultiFilter es -> m [Field (WithChange es)] instance QueryAllLogs '[] where queryAllLogs NilFilters = pure [] @@ -217,13 +239,21 @@ instance HasLogIndex (FilterChange e) where (,) <$> changeBlockNumber filterChangeRawChange <*> changeLogIndex filterChangeRawChange sortChanges +#if MIN_VERSION_vinyl(0,10,0) + :: ( RPureConstrained HasLogIndex es +#else :: ( AllAllSat '[HasLogIndex] es +#endif , RecApplicative es ) => [Field es] -> [Field es] sortChanges changes = +#if MIN_VERSION_vinyl(0,10,0) + let sorterProj change = onField @HasLogIndex getLogIndex change +#else let sorterProj change = onField (Proxy @'[HasLogIndex]) getLogIndex change +#endif in sortOn sorterProj changes class MapHandlers m es es' where @@ -239,11 +269,11 @@ instance , MapHandlers m es es' ) => MapHandlers m (e : es) (FilterChange e : es') where - mapHandlers ((H f) :& fs) = - let f' = \FilterChange{..} -> do + mapHandlers (H f :& fs) = + let f' FilterChange{..} = do act <- runReaderT (f filterChangeEvent) filterChangeRawChange return ((,) act <$> changeBlockNumber filterChangeRawChange) - in (H f') :& mapHandlers fs + in H f' :& mapHandlers fs reduceMultiEventStream @@ -270,30 +300,35 @@ reduceMultiEventStream filterChanges handlers = fmap listToMaybe . runT $ -- | 'playLogs' streams the 'filterStream' and calls eth_getLogs on these 'Filter' objects. playMultiLogs - :: forall es k. + :: forall es k m. ( QueryAllLogs es +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilterStreamState es - -> MachineT Web3 k [Field (WithChange es)] + -> MachineT m k [Field (WithChange es)] playMultiLogs s = fmap sortChanges $ multiFilterStream s ~> autoM queryAllLogs data TaggedFilterIds (es :: [*]) where - TaggedFilterNil :: TaggedFilterIds '[] - TaggedFilterCons :: Tagged e Quantity -> TaggedFilterIds es -> TaggedFilterIds (e : es) + TaggedFilterNil :: TaggedFilterIds '[] + TaggedFilterCons :: Tagged e Quantity -> TaggedFilterIds es -> TaggedFilterIds (e : es) class PollFilters (es :: [*]) where - openMultiFilter :: MultiFilter es -> Web3 (TaggedFilterIds es) - checkMultiFilter :: TaggedFilterIds es -> Web3 [Field (WithChange es)] - closeMultiFilter :: TaggedFilterIds es -> Web3 () + openMultiFilter :: JsonRpc m => MultiFilter es -> m (TaggedFilterIds es) + checkMultiFilter :: JsonRpc m => TaggedFilterIds es -> m [Field (WithChange es)] + closeMultiFilter :: JsonRpc m => TaggedFilterIds es -> m () instance PollFilters '[] where - openMultiFilter _ = pure TaggedFilterNil - checkMultiFilter _ = pure [] - closeMultiFilter _ = pure () + openMultiFilter _ = pure TaggedFilterNil + checkMultiFilter _ = pure [] + closeMultiFilter _ = pure () instance forall e i ni es. ( DecodeEvent i ni e @@ -321,14 +356,18 @@ instance forall e i ni es. pollMultiFilter :: ( PollFilters es , RecApplicative (WithChange es) +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif + , JsonRpc m ) => TaggedFilterIds es -> DefaultBlock - -> MachineT Web3 k [Field (WithChange es)] + -> MachineT m k [Field (WithChange es)] pollMultiFilter is = construct . pollPlan is where - -- pollPlan :: TaggedFilterIds es -> DefaultBlock -> PlanT k [Field (Map (TyCon1 FilterChange) es)] Web3 () pollPlan (fIds :: TaggedFilterIds es) end = do bn <- lift $ Eth.blockNumber if BlockWithNumber bn > end @@ -343,41 +382,39 @@ pollMultiFilter is = construct . pollPlan is -------------------------------------------------------------------------------- - multiEventNoFilter :: ( QueryAllLogs es - , MapHandlers Web3 es (WithChange es) - , AllAllSat '[HasLogIndex] (WithChange es) - , RecApplicative (WithChange es) - ) - => MultiFilter es - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 (Async ()) -multiEventNoFilter fltrs = forkWeb3 . multiEventNoFilter' fltrs - -multiEventNoFilter' - :: ( QueryAllLogs es - , MapHandlers Web3 es (WithChange es) + , MapHandlers m es (WithChange es) +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilter es - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 () -multiEventNoFilter' fltrs = multiEventManyNoFilter' fltrs 0 + -> Handlers es (ReaderT Change m EventAction) + -> m () +multiEventNoFilter fltrs = multiEventManyNoFilter fltrs 0 -multiEventManyNoFilter' +multiEventManyNoFilter :: ( QueryAllLogs es - , MapHandlers Web3 es (WithChange es) + , MapHandlers m es (WithChange es) +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilter es -> Integer - -> Handlers es (ReaderT Change Web3 EventAction) - -> Web3 () -multiEventManyNoFilter' fltrs window handlers = do + -> Handlers es (ReaderT Change m EventAction) + -> m () +multiEventManyNoFilter fltrs window handlers = do start <- mkBlockNumber $ minStartBlock fltrs let initState = MultiFilterStreamState { mfssCurrentBlock = start @@ -402,15 +439,18 @@ multiEventManyNoFilter' fltrs window handlers = do } in void $ reduceMultiEventStream (playNewMultiLogs pollingFilterState) handlers -newMultiFilterStream - :: MultiFilterStreamState es - -> MachineT Web3 k (MultiFilter es) +newMultiFilterStream :: JsonRpc m + => MultiFilterStreamState es + -> MachineT m k (MultiFilter es) newMultiFilterStream initialPlan = do unfoldPlan initialPlan $ \s -> do let end = minEndBlock . mfssInitialMultiFilter $ initialPlan filterPlan end s where - filterPlan :: DefaultBlock -> MultiFilterStreamState es -> PlanT k (MultiFilter es) Web3 (MultiFilterStreamState es) + filterPlan :: JsonRpc m + => DefaultBlock + -> MultiFilterStreamState es + -> PlanT k (MultiFilter es) m (MultiFilterStreamState es) filterPlan end initialState@MultiFilterStreamState{..} = do if BlockWithNumber mfssCurrentBlock > end then stop @@ -424,13 +464,18 @@ newMultiFilterStream initialPlan = do filterPlan end initialState { mfssCurrentBlock = newestBlockNumber + 1 } playNewMultiLogs - :: forall es k. + :: forall es k m. ( QueryAllLogs es +#if MIN_VERSION_vinyl(0,10,0) + , RPureConstrained HasLogIndex (WithChange es) +#else , AllAllSat '[HasLogIndex] (WithChange es) +#endif , RecApplicative (WithChange es) + , JsonRpc m ) => MultiFilterStreamState es - -> MachineT Web3 k [Field (WithChange es)] + -> MachineT m k [Field (WithChange es)] playNewMultiLogs s = fmap sortChanges $ newMultiFilterStream s ~> autoM queryAllLogs diff --git a/src/Network/Ethereum/Contract/Event/SingleFilter.hs b/packages/ethereum/src/Network/Ethereum/Contract/Event/SingleFilter.hs similarity index 76% rename from src/Network/Ethereum/Contract/Event/SingleFilter.hs rename to packages/ethereum/src/Network/Ethereum/Contract/Event/SingleFilter.hs index bffde2ce..0d06d4f3 100644 --- a/src/Network/Ethereum/Contract/Event/SingleFilter.hs +++ b/packages/ethereum/src/Network/Ethereum/Contract/Event/SingleFilter.hs @@ -1,31 +1,36 @@ {-# LANGUAGE DataKinds #-} {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE FunctionalDependencies #-} {-# LANGUAGE GADTs #-} {-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE RankNTypes #-} {-# LANGUAGE RecordWildCards #-} {-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeApplications #-} -{-# LANGUAGE TypeFamilies #-} {-# LANGUAGE TypeFamilyDependencies #-} {-# LANGUAGE TypeOperators #-} {-# LANGUAGE UndecidableInstances #-} -module Network.Ethereum.Contract.Event.SingleFilter - ( event - , event' - , eventMany' - , eventNoFilter - , eventNoFilter' - , eventManyNoFilter' - ) +-- | +-- Module : Network.Ethereum.Contract.Event.SingleFilter +-- Copyright : FOAM team 2018 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Contract event filters. +-- - where +module Network.Ethereum.Contract.Event.SingleFilter + ( + event + , eventMany + , eventNoFilter + , eventManyNoFilter + ) where import Control.Concurrent (threadDelay) -import Control.Concurrent.Async (Async) import Control.Monad (forM, void, when) import Control.Monad.IO.Class (MonadIO (..)) import Control.Monad.Trans.Class (lift) @@ -37,40 +42,34 @@ import Data.Machine (MachineT, asParts, unfoldPlan, (~>)) import Data.Machine.Plan (PlanT, stop, yield) import Data.Maybe (catMaybes, listToMaybe) -import Network.Ethereum.ABI.Event (DecodeEvent (..)) -import Network.Ethereum.Contract.Event.Common -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Provider (Web3, forkWeb3) -import Network.Ethereum.Web3.Types (Change (..), + +import Data.Solidity.Event (DecodeEvent (..)) +import qualified Network.Ethereum.Api.Eth as Eth +import Network.Ethereum.Api.Types (Change (..), DefaultBlock (..), Filter (..), Quantity) +import Network.Ethereum.Contract.Event.Common +import Network.JsonRpc.TinyClient (JsonRpc (..)) --- | Run 'event\'' one block at a time. -event :: DecodeEvent i ni e - => Filter e - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 (Async ()) -event fltr = forkWeb3 . event' fltr - --- | Same as 'event', but does not immediately spawn a new thread. -event' :: DecodeEvent i ni e +-- | Run one block at a time. +event :: (DecodeEvent i ni e, JsonRpc m) => Filter e - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 () -event' fltr = eventMany' fltr 0 + -> (e -> ReaderT Change m EventAction) + -> m () +event fltr = eventMany fltr 0 --- | 'eventMany\'' take s a filter, a window size, and a handler. +-- | 'eventMany' take s a filter, a window size, and a handler. -- -- It runs the handler over the results of 'eventLogs' results using -- 'reduceEventStream'. If no 'TerminateEvent' action is thrown and -- the toBlock is not yet reached, it then transitions to polling. -- -eventMany' :: DecodeEvent i ni e +eventMany :: (DecodeEvent i ni e, JsonRpc m) => Filter e -> Integer - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 () -eventMany' fltr window handler = do + -> (e -> ReaderT Change m EventAction) + -> m () +eventMany fltr window handler = do start <- mkBlockNumber $ filterFromBlock fltr let initState = FilterStreamState { fssCurrentBlock = start , fssInitialFilter = fltr @@ -118,22 +117,21 @@ reduceEventStream filterChanges handler = fmap listToMaybe . runT $ return ((,) act <$> changeBlockNumber filterChangeRawChange) -- | 'playLogs' streams the 'filterStream' and calls eth_getLogs on these 'Filter' objects. -playOldLogs - :: DecodeEvent i ni e - => FilterStreamState e - -> MachineT Web3 k [FilterChange e] +playOldLogs :: (DecodeEvent i ni e, JsonRpc m) + => FilterStreamState e + -> MachineT m k [FilterChange e] playOldLogs s = filterStream s ~> autoM Eth.getLogs ~> autoM (liftIO . mkFilterChanges) -- | Polls a filter from the given filterId until the target toBlock is reached. -pollFilter :: forall i ni e k . DecodeEvent i ni e +pollFilter :: forall i ni e k m . (DecodeEvent i ni e, JsonRpc m) => Quantity -> DefaultBlock - -> MachineT Web3 k [FilterChange e] + -> MachineT m k [FilterChange e] pollFilter i = construct . pollPlan i where - pollPlan :: Quantity -> DefaultBlock -> PlanT k [FilterChange e] Web3 () + pollPlan :: Quantity -> DefaultBlock -> PlanT k [FilterChange e] m () pollPlan fid end = do bn <- lift $ Eth.blockNumber if BlockWithNumber bn > end @@ -153,11 +151,12 @@ pollFilter i = construct . pollPlan i -- which cover this filter in intervals of size `windowSize`. The machine -- halts whenever the `fromBlock` of a spanning filter either (1) excedes then -- initial filter's `toBlock` or (2) is greater than the chain head's block number. -filterStream :: FilterStreamState e - -> MachineT Web3 k (Filter e) +filterStream :: JsonRpc m + => FilterStreamState e + -> MachineT m k (Filter e) filterStream initialPlan = unfoldPlan initialPlan filterPlan where - filterPlan :: FilterStreamState e -> PlanT k (Filter e) Web3 (FilterStreamState e) + filterPlan :: JsonRpc m => FilterStreamState e -> PlanT k (Filter e) m (FilterStreamState e) filterPlan initialState@FilterStreamState{..} = do end <- lift . mkBlockNumber $ filterToBlock fssInitialFilter if fssCurrentBlock > end @@ -172,29 +171,18 @@ filterStream initialPlan = unfoldPlan initialPlan filterPlan -------------------------------------------------------------------------------- --- | Run 'event\'' one block at a time. -eventNoFilter - :: DecodeEvent i ni e - => Filter e - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 (Async ()) -eventNoFilter fltr = forkWeb3 . event' fltr - --- | Same as 'event', but does not immediately spawn a new thread. -eventNoFilter' - :: DecodeEvent i ni e - => Filter e - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 () -eventNoFilter' fltr = eventManyNoFilter' fltr 0 - -eventManyNoFilter' - :: DecodeEvent i ni e - => Filter e - -> Integer - -> (e -> ReaderT Change Web3 EventAction) - -> Web3 () -eventManyNoFilter' fltr window handler = do +eventNoFilter :: (DecodeEvent i ni e, JsonRpc m) + => Filter e + -> (e -> ReaderT Change m EventAction) + -> m () +eventNoFilter fltr = eventManyNoFilter fltr 0 + +eventManyNoFilter :: (DecodeEvent i ni e, JsonRpc m) + => Filter e + -> Integer + -> (e -> ReaderT Change m EventAction) + -> m () +eventManyNoFilter fltr window handler = do start <- mkBlockNumber $ filterFromBlock fltr let initState = FilterStreamState { fssCurrentBlock = start , fssInitialFilter = fltr @@ -219,21 +207,20 @@ eventManyNoFilter' fltr window handler = do in void $ reduceEventStream (playNewLogs pollingFilterState) handler -- | 'playLogs' streams the 'filterStream' and calls eth_getLogs on these 'Filter' objects. -playNewLogs - :: DecodeEvent i ni e - => FilterStreamState e - -> MachineT Web3 k [FilterChange e] +playNewLogs :: (DecodeEvent i ni e, JsonRpc m) + => FilterStreamState e + -> MachineT m k [FilterChange e] playNewLogs s = newFilterStream s ~> autoM Eth.getLogs ~> autoM (liftIO . mkFilterChanges) -newFilterStream - :: FilterStreamState e - -> MachineT Web3 k (Filter e) +newFilterStream :: JsonRpc m + => FilterStreamState e + -> MachineT m k (Filter e) newFilterStream initialState = unfoldPlan initialState filterPlan where - filterPlan :: FilterStreamState e -> PlanT k (Filter e) Web3 (FilterStreamState e) + filterPlan :: JsonRpc m => FilterStreamState e -> PlanT k (Filter e) m (FilterStreamState e) filterPlan s@FilterStreamState{..} = do if BlockWithNumber fssCurrentBlock > filterToBlock fssInitialFilter then stop diff --git a/packages/ethereum/src/Network/Ethereum/Contract/Method.hs b/packages/ethereum/src/Network/Ethereum/Contract/Method.hs new file mode 100644 index 00000000..c41b13ea --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Contract/Method.hs @@ -0,0 +1,33 @@ +-- | +-- Module : Network.Ethereum.Contract.Method +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum contract method support. +-- + +module Network.Ethereum.Contract.Method where + +import Data.Proxy (Proxy) +import Data.Solidity.Abi (AbiPut, AbiType (..)) +import Data.Solidity.Abi.Generic () +import Data.Solidity.Prim.Bytes (Bytes) + +-- | Smart contract method encoding +class AbiPut a => Method a where + -- | Solidity function selector + -- https://solidity.readthedocs.io/en/latest/abi-spec.html#function-selector-and-argument-encoding + selector :: Proxy a -> Bytes + +instance AbiType () where + isDynamic _ = False + +instance AbiPut () + +-- | Fallback contract method +instance Method () where + selector _ = mempty diff --git a/packages/ethereum/src/Network/Ethereum/Contract/TH.hs b/packages/ethereum/src/Network/Ethereum/Contract/TH.hs new file mode 100644 index 00000000..ff3a13a9 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Contract/TH.hs @@ -0,0 +1,360 @@ +{-# LANGUAGE BangPatterns #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Ethereum.Contract.TH +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Contract abstraction is a high level interface of web3 library. +-- +-- The Application Binary Interface is the standard way to interact +-- with contracts in the Ethereum ecosystem. It can be described by +-- specially JSON file, like @ERC20.json@. This module use TemplateHaskell +-- for generation described in Abi contract methods and events. Helper +-- functions and instances inserted in haskell module and can be used in +-- another modules or in place. +-- +-- @ +-- import Network.Ethereum.Contract.TH +-- +-- [abiFrom|examples/ERC20.json|] +-- +-- main = do +-- runWeb3 $ event' def $ +-- \(Transfer _ to val) -> liftIO $ do print to +-- print val +-- @ +-- +-- Full code example available in examples folder. +-- + +module Network.Ethereum.Contract.TH + ( + -- * The contract quasiquoters + abi + , abiFrom + ) where + +import Control.Applicative ((<|>)) +import Control.Monad (replicateM, (<=<)) +import qualified Data.Aeson as Aeson +import Data.Aeson.Casing (aesonDrop, camelCase) +import Data.ByteArray (convert) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower, toUpper) +import qualified Data.Char as Char +import Data.Default (Default (..)) +import Data.List (group, sort, uncons) +import Data.Tagged (Tagged) +import Data.Text (Text) +import qualified Data.Text as T +import qualified Data.Text.Lazy as LT +import qualified Data.Text.Lazy.Encoding as LT +import Data.Tuple.OneTuple (OneTuple, only) +import Generics.SOP (Generic) +import qualified GHC.Generics as GHC (Generic) +import Language.Haskell.TH +import Language.Haskell.TH.Quote +import Lens.Micro (_head, over, (^?)) +import Lens.Micro.Aeson (_JSON, _String, key) + +import Data.Solidity.Abi (AbiGet, AbiPut, AbiType (..)) +import Data.Solidity.Event (IndexedEvent (..)) +import Data.Solidity.Prim (Address, Bytes, BytesN, IntN, + ListN, UIntN) +import Language.Solidity.Abi (ContractAbi (..), + Declaration (..), + EventArg (..), + FunctionArg (..), + SolidityType (..), eventId, + methodId, + parseSolidityEventArgType, + parseSolidityFunctionArgType) +import Network.Ethereum.Account.Class (Account (..)) +import Network.Ethereum.Api.Types (DefaultBlock (..), + Filter (..), TxReceipt) +import qualified Network.Ethereum.Contract as Contract (Contract (..)) +import Network.Ethereum.Contract.Method (Method (..)) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Read contract Abi from file +abiFrom :: QuasiQuoter +abiFrom = quoteFile abi + +-- | QQ reader for contract Abi +abi :: QuasiQuoter +abi = QuasiQuoter + { quoteDec = quoteAbiDec + , quoteExp = quoteAbiExp + , quotePat = undefined + , quoteType = undefined } + +-- | Instance declaration with empty context +instanceD' :: Name -> TypeQ -> [DecQ] -> DecQ +instanceD' name insType = + instanceD (cxt []) (appT insType (conT name)) + +-- | Simple data type declaration with one constructor +dataD' :: Name -> ConQ -> [Name] -> DecQ +dataD' name rec' derive = + dataD (cxt []) name [] Nothing [rec'] [derivClause Nothing (conT <$> derive)] + +-- | Simple function declaration +funD' :: Name -> [PatQ] -> ExpQ -> DecQ +funD' name p f = funD name [clause p (normalB f) []] + +-- | Abi and Haskell types association +toHSType :: SolidityType -> TypeQ +toHSType s = case s of + SolidityBool -> conT ''Bool + SolidityAddress -> conT ''Address + SolidityUint n -> appT (conT ''UIntN) (numLit n) + SolidityInt n -> appT (conT ''IntN) (numLit n) + SolidityString -> conT ''Text + SolidityBytesN n -> appT (conT ''BytesN) (numLit n) + SolidityBytes -> conT ''Bytes + SolidityTuple [a] -> appT (conT ''OneTuple) (toHSType a) + SolidityTuple as -> foldl ( \b a -> appT b $ toHSType a ) ( tupleT (length as) ) as + SolidityVector ns a -> expandVector ns a + SolidityArray a -> appT listT $ toHSType a + where + numLit n = litT (numTyLit $ toInteger n) + expandVector :: [Int] -> SolidityType -> TypeQ + expandVector ns a = case uncons ns of + Just (n, rest) -> + if null rest + then conT ''ListN `appT` numLit n `appT` toHSType a + else conT ''ListN `appT` numLit n `appT` expandVector rest a + _ -> error $ "Impossible Nothing branch in `expandVector`: " ++ show ns ++ " " ++ show a + +typeFuncQ :: FunctionArg -> TypeQ +typeFuncQ t = case parseSolidityFunctionArgType t of + Left e -> error $ "Unable to parse solidity type: " ++ show e + Right ty -> toHSType ty + +typeEventQ :: EventArg -> TypeQ +typeEventQ t = case parseSolidityEventArgType t of + Left e -> error $ "Unable to parse solidity type: " ++ show e + Right ty -> toHSType ty + + +-- | Function argument to TH type +funBangType :: FunctionArg -> BangTypeQ +funBangType fa = + bangType (bang sourceNoUnpack sourceStrict) (typeFuncQ fa) + +funWrapper :: Bool + -- ^ Is constant? + -> Name + -- ^ Function name + -> Name + -- ^ Function data name + -> [FunctionArg] + -- ^ Parameters + -> Maybe [FunctionArg] + -- ^ Results + -> DecsQ +funWrapper c name dname args result = do + vars <- replicateM (length args) (newName "t") + a <- varT <$> newName "a" + t <- varT <$> newName "t" + m <- varT <$> newName "m" + + + let params = appsE $ conE dname : fmap varE vars + inputT = fmap typeFuncQ args + outputT = case result of + Nothing -> [t|$t $m ()|] + Just [x] -> [t|$t $m $(typeFuncQ x)|] + Just xs -> let outs = fmap typeFuncQ xs + in [t|$t $m $(foldl appT (tupleT (length xs)) outs)|] + receiptT = [t|$t $m (Either HexString TxReceipt)|] + + sequence [ + sigD name $ [t| + (JsonRpc $m, Account $a $t, Functor ($t $m)) => + $(arrowing $ inputT ++ [if c then outputT else receiptT]) + |] + , if c + then funD' name (varP <$> vars) $ case result of + Just [_] -> [|only <$> call $(params)|] + _ -> [|call $(params)|] + else funD' name (varP <$> vars) $ [|send $(params)|] + ] + where + arrowing [] = error "Impossible branch call" + arrowing [x] = x + arrowing (x : xs) = [t|$x -> $(arrowing xs)|] + +mkDecl :: Declaration -> DecsQ + +mkDecl ev@(DEvent uncheckedName inputs anonymous) = sequence + [ dataD' indexedName (normalC indexedName (map (toBang <=< tag) indexedArgs)) derivingD + , instanceD' indexedName (conT ''Generic) [] + , instanceD' indexedName (conT ''AbiType) [funD' 'isDynamic [] [|const False|]] + , instanceD' indexedName (conT ''AbiGet) [] + , dataD' nonIndexedName (normalC nonIndexedName (map (toBang <=< tag) nonIndexedArgs)) derivingD + , instanceD' nonIndexedName (conT ''Generic) [] + , instanceD' nonIndexedName (conT ''AbiType) [funD' 'isDynamic [] [|const False|]] + , instanceD' nonIndexedName (conT ''AbiGet) [] + , dataD' allName (recC allName (map (\(n, a) -> (\(b,t) -> return (n,b,t)) <=< toBang <=< typeEventQ $ a) allArgs)) derivingD + , instanceD' allName (conT ''Generic) [] + , instanceD' allName (conT ''Aeson.ToJSON) [funD' 'Aeson.toJSON [] [| Aeson.genericToJSON $ aesonDrop nameL (init' . camelCase) |] ] + , instanceD (cxt []) + (pure $ ConT ''IndexedEvent `AppT` ConT indexedName `AppT` ConT nonIndexedName `AppT` ConT allName) + [funD' 'isAnonymous [] [|const anonymous|]] + , instanceD (cxt []) + (pure $ ConT ''Default `AppT` (ConT ''Filter `AppT` ConT allName)) + [funD' 'def [] [|Filter Nothing Latest Latest $ Just topics|] ] + ] + where + name = if toLower (T.head uncheckedName) == Char.toUpper (T.head uncheckedName) then "EvT" <> uncheckedName else uncheckedName + !nameL = length (T.unpack name) + topics = [Just (T.unpack $ eventId ev)] <> replicate (length indexedArgs) Nothing + toBang ty = bangType (bang sourceNoUnpack sourceStrict) (return ty) + tag (n, ty) = AppT (AppT (ConT ''Tagged) (LitT $ NumTyLit n)) <$> typeEventQ ty + labeledArgs = zip [1..] inputs + indexedArgs = map (\(n, ea) -> (n, ea)) . filter (eveArgIndexed . snd) $ labeledArgs + indexedName = mkName $ over _head toUpper (T.unpack name) <> "Indexed" + nonIndexedArgs = map (\(n, ea) -> (n, ea)) . filter (not . eveArgIndexed . snd) $ labeledArgs + nonIndexedName = mkName $ over _head toUpper (T.unpack name) <> "NonIndexed" + allArgs :: [(Name, EventArg)] + allArgs = makeArgs name $ map (\i -> (eveArgName i, i)) inputs + allName = mkName $ over _head toUpper (T.unpack name) + derivingD = [''Show, ''Eq, ''Ord, ''GHC.Generic] + +-- TODO change this type name also +-- | Method declarations maker +mkDecl fun@(DFunction name constant inputs outputs) = (++) + <$> funWrapper constant fnName dataName inputs outputs + <*> sequence + [ dataD' dataName (normalC dataName bangInput) derivingD + , instanceD' dataName (conT ''Generic) [] + , instanceD' dataName (conT ''AbiType) + [funD' 'isDynamic [] [|const False|]] + , instanceD' dataName (conT ''AbiPut) [] + , instanceD' dataName (conT ''AbiGet) [] + , instanceD' dataName (conT ''Method) + [funD' 'selector [] [|const mIdent|]] + ] + where mIdent = T.unpack (methodId $ fun {funName = T.replace "'" "" name}) + dataName = mkName (over _head toUpper (T.unpack $ T.dropWhile (== '_') name <> "Data")) + fnName = mkName (over _head toLower (T.unpack name)) + bangInput = fmap funBangType inputs + derivingD = [''Show, ''Eq, ''Ord, ''GHC.Generic] + +mkDecl _ = return [] + +-- | Best-effort name recovery from ADT to original 'eveArgName' on inputs. +init' :: String -> String +init' [] = [] +init' xs = if Char.isDigit (last xs) then xs else init xs + +mkContractDecl :: Text -> Text -> Text -> Declaration -> DecsQ +mkContractDecl name a b (DConstructor inputs) = sequence + [ dataD' dataName (normalC dataName bangInput) derivingD + , instanceD' dataName (conT ''Generic) [] + , instanceD' dataName (conT ''AbiType) + [funD' 'isDynamic [] [|const False|]] + , instanceD' dataName (conT ''AbiPut) [] + , instanceD' dataName (conT ''Method) + [funD' 'selector [] [|convert . Contract.bytecode|]] + , instanceD' dataName (conT ''Contract.Contract) + [ funD' 'Contract.abi [] [|const abiString|] + , funD' 'Contract.bytecode [] [|const bytecodeString|] + ] + ] + where abiString = T.unpack a + bytecodeString = T.unpack b + dataName = mkName (over _head toUpper (T.unpack $ name <> "Contract")) + bangInput = fmap funBangType inputs + derivingD = [''Show, ''Eq, ''Ord, ''GHC.Generic] + +mkContractDecl _ _ _ _ = return [] + +-- | this function gives appropriate names for the accessors in the following way +-- | argName -> evArgName +-- | arg_name -> evArg_name +-- | _argName -> evArgName +-- | "" -> evi , for example Transfer(address, address uint256) ~> Transfer {transfer1 :: address, transfer2 :: address, transfer3 :: Integer} +makeArgs :: Text -> [(Text, EventArg)] -> [(Name, EventArg)] +makeArgs prefix ns = go 1 ns + where + prefixStr = over _head toLower . T.unpack $ prefix + go :: Int -> [(Text, EventArg)] -> [(Name, EventArg)] + go _ [] = [] + go i ((h, ty) : tail') + | T.null h = (mkName $ prefixStr ++ show i, ty) : go (i + 1) tail' + | otherwise = (mkName . (++ "_") . (++) prefixStr . over _head toUpper . T.unpack $ h, ty) : go (i + 1) tail' + +escape :: [Declaration] -> [Declaration] +escape = escapeEqualNames . fmap escapeReservedNames + +escapeEqualNames :: [Declaration] -> [Declaration] +escapeEqualNames = concatMap go . group . sort + where go [] = [] + go (x : xs) = x : zipWith appendToName xs hats + hats = [T.replicate n "'" | n <- [1..]] + appendToName d@(DFunction n _ _ _) a = d { funName = n <> a } + appendToName d@(DEvent n _ _) a = d { eveName = n <> a } + appendToName d _ = d + +escapeReservedNames :: Declaration -> Declaration +escapeReservedNames d@(DFunction n _ _ _) + | isKeyword n = d { funName = n <> "'" } + | otherwise = d +escapeReservedNames d = d + +isKeyword :: Text -> Bool +isKeyword = flip elem [ "as", "case", "of", "class" + , "data", "family", "instance" + , "default", "deriving", "do" + , "forall", "foreign", "hiding" + , "if", "then", "else", "import" + , "infix", "infixl", "infixr" + , "let", "in", "mdo", "module" + , "newtype", "proc", "qualified" + , "rec", "type", "where" + ] + +constructorSpec :: String -> Maybe (Text, Text, Text, Declaration) +constructorSpec str = do + name <- str ^? key "contractName" . _String + abiValue <- str ^? key "abi" + bytecode <- str ^? key "bytecode" . _String + decl <- filter isContructor . unAbi <$> str ^? key "abi" . _JSON + return (name, jsonEncode abiValue, bytecode, toConstructor decl) + where + jsonEncode = LT.toStrict . LT.decodeUtf8 . Aeson.encode + isContructor (DConstructor _) = True + isContructor _ = False + toConstructor [] = DConstructor [] + toConstructor [a] = a + toConstructor _ = error "Broken ABI: more that one constructor" + +-- | Abi to declarations converter +quoteAbiDec :: String -> DecsQ +quoteAbiDec str = + case str ^? _JSON <|> str ^? key "abi" . _JSON <|> str ^? key "compilerOutput" . key "abi" . _JSON of + Nothing -> fail "Unable to decode contract ABI" + Just (ContractAbi decs) -> do + funEvDecs <- concat <$> mapM mkDecl (escape decs) + case constructorSpec str of + Nothing -> return funEvDecs + Just (a, b, c, d) -> (funEvDecs ++) <$> mkContractDecl a b c d + +-- | Abi information string +quoteAbiExp :: String -> ExpQ +quoteAbiExp str = + case str ^? _JSON <|> str ^? key "abi" . _JSON of + Nothing -> fail "Unable to decode contract ABI" + Just a@(ContractAbi _) -> stringE (show a) diff --git a/packages/ethereum/src/Network/Ethereum/Ens.hs b/packages/ethereum/src/Network/Ethereum/Ens.hs new file mode 100644 index 00000000..c1b4491e --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Ens.hs @@ -0,0 +1,59 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Ethereum.Ens +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- ENS offers a secure & decentralised way to address resources both on +-- and off the blockchain using simple, human-readable names. +-- +-- This module provide basic ENS resolvers. +-- + +module Network.Ethereum.Ens where + +import Crypto.Ethereum (keccak256) +import Data.ByteArray (zero) +import Data.ByteArray.Sized (unsafeFromByteArrayAccess) +import Data.ByteString (ByteString) +import Data.ByteString.Char8 (split) +import Lens.Micro ((.~)) + +import Data.Solidity.Prim (Address, BytesN) +import Network.Ethereum.Account.Class (Account) +import Network.Ethereum.Account.Internal (AccountT, to, withParam) +import qualified Network.Ethereum.Ens.PublicResolver as Resolver +import qualified Network.Ethereum.Ens.Registry as Reg +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Namehash algorithm +-- http://docs.ens.domains/en/latest/implementers.html#algorithm +namehash :: ByteString + -- ^ Domain name + -> BytesN 32 + -- ^ Associated ENS node +namehash = + unsafeFromByteArrayAccess . foldr algo (zero 32) . split '.' + where + algo :: ByteString -> ByteString -> ByteString + algo a b = keccak256 (b <> keccak256 a) + +-- | Get address of ENS domain +resolve :: (JsonRpc m, Account p (AccountT p)) + => ByteString + -- ^ Domain name + -> AccountT p m Address + -- ^ Associated address +resolve name = do + r <- ensRegistry $ Reg.resolver node + withParam (to .~ r) $ Resolver.addr node + where + node = namehash name + ensRegistry = withParam $ to .~ "0x314159265dD8dbb310642f98f50C066173C1259b" diff --git a/packages/ethereum/src/Network/Ethereum/Ens/PublicResolver.hs b/packages/ethereum/src/Network/Ethereum/Ens/PublicResolver.hs new file mode 100644 index 00000000..c63881e1 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Ens/PublicResolver.hs @@ -0,0 +1,25 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Ethereum.Ens.PublicResolver +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum Name System public resolver smart contract. +-- + +module Network.Ethereum.Ens.PublicResolver where + +import Network.Ethereum.Contract.TH + +[abi|[{"stateMutability":"view","inputs":[{"name":"interfaceID","type":"bytes4"}],"name":"supportsInterface","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"},{"name":"contentTypes","type":"uint256"}],"name":"ABI","outputs":[{"name":"contentType","type":"uint256"},{"name":"data","type":"bytes"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"x","type":"bytes32"},{"name":"y","type":"bytes32"}],"name":"setPubkey","outputs":[],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"content","outputs":[{"name":"ret","type":"bytes32"}],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"addr","outputs":[{"name":"ret","type":"address"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"contentType","type":"uint256"},{"name":"data","type":"bytes"}],"name":"setABI","outputs":[],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"name","outputs":[{"name":"ret","type":"string"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"name","type":"string"}],"name":"setName","outputs":[],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"hash","type":"bytes32"}],"name":"setContent","outputs":[],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"pubkey","outputs":[{"name":"x","type":"bytes32"},{"name":"y","type":"bytes32"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"addr","type":"address"}],"name":"setAddr","outputs":[],"payable":false,"type":"function"},{"inputs":[{"name":"ensAddr","type":"address"}],"payable":false,"type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"a","type":"address"}],"name":"AddrChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"hash","type":"bytes32"}],"name":"ContentChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"name","type":"string"}],"name":"NameChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":true,"name":"contentType","type":"uint256"}],"name":"ABIChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"x","type":"bytes32"},{"indexed":false,"name":"y","type":"bytes32"}],"name":"PubkeyChanged","type":"event"}]|] diff --git a/packages/ethereum/src/Network/Ethereum/Ens/Registry.hs b/packages/ethereum/src/Network/Ethereum/Ens/Registry.hs new file mode 100644 index 00000000..abd64aad --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Ens/Registry.hs @@ -0,0 +1,25 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Ethereum.Ens.Registry +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ethereum Name System registry smart contract. +-- + +module Network.Ethereum.Ens.Registry where + +import Network.Ethereum.Contract.TH + +[abi|[{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"resolver","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"owner","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"label","type":"bytes32"},{"name":"owner","type":"address"}],"name":"setSubnodeOwner","outputs":[],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"ttl","type":"uint64"}],"name":"setTTL","outputs":[],"payable":false,"type":"function"},{"stateMutability":"view","inputs":[{"name":"node","type":"bytes32"}],"name":"ttl","outputs":[{"name":"","type":"uint64"}],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"resolver","type":"address"}],"name":"setResolver","outputs":[],"payable":false,"type":"function"},{"stateMutability":"nonpayable","inputs":[{"name":"node","type":"bytes32"},{"name":"owner","type":"address"}],"name":"setOwner","outputs":[],"payable":false,"type":"function"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"owner","type":"address"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":true,"name":"label","type":"bytes32"},{"indexed":false,"name":"owner","type":"address"}],"name":"NewOwner","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"resolver","type":"address"}],"name":"NewResolver","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"node","type":"bytes32"},{"indexed":false,"name":"ttl","type":"uint64"}],"name":"NewTTL","type":"event"}]|] diff --git a/packages/ethereum/src/Network/Ethereum/Transaction.hs b/packages/ethereum/src/Network/Ethereum/Transaction.hs new file mode 100644 index 00000000..31d20839 --- /dev/null +++ b/packages/ethereum/src/Network/Ethereum/Transaction.hs @@ -0,0 +1,59 @@ +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Ethereum.Transaction +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- Roy Blankman 2018 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Transaction managing utils. +-- + +module Network.Ethereum.Transaction where + +import Data.ByteArray (ByteArray, convert) +import Data.ByteString (ByteString, empty) +import Data.Maybe (fromJust, fromMaybe) +import Data.RLP (packRLP, rlpEncode) +import Data.Word (Word8) + +import Data.ByteArray.HexString (toBytes) +import Data.Solidity.Prim.Address (toHexString) +import Network.Ethereum.Api.Types (Call (..), Quantity (unQuantity)) +import Network.Ethereum.Unit (Shannon, toWei) + +-- | Ethereum transaction packer. +-- +-- Two way RLP encoding of Ethereum transaction: for unsigned and signed. +-- Packing scheme described in https://github.com/ethereum/EIPs/blob/master/EIPS/eip-155.md +encodeTransaction :: ByteArray ba + => Call + -- ^ Transaction call + -> Integer + -- ^ Chain ID + -> Maybe (Integer, Integer, Word8) + -- ^ Should contain signature when transaction signed + -> ba + -- ^ RLP encoded transaction +encodeTransaction Call{..} chain_id rsv = + let (to :: ByteString) = maybe mempty (toBytes . toHexString) callTo + (value :: Integer) = unQuantity $ fromJust callValue + (nonce :: Integer) = unQuantity $ fromJust callNonce + (gasPrice :: Integer) = maybe defaultGasPrice unQuantity callGasPrice + (gasLimit :: Integer) = unQuantity $ fromJust callGas + (input :: ByteString) = convert $ fromMaybe mempty callData + + in convert . packRLP $ case rsv of + -- Unsigned transaction by EIP155 + Nothing -> rlpEncode (nonce, gasPrice, gasLimit, to, value, input, chain_id, empty, empty) + -- Signed transaction + Just (r, s, v) -> + let v' = fromIntegral v + 8 + 2 * chain_id -- Improved 'v' according to EIP155 + in rlpEncode (nonce, gasPrice, gasLimit, to, value, input, v', r, s) + where + defaultGasPrice = toWei (10 :: Shannon) diff --git a/src/Network/Ethereum/Unit.hs b/packages/ethereum/src/Network/Ethereum/Unit.hs similarity index 87% rename from src/Network/Ethereum/Unit.hs rename to packages/ethereum/src/Network/Ethereum/Unit.hs index 2e706176..05d5749b 100644 --- a/src/Network/Ethereum/Unit.hs +++ b/packages/ethereum/src/Network/Ethereum/Unit.hs @@ -1,13 +1,12 @@ -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeSynonymInstances #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE ScopedTypeVariables #-} -- | -- Module : Network.Ethereum.Unit --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental @@ -47,18 +46,21 @@ -- @ -- -module Network.Ethereum.Unit ( - Unit(..) - , UnitSpec(..) - , Wei - , Babbage - , Lovelace - , Shannon - , Szabo - , Finney - , Ether - , KEther - ) where +module Network.Ethereum.Unit + ( + -- * The @Unit@ type class + Unit(..) + + -- * Ethereum value metrics + , Wei + , Babbage + , Lovelace + , Shannon + , Szabo + , Finney + , Ether + , KEther + ) where import Data.Proxy (Proxy (..)) import Data.Text.Lazy (Text, unpack) @@ -71,13 +73,10 @@ import qualified Text.Read.Lex as L -- | Ethereum value unit class (Read a, Show a, UnitSpec a, Fractional a) => Unit a where -- | Make a value from integer wei - fromWei :: Integer -> a + fromWei :: Integral b => b -> a + -- | Convert a value to integer wei - toWei :: a -> Integer - -- | Conversion beween two values - convert :: Unit b => a -> b - {-# INLINE convert #-} - convert = fromWei . toWei + toWei :: Integral b => a -> b -- | Unit specification class UnitSpec a where @@ -92,8 +91,8 @@ mkValue :: forall a b . (UnitSpec a, RealFrac b) => b -> Value a mkValue = MkValue . round . (* divider (Proxy :: Proxy a)) instance UnitSpec a => Unit (Value a) where - fromWei = MkValue - toWei = unValue + fromWei = MkValue . toInteger + toWei = fromInteger . unValue instance UnitSpec a => UnitSpec (Value a) where divider = const $ divider (Proxy :: Proxy a) diff --git a/unit/Network/Ethereum/Web3/Test/EventSpec.hs b/packages/ethereum/tests/Network/Ethereum/Test/EventSpec.hs similarity index 69% rename from unit/Network/Ethereum/Web3/Test/EventSpec.hs rename to packages/ethereum/tests/Network/Ethereum/Test/EventSpec.hs index 696bd93b..3d42d8f4 100644 --- a/unit/Network/Ethereum/Web3/Test/EventSpec.hs +++ b/packages/ethereum/tests/Network/Ethereum/Test/EventSpec.hs @@ -3,29 +3,34 @@ {-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE OverloadedStrings #-} -module Network.Ethereum.Web3.Test.EventSpec where +-- | +-- Module : Network.Ethereum.Test.EventSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- -import Data.Tagged (Tagged) -import Generics.SOP (Generic) -import qualified GHC.Generics as GHC (Generic) -import Test.Hspec (Spec, describe, it, - shouldBe) +module Network.Ethereum.Test.EventSpec where -import Network.Ethereum.ABI.Class (ABIGet) -import Network.Ethereum.ABI.Event (IndexedEvent (..), - decodeEvent) -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.ABI.Prim.Bytes () -import Network.Ethereum.ABI.Prim.Int (UIntN) -import Network.Ethereum.ABI.Prim.Tagged () -import Network.Ethereum.Web3.Types (Change (..)) +import Data.Tagged (Tagged) +import Generics.SOP (Generic) +import qualified GHC.Generics as GHC (Generic) +import Test.Hspec + +import Data.Solidity.Abi (AbiGet, AbiType (..)) +import Data.Solidity.Event (IndexedEvent (..), decodeEvent) +import Data.Solidity.Prim (Address, UIntN) +import Network.Ethereum.Api.Types (Change (..)) spec :: Spec spec = eventTest eventTest :: Spec -eventTest = +eventTest = parallel $ describe "event tests" $ do it "can decode simple storage" $ @@ -38,7 +43,7 @@ eventTest = , changeData = "0x000000000000000000000000000000000000000000000000000000000000000a" , changeTopics = ["0xa32bc18230dd172221ac5c4821a5f1f1a831f27b1396d244cdd891c58f132435"] } - in decodeEvent change `shouldBe` Right (NewCount 10) + in decodeEvent (changeTopics change) (changeData change) `shouldBe` Right (NewCount 10) it "can decode erc20" $ let ercchange = Change { changeLogIndex = Just "0x2" @@ -53,18 +58,25 @@ eventTest = , "0x0000000000000000000000000000000000000000000000000000000000000002" ] } - in decodeEvent ercchange `shouldBe` Right (Transfer "0x0000000000000000000000000000000000000001" 10 "0x0000000000000000000000000000000000000002") + in decodeEvent (changeTopics ercchange) (changeData ercchange) `shouldBe` Right (Transfer "0x0000000000000000000000000000000000000001" 10 "0x0000000000000000000000000000000000000002") -- SimpleStorage Event Types data NewCount = NewCount (UIntN 256) deriving (Eq, Show, GHC.Generic) instance Generic NewCount + data NewCountIndexed = NewCountIndexed deriving (Eq, Show, GHC.Generic) instance Generic NewCountIndexed +instance AbiType NewCountIndexed where + isDynamic = const False +instance AbiGet NewCountIndexed data NewCountNonIndexed = NewCountNonIndexed (Tagged 1 (UIntN 256)) deriving (Eq, Show, GHC.Generic) instance Generic NewCountNonIndexed +instance AbiType NewCountNonIndexed where + isDynamic = const False +instance AbiGet NewCountNonIndexed instance IndexedEvent NewCountIndexed NewCountNonIndexed NewCount where isAnonymous = const False @@ -75,9 +87,15 @@ instance Generic Transfer data TransferIndexed = TransferIndexed (Tagged 1 Address) (Tagged 3 Address) deriving (Eq, Show, GHC.Generic) instance Generic TransferIndexed +instance AbiType TransferIndexed where + isDynamic = const False +instance AbiGet TransferIndexed data TransferNonIndexed = TransferNonIndexed (Tagged 2 (UIntN 256)) deriving (Eq, Show, GHC.Generic) instance Generic TransferNonIndexed +instance AbiType TransferNonIndexed where + isDynamic = const False +instance AbiGet TransferNonIndexed instance IndexedEvent TransferIndexed TransferNonIndexed Transfer where isAnonymous = const False diff --git a/packages/ethereum/tests/Network/Ethereum/Test/MethodDumpSpec.hs b/packages/ethereum/tests/Network/Ethereum/Test/MethodDumpSpec.hs new file mode 100644 index 00000000..2a2e793b --- /dev/null +++ b/packages/ethereum/tests/Network/Ethereum/Test/MethodDumpSpec.hs @@ -0,0 +1,23 @@ +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Ethereum.Test.MethodDumpSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Network.Ethereum.Test.MethodDumpSpec where + +import Network.Ethereum.Contract.TH +import Test.Hspec + +spec :: Spec +spec = parallel $ + describe "methodDump" $ + it "can dump an ABI" $ + let theApiDump = [abiFrom|tests/contracts/ERC20.json|] + in theApiDump `shouldNotBe` "" diff --git a/packages/ethereum/tests/Network/Ethereum/Test/THSpec.hs b/packages/ethereum/tests/Network/Ethereum/Test/THSpec.hs new file mode 100644 index 00000000..e8331f3c --- /dev/null +++ b/packages/ethereum/tests/Network/Ethereum/Test/THSpec.hs @@ -0,0 +1,38 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Ethereum.Test.THSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Network.Ethereum.Test.THSpec where + +import Data.Tuple.OneTuple +import Network.Ethereum.Contract.TH +import Test.Hspec + +-- 0x Exchange Contract that includes Tuples taken from: +-- https://raw.githubusercontent.com/0xProject/0x-monorepo/%400x/website%400.0.89/packages/contract-artifacts/artifacts/Exchange.json +[abiFrom|tests/contracts/Exchange.json|] + +[abiFrom|tests/contracts/SingleField.json|] + +spec :: Spec +spec = parallel $ + describe "quasi-quoter" $ do + it "can compile contract with tuples" $ + True `shouldBe` True + + it "can compile single field structs" $ do + let _ = SingleFieldFunctionData (OneTuple 123) + True `shouldBe` True diff --git a/packages/ethereum/tests/Network/Ethereum/Test/TransactionSpec.hs b/packages/ethereum/tests/Network/Ethereum/Test/TransactionSpec.hs new file mode 100644 index 00000000..f54b60ba --- /dev/null +++ b/packages/ethereum/tests/Network/Ethereum/Test/TransactionSpec.hs @@ -0,0 +1,37 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Ethereum.Test.TransactionSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Network.Ethereum.Test.TransactionSpec where + +import Crypto.Ecdsa.Utils (importKey) +import Crypto.Ethereum.Signature (signTransaction) +import Data.ByteArray.HexString (HexString) +import Network.Ethereum.Api.Types (Call (..)) +import Network.Ethereum.Transaction (encodeTransaction) +import Test.Hspec + +spec :: Spec +spec = parallel $ + describe "Ethereum raw transactions" $ + it "can create and sign valid raw transaction" $ do + -- using same example as in this blog post: + -- https://medium.com/@codetractio/walkthrough-of-an-ethereum-improvement-proposal-eip-6fda3966d171 + let testCall = Call Nothing + (Just "0x3535353535353535353535353535353535353535") + (Just 21000) + (Just 20000000000) + (Just 1000000000000000000) + Nothing + (Just 9) + key = "4646464646464646464646464646464646464646464646464646464646464646" :: HexString + correctSignedTx = "f86c098504a817c800825208943535353535353535353535353535353535353535880de0b6b3a76400008025a028ef61340bd939bc2195fe537567866003e1a15d3c71ff63e1590620aa636276a067cbe9d8997f761aecb703304b3800ccf555c9f3dc64214b297fb1966a3b6d83" + signTransaction (encodeTransaction testCall 1) (importKey key) `shouldBe` (correctSignedTx :: HexString) diff --git a/packages/ethereum/tests/Spec.hs b/packages/ethereum/tests/Spec.hs new file mode 100644 index 00000000..a824f8c3 --- /dev/null +++ b/packages/ethereum/tests/Spec.hs @@ -0,0 +1 @@ +{-# OPTIONS_GHC -F -pgmF hspec-discover #-} diff --git a/packages/ethereum/tests/contracts/ERC20.json b/packages/ethereum/tests/contracts/ERC20.json new file mode 100644 index 00000000..4dcb87dc --- /dev/null +++ b/packages/ethereum/tests/contracts/ERC20.json @@ -0,0 +1 @@ +[{"constant":true,"inputs":[],"name":"name","outputs":[{"name":"","type":"string"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_spender","type":"address"},{"name":"_value","type":"uint256"}],"name":"approve","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"totalSupply","outputs":[{"name":"","type":"uint256"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_to","type":"address"},{"name":"_value","type":"uint256"}],"name":"transferFrom","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"decimals","outputs":[{"name":"","type":"uint8"}],"payable":false,"type":"function"},{"constant":false,"inputs":[],"name":"kill","outputs":[],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_owner","type":"address"}],"name":"delegate","outputs":[],"payable":false,"type":"function"},{"constant":true,"inputs":[{"name":"_owner","type":"address"}],"name":"balanceOf","outputs":[{"name":"","type":"uint256"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"owner","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"symbol","outputs":[{"name":"","type":"string"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_to","type":"address"},{"name":"_value","type":"uint256"}],"name":"transfer","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"constant":true,"inputs":[{"name":"_owner","type":"address"},{"name":"_spender","type":"address"}],"name":"allowance","outputs":[{"name":"","type":"uint256"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_spender","type":"address"}],"name":"unapprove","outputs":[],"payable":false,"type":"function"},{"inputs":[{"name":"_name","type":"string"},{"name":"_symbol","type":"string"},{"name":"_decimals","type":"uint8"},{"name":"_count","type":"uint256"}],"type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"name":"_from","type":"address"},{"indexed":true,"name":"_to","type":"address"},{"indexed":false,"name":"_value","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"_owner","type":"address"},{"indexed":true,"name":"_spender","type":"address"},{"indexed":false,"name":"_value","type":"uint256"}],"name":"Approval","type":"event"}] \ No newline at end of file diff --git a/packages/ethereum/tests/contracts/Exchange.json b/packages/ethereum/tests/contracts/Exchange.json new file mode 100644 index 00000000..7de41066 --- /dev/null +++ b/packages/ethereum/tests/contracts/Exchange.json @@ -0,0 +1,1059 @@ +{ + "schemaVersion": "2.0.0", + "contractName": "Exchange", + "compilerOutput": { + "abi": [ + { + "constant": true, + "inputs": [{ "name": "", "type": "bytes32" }], + "name": "filled", + "outputs": [{ "name": "", "type": "uint256" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "takerAssetFillAmounts", "type": "uint256[]" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "batchFillOrders", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "bytes32" }], + "name": "cancelled", + "outputs": [{ "name": "", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { "name": "hash", "type": "bytes32" }, + { "name": "signerAddress", "type": "address" }, + { "name": "signature", "type": "bytes" } + ], + "name": "preSign", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "leftOrder", + "type": "tuple" + }, + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "rightOrder", + "type": "tuple" + }, + { "name": "leftSignature", "type": "bytes" }, + { "name": "rightSignature", "type": "bytes" } + ], + "name": "matchOrders", + "outputs": [ + { + "components": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "left", + "type": "tuple" + }, + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "right", + "type": "tuple" + }, + { "name": "leftMakerAssetSpreadAmount", "type": "uint256" } + ], + "name": "matchedFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "order", + "type": "tuple" + }, + { "name": "takerAssetFillAmount", "type": "uint256" }, + { "name": "signature", "type": "bytes" } + ], + "name": "fillOrderNoThrow", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "fillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "bytes4" }], + "name": "assetProxies", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + } + ], + "name": "batchCancelOrders", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "takerAssetFillAmounts", "type": "uint256[]" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "batchFillOrKillOrders", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "targetOrderEpoch", "type": "uint256" }], + "name": "cancelOrdersUpTo", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "takerAssetFillAmounts", "type": "uint256[]" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "batchFillOrdersNoThrow", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "assetProxyId", "type": "bytes4" }], + "name": "getAssetProxy", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "bytes32" }], + "name": "transactions", + "outputs": [{ "name": "", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "order", + "type": "tuple" + }, + { "name": "takerAssetFillAmount", "type": "uint256" }, + { "name": "signature", "type": "bytes" } + ], + "name": "fillOrKillOrder", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "fillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "validatorAddress", "type": "address" }, { "name": "approval", "type": "bool" }], + "name": "setSignatureValidatorApproval", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "address" }, { "name": "", "type": "address" }], + "name": "allowedValidators", + "outputs": [{ "name": "", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "takerAssetFillAmount", "type": "uint256" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "marketSellOrders", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + } + ], + "name": "getOrdersInfo", + "outputs": [ + { + "components": [ + { "name": "orderStatus", "type": "uint8" }, + { "name": "orderHash", "type": "bytes32" }, + { "name": "orderTakerAssetFilledAmount", "type": "uint256" } + ], + "name": "", + "type": "tuple[]" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "bytes32" }, { "name": "", "type": "address" }], + "name": "preSigned", + "outputs": [{ "name": "", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "owner", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { "name": "hash", "type": "bytes32" }, + { "name": "signerAddress", "type": "address" }, + { "name": "signature", "type": "bytes" } + ], + "name": "isValidSignature", + "outputs": [{ "name": "isValid", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "makerAssetFillAmount", "type": "uint256" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "marketBuyOrdersNoThrow", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "order", + "type": "tuple" + }, + { "name": "takerAssetFillAmount", "type": "uint256" }, + { "name": "signature", "type": "bytes" } + ], + "name": "fillOrder", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "fillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { "name": "salt", "type": "uint256" }, + { "name": "signerAddress", "type": "address" }, + { "name": "data", "type": "bytes" }, + { "name": "signature", "type": "bytes" } + ], + "name": "executeTransaction", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "assetProxy", "type": "address" }], + "name": "registerAssetProxy", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "order", + "type": "tuple" + } + ], + "name": "getOrderInfo", + "outputs": [ + { + "components": [ + { "name": "orderStatus", "type": "uint8" }, + { "name": "orderHash", "type": "bytes32" }, + { "name": "orderTakerAssetFilledAmount", "type": "uint256" } + ], + "name": "orderInfo", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "order", + "type": "tuple" + } + ], + "name": "cancelOrder", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "name": "", "type": "address" }, { "name": "", "type": "address" }], + "name": "orderEpoch", + "outputs": [{ "name": "", "type": "uint256" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "ZRX_ASSET_DATA", + "outputs": [{ "name": "", "type": "bytes" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "takerAssetFillAmount", "type": "uint256" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "marketSellOrdersNoThrow", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "EIP712_DOMAIN_HASH", + "outputs": [{ "name": "", "type": "bytes32" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "makerAddress", "type": "address" }, + { "name": "takerAddress", "type": "address" }, + { "name": "feeRecipientAddress", "type": "address" }, + { "name": "senderAddress", "type": "address" }, + { "name": "makerAssetAmount", "type": "uint256" }, + { "name": "takerAssetAmount", "type": "uint256" }, + { "name": "makerFee", "type": "uint256" }, + { "name": "takerFee", "type": "uint256" }, + { "name": "expirationTimeSeconds", "type": "uint256" }, + { "name": "salt", "type": "uint256" }, + { "name": "makerAssetData", "type": "bytes" }, + { "name": "takerAssetData", "type": "bytes" } + ], + "name": "orders", + "type": "tuple[]" + }, + { "name": "makerAssetFillAmount", "type": "uint256" }, + { "name": "signatures", "type": "bytes[]" } + ], + "name": "marketBuyOrders", + "outputs": [ + { + "components": [ + { "name": "makerAssetFilledAmount", "type": "uint256" }, + { "name": "takerAssetFilledAmount", "type": "uint256" }, + { "name": "makerFeePaid", "type": "uint256" }, + { "name": "takerFeePaid", "type": "uint256" } + ], + "name": "totalFillResults", + "type": "tuple" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "currentContextAddress", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "newOwner", "type": "address" }], + "name": "transferOwnership", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "VERSION", + "outputs": [{ "name": "", "type": "string" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [{ "name": "_zrxAssetData", "type": "bytes" }], + "payable": false, + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "name": "signerAddress", "type": "address" }, + { "indexed": true, "name": "validatorAddress", "type": "address" }, + { "indexed": false, "name": "approved", "type": "bool" } + ], + "name": "SignatureValidatorApproval", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "name": "makerAddress", "type": "address" }, + { "indexed": true, "name": "feeRecipientAddress", "type": "address" }, + { "indexed": false, "name": "takerAddress", "type": "address" }, + { "indexed": false, "name": "senderAddress", "type": "address" }, + { "indexed": false, "name": "makerAssetFilledAmount", "type": "uint256" }, + { "indexed": false, "name": "takerAssetFilledAmount", "type": "uint256" }, + { "indexed": false, "name": "makerFeePaid", "type": "uint256" }, + { "indexed": false, "name": "takerFeePaid", "type": "uint256" }, + { "indexed": true, "name": "orderHash", "type": "bytes32" }, + { "indexed": false, "name": "makerAssetData", "type": "bytes" }, + { "indexed": false, "name": "takerAssetData", "type": "bytes" } + ], + "name": "Fill", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "name": "makerAddress", "type": "address" }, + { "indexed": true, "name": "feeRecipientAddress", "type": "address" }, + { "indexed": false, "name": "senderAddress", "type": "address" }, + { "indexed": true, "name": "orderHash", "type": "bytes32" }, + { "indexed": false, "name": "makerAssetData", "type": "bytes" }, + { "indexed": false, "name": "takerAssetData", "type": "bytes" } + ], + "name": "Cancel", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "name": "makerAddress", "type": "address" }, + { "indexed": true, "name": "senderAddress", "type": "address" }, + { "indexed": false, "name": "orderEpoch", "type": "uint256" } + ], + "name": "CancelUpTo", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "name": "id", "type": "bytes4" }, + { "indexed": false, "name": "assetProxy", "type": "address" } + ], + "name": "AssetProxyRegistered", + "type": "event" + } + ], + "devdoc": { + "methods": { + "batchCancelOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[])": { + "details": "Synchronously cancels multiple orders in a single transaction.", + "params": { "orders": "Array of order specifications." } + }, + "batchFillOrKillOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256[],bytes[])": { + "details": "Synchronously executes multiple calls of fillOrKill.", + "params": { + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been created by makers.", + "takerAssetFillAmounts": "Array of desired amounts of takerAsset to sell in orders." + }, + "return": "Amounts filled and fees paid by makers and taker. NOTE: makerAssetFilledAmount and takerAssetFilledAmount may include amounts filled of different assets." + }, + "batchFillOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256[],bytes[])": { + "details": "Synchronously executes multiple calls of fillOrder.", + "params": { + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been created by makers.", + "takerAssetFillAmounts": "Array of desired amounts of takerAsset to sell in orders." + }, + "return": "Amounts filled and fees paid by makers and taker. NOTE: makerAssetFilledAmount and takerAssetFilledAmount may include amounts filled of different assets." + }, + "batchFillOrdersNoThrow((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256[],bytes[])": { + "details": "Fills an order with specified parameters and ECDSA signature. Returns false if the transaction would otherwise revert.", + "params": { + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been created by makers.", + "takerAssetFillAmounts": "Array of desired amounts of takerAsset to sell in orders." + }, + "return": "Amounts filled and fees paid by makers and taker. NOTE: makerAssetFilledAmount and takerAssetFilledAmount may include amounts filled of different assets." + }, + "cancelOrder((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes))": { + "details": "After calling, the order can not be filled anymore. Throws if order is invalid or sender does not have permission to cancel.", + "params": { "order": "Order to cancel. Order must be OrderStatus.FILLABLE." } + }, + "cancelOrdersUpTo(uint256)": { + "details": "Cancels all orders created by makerAddress with a salt less than or equal to the targetOrderEpoch and senderAddress equal to msg.sender (or null address if msg.sender == makerAddress).", + "params": { + "targetOrderEpoch": "Orders created with a salt less or equal to this value will be cancelled." + } + }, + "executeTransaction(uint256,address,bytes,bytes)": { + "details": "Executes an exchange method call in the context of signer.", + "params": { + "data": "AbiV2 encoded calldata.", + "salt": "Arbitrary number to ensure uniqueness of transaction hash.", + "signature": "Proof of signer transaction by signer.", + "signerAddress": "Address of transaction signer." + } + }, + "fillOrKillOrder((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),uint256,bytes)": { + "details": "Fills the input order. Reverts if exact takerAssetFillAmount not filled.", + "params": { + "order": "Order struct containing order specifications.", + "signature": "Proof that order has been created by maker.", + "takerAssetFillAmount": "Desired amount of takerAsset to sell." + } + }, + "fillOrder((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),uint256,bytes)": { + "details": "Fills the input order.", + "params": { + "order": "Order struct containing order specifications.", + "signature": "Proof that order has been created by maker.", + "takerAssetFillAmount": "Desired amount of takerAsset to sell." + }, + "return": "Amounts filled and fees paid by maker and taker." + }, + "fillOrderNoThrow((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),uint256,bytes)": { + "details": "Fills the input order. Returns false if the transaction would otherwise revert.", + "params": { + "order": "Order struct containing order specifications.", + "signature": "Proof that order has been created by maker.", + "takerAssetFillAmount": "Desired amount of takerAsset to sell." + }, + "return": "Amounts filled and fees paid by maker and taker." + }, + "getAssetProxy(bytes4)": { + "details": "Gets an asset proxy.", + "params": { "assetProxyId": "Id of the asset proxy." }, + "return": "The asset proxy registered to assetProxyId. Returns 0x0 if no proxy is registered." + }, + "getOrderInfo((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes))": { + "details": "Gets information about an order: status, hash, and amount filled.", + "params": { "order": "Order to gather information on." }, + "return": "OrderInfo Information about the order and its state. See LibOrder.OrderInfo for a complete description." + }, + "getOrdersInfo((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[])": { + "details": "Fetches information for all passed in orders.", + "params": { "orders": "Array of order specifications." }, + "return": "Array of OrderInfo instances that correspond to each order." + }, + "isValidSignature(bytes32,address,bytes)": { + "details": "Verifies that a hash has been signed by the given signer.", + "params": { + "hash": "Any 32 byte hash.", + "signature": "Proof that the hash has been signed by signer.", + "signerAddress": "Address that should have signed the given hash." + }, + "return": "True if the address recovered from the provided signature matches the input signer address." + }, + "marketBuyOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256,bytes[])": { + "details": "Synchronously executes multiple calls of fillOrder until total amount of makerAsset is bought by taker.", + "params": { + "makerAssetFillAmount": "Desired amount of makerAsset to buy.", + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been signed by makers." + }, + "return": "Amounts filled and fees paid by makers and taker." + }, + "marketBuyOrdersNoThrow((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256,bytes[])": { + "details": "Synchronously executes multiple fill orders in a single transaction until total amount is bought by taker. Returns false if the transaction would otherwise revert.", + "params": { + "makerAssetFillAmount": "Desired amount of makerAsset to buy.", + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been signed by makers." + }, + "return": "Amounts filled and fees paid by makers and taker." + }, + "marketSellOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256,bytes[])": { + "details": "Synchronously executes multiple calls of fillOrder until total amount of takerAsset is sold by taker.", + "params": { + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been created by makers.", + "takerAssetFillAmount": "Desired amount of takerAsset to sell." + }, + "return": "Amounts filled and fees paid by makers and taker." + }, + "marketSellOrdersNoThrow((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256,bytes[])": { + "details": "Synchronously executes multiple calls of fillOrder until total amount of takerAsset is sold by taker. Returns false if the transaction would otherwise revert.", + "params": { + "orders": "Array of order specifications.", + "signatures": "Proofs that orders have been signed by makers.", + "takerAssetFillAmount": "Desired amount of takerAsset to sell." + }, + "return": "Amounts filled and fees paid by makers and taker." + }, + "matchOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),(address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),bytes,bytes)": { + "details": "Match two complementary orders that have a profitable spread. Each order is filled at their respective price point. However, the calculations are carried out as though the orders are both being filled at the right order's price point. The profit made by the left order goes to the taker (who matched the two orders).", + "params": { + "leftOrder": "First order to match.", + "leftSignature": "Proof that order was created by the left maker.", + "rightOrder": "Second order to match.", + "rightSignature": "Proof that order was created by the right maker." + }, + "return": "matchedFillResults Amounts filled and fees paid by maker and taker of matched orders." + }, + "preSign(bytes32,address,bytes)": { + "details": "Approves a hash on-chain using any valid signature type. After presigning a hash, the preSign signature type will become valid for that hash and signer.", + "params": { + "signature": "Proof that the hash has been signed by signer.", + "signerAddress": "Address that should have signed the given hash." + } + }, + "registerAssetProxy(address)": { + "details": "Registers an asset proxy to its asset proxy id. Once an asset proxy is registered, it cannot be unregistered.", + "params": { "assetProxy": "Address of new asset proxy to register." } + }, + "setSignatureValidatorApproval(address,bool)": { + "details": "Approves/unnapproves a Validator contract to verify signatures on signer's behalf.", + "params": { + "approval": "Approval or disapproval of Validator contract.", + "validatorAddress": "Address of Validator contract." + } + } + } + }, + "evm": { + "bytecode": { + "object": "0x60806040526000805460ff191690553480156200001b57600080fd5b5060405162005ec038038062005ec083398101806040526200004191908101906200044d565b80518190620000589060019060208401906200034c565b5050604080517f454950373132446f6d61696e28000000000000000000000000000000000000006020808301919091527f737472696e67206e616d652c0000000000000000000000000000000000000000602d8301527f737472696e672076657273696f6e2c000000000000000000000000000000000060398301527f6164647265737320766572696679696e67436f6e74726163740000000000000060488301527f2900000000000000000000000000000000000000000000000000000000000000606183015282516042818403018152606290920192839052815191929182918401908083835b60208310620001625780518252601f19909201916020918201910162000141565b51815160209384036101000a6000190180199092169116179052604080519290940182900382208285018552600b8084527f30782050726f746f636f6c000000000000000000000000000000000000000000928401928352945190965091945090928392508083835b60208310620001ec5780518252601f199092019160209182019101620001cb565b51815160209384036101000a600019018019909216911617905260408051929094018290038220828501855260018084527f3200000000000000000000000000000000000000000000000000000000000000928401928352945190965091945090928392508083835b60208310620002765780518252601f19909201916020918201910162000255565b51815160209384036101000a6000190180199092169116179052604080519290940182900382208282019890985281840196909652606081019690965250306080808701919091528151808703909101815260a09095019081905284519093849350850191508083835b60208310620003015780518252601f199092019160209182019101620002e0565b5181516000196020949094036101000a939093019283169219169190911790526040519201829003909120600255505060038054600160a060020a03191633179055506200050f9050565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106200038f57805160ff1916838001178555620003bf565b82800160010185558215620003bf579182015b82811115620003bf578251825591602001919060010190620003a2565b50620003cd929150620003d1565b5090565b620003ee91905b80821115620003cd5760008155600101620003d8565b90565b6000601f820183136200040357600080fd5b81516200041a6200041482620004b4565b6200048d565b915080825260208301602083018583830111156200043757600080fd5b62000444838284620004dc565b50505092915050565b6000602082840312156200046057600080fd5b81516001604060020a038111156200047757600080fd5b6200048584828501620003f1565b949350505050565b6040518181016001604060020a0381118282101715620004ac57600080fd5b604052919050565b60006001604060020a03821115620004cb57600080fd5b506020601f91909101601f19160190565b60005b83811015620004f9578181015183820152602001620004df565b8381111562000509576000848401525b50505050565b6159a1806200051f6000396000f3006080604052600436106101b65763ffffffff7c0100000000000000000000000000000000000000000000000000000000600035041663288cdc9181146101bb578063297bb70b146101f15780632ac126221461021e5780633683ef8e1461024b5780633c28d8611461026d5780633e228bae1461029a5780633fd3c997146102ba5780634ac14782146102e75780634d0ae546146103075780634f9559b11461032757806350dde190146103475780636070410814610367578063642f2eaf1461039457806364a3bc15146103b457806377fcce68146103d45780637b8e3514146103f45780637e1d9808146104145780637e9d74dc1461043457806382c174d0146104615780638da5cb5b146104815780639363470214610496578063a3e20380146104b6578063b4be83d5146104d6578063bfc8bfce146104f6578063c585bb9314610516578063c75e0a8114610536578063d46b02c314610563578063d9bfa73e14610583578063db123b1a146105a3578063dd1c7d18146105c5578063e306f779146105e5578063e5fa431b146105fa578063eea086ba1461061a578063f2fde38b1461062f578063ffa1ad741461064f575b600080fd5b3480156101c757600080fd5b506101db6101d63660046148ee565b610664565b6040516101e89190615513565b60405180910390f35b3480156101fd57600080fd5b5061021161020c366004614811565b610676565b6040516101e891906157ed565b34801561022a57600080fd5b5061023e6102393660046148ee565b6107a1565b6040516101e89190615505565b34801561025757600080fd5b5061026b61026636600461492b565b6107b6565b005b34801561027957600080fd5b5061028d610288366004614a5f565b6108a3565b6040516101e891906157fb565b3480156102a657600080fd5b506102116102b5366004614b1f565b610a3a565b3480156102c657600080fd5b506102da6102d53660046149ee565b610a90565b6040516101e891906155cf565b3480156102f357600080fd5b5061026b6103023660046147dc565b610ab8565b34801561031357600080fd5b50610211610322366004614811565b610b85565b34801561033357600080fd5b5061026b6103423660046148ee565b610c75565b34801561035357600080fd5b50610211610362366004614811565b610e2a565b34801561037357600080fd5b506103876103823660046149ee565b610ebe565b6040516101e89190615425565b3480156103a057600080fd5b5061023e6103af3660046148ee565b610f0c565b3480156103c057600080fd5b506102116103cf366004614b1f565b610f21565b3480156103e057600080fd5b5061026b6103ef3660046147ac565b610fcc565b34801561040057600080fd5b5061023e61040f366004614772565b611106565b34801561042057600080fd5b5061021161042f3660046148a5565b611126565b34801561044057600080fd5b5061045461044f3660046147dc565b61128a565b6040516101e891906154f4565b34801561046d57600080fd5b5061023e61047c36600461490c565b61131f565b34801561048d57600080fd5b5061038761133f565b3480156104a257600080fd5b5061023e6104b1366004614993565b61135b565b3480156104c257600080fd5b506102116104d13660046148a5565b6118de565b3480156104e257600080fd5b506102116104f1366004614b1f565b6119f1565b34801561050257600080fd5b5061026b610511366004614b68565b611a6c565b34801561052257600080fd5b5061026b610531366004614754565b611d05565b34801561054257600080fd5b50610556610551366004614a2a565b611f30565b6040516101e8919061580a565b34801561056f57600080fd5b5061026b61057e366004614a2a565b61202a565b34801561058f57600080fd5b506101db61059e366004614772565b6120c6565b3480156105af57600080fd5b506105b86120e3565b6040516101e891906155be565b3480156105d157600080fd5b506102116105e03660046148a5565b61218e565b3480156105f157600080fd5b506101db612263565b34801561060657600080fd5b506102116106153660046148a5565b612269565b34801561062657600080fd5b506103876123db565b34801561063b57600080fd5b5061026b61064a366004614754565b6123f7565b34801561065b57600080fd5b506105b86124a8565b60046020526000908152604090205481565b61067e614386565b600080610689614386565b60005460ff16156106cf576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b60405180910390fd5b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011781558751935091505b81831461076f57610758878381518110151561071957fe5b90602001906020020151878481518110151561073157fe5b90602001906020020151878581518110151561074957fe5b906020019060200201516124df565b9050610764848261257d565b600190910190610701565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00169055509392505050565b60056020526000908152604090205460ff1681565b73ffffffffffffffffffffffffffffffffffffffff831633146108465761080e848484848080601f0160208091040260200160405190810160405280939291908181526020018383808284375061135b945050505050565b1515610846576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061569d565b5050600091825260076020908152604080842073ffffffffffffffffffffffffffffffffffffffff9093168452919052902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055565b6108ab6143af565b6108b36143de565b6108bb6143de565b6000805460ff16156108f9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117905561016080890151610140808a01919091528901519088015261094588611f30565b925061095087611f30565b915061095a6125df565b905061096888848389612611565b61097487838388612611565b61097e88886127a9565b610992888885604001518560400151612809565b8051602081015190519195506109ad918a9186918190612990565b6020808501519081015190516109c99189918591908190612990565b6109e28882856020015186604001518860000151612aa9565b6109fb8782846020015185604001518860200151612aa9565b610a0788888387612b55565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016905550949350505050565b610a42614386565b6060610a4f858585612d2d565b9050608081825160208401305af48015610a8657815183526020820151602084015260408201516040840152606082015160608401525b505b509392505050565b600b6020526000908152604090205473ffffffffffffffffffffffffffffffffffffffff1681565b60008054819060ff1615610af8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011781558151905b808214610b5857610b508382815181101515610b4157fe5b90602001906020020151612eff565b600101610b29565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016905550565b610b8d614386565b600080610b98614386565b60005460ff1615610bd5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011781558751935091505b81831461076f57610c5e8783815181101515610c1f57fe5b906020019060200201518784815181101515610c3757fe5b906020019060200201518785815181101515610c4f57fe5b90602001906020020151612f2a565b9050610c6a848261257d565b600190910190610c07565b6000805481908190819060ff1615610cb9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055610cec6125df565b935073ffffffffffffffffffffffffffffffffffffffff84163314610d115733610d14565b60005b73ffffffffffffffffffffffffffffffffffffffff8086166000908152600660209081526040808320938516835292905220549093506001860192509050808211610d8b576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061572d565b73ffffffffffffffffffffffffffffffffffffffff80851660008181526006602090815260408083209488168084529490915290819020859055517f82af639571738f4ebd4268fb0363d8957ebe1bbb9e78dba5ebd69eed39b154f090610df3908690615513565b60405180910390a35050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00169055505050565b610e32614386565b600080610e3d614386565b86519250600091505b818314610eb457610e9d8783815181101515610e5e57fe5b906020019060200201518784815181101515610e7657fe5b906020019060200201518785815181101515610e8e57fe5b90602001906020020151610a3a565b9050610ea9848261257d565b600190910190610e46565b5050509392505050565b7fffffffff0000000000000000000000000000000000000000000000000000000081166000908152600b602052604090205473ffffffffffffffffffffffffffffffffffffffff165b919050565b60096020526000908152604090205460ff1681565b610f29614386565b60005460ff1615610f66576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055610f9c848484612f2a565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00169055949350505050565b6000805460ff161561100a576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117905561103d6125df565b73ffffffffffffffffffffffffffffffffffffffff8181166000818152600860209081526040808320948916808452949091529081902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00168715151790555192935090917fa8656e308026eeabce8f0bc18048433252318ab80ac79da0b3d3d8697dfba891906110d1908690615505565b60405180910390a35050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016905550565b600860209081526000928352604080842090915290825290205460ff1681565b61112e614386565b6060600080600061113d614386565b60005460ff161561117a576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117815589518a919081106111b257fe5b906020019060200201516101600151945088519350600092505b828414611255578489848151811015156111e257fe5b906020019060200201516101600181905250611202888760200151612f7d565b915061122e898481518110151561121557fe5b9060200190602002015183898681518110151561074957fe5b905061123a868261257d565b6020860151881161124a57611255565b6001909201916111cc565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00169055509195945050505050565b606060006060600084519250826040519080825280602002602001820160405280156112d057816020015b6112bd6143de565b8152602001906001900390816112b55790505b509150600090505b808314610a88576112ff85828151811015156112f057fe5b90602001906020020151611f30565b828281518110151561130d57fe5b602090810290910101526001016112d8565b600760209081526000928352604080842090915290825290205460ff1681565b60035473ffffffffffffffffffffffffffffffffffffffff1681565b600080600080600080600080600089511115156113a4576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061571d565b6113ad89612fc4565b7f010000000000000000000000000000000000000000000000000000000000000090049650600760ff88161061140f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061563d565b8660ff16600781111561141e57fe5b9550600086600781111561142e57fe5b1415611466576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061570d565b600186600781111561147457fe5b14156114bc578851156114b3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906157dd565b600097506118d0565b60028660078111156114ca57fe5b141561160557885160411461150b576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906155dd565b88600081518110151561151a57fe5b01602001517f010000000000000000000000000000000000000000000000000000000000000090819004810204945061155a89600163ffffffff61308816565b935061156d89602163ffffffff61308816565b925060018b86868660405160008152602001604052604051611592949392919061556e565b60206040516020810390808403906000865af11580156115b6573d6000803e3d6000fd5b50506040517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0015173ffffffffffffffffffffffffffffffffffffffff8c811690821614995092506118d09050565b600386600781111561161357fe5b14156117b9578851604114611654576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906155dd565b88600081518110151561166357fe5b01602001517f01000000000000000000000000000000000000000000000000000000000000009081900481020494506116a389600163ffffffff61308816565b93506116b689602163ffffffff61308816565b925060018b60405160200180807f19457468657265756d205369676e6564204d6573736167653a0a333200000000815250601c0182600019166000191681526020019150506040516020818303038152906040526040518082805190602001908083835b6020831061175757805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161171a565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040805192909401829003822060008352910192839052611592945092508991899150889061556e565b60048660078111156117c757fe5b14156117df576117d88b8b8b6130d3565b97506118d0565b60058660078111156117ed57fe5b1415611850576117fc89613228565b73ffffffffffffffffffffffffffffffffffffffff808c1660009081526008602090815260408083209385168352929052205490915060ff16151561184457600097506118d0565b6117d8818c8c8c6132a1565b600686600781111561185e57fe5b141561189e5760008b815260076020908152604080832073ffffffffffffffffffffffffffffffffffffffff8e16845290915290205460ff1697506118d0565b6040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061563d565b505050505050509392505050565b6118e6614386565b60606000806000806118f6614386565b89600081518110151561190557fe5b906020019060200201516101400151955089519450600093505b8385146119e457858a8581518110151561193557fe5b6020908102909101015161014001528651611951908a90612f7d565b92506119948a8581518110151561196457fe5b9060200190602002015160a001518b8681518110151561198057fe5b9060200190602002015160800151856133fd565b91506119c08a858151811015156119a757fe5b90602001906020020151838a87815181101515610e8e57fe5b90506119cc878261257d565b865189116119d9576119e4565b60019093019261191f565b5050505050509392505050565b6119f9614386565b60005460ff1615611a36576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055610f9c8484846124df565b600a5460009073ffffffffffffffffffffffffffffffffffffffff1615611abf576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b611b02611afd888888888080601f01602080910402602001604051908101604052809392919081815260200183838082843750613453945050505050565b613694565b60008181526009602052604090205490915060ff1615611b4e576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061568d565b73ffffffffffffffffffffffffffffffffffffffff86163314611c1f57611ba6818785858080601f0160208091040260200160405190810160405280939291908181526020018383808284375061135b945050505050565b1515611bde576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906157cd565b600a80547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff88161790555b6000818152600960205260409081902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011790555130908690869080838380828437820191505092505050600060405180830381855af49150501515611cb6576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156bd565b73ffffffffffffffffffffffffffffffffffffffff86163314611cfc57600a80547fffffffffffffffffffffffff00000000000000000000000000000000000000001690555b50505050505050565b6003546000908190819073ffffffffffffffffffffffffffffffffffffffff163314611d5d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061577d565b8392508273ffffffffffffffffffffffffffffffffffffffff1663ae25532e6040518163ffffffff167c0100000000000000000000000000000000000000000000000000000000028152600401602060405180830381600087803b158015611dc457600080fd5b505af1158015611dd8573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250611dfc9190810190614a0c565b7fffffffff0000000000000000000000000000000000000000000000000000000081166000908152600b602052604090205490925073ffffffffffffffffffffffffffffffffffffffff1690508015611e81576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061561d565b7fffffffff0000000000000000000000000000000000000000000000000000000082166000908152600b60205260409081902080547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff8616179055517fd2c6b762299c609bdb96520b58a49bfb80186934d4f71a86a367571a15c0319490611f2290849087906155a3565b60405180910390a150505050565b611f386143de565b611f41826136d1565b6020808301829052600091825260049052604090819020549082015260808201511515611f755760015b60ff168152610f07565b60a08201511515611f87576002611f6b565b60a0820151604082015110611f9d576005611f6b565b6101008201514210611fb0576004611f6b565b60208082015160009081526005909152604090205460ff1615611fd4576006611f6b565b610120820151825173ffffffffffffffffffffffffffffffffffffffff90811660009081526006602090815260408083206060880151909416835292905220541115612021576006611f6b565b60038152919050565b60005460ff1615612067576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117905561209b81612eff565b50600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00169055565b600660209081526000928352604080842090915290825290205481565b60018054604080516020600284861615610100027fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0190941693909304601f810184900484028201840190925281815292918301828280156121865780601f1061215b57610100808354040283529160200191612186565b820191906000526020600020905b81548152906001019060200180831161216957829003601f168201915b505050505081565b612196614386565b606060008060006121a5614386565b8860008151811015156121b457fe5b906020019060200201516101600151945088519350600092505b828414612257578489848151811015156121e457fe5b906020019060200201516101600181905250612204888760200151612f7d565b9150612230898481518110151561221757fe5b90602001906020020151838986815181101515610e8e57fe5b905061223c868261257d565b6020860151881161224c57612257565b6001909201916121ce565b50505050509392505050565b60025481565b612271614386565b6060600080600080612281614386565b60005460ff16156122be576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061576d565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011781558a518b919081106122f657fe5b906020019060200201516101400151955089519450600093505b8385146123a557858a8581518110151561232657fe5b6020908102909101015161014001528651612342908a90612f7d565b92506123558a8581518110151561196457fe5b91506123818a8581518110151561236857fe5b90602001906020020151838a8781518110151561074957fe5b905061238d878261257d565b8651891161239a576123a5565b600190930192612310565b5050600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016905550929695505050505050565b600a5473ffffffffffffffffffffffffffffffffffffffff1681565b60035473ffffffffffffffffffffffffffffffffffffffff163314612448576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061577d565b73ffffffffffffffffffffffffffffffffffffffff8116156124a557600380547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83161790555b50565b60408051808201909152600581527f322e302e30000000000000000000000000000000000000000000000000000000602082015281565b6124e7614386565b6124ef6143de565b60008060006124fd88611f30565b93506125076125df565b925061251588858589612611565b6125278860a001518560400151612f7d565b915061253387836136df565b9050612546888589848960000151612990565b61255088826136f5565b945061256788848660200151876040015189612aa9565b612572888487613756565b505050509392505050565b8151815161258b9190613864565b8252602080830151908201516125a19190613864565b6020830152604080830151908201516125ba9190613864565b6040830152606080830151908201516125d39190613864565b60609092019190915250565b600a5460009073ffffffffffffffffffffffffffffffffffffffff16818115612608578161260a565b335b9392505050565b825160ff1660031461264f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061579d565b606084015173ffffffffffffffffffffffffffffffffffffffff16156126c257606084015173ffffffffffffffffffffffffffffffffffffffff1633146126c2576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906157ad565b602084015173ffffffffffffffffffffffffffffffffffffffff161561274d578173ffffffffffffffffffffffffffffffffffffffff16846020015173ffffffffffffffffffffffffffffffffffffffff1614151561274d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906155ed565b604083015115156127a35761276b836020015185600001518361135b565b15156127a3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061565d565b50505050565b6127bb8260a001518260a001516138ae565b6127cd836080015183608001516138ae565b1015612805576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906157bd565b5050565b6128116143af565b6000806000806128258960a0015188612f7d565b935061283a89608001518a60a0015186613909565b925061284a8860a0015187612f7d565b915061285f88608001518960a0015184613909565b90508084106128a25760208086018051839052805182018490525151865182015260808a015160a08b015187519092015161289a9290613909565b8551526128df565b845183905284516020908101859052855181015190860180519190915260a089015160808a01519151516128d69290613986565b60208087015101525b84515160208087015101516128f49190612f7d565b604086015284515160808a015160c08b0151612911929190613909565b85516040015284516020015160a08a015160e08b0151612932929190613909565b855160600152602085015151608089015160c08a0151612953929190613909565b8560200151604001818152505061297b8560200151602001518960a001518a60e00151613909565b60208601516060015250505050949350505050565b8215156129c9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156dd565b82821115612a03576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156cd565b8460a00151612a16856040015184613864565b1115612a4e576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906155fd565b612a5c8560800151836138ae565b612a6a828760a001516138ae565b1115612aa2576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061575d565b5050505050565b612ab7828260200151613864565b600084815260046020908152604091829020929092558681015187518451938501518584015160608701516101408c01516101608d015196518b9873ffffffffffffffffffffffffffffffffffffffff9788169897909616967f0bcc4c97732e47d9946f229edb95f5b6323f601300e4690de719993f3c37112996612b46968f96339692959194909390615433565b60405180910390a45050505050565b60018054604080516020601f60027fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6101008789161502019095169490940493840181900481028201810190925282815260609390929091830182828015612bfe5780601f10612bd357610100808354040283529160200191612bfe565b820191906000526020600020905b815481529060010190602001808311612be157829003601f168201915b50505050509050612c2685610140015186600001518660000151856020015160200151613a23565b61014084015184518651845160200151612c4293929190613a23565b612c5b8561014001518660000151858560400151613a23565b612c778186600001518760400151856000015160400151613a23565b612c938185600001518660400151856020015160400151613a23565b836040015173ffffffffffffffffffffffffffffffffffffffff16856040015173ffffffffffffffffffffffffffffffffffffffff161415612cfd57612cf881848760400151612cf3866000015160600151876020015160600151613864565b613a23565b612aa2565b612d1581848760400151856000015160600151613a23565b612aa281848660400151856020015160600151613a23565b604080517fb4be83d5000000000000000000000000000000000000000000000000000000006020808301919091526060602483018181528751608485019081528884015160a48601529488015160c48501529087015160e4840152608087015161010484015260a087015161012484015260c087015161014484015260e08701516101648401526101008701516101848401526101208701516101a4840152610140870180516101c485019081526101608901516101e4860152610180905251805161020485018190529394919384936044870192849261022489019291820191601f82010460005b81811015612e34578351855260209485019490930192600101612e16565b50505050818103610160808401919091528a0151805180835260209283019291820191601f82010460005b81811015612e7d578351855260209485019490930192600101612e5f565b50505089845250848103602093840190815288518083529093918201918981019190601f82010460005b81811015612ec5578351855260209485019490930192600101612ea7565b5050507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08883030188525060405250505050509392505050565b612f076143de565b612f1082611f30565b9050612f1c8282613bed565b612805828260200151613d04565b612f32614386565b612f3d8484846124df565b6020810151909150831461260a576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061574d565b600082821115612fb9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061560d565b508082035b92915050565b6000808251111515613002576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156fd565b815182907fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff810190811061303257fe5b016020015182517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01909252507f0100000000000000000000000000000000000000000000000000000000000000908190040290565b6000816020018351101515156130ca576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061562d565b50016020015190565b6040516000906060907f1626ba7e000000000000000000000000000000000000000000000000000000009061310e908790869060240161554e565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0818403018152919052602080820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff00000000000000000000000000000000000000000000000000000000909416939093178352815191935090829081885afa8080156131ab576001811461321c57612572565b7f08c379a0000000000000000000000000000000000000000000000000000000006000527c20000000000000000000000000000000000000000000000000000000006020527c0c57414c4c45545f4552524f5200000000000000000000000000000000604052600060605260646000fd5b50505195945050505050565b60006014825110151515613268576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061578d565b613276826014845103613dab565b82517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffec019092525090565b6040516000906060907f9363470200000000000000000000000000000000000000000000000000000000906132de90879087908790602401615521565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0818403018152919052602080820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff000000000000000000000000000000000000000000000000000000009094169390931783528151919350908290818a5afa80801561337b57600181146133ec576133f1565b7f08c379a0000000000000000000000000000000000000000000000000000000006000527c20000000000000000000000000000000000000000000000000000000006020527c0f56414c494441544f525f4552524f5200000000000000000000000000604052600060605260646000fd5b825194505b50505050949350505050565b6000808311613438576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061564d565b61344b61344585846138ae565b84613e0c565b949350505050565b604080517f5a65726f45785472616e73616374696f6e2800000000000000000000000000006020808301919091527f75696e743235362073616c742c0000000000000000000000000000000000000060328301527f61646472657373207369676e6572416464726573732c00000000000000000000603f8301527f627974657320646174610000000000000000000000000000000000000000000060558301527f2900000000000000000000000000000000000000000000000000000000000000605f830152825180830384018152606090920192839052815160009384938493909282918401908083835b6020831061357c57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161353f565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff018019909216911617905260405191909301819003812089519097508995509093508392850191508083835b6020831061361257805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe090920191602091820191016135d5565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040805192909401829003822097825281019a909a525073ffffffffffffffffffffffffffffffffffffffff97909716968801969096525050606085015250506080909120919050565b600280546040517f190100000000000000000000000000000000000000000000000000000000000081529182015260228101919091526042902090565b6000612fbe611afd83613e23565b60008183106136ee578161260a565b5090919050565b6136fd614386565b6020810182905260a08301516080840151613719918491613909565b808252608084015160c0850151613731929190613909565b604082015260a083015160e084015161374b918491613909565b606082015292915050565b60018054604080516020601f60027fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff61010087891615020190951694909404938401819004810282018101909252828152606093909290918301828280156137ff5780601f106137d4576101008083540402835291602001916137ff565b820191906000526020600020905b8154815290600101906020018083116137e257829003601f168201915b5050505050905061381f8461014001518560000151858560000151613a23565b6138388461016001518486600001518560200151613a23565b61385081856000015186604001518560400151613a23565b6127a3818486604001518560600151613a23565b6000828201838110156138a3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061567d565b8091505b5092915050565b6000808315156138c157600091506138a7565b508282028284828115156138d157fe5b04146138a3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061567d565b6000808311613944576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061564d565b61394f84848461427c565b15613438576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156ad565b60008083116139c1576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061564d565b6139cc848484614301565b15613a03576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156ad565b61344b613445613a1386856138ae565b613a1e866001612f7d565b613864565b600080600083118015613a6257508373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff1614155b15613be5578551600310613aa2576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061573d565b50506020848101517fffffffff00000000000000000000000000000000000000000000000000000000166000818152600b90925260409091205473ffffffffffffffffffffffffffffffffffffffff16801515613b2b576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906156ed565b604051660fffffffffffe0603f885101168060840182017fa85e59e40000000000000000000000000000000000000000000000000000000083526080600484015273ffffffffffffffffffffffffffffffffffffffff8816602484015273ffffffffffffffffffffffffffffffffffffffff87166044840152856064840152608483015b81811015613bc757895181526020998a019901613baf565b61020084858403866000895af1801515613bdf573d85fd5b50505050505b505050505050565b805160009060ff16600314613c2e576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061579d565b606083015173ffffffffffffffffffffffffffffffffffffffff1615613ca157606083015173ffffffffffffffffffffffffffffffffffffffff163314613ca1576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c6906157ad565b613ca96125df565b835190915073ffffffffffffffffffffffffffffffffffffffff808316911614613cff576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061566d565b505050565b6000818152600560205260409081902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660011790558281015183516101408501516101608601519351859473ffffffffffffffffffffffffffffffffffffffff9485169493909316927fdc47b3613d9fe400085f6dbdc99453462279057e6207385042827ed6b1a62cf792613d9f923392906154b7565b60405180910390a45050565b600081601401835110151515613ded576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061578d565b50016014015173ffffffffffffffffffffffffffffffffffffffff1690565b6000808284811515613e1a57fe5b04949350505050565b604080517f4f726465722800000000000000000000000000000000000000000000000000006020808301919091527f61646472657373206d616b6572416464726573732c000000000000000000000060268301527f616464726573732074616b6572416464726573732c0000000000000000000000603b8301527f6164647265737320666565526563697069656e74416464726573732c0000000060508301527f616464726573732073656e646572416464726573732c00000000000000000000606c8301527f75696e74323536206d616b65724173736574416d6f756e742c0000000000000060828301527f75696e743235362074616b65724173736574416d6f756e742c00000000000000609b8301527f75696e74323536206d616b65724665652c00000000000000000000000000000060b48301527f75696e743235362074616b65724665652c00000000000000000000000000000060c58301527f75696e743235362065787069726174696f6e54696d655365636f6e64732c000060d68301527f75696e743235362073616c742c0000000000000000000000000000000000000060f48301527f6279746573206d616b65724173736574446174612c00000000000000000000006101018301527f62797465732074616b65724173736574446174610000000000000000000000006101168301527f290000000000000000000000000000000000000000000000000000000000000061012a830152825161010b81840301815261012b90920192839052815160009384938493849391929182918401908083835b602083106140ab57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161406e565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930181900381206101408b0151805191995095509093508392850191508083835b6020831061414657805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101614109565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930181900381206101608b0151805191985095509093508392850191508083835b602083106141e157805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe090920191602091820191016141a4565b5181516020939093036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff018019909116921691909117905260405192018290039091207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0890180516101408b018051610160909c0180519a84529881529288526101a0822091529890525050509190525090919050565b6000808084116142b8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061564d565b8215806142c3575084155b156142d15760009150610a88565b838015156142db57fe5b85840990506142ea85846138ae565b6142f66103e8836138ae565b101595945050505050565b60008080841161433d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016106c69061564d565b821580614348575084155b156143565760009150610a88565b8380151561436057fe5b8584099050836143708583612f7d565b81151561437957fe5b0690506142ea85846138ae565b608060405190810160405280600081526020016000815260200160008152602001600081525090565b610120604051908101604052806143c4614386565b81526020016143d1614386565b8152602001600081525090565b604080516060810182526000808252602082018190529181019190915290565b600061260a82356158b0565b6000601f8201831361441b57600080fd5b813561442e6144298261583f565b615818565b81815260209384019390925082018360005b8381101561446c578135860161445688826145bc565b8452506020928301929190910190600101614440565b5050505092915050565b6000601f8201831361448757600080fd5b81356144956144298261583f565b81815260209384019390925082018360005b8381101561446c57813586016144bd888261460b565b84525060209283019291909101906001016144a7565b6000601f820183136144e457600080fd5b81356144f26144298261583f565b9150818183526020840193506020810190508385602084028201111561451757600080fd5b60005b8381101561446c578161452d888261454f565b845250602092830192919091019060010161451a565b600061260a82356158c9565b600061260a82356158ce565b600061260a82356158d1565b600061260a82516158d1565b600080601f8301841361458557600080fd5b50813567ffffffffffffffff81111561459d57600080fd5b6020830191508360018202830111156145b557600080fd5b9250929050565b6000601f820183136145cd57600080fd5b81356145db61442982615860565b915080825260208301602083018583830111156145f757600080fd5b614602838284615907565b50505092915050565b6000610180828403121561461e57600080fd5b614629610180615818565b9050600061463784846143fe565b8252506020614648848483016143fe565b602083015250604061465c848285016143fe565b6040830152506060614670848285016143fe565b60608301525060806146848482850161454f565b60808301525060a06146988482850161454f565b60a08301525060c06146ac8482850161454f565b60c08301525060e06146c08482850161454f565b60e0830152506101006146d58482850161454f565b610100830152506101206146eb8482850161454f565b6101208301525061014082013567ffffffffffffffff81111561470d57600080fd5b614719848285016145bc565b6101408301525061016082013567ffffffffffffffff81111561473b57600080fd5b614747848285016145bc565b6101608301525092915050565b60006020828403121561476657600080fd5b600061344b84846143fe565b6000806040838503121561478557600080fd5b600061479185856143fe565b92505060206147a2858286016143fe565b9150509250929050565b600080604083850312156147bf57600080fd5b60006147cb85856143fe565b92505060206147a285828601614543565b6000602082840312156147ee57600080fd5b813567ffffffffffffffff81111561480557600080fd5b61344b84828501614476565b60008060006060848603121561482657600080fd5b833567ffffffffffffffff81111561483d57600080fd5b61484986828701614476565b935050602084013567ffffffffffffffff81111561486657600080fd5b614872868287016144d3565b925050604084013567ffffffffffffffff81111561488f57600080fd5b61489b8682870161440a565b9150509250925092565b6000806000606084860312156148ba57600080fd5b833567ffffffffffffffff8111156148d157600080fd5b6148dd86828701614476565b93505060206148728682870161454f565b60006020828403121561490057600080fd5b600061344b848461454f565b6000806040838503121561491f57600080fd5b6000614791858561454f565b6000806000806060858703121561494157600080fd5b600061494d878761454f565b945050602061495e878288016143fe565b935050604085013567ffffffffffffffff81111561497b57600080fd5b61498787828801614573565b95989497509550505050565b6000806000606084860312156149a857600080fd5b60006149b4868661454f565b93505060206149c5868287016143fe565b925050604084013567ffffffffffffffff8111156149e257600080fd5b61489b868287016145bc565b600060208284031215614a0057600080fd5b600061344b848461455b565b600060208284031215614a1e57600080fd5b600061344b8484614567565b600060208284031215614a3c57600080fd5b813567ffffffffffffffff811115614a5357600080fd5b61344b8482850161460b565b60008060008060808587031215614a7557600080fd5b843567ffffffffffffffff811115614a8c57600080fd5b614a988782880161460b565b945050602085013567ffffffffffffffff811115614ab557600080fd5b614ac18782880161460b565b935050604085013567ffffffffffffffff811115614ade57600080fd5b614aea878288016145bc565b925050606085013567ffffffffffffffff811115614b0757600080fd5b614b13878288016145bc565b91505092959194509250565b600080600060608486031215614b3457600080fd5b833567ffffffffffffffff811115614b4b57600080fd5b614b578682870161460b565b93505060206149c58682870161454f565b60008060008060008060808789031215614b8157600080fd5b6000614b8d898961454f565b9650506020614b9e89828a016143fe565b955050604087013567ffffffffffffffff811115614bbb57600080fd5b614bc789828a01614573565b9450945050606087013567ffffffffffffffff811115614be657600080fd5b614bf289828a01614573565b92509250509295509295509295565b614c0a816158b0565b82525050565b6000614c1b826158ac565b808452602084019350614c2d836158a6565b60005b82811015614c5d57614c438683516153e5565b614c4c826158a6565b606096909601959150600101614c30565b5093949350505050565b614c0a816158c9565b614c0a816158ce565b614c0a816158d1565b6000614c8d826158ac565b808452614ca1816020860160208601615913565b614caa8161593f565b9093016020019392505050565b614c0a816158fc565b601281527f4c454e4754485f36355f52455155495245440000000000000000000000000000602082015260400190565b600d81527f494e56414c49445f54414b455200000000000000000000000000000000000000602082015260400190565b600e81527f4f524445525f4f56455246494c4c000000000000000000000000000000000000602082015260400190565b601181527f55494e543235365f554e444552464c4f57000000000000000000000000000000602082015260400190565b601a81527f41535345545f50524f58595f414c52454144595f455849535453000000000000602082015260400190565b602681527f475245415445525f4f525f455155414c5f544f5f33325f4c454e4754485f524560208201527f5155495245440000000000000000000000000000000000000000000000000000604082015260600190565b601581527f5349474e41545552455f554e535550504f525445440000000000000000000000602082015260400190565b601081527f4449564953494f4e5f42595f5a45524f00000000000000000000000000000000602082015260400190565b601781527f494e56414c49445f4f524445525f5349474e4154555245000000000000000000602082015260400190565b600d81527f494e56414c49445f4d414b455200000000000000000000000000000000000000602082015260400190565b601081527f55494e543235365f4f564552464c4f5700000000000000000000000000000000602082015260400190565b600f81527f494e56414c49445f54585f484153480000000000000000000000000000000000602082015260400190565b601181527f494e56414c49445f5349474e4154555245000000000000000000000000000000602082015260400190565b600e81527f524f554e44494e475f4552524f52000000000000000000000000000000000000602082015260400190565b601081527f4641494c45445f455845435554494f4e00000000000000000000000000000000602082015260400190565b600d81527f54414b45525f4f56455250415900000000000000000000000000000000000000602082015260400190565b601481527f494e56414c49445f54414b45525f414d4f554e54000000000000000000000000602082015260400190565b601a81527f41535345545f50524f58595f444f45535f4e4f545f4558495354000000000000602082015260400190565b602181527f475245415445525f5448414e5f5a45524f5f4c454e4754485f5245515549524560208201527f4400000000000000000000000000000000000000000000000000000000000000604082015260600190565b601181527f5349474e41545552455f494c4c4547414c000000000000000000000000000000602082015260400190565b601e81527f4c454e4754485f475245415445525f5448414e5f305f52455155495245440000602082015260400190565b601781527f494e56414c49445f4e45575f4f524445525f45504f4348000000000000000000602082015260400190565b601e81527f4c454e4754485f475245415445525f5448414e5f335f52455155495245440000602082015260400190565b601481527f434f4d504c4554455f46494c4c5f4641494c4544000000000000000000000000602082015260400190565b601281527f494e56414c49445f46494c4c5f50524943450000000000000000000000000000602082015260400190565b601281527f5245454e5452414e43595f494c4c4547414c0000000000000000000000000000602082015260400190565b601381527f4f4e4c595f434f4e54524143545f4f574e455200000000000000000000000000602082015260400190565b602681527f475245415445525f4f525f455155414c5f544f5f32305f4c454e4754485f524560208201527f5155495245440000000000000000000000000000000000000000000000000000604082015260600190565b601081527f4f524445525f554e46494c4c41424c4500000000000000000000000000000000602082015260400190565b600e81527f494e56414c49445f53454e444552000000000000000000000000000000000000602082015260400190565b601881527f4e454741544956455f5350524541445f52455155495245440000000000000000602082015260400190565b601481527f494e56414c49445f54585f5349474e4154555245000000000000000000000000602082015260400190565b601181527f4c454e4754485f305f5245515549524544000000000000000000000000000000602082015260400190565b805160808301906153738482614c70565b5060208201516153866020850182614c70565b5060408201516153996040850182614c70565b5060608201516127a36060850182614c70565b80516101208301906153be8482615362565b5060208201516153d16080850182615362565b5060408201516127a3610100850182614c70565b805160608301906153f6848261541c565b5060208201516154096020850182614c70565b5060408201516127a36040850182614c70565b614c0a816158f6565b60208101612fbe8284614c01565b6101008101615442828b614c01565b61544f602083018a614c01565b61545c6040830189614c70565b6154696060830188614c70565b6154766080830187614c70565b61548360a0830186614c70565b81810360c08301526154958185614c82565b905081810360e08301526154a98184614c82565b9a9950505050505050505050565b606081016154c58286614c01565b81810360208301526154d78185614c82565b905081810360408301526154eb8184614c82565b95945050505050565b6020808252810161260a8184614c10565b60208101612fbe8284614c67565b60208101612fbe8284614c70565b6060810161552f8286614c70565b61553c6020830185614c01565b81810360408301526154eb8184614c82565b6040810161555c8285614c70565b818103602083015261344b8184614c82565b6080810161557c8287614c70565b615589602083018661541c565b6155966040830185614c70565b6154eb6060830184614c70565b604081016155b18285614c79565b61260a6020830184614c01565b6020808252810161260a8184614c82565b60208101612fbe8284614cb7565b60208082528101612fbe81614cc0565b60208082528101612fbe81614cf0565b60208082528101612fbe81614d20565b60208082528101612fbe81614d50565b60208082528101612fbe81614d80565b60208082528101612fbe81614db0565b60208082528101612fbe81614e06565b60208082528101612fbe81614e36565b60208082528101612fbe81614e66565b60208082528101612fbe81614e96565b60208082528101612fbe81614ec6565b60208082528101612fbe81614ef6565b60208082528101612fbe81614f26565b60208082528101612fbe81614f56565b60208082528101612fbe81614f86565b60208082528101612fbe81614fb6565b60208082528101612fbe81614fe6565b60208082528101612fbe81615016565b60208082528101612fbe81615046565b60208082528101612fbe8161509c565b60208082528101612fbe816150cc565b60208082528101612fbe816150fc565b60208082528101612fbe8161512c565b60208082528101612fbe8161515c565b60208082528101612fbe8161518c565b60208082528101612fbe816151bc565b60208082528101612fbe816151ec565b60208082528101612fbe8161521c565b60208082528101612fbe81615272565b60208082528101612fbe816152a2565b60208082528101612fbe816152d2565b60208082528101612fbe81615302565b60208082528101612fbe81615332565b60808101612fbe8284615362565b6101208101612fbe82846153ac565b60608101612fbe82846153e5565b60405181810167ffffffffffffffff8111828210171561583757600080fd5b604052919050565b600067ffffffffffffffff82111561585657600080fd5b5060209081020190565b600067ffffffffffffffff82111561587757600080fd5b506020601f919091017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0160190565b60200190565b5190565b73ffffffffffffffffffffffffffffffffffffffff1690565b151590565b90565b7fffffffff000000000000000000000000000000000000000000000000000000001690565b60ff1690565b6000612fbe826158b0565b82818337506000910152565b60005b8381101561592e578181015183820152602001615916565b838111156127a35750506000910152565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe016905600a265627a7a72305820d41ee66f45c4d1637cb6e5f109447c6d5d7fef3204a685dc442151c0f029b7da6c6578706572696d656e74616cf50037" + } + } + }, + "networks": {} +} \ No newline at end of file diff --git a/packages/ethereum/tests/contracts/SingleField.json b/packages/ethereum/tests/contracts/SingleField.json new file mode 100644 index 00000000..5f218f41 --- /dev/null +++ b/packages/ethereum/tests/contracts/SingleField.json @@ -0,0 +1,25 @@ +{ + "schemaVersion": "2.0.0", + "contractName": "SingleField", + "compilerOutput": { + "abi": [ + { + "constant": false, + "inputs": [ + { + "components": [ + { "name": "singleField", "type": "uint256" } + ], + "name": "SingleFieldStruct", + "type": "tuple" + } + ], + "name": "SingleFieldFunction", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + } + ] + } +} diff --git a/packages/ethereum/web3-ethereum.cabal b/packages/ethereum/web3-ethereum.cabal new file mode 100644 index 00000000..d6b3dc4c --- /dev/null +++ b/packages/ethereum/web3-ethereum.cabal @@ -0,0 +1,155 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-ethereum +version: 1.1.0.1 +synopsis: Ethereum support for Haskell Web3 library. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple +data-files: + tests/contracts/ERC20.json + tests/contracts/Exchange.json + tests/contracts/SingleField.json + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Network.Ethereum + Network.Ethereum.Account + Network.Ethereum.Account.Class + Network.Ethereum.Account.Default + Network.Ethereum.Account.Internal + Network.Ethereum.Account.LocalKey + Network.Ethereum.Account.Personal + Network.Ethereum.Account.Safe + Network.Ethereum.Api.Eth + Network.Ethereum.Api.Net + Network.Ethereum.Api.Personal + Network.Ethereum.Api.Types + Network.Ethereum.Api.Web3 + Network.Ethereum.Chain + Network.Ethereum.Contract + Network.Ethereum.Contract.Event + Network.Ethereum.Contract.Event.Common + Network.Ethereum.Contract.Event.MultiFilter + Network.Ethereum.Contract.Event.SingleFilter + Network.Ethereum.Contract.Method + Network.Ethereum.Contract.TH + Network.Ethereum.Ens + Network.Ethereum.Ens.PublicResolver + Network.Ethereum.Ens.Registry + Network.Ethereum.Transaction + Network.Ethereum.Unit + other-modules: + Paths_web3_ethereum + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + OneTuple >=0.2 && <0.5 + , aeson >=1.2 && <2.3 + , aeson-casing ==0.2.* + , base >=4.11 && <4.21 + , bytestring >=0.10 && <0.13 + , data-default >=0.7 && <0.9 + , exceptions >=0.8 && <0.11 + , generics-sop >=0.3 && <0.6 + , jsonrpc-tinyclient >=1.0 && <1.2 + , machines >=0.6 && <0.8 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , microlens-aeson >=2.2 && <2.6 + , mtl >=2.2 && <2.4 + , relapse ==1.0.* + , tagged ==0.8.* + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , transformers >=0.5 && <0.7 + , vinyl >=0.5 && <0.15 + , web3-crypto >=1.0 && <1.2 + , web3-solidity >=1.0 && <1.2 + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Network.Ethereum.Test.EventSpec + Network.Ethereum.Test.MethodDumpSpec + Network.Ethereum.Test.THSpec + Network.Ethereum.Test.TransactionSpec + Network.Ethereum + Network.Ethereum.Account + Network.Ethereum.Account.Class + Network.Ethereum.Account.Default + Network.Ethereum.Account.Internal + Network.Ethereum.Account.LocalKey + Network.Ethereum.Account.Personal + Network.Ethereum.Account.Safe + Network.Ethereum.Api.Eth + Network.Ethereum.Api.Net + Network.Ethereum.Api.Personal + Network.Ethereum.Api.Types + Network.Ethereum.Api.Web3 + Network.Ethereum.Chain + Network.Ethereum.Contract + Network.Ethereum.Contract.Event + Network.Ethereum.Contract.Event.Common + Network.Ethereum.Contract.Event.MultiFilter + Network.Ethereum.Contract.Event.SingleFilter + Network.Ethereum.Contract.Method + Network.Ethereum.Contract.TH + Network.Ethereum.Ens + Network.Ethereum.Ens.PublicResolver + Network.Ethereum.Ens.Registry + Network.Ethereum.Transaction + Network.Ethereum.Unit + Paths_web3_ethereum + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + OneTuple >=0.2 && <0.5 + , aeson >=1.2 && <2.3 + , aeson-casing ==0.2.* + , base >=4.11 && <4.21 + , bytestring >=0.10 && <0.13 + , data-default >=0.7 && <0.9 + , exceptions >=0.8 && <0.11 + , generics-sop >=0.3 && <0.6 + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , jsonrpc-tinyclient >=1.0 && <1.2 + , machines >=0.6 && <0.8 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , microlens-aeson >=2.2 && <2.6 + , mtl >=2.2 && <2.4 + , relapse ==1.0.* + , tagged ==0.8.* + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , transformers >=0.5 && <0.7 + , vinyl >=0.5 && <0.15 + , web3-crypto >=1.0 && <1.2 + , web3-solidity >=1.0 && <1.2 + default-language: Haskell2010 diff --git a/packages/hexstring/LICENSE b/packages/hexstring/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/hexstring/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/hexstring/Setup.hs b/packages/hexstring/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/hexstring/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/hexstring/memory-hexstring.cabal b/packages/hexstring/memory-hexstring.cabal new file mode 100644 index 00000000..f3b212c2 --- /dev/null +++ b/packages/hexstring/memory-hexstring.cabal @@ -0,0 +1,44 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: memory-hexstring +version: 1.1.0.0 +synopsis: Hex-string type for Haskell Web3 library. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Data.ByteArray.HexString + Data.ByteArray.HexString.Convert + Data.ByteArray.HexString.Internal + Data.ByteArray.HexString.TH + other-modules: + Paths_memory_hexstring + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , bytestring >=0.10 && <0.13 + , memory >=0.14 && <0.19 + , scale >=1.0 && <1.2 + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + default-language: Haskell2010 diff --git a/packages/hexstring/package.yaml b/packages/hexstring/package.yaml new file mode 100644 index 00000000..829850c2 --- /dev/null +++ b/packages/hexstring/package.yaml @@ -0,0 +1,47 @@ +name: memory-hexstring +version: 1.1.0.0 +synopsis: Hex-string type for Haskell Web3 library. +description: Client library for Third Generation of Web. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- aeson >=1.2 && <2.3 +- memory >=0.14 && <0.19 +- bytestring >=0.10 && <0.13 +- template-haskell >=2.11 && <2.23 +- scale >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src diff --git a/packages/hexstring/src/Data/ByteArray/HexString.hs b/packages/hexstring/src/Data/ByteArray/HexString.hs new file mode 100644 index 00000000..12f36bcd --- /dev/null +++ b/packages/hexstring/src/Data/ByteArray/HexString.hs @@ -0,0 +1,19 @@ +-- | +-- Module : Data.ByteArray.HexString +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Hex string data type top level module. +-- + +module Data.ByteArray.HexString + ( module Internal + , module Convert + ) where + +import Data.ByteArray.HexString.Convert as Convert +import Data.ByteArray.HexString.Internal as Internal diff --git a/packages/hexstring/src/Data/ByteArray/HexString/Convert.hs b/packages/hexstring/src/Data/ByteArray/HexString/Convert.hs new file mode 100644 index 00000000..ececd1fb --- /dev/null +++ b/packages/hexstring/src/Data/ByteArray/HexString/Convert.hs @@ -0,0 +1,52 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.ByteArray.HexString.Convert +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- From/to hex conversion functions. +-- + +module Data.ByteArray.HexString.Convert where + +import Data.Aeson (FromJSON (..), ToJSON (..), + Value (String), withText) +import Data.ByteArray (ByteArray, ByteArrayAccess, + convert) +import Data.ByteArray.Encoding (Base (Base16), + convertToBase) +import Data.Text (Text) +import Data.Text.Encoding (decodeUtf8, encodeUtf8) + +import Data.ByteArray.HexString.Internal (HexString (..), hexString) + +-- | Convert type into it's hex representation. +class ToHex a where + toHex :: a -> HexString + +-- | Convert hex string into a type or return an error. +class FromHex a where + fromHex :: HexString -> Either String a + +-- | Reads a raw bytes and converts to hex representation. +fromBytes :: ByteArrayAccess ba => ba -> HexString +fromBytes = HexString . convert + +-- | Access to the raw bytes of 'HexString'. +toBytes :: ByteArray ba => HexString -> ba +toBytes = convert . unHexString + +-- | Access to a 'Text' representation of the 'HexString' +toText :: HexString -> Text +toText = ("0x" <>) . decodeUtf8 . convertToBase Base16 . unHexString + +instance FromJSON HexString where + parseJSON = withText "HexString" $ either fail pure . hexString . encodeUtf8 + +instance ToJSON HexString where + toJSON = String . toText diff --git a/packages/hexstring/src/Data/ByteArray/HexString/Internal.hs b/packages/hexstring/src/Data/ByteArray/HexString/Internal.hs new file mode 100644 index 00000000..1e7ad8ad --- /dev/null +++ b/packages/hexstring/src/Data/ByteArray/HexString/Internal.hs @@ -0,0 +1,50 @@ +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.ByteArray.HexString.Internal +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Hex string data type. +-- + +module Data.ByteArray.HexString.Internal where + +import Codec.Scale (Decode, Encode) +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) +import qualified Data.ByteArray as BA (drop, take) +import Data.ByteArray.Encoding (Base (Base16), convertFromBase, + convertToBase) +import Data.ByteString (ByteString) +import qualified Data.ByteString.Char8 as C8 (unpack) +import Data.String (IsString (..)) + +-- | Represents a Hex string. Guarantees that all characters it contains +-- are valid hex characters. +newtype HexString = HexString { unHexString :: ByteString } + deriving (Eq, Ord, Semigroup, Monoid, ByteArrayAccess, ByteArray, Encode, Decode) + +instance Show HexString where + show = ("0x" ++) . C8.unpack . unHexString' + where + unHexString' :: HexString -> ByteString + unHexString' = convertToBase Base16 . unHexString + +instance IsString HexString where + fromString = hexString' . fromString + where + hexString' :: ByteString -> HexString + hexString' = either error id . hexString + +-- | Smart constructor which trims '0x' and validates length is even. +hexString :: ByteArray ba => ba -> Either String HexString +hexString bs = HexString <$> convertFromBase Base16 bs' + where + hexStart = convert ("0x" :: ByteString) + bs' | BA.take 2 bs == hexStart = BA.drop 2 bs + | otherwise = bs diff --git a/packages/hexstring/src/Data/ByteArray/HexString/TH.hs b/packages/hexstring/src/Data/ByteArray/HexString/TH.hs new file mode 100644 index 00000000..f332a6c1 --- /dev/null +++ b/packages/hexstring/src/Data/ByteArray/HexString/TH.hs @@ -0,0 +1,33 @@ +{-# LANGUAGE QuasiQuotes #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Data.ByteArray.HexString.TH +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Hex string template haskell helpers. +-- + +module Data.ByteArray.HexString.TH where + +import Data.ByteArray.HexString.Internal (HexString) +import Data.String (fromString) +import Language.Haskell.TH.Quote (QuasiQuoter (..), quoteFile) + +-- | Get hex string from a file. +hexFrom :: QuasiQuoter +hexFrom = quoteFile hex + +-- | Get hex string from plain text. +hex :: QuasiQuoter +hex = QuasiQuoter + { quoteExp = \s -> [|fromString s :: HexString|] + , quotePat = undefined + , quoteType = undefined + , quoteDec = undefined + } diff --git a/packages/jsonrpc/LICENSE b/packages/jsonrpc/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/jsonrpc/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/jsonrpc/Setup.hs b/packages/jsonrpc/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/jsonrpc/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/jsonrpc/jsonrpc-tinyclient.cabal b/packages/jsonrpc/jsonrpc-tinyclient.cabal new file mode 100644 index 00000000..0eaf6022 --- /dev/null +++ b/packages/jsonrpc/jsonrpc-tinyclient.cabal @@ -0,0 +1,44 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: jsonrpc-tinyclient +version: 1.1.0.0 +synopsis: Tiny JSON-RPC client for Haskell Web3 library. +description: Minimalistic JSON-RPC client, inspired by haxr library. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Network.JsonRpc.TinyClient + other-modules: + Paths_jsonrpc_tinyclient + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , bytestring >=0.10 && <0.13 + , exceptions >=0.8 && <0.11 + , http-client >=0.5 && <0.8 + , http-client-tls ==0.3.* + , mtl >=2.2 && <2.4 + , random >=1.0 && <1.3 + , text >=1.2 && <2.2 + , websockets >=0.10 && <0.14 + default-language: Haskell2010 diff --git a/packages/jsonrpc/package.yaml b/packages/jsonrpc/package.yaml new file mode 100644 index 00000000..11e55ddf --- /dev/null +++ b/packages/jsonrpc/package.yaml @@ -0,0 +1,50 @@ +name: jsonrpc-tinyclient +version: 1.1.0.0 +synopsis: Tiny JSON-RPC client for Haskell Web3 library. +description: Minimalistic JSON-RPC client, inspired by haxr library. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- aeson >=1.2 && <2.3 +- random >=1.0 && <1.3 +- bytestring >=0.10 && <0.13 +- exceptions >=0.8 && <0.11 +- websockets >=0.10 && <0.14 +- http-client >=0.5 && <0.8 +- http-client-tls >=0.3 && <0.4 +- mtl >=2.2 && <2.4 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src diff --git a/packages/jsonrpc/src/Network/JsonRpc/TinyClient.hs b/packages/jsonrpc/src/Network/JsonRpc/TinyClient.hs new file mode 100644 index 00000000..a310f507 --- /dev/null +++ b/packages/jsonrpc/src/Network/JsonRpc/TinyClient.hs @@ -0,0 +1,217 @@ +{-# LANGUAGE CPP #-} +{-# LANGUAGE ConstraintKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE FunctionalDependencies #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE UndecidableInstances #-} + +-- | +-- Module : Network.JsonRpc.TinyClient +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Tiny JSON-RPC 2.0 client. +-- Functions for implementing the client side of JSON-RPC 2.0. +-- See . +-- +-- If you have monad with 'MonadIO', 'MonadThrow' and 'MonadReader' instances, +-- it can be used as base for JSON-RPC calls. +-- +-- Example: +-- +-- @ +-- newtype MyMonad a = ... +-- +-- instance JsonRpc MyMonad +-- +-- foo :: Mymonad Text +-- foo = remote "foo" +-- @ +-- +-- Arguments of function are stored into @params@ request array. +-- +-- Example: +-- +-- @ +-- myMethod :: JsonRpc m => Int -> Bool -> m String +-- myMethod = remote "myMethod" +-- @ +-- + +module Network.JsonRpc.TinyClient + ( + -- * The JSON-RPC remote call monad + JsonRpc(..) + , MethodName + + -- * JSON-RPC client settings + , JsonRpcClient(..) + , defaultSettings + + -- * Error handling + , JsonRpcException(..) + , RpcError(..) + ) where + +import Control.Applicative ((<|>)) +import Control.Exception (Exception) +import Control.Monad ((<=<)) +import Control.Monad.Catch (MonadThrow (..)) +import Control.Monad.IO.Class (MonadIO (..)) +import Control.Monad.State (MonadState, get) +import Data.Aeson (FromJSON (..), ToJSON (..), + Value (String), eitherDecode, encode, + object, withObject, (.:), (.:?), (.=)) +import Data.ByteString.Lazy (ByteString) +import Data.Text (Text, unpack) +import Network.HTTP.Client (Manager, RequestBody (RequestBodyLBS), + httpLbs, method, newManager, + parseRequest, requestBody, + requestHeaders, responseBody) +import Network.HTTP.Client.TLS (tlsManagerSettings) +import qualified Network.WebSockets as WS (Connection, receiveData, + sendTextData) +import System.Random (randomRIO) + +-- | JSON-RPC monad constrait. +type JsonRpcM m = (MonadIO m, MonadThrow m, MonadState JsonRpcClient m) + +-- | JSON-RPC client state vars. +data JsonRpcClient = JsonRpcHttpClient + { jsonRpcManager :: Manager + -- ^ HTTP connection manager. + , jsonRpcServer :: String + -- ^ Remote server URI. + } + | JsonRpcWsClient + { jsonRpcWsConnection :: WS.Connection + -- ^ WebSocket connection. + } + +-- | Create default 'JsonRpcClient' settings. +defaultSettings :: MonadIO m + => String -- ^ JSON-RPC server URI + -> m JsonRpcClient +defaultSettings srv = liftIO $ JsonRpcHttpClient + <$> newManager tlsManagerSettings + <*> pure srv + +instance Show JsonRpcClient where + show JsonRpcHttpClient{..} = "" + show JsonRpcWsClient{..} = "" + +-- | JSON-RPC request. +data Request = Request + { rqMethod :: !Text + , rqId :: !Int + , rqParams :: !Value + } + deriving (Eq, Show) + +instance ToJSON Request where + toJSON rq = object [ "jsonrpc" .= String "2.0" + , "method" .= rqMethod rq + , "params" .= rqParams rq + , "id" .= rqId rq + ] + +-- | JSON-RPC response. +data Response = Response + { rsResult :: !(Either RpcError Value) + } + deriving (Eq, Show) + +instance FromJSON Response where + parseJSON = + withObject "JSON-RPC response object" $ + \v -> Response <$> + (Right <$> v .: "result" <|> Left <$> v .: "error") + +-- | JSON-RPC error message +data RpcError = RpcError + { errCode :: !Int + , errMessage :: !Text + , errData :: !(Maybe Value) + } + deriving Eq + +instance Show RpcError where + show (RpcError code msg dat) = + "JSON-RPC error " ++ show code ++ ": " ++ unpack msg + ++ ". Data: " ++ show dat + +instance FromJSON RpcError where + parseJSON = withObject "JSON-RPC error object" $ + \v -> RpcError <$> v .: "code" + <*> v .: "message" + <*> v .:? "data" + +data JsonRpcException = ParsingException String + | CallException RpcError + deriving (Show, Eq) + +instance Exception JsonRpcException + +class JsonRpcM m => Remote m a | a -> m where + remote' :: ([Value] -> m ByteString) -> a + +instance (ToJSON a, Remote m b) => Remote m (a -> b) where + remote' f x = remote' (\xs -> f (toJSON x : xs)) + +instance {-# INCOHERENT #-} (JsonRpcM m, FromJSON b) => Remote m (m b) where + remote' f = decodeResponse =<< f [] + +-- | Name of called method. +type MethodName = Text + +-- | JSON-RPC call monad. +class JsonRpcM m => JsonRpc m where + -- | Remote call of JSON-RPC method. + remote :: Remote m a => MethodName -> a + {-# INLINE remote #-} + remote = remote' . call + +call :: JsonRpcM m + => MethodName + -> [Value] + -> m ByteString +call m r = do + rid <- liftIO $ randomRIO (0, maxInt) + connection . encode $ Request m (fromInteger rid) (toJSON r) + where + maxInt = toInteger (maxBound :: Int) + connection body = do + jsonRpcInstance <- get + case jsonRpcInstance of + JsonRpcHttpClient{..} -> do + request <- parseRequest jsonRpcServer + let request' = request { + requestBody = RequestBodyLBS body + , requestHeaders = [("Content-Type", "application/json")] + , method = "POST" + } + responseBody <$> liftIO (httpLbs request' jsonRpcManager) + + JsonRpcWsClient{..} -> liftIO $ do + WS.sendTextData jsonRpcWsConnection body + WS.receiveData jsonRpcWsConnection + + + +decodeResponse :: (MonadThrow m, FromJSON a) + => ByteString + -> m a +decodeResponse = (tryParse . eitherDecode . encode) + <=< tryResult . rsResult + <=< tryParse . eitherDecode + where + tryParse = either (throwM . ParsingException) return + tryResult = either (throwM . CallException) return diff --git a/packages/polkadot/LICENSE b/packages/polkadot/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/polkadot/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/polkadot/Setup.hs b/packages/polkadot/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/polkadot/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/polkadot/package.yaml b/packages/polkadot/package.yaml new file mode 100644 index 00000000..93446967 --- /dev/null +++ b/packages/polkadot/package.yaml @@ -0,0 +1,81 @@ +name: web3-polkadot +version: 1.1.0.1 +synopsis: Polkadot support for Haskell Web3 library. +description: Client library for Third Generation of Web. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- mtl >=2.2 && <2.4 +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- aeson >=1.2 && <2.3 +- scale >=1.0 && <1.2 +- parsec >=3.0 && <3.2 +- memory >=0.14 && <0.19 +- microlens >=0.4 && <0.5 +- containers >=0.6 && <0.8 +- crypton >=0.30 && <1.1 +- bytestring >=0.10 && <0.13 +- base58-bytestring >=0.1 && <0.2 +- cases >=0.1 && <0.2 +- generics-sop >=0.3 && <0.6 +- microlens-th >=0.4 && <0.5 +- microlens-mtl >=0.2 && <0.3 +- web3-crypto >=1.0 && <1.2 +- web3-bignum >=1.0 && <1.2 +- jsonrpc-tinyclient >=1.0 && <1.2 +- memory-hexstring >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + +data-files: +- tests/meta/*.hex +- tests/meta/*.json + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + dependencies: + - hspec-expectations-json >=1.0.0 && <1.1 + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/polkadot/src/Network/Polkadot.hs b/packages/polkadot/src/Network/Polkadot.hs new file mode 100644 index 00000000..c81ad024 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot.hs @@ -0,0 +1,37 @@ +-- | +-- Module : Network.Polkadot +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- A scalable, interoperable & secure network protocol for the next web. +-- + +module Network.Polkadot + ( + -- * Query blockchain storage. + query + , Argument(..) + -- * Base types and codecs. + , module Scale + , module Primitives + , module Crypto + -- * Extrinsic sign & send functions. + , module Account + , module Extrinsic + , module Call + ) where + +import Codec.Scale as Scale +import Network.Polkadot.Account as Account hiding (AccountId) +import Network.Polkadot.Call as Call +import Network.Polkadot.Crypto as Crypto hiding (MultiAddress, + MultiSignature, + MultiSigner) +import Network.Polkadot.Extrinsic as Extrinsic +import Network.Polkadot.Primitives as Primitives +import Network.Polkadot.Query (query) +import Network.Polkadot.Storage.Key (Argument (..)) diff --git a/packages/polkadot/src/Network/Polkadot/Account.hs b/packages/polkadot/src/Network/Polkadot/Account.hs new file mode 100644 index 00000000..48eff351 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Account.hs @@ -0,0 +1,112 @@ +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE TypeFamilies #-} + +-- | +-- Module : Network.Polkadot.Account +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot account types. +-- + +module Network.Polkadot.Account (Ss58Codec(..), IdentifyAccount(..)) where + +import Codec.Scale (decode, encode) +import Control.Monad ((<=<)) +import Data.BigNum (h256) +import Data.Bits (bit, shiftL, shiftR, (.&.), (.|.)) +import Data.ByteArray (cons, convert) +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS (drop, length, pack, take) +import Data.ByteString.Base58 (bitcoinAlphabet, decodeBase58, + encodeBase58) +import Data.Digest.Blake2 (blake2_256, blake2_512) +import Data.Maybe (fromJust) +import Data.Word (Word16) + +import Network.Polkadot.Primitives (MultiSigner (..)) +import qualified Network.Polkadot.Primitives as P (AccountId) + +-- | Some type that is able to be collapsed into an account ID. +-- +-- It is not possible to recreate the original value from the account ID. +class IdentifyAccount a where + -- | The account ID that this can be transformed into. + type AccountId a + + -- | Transform into an account. + into_account :: a -> AccountId a + +instance IdentifyAccount MultiSigner where + type AccountId MultiSigner = P.AccountId + into_account (Ed25519Signer pub) = fromJust (h256 pub) + into_account (EcdsaSigner px pub) = fromJust (h256 $ blake2_256 $ cons px $ convert pub) + into_account Sr25519Signer = error "Sr25519 has no support yet" + +instance Show MultiSigner where + show = show . to_ss58check . into_account + +-- | Key that can be encoded to/from SS58. +-- +-- See +-- for information on the codec. +class Ss58Codec a where + -- | Some if the string is a properly encoded SS58Check address (default prefix). + from_ss58check :: ByteString -> Either String a + from_ss58check = from_ss58check_with_version 42 + + -- | Return the ss58-check string for this key (default prefix). + to_ss58check :: a -> ByteString + to_ss58check = to_ss58check_with_version 42 + + -- | Return the ss58-check string for this key. + to_ss58check_with_version :: Word16 -> a -> ByteString + + -- | Some if the string is a properly encoded SS58Check address (default prefix). + from_ss58check_with_version :: Word16 -> ByteString -> Either String a + +instance Ss58Codec P.AccountId where + from_ss58check_with_version v = decode <=< from_ss58check_with_version' v <=< from_base58 + to_ss58check_with_version v = to_base58 . to_ss58check_with_version' v . encode + +to_base58 :: ByteString -> ByteString +to_base58 = encodeBase58 bitcoinAlphabet + +from_base58 :: ByteString -> Either String ByteString +from_base58 = maybe (Left "Bad encoding") Right . decodeBase58 bitcoinAlphabet + +to_ss58check_with_version' :: Word16 -> ByteString -> ByteString +to_ss58check_with_version' v input = out <> ss58hash out + where + out = encode_version v <> input + +from_ss58check_with_version' :: Word16 -> ByteString -> Either String ByteString +from_ss58check_with_version' v input = versionGuard >> ss58hashGuard + where + checksumLen = 2 + versionLen | v < 64 = 1 + | otherwise = 2 + inputLen = BS.length input - checksumLen - versionLen + input' = BS.take inputLen (BS.drop versionLen input) + versionGuard + | encode_version v == BS.take versionLen input = return () + | otherwise = Left "Bad version" + ss58hashGuard + | ss58hash (BS.take (versionLen + inputLen) input) + == BS.drop (versionLen + inputLen) input = return input' + | otherwise = Left "Bad checksum" + +ss58hash :: ByteString -> ByteString +ss58hash = BS.take 2 . blake2_512 . ("SS58PRE" <>) + +encode_version :: Word16 -> ByteString +encode_version v + | v < 64 = BS.pack [fromIntegral v] + | otherwise = let first = bit 6 .|. ((v `shiftR` 2) .&. 63) + second = (v `shiftR` 8) .|. ((v .&. 3) `shiftL` 6) + in BS.pack (fromIntegral <$> [first, second]) diff --git a/packages/polkadot/src/Network/Polkadot/Call.hs b/packages/polkadot/src/Network/Polkadot/Call.hs new file mode 100644 index 00000000..9817508c --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Call.hs @@ -0,0 +1,52 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} + +-- | +-- Module : Network.Polkadot.Call +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- + +module Network.Polkadot.Call where + +import Codec.Scale (Decode, Encode, Generic, decode) +import Control.Monad.Fail (MonadFail) +import Data.List (findIndex) +import Data.Text (Text) +import Data.Word (Word8) +import qualified GHC.Generics as GHC (Generic) +import Network.JsonRpc.TinyClient (JsonRpc) + +import Network.Polkadot.Metadata (MetadataVersioned (V13), + metadata) +import Network.Polkadot.Metadata.V13 (moduleCalls, moduleName, + modules) +import Network.Polkadot.Metadata.V9 (functionName) +import Network.Polkadot.Rpc.State (getMetadata) + +-- | Call function of module using standard substrate extrionsic. +data Call a = Call !Word8 !Word8 !a + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +-- | Create 'Call' type from text-encoded module and function. +new_call :: (Encode a, Decode a, JsonRpc m, MonadFail m) + => Text + -- ^ Module name. + -> Text + -- ^ Function name. + -> a + -- ^ Tuple of arguments. + -> m (Call a) +new_call modName funName args = do + Right (V13 meta) <- (fmap metadata . decode) <$> getMetadata + case findIndex ((modName ==) . moduleName) (modules meta) of + Nothing -> fail $ "module " <> show modName <> " not found" + Just modIx -> + case findIndex ((funName ==) . functionName) =<< moduleCalls (modules meta !! modIx) of + Nothing -> fail $ "function " <> show funName <> " not found" + Just funIx -> return $ Call (fromIntegral modIx) (fromIntegral funIx) args diff --git a/packages/polkadot/src/Network/Polkadot/Crypto.hs b/packages/polkadot/src/Network/Polkadot/Crypto.hs new file mode 100644 index 00000000..c5370446 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Crypto.hs @@ -0,0 +1,162 @@ +{-# LANGUAGE TypeFamilies #-} + +-- | +-- Module : Network.Polkadot.Crypto +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot signing types and methods. +-- + +module Network.Polkadot.Crypto + ( Pair(..) + , Verify(..) + , MultiPair(..) + , Ed25519 + , Ecdsa + ) where + +import qualified Crypto.Ecdsa.Signature as Ecdsa (pack, sign) +import Crypto.Ecdsa.Utils as Ecdsa (derivePubKey, + exportPubKeyCompress, + importKey) +import Crypto.Error (CryptoFailable (..)) +import qualified Crypto.PubKey.ECC.ECDSA as Ecdsa (PrivateKey (..), + PublicKey (..)) +import qualified Crypto.PubKey.ECC.Generate as Ecdsa (generate) +import Crypto.PubKey.ECC.Types (CurveName (SEC_p256k1), + getCurveByName) +import qualified Crypto.PubKey.Ed25519 as Ed25519 (PublicKey, SecretKey, + generateSecretKey, + secretKey, sign, + toPublic) +import Data.BigNum (H256, H512, h256, h512) +import Data.ByteArray (ByteArrayAccess, uncons) +import qualified Data.ByteArray as BA (length) +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS (last, take) +import Data.Maybe (fromJust) +import Data.Text (Text) +import Data.Word (Word8) + +import Network.Polkadot.Account (IdentifyAccount (..)) +import qualified Network.Polkadot.Primitives as P (MultiAddress (..), + MultiSignature (..), + MultiSigner (..)) + +-- | Class suitable for typical cryptographic PKI key pair type. +class Pair a where + -- | The type which is used to encode a public key. + type PublicKey a + -- | The type used to represent a signature. Can be created from a key pair and a message + -- and verified with the message and a public key. + type Signature a + -- | Generate new secure (random) key pair. + generate :: IO a + -- | Generate new key pair from the provided `seed`. + from_seed :: ByteArrayAccess ba => ba -> Either String a + -- | Generate key pair from given recovery phrase and password. + from_phrase :: Text -> Maybe Text -> Either String a + -- | Get a public key. + public :: a -> PublicKey a + -- | Sign a message. + sign :: ByteArrayAccess ba => a -> ba -> Signature a + +-- | Means of signature verification. +class Verify a where + -- | Verify a message. + verify :: (IdentifyAccount s, ByteArrayAccess ba) + => a + -- ^ Message signature. + -> ba + -- ^ Message content. + -> s + -- ^ Type of the signer. + -> Bool + -- ^ Returns `true` if signature is valid for the value. + +-- | Multiple cryptographic type support. +class Pair a => MultiPair a where + -- | Universal short representation of signer account. + type MultiAddress a + -- | Universal signer account identifier. + type MultiSigner a + -- | Universal signature representation. + type MultiSignature a + -- | Derive universal account address. + multi_address :: a -> MultiAddress a + -- | Derive universal signer account identifier. + multi_signer :: a -> MultiSigner a + -- | Sign message and derive universal signature. + multi_sign :: ByteArrayAccess ba => a -> ba -> MultiSignature a + +-- | Ed25519 cryptographic pair. +data Ed25519 = Ed25519 !Ed25519.PublicKey !Ed25519.SecretKey + deriving Eq + +instance Show Ed25519 where + show = ("Ed25519 " ++) . show . public + +instance Pair Ed25519 where + type PublicKey Ed25519 = H256 + type Signature Ed25519 = H512 + generate = do + sec <- Ed25519.generateSecretKey + return $ Ed25519 (Ed25519.toPublic sec) sec + from_seed seed = case Ed25519.secretKey seed of + CryptoPassed sec -> Right $ Ed25519 (Ed25519.toPublic sec) sec + CryptoFailed e -> Left (show e) + from_phrase = undefined + public (Ed25519 pub _) = fromJust $ h256 pub + sign (Ed25519 pub sec) input = ed25519_sign sec pub input + +-- | ECDSA cryptographic pair. +data Ecdsa = Ecdsa !Ecdsa.PublicKey !Ecdsa.PrivateKey + deriving Eq + +instance Show Ecdsa where + show = ("Ecdsa " ++) . show . public + +instance Pair Ecdsa where + type PublicKey Ecdsa = (Word8, H256) + type Signature Ecdsa = (H512, Word8) + generate = uncurry Ecdsa <$> Ecdsa.generate (getCurveByName SEC_p256k1) + from_seed seed + | BA.length seed == 32 = let sec = Ecdsa.importKey seed + in Right $ Ecdsa (Ecdsa.derivePubKey sec) sec + | otherwise = Left "Seed should be 32 byte length" + from_phrase = undefined + public (Ecdsa pub _) = pack $ uncons $ Ecdsa.exportPubKeyCompress pub + where + pack :: Maybe (Word8, ByteString) -> (Word8, H256) + pack (Just (px, key)) = (px, fromJust (h256 key)) + pack _ = error "impossible branch" + sign (Ecdsa _ sec) input = ecdsa_sign sec input + +ed25519_sign :: ByteArrayAccess a => Ed25519.SecretKey -> Ed25519.PublicKey -> a -> H512 +ed25519_sign sec pub = fromJust . h512 . Ed25519.sign sec pub + +ecdsa_sign :: ByteArrayAccess a => Ecdsa.PrivateKey -> a -> (H512, Word8) +ecdsa_sign sec input = (fromJust $ h512 $ BS.take 64 rsv, BS.last rsv) + where + rsv = Ecdsa.pack (Ecdsa.sign sec input) + +instance MultiPair Ed25519 where + type MultiSigner Ed25519 = P.MultiSigner + type MultiAddress Ed25519 = P.MultiAddress + type MultiSignature Ed25519 = P.MultiSignature + multi_signer = P.Ed25519Signer . public + multi_address = P.MaId . into_account . multi_signer + multi_sign = (P.Ed25519Signature .) . sign + +instance MultiPair Ecdsa where + type MultiSigner Ecdsa = P.MultiSigner + type MultiAddress Ecdsa = P.MultiAddress + type MultiSignature Ecdsa = P.MultiSignature + multi_signer = uncurry P.EcdsaSigner . public + multi_address = P.MaId . into_account . multi_signer + multi_sign = (uncurry P.EcdsaSignature .) . sign diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic.hs new file mode 100644 index 00000000..a6cf4e89 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic.hs @@ -0,0 +1,129 @@ +{-# LANGUAGE FlexibleContexts #-} + +-- | +-- Module : Network.Polkadot.Extrinsic +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Extrinsic is a piece of data from external world. +-- + +module Network.Polkadot.Extrinsic + ( Extrinsic + , SignedExtra + , sign_and_send + , mortal_max + , new_extra' + , new_extra + ) where + +import Codec.Scale (Compact (..), + Encode, + encode) +import Data.ByteArray.HexString (HexString) +import Data.Maybe (fromJust) +import Data.Text.Encoding (decodeUtf8) +import Network.JsonRpc.TinyClient (JsonRpc) + +import Network.Polkadot.Account (AccountId, + IdentifyAccount (..), + Ss58Codec (to_ss58check)) +import Network.Polkadot.Crypto (MultiPair (..)) +import Network.Polkadot.Extrinsic.Era (Era (..)) +import Network.Polkadot.Extrinsic.SignedExtension.System +import Network.Polkadot.Extrinsic.SignedExtension.TransactionPayment +import Network.Polkadot.Extrinsic.Unchecked (UncheckedExtrinsic, + sign_extrinsic) +import Network.Polkadot.Primitives (Balance, + Index) +import qualified Network.Polkadot.Primitives as P (MultiAddress, + MultiSignature) +import Network.Polkadot.Rpc.Account (nextIndex) +import Network.Polkadot.Rpc.Author (submitExtrinsic) +import Network.Polkadot.Rpc.Chain (getHeader) +import Network.Polkadot.Rpc.Types (headerNumber, + unBlockNumber) + +-- | Default Polkadot compatible extrinsic type. +type Extrinsic a = UncheckedExtrinsic a P.MultiAddress P.MultiSignature SignedExtra + +-- | Default Polkadot signed extra. +type SignedExtra = + ( CheckSpecVersion + , CheckTxVersion + , CheckGenesis + , CheckEra + , CheckNonce + , CheckWeight + , ChargeTransactionPayment + ) + +new_extra :: (Ss58Codec a, JsonRpc m) + => a + -- ^ Transaction sender address. + -> Balance + -- ^ Transaction tips, or set zero for no tips. + -> m SignedExtra + -- ^ Returns Polkadot transaction extra. +new_extra account_id tip = do + nonce <- fromIntegral <$> nextIndex ss58account + era <- mortal_max + return $ new_extra' era nonce tip + where + ss58account = decodeUtf8 $ to_ss58check account_id + +-- | Create signed extra from general data. +new_extra' :: Era + -- ^ Transaction mortality. + -> Index + -- ^ Transaction nonce value. + -> Balance + -- ^ Transaction tips, or set zero for no tips. + -> SignedExtra + -- ^ Returns Polkadot transaction extra. +new_extra' era nonce tip = + ( CheckSpecVersion + , CheckTxVersion + , CheckGenesis + , CheckEra era + , CheckNonce (Compact nonce) + , CheckWeight + , ChargeTransactionPayment (Compact tip) + ) + +-- | Create a mortal 'Era' with biggest lifetime period. +-- +-- Note: The assumption is runtime has `BlockHashCount` = 2400. This is common +-- for Polkadot runtimes. +mortal_max :: JsonRpc m => m Era +mortal_max = do + current <- (unBlockNumber . headerNumber . fromJust) <$> getHeader Nothing + return $ MortalEra 2048 $ fromIntegral (current - 1) + +-- | Sign extrinsic and send it using node RPC call. +sign_and_send :: ( MultiPair pair + , IdentifyAccount (MultiSigner pair) + , Ss58Codec (AccountId (MultiSigner pair)) + , Encode (MultiAddress pair) + , Encode (MultiSignature pair) + , Encode call + , JsonRpc m + ) + => pair + -- ^ Sender account pair. + -> call + -- ^ Runtime function to call. + -> Balance + -- ^ Tips for speedup transaction (set zero for no boost). + -> m HexString + -- ^ Transaction hash. +sign_and_send pair call tip = do + extra <- new_extra account_id tip + xt <- sign_extrinsic pair call extra + submitExtrinsic (encode xt) + where + account_id = into_account (multi_signer pair) diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/Era.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/Era.hs new file mode 100644 index 00000000..34985548 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/Era.hs @@ -0,0 +1,92 @@ +-- | +-- Module : Network.Polkadot.Extrinsic.Era +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- An era to describe the longevity of a transaction. +-- + +module Network.Polkadot.Extrinsic.Era + ( Era(..) + , new_mortal_compact + , birth + , death + ) where + +import Codec.Scale.Class (Decode (..), Encode (..)) +import Codec.Scale.Core () +import Data.Bits (shiftL, shiftR, (.|.)) +import Data.Word (Word16, Word32, Word8, byteSwap16) + +-- | The era for an extrinsic, indicating either a mortal or immortal extrinsic. +data Era + = ImmortalEra + -- ^ The ImmortalEra for an extrinsic. + | MortalEra !Word32 !Word32 + -- ^ The MortalEra for an extrinsic, indicating period and phase. + -- + -- Period and phase are encoded: + -- - The period of validity from the block hash found in the signing material. + -- - The phase in the period that this transaction's lifetime begins (and, importantly, + -- implies which block hash is included in the signature material). If the `period` is + -- greater than 1 << 12, then it will be a factor of the times greater than 1 << 12 that + -- `period` is. + deriving (Eq, Ord, Show) + +instance Decode Era where + get = do + first <- get + case first :: Word8 of + 0 -> return ImmortalEra + _ -> decodeMortal first <$> get + where + decodeMortal :: Word8 -> Word8 -> Era + decodeMortal first second = + let first' = fromIntegral first + second' = fromIntegral second + in new_mortal_compact (first' + second' `shiftL` 8) + +instance Encode Era where + put ImmortalEra = put (0 :: Word8) + put (MortalEra period' phase') = put encoded + where + encoded :: Word16 + encoded = first .|. second + first = (1 `max` (trailing_zeros period - 1)) `min` 15 + second = (phase `div` quantizeFactor) `shiftL` 4 + quantizeFactor = max (period `shiftR` 12) 1 + period = fromIntegral period' + phase = fromIntegral phase' + +-- | Create a mortal 'Era' type from two bytes of data. +new_mortal_compact :: Word16 -> Era +new_mortal_compact raw = MortalEra period phase + where + era = fromIntegral $ byteSwap16 raw + + period = 2 `shiftL` (fromIntegral (era `rem` 16)) + quantizeFactor = max (period `shiftR` 12) 1 + phase = (era `shiftR` 4) * quantizeFactor + +trailing_zeros :: Integral a => a -> a +trailing_zeros = foldl zero 0 . takeWhile (> 0) . iterate (`div` 2) + where + zero a x + | x `mod` 2 == 0 = a + 1 + | otherwise = a + +-- | Get the block number of the start of the era whose properties this object +-- describes that `current` belongs to. +birth :: (Integral a, Integral b) => Era -> a -> b +birth ImmortalEra _ = 0 +birth (MortalEra period phase) current = fromIntegral $ + (max (fromIntegral current) phase - phase) `div` period * period + phase + +-- | Get the block number of the first block at which the era has ended. +death :: (Integral a, Integral b, Bounded b) => Era -> a -> b +death ImmortalEra _ = maxBound +death e@(MortalEra period _) current = fromIntegral $ birth e current + period diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/Payload.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/Payload.hs new file mode 100644 index 00000000..7df1d13a --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/Payload.hs @@ -0,0 +1,41 @@ +-- | +-- Module : Network.Polkadot.Extrinsic.Payload +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Extrinsic payload and payload signing methods. +-- + +module Network.Polkadot.Extrinsic.Payload where + +import Codec.Scale (encode) +import Codec.Scale.Class (Encode (..)) +import qualified Data.ByteString as BS (length) +import Data.Digest.Blake2 (blake2_256) +import Network.JsonRpc.TinyClient (JsonRpc) + +import Network.Polkadot.Crypto (MultiPair (MultiSignature, multi_sign)) +import Network.Polkadot.Extrinsic.SignedExtension (SignedExtension (..)) + +-- | A payload that has been signed for an unchecked extrinsics. +-- +-- Note that the payload that we sign to produce unchecked extrinsic signature +-- is going to be different than the `Payload` - so the thing the extrinsic +-- actually contains. +type Payload call extra = (call, extra) + +-- | Sign extrinsic's payload by multi-pair. +sign_payload :: (MultiPair a, Encode c, SignedExtension e, JsonRpc m) + => a + -> Payload c e + -> m (MultiSignature a) +sign_payload pair (call, extra) = do + additional <- additional_signed extra + let encoded = encode (call, extra, additional) + payload | BS.length encoded > 256 = blake2_256 encoded + | otherwise = encoded + return $ multi_sign pair payload diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension.hs new file mode 100644 index 00000000..e6fcef7a --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension.hs @@ -0,0 +1,87 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE TypeFamilies #-} + +-- | +-- Module : Network.Polkadot.Extrinsic.SignedExtension +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Additional data that could be attached to the transaction. +-- + +module Network.Polkadot.Extrinsic.SignedExtension where + + +import Codec.Scale (Decode, Encode) +import Network.JsonRpc.TinyClient (JsonRpc) + +-- | Means by which a transaction may be extended. This type embodies both the data and the logic +-- that should be additionally associated with the transaction. It should be plain old data. +class (Encode a, Decode a, Encode (AdditionalSigned a), Decode (AdditionalSigned a)) + => SignedExtension a where + -- | Any additional data that will go into the signed payload. This may be created dynamically + -- from the transaction using the `additional_signed` function. + type AdditionalSigned a + + -- | Construct any additional data that should be in the signed payload of the transaction. Can + -- also perform any pre-signature-verification checks and return an error if needed. + additional_signed :: JsonRpc m => a -> m (AdditionalSigned a) + +instance SignedExtension () where + type AdditionalSigned () = () + additional_signed _ = return () + +instance (SignedExtension a, SignedExtension b) => SignedExtension (a, b) where + type AdditionalSigned (a, b) = (AdditionalSigned a, AdditionalSigned b) + additional_signed (a, b) = (,) + <$> additional_signed a + <*> additional_signed b + +instance (SignedExtension a, SignedExtension b, SignedExtension c) => SignedExtension (a, b, c) where + type AdditionalSigned (a, b, c) = (AdditionalSigned a, AdditionalSigned b, AdditionalSigned c) + additional_signed (a, b, c) = (,,) + <$> additional_signed a + <*> additional_signed b + <*> additional_signed c + +instance (SignedExtension a, SignedExtension b, SignedExtension c, SignedExtension d) => SignedExtension (a, b, c, d) where + type AdditionalSigned (a, b, c, d) = (AdditionalSigned a, AdditionalSigned b, AdditionalSigned c, AdditionalSigned d) + additional_signed (a, b, c, d) = (,,,) + <$> additional_signed a + <*> additional_signed b + <*> additional_signed c + <*> additional_signed d + +instance (SignedExtension a, SignedExtension b, SignedExtension c, SignedExtension d, SignedExtension e) => SignedExtension (a, b, c, d, e) where + type AdditionalSigned (a, b, c, d, e) = (AdditionalSigned a, AdditionalSigned b, AdditionalSigned c, AdditionalSigned d, AdditionalSigned e) + additional_signed (a, b, c, d, e) = (,,,,) + <$> additional_signed a + <*> additional_signed b + <*> additional_signed c + <*> additional_signed d + <*> additional_signed e + +instance (SignedExtension a, SignedExtension b, SignedExtension c, SignedExtension d, SignedExtension e, SignedExtension f) => SignedExtension (a, b, c, d, e, f) where + type AdditionalSigned (a, b, c, d, e, f) = (AdditionalSigned a, AdditionalSigned b, AdditionalSigned c, AdditionalSigned d, AdditionalSigned e, AdditionalSigned f) + additional_signed (a, b, c, d, e, f) = (,,,,,) + <$> additional_signed a + <*> additional_signed b + <*> additional_signed c + <*> additional_signed d + <*> additional_signed e + <*> additional_signed f + +instance (SignedExtension a, SignedExtension b, SignedExtension c, SignedExtension d, SignedExtension e, SignedExtension f, SignedExtension g) => SignedExtension (a, b, c, d, e, f, g) where + type AdditionalSigned (a, b, c, d, e, f, g) = (AdditionalSigned a, AdditionalSigned b, AdditionalSigned c, AdditionalSigned d, AdditionalSigned e, AdditionalSigned f, AdditionalSigned g) + additional_signed (a, b, c, d, e, f, g) = (,,,,,,) + <$> additional_signed a + <*> additional_signed b + <*> additional_signed c + <*> additional_signed d + <*> additional_signed e + <*> additional_signed f + <*> additional_signed g diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/System.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/System.hs new file mode 100644 index 00000000..4a47ab37 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/System.hs @@ -0,0 +1,82 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TypeFamilies #-} + +-- | +-- Module : Network.Polkadot.Extrinsic.SignedExtension.System +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- A frame system signed extensions. +-- + +module Network.Polkadot.Extrinsic.SignedExtension.System where + +import Codec.Scale (Compact, Decode, + Encode, Generic) +import Data.BigNum (h256) +import Data.Maybe (fromJust) +import Data.Word (Word32) +import qualified GHC.Generics as GHC (Generic) + +import Network.Polkadot.Extrinsic.Era (Era, birth) +import Network.Polkadot.Extrinsic.SignedExtension (SignedExtension (..)) +import Network.Polkadot.Primitives (Hash, Index) +import Network.Polkadot.Rpc.Chain (getBlockHash, + getHeader) +import Network.Polkadot.Rpc.State (getRuntimeVersion) +import Network.Polkadot.Rpc.Types (RuntimeVersion (..), + headerNumber, + unBlockNumber) + +-- | Ensure the runtime version registered in the transaction is the same as at present. +data CheckSpecVersion = CheckSpecVersion + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckSpecVersion where + type AdditionalSigned CheckSpecVersion = Word32 + additional_signed _ = runtimeSpecVersion <$> getRuntimeVersion Nothing + +data CheckTxVersion = CheckTxVersion + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckTxVersion where + type AdditionalSigned CheckTxVersion = Word32 + additional_signed _ = runtimeTransactionVersion <$> getRuntimeVersion Nothing + +data CheckGenesis = CheckGenesis + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckGenesis where + type AdditionalSigned CheckGenesis = Hash + additional_signed _ = do + -- chain must have genesis block, fromJust is safe + (fromJust . (h256 =<<)) <$> getBlockHash (Just 0) + +newtype CheckEra = CheckEra Era + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckEra where + type AdditionalSigned CheckEra = Hash + additional_signed (CheckEra era) = do + -- chain must have top header, fromJust is safe here + current <- (unBlockNumber . headerNumber . fromJust) <$> getHeader Nothing + (fromJust . (h256 =<<)) <$> getBlockHash (Just $ birth era current) + +newtype CheckNonce = CheckNonce (Compact Index) + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckNonce where + type AdditionalSigned CheckNonce = () + additional_signed _ = return () + +data CheckWeight = CheckWeight + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension CheckWeight where + type AdditionalSigned CheckWeight = () + additional_signed _ = return () diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/TransactionPayment.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/TransactionPayment.hs new file mode 100644 index 00000000..a77f95fa --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/SignedExtension/TransactionPayment.hs @@ -0,0 +1,33 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TypeFamilies #-} + +-- | +-- Module : Network.Polkadot.Extrinsic.SignedExtension.TransactionPayment +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- A pallet-transaction-payment signed extension. +-- + +module Network.Polkadot.Extrinsic.SignedExtension.TransactionPayment where + +import Codec.Scale (Compact, Decode, + Encode, Generic) +import qualified GHC.Generics as GHC (Generic) + +import Network.Polkadot.Extrinsic.SignedExtension (SignedExtension (..)) +import Network.Polkadot.Primitives (Balance) + +-- | Require the transactor pay for themselves and maybe include a tip to +-- gain additional priority in the queue. +newtype ChargeTransactionPayment = ChargeTransactionPayment (Compact Balance) + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +instance SignedExtension ChargeTransactionPayment where + type AdditionalSigned ChargeTransactionPayment = () + additional_signed _ = return () diff --git a/packages/polkadot/src/Network/Polkadot/Extrinsic/Unchecked.hs b/packages/polkadot/src/Network/Polkadot/Extrinsic/Unchecked.hs new file mode 100644 index 00000000..6628596a --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Extrinsic/Unchecked.hs @@ -0,0 +1,100 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Network.Polkadot.Extrinsic.Unchecked +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Extrinsic is a piece of data from external world. +-- + +module Network.Polkadot.Extrinsic.Unchecked + ( UncheckedExtrinsic (..) + , new_unsigned + , new_signed + , sign_extrinsic + ) where + +import Codec.Scale (encode) +import Codec.Scale.Class (Decode (..), + Encode (..)) +import Control.Arrow ((&&&)) +import Control.Monad (when) +import Data.Bits (clearBit, setBit, + testBit) +import Data.ByteArray.HexString (HexString) +import Data.ByteString (ByteString) +import Data.Word (Word8) +import Network.JsonRpc.TinyClient (JsonRpc) + +import Network.Polkadot.Crypto (MultiPair (..)) +import Network.Polkadot.Extrinsic.Payload (sign_payload) +import Network.Polkadot.Extrinsic.SignedExtension (SignedExtension) + +-- | Current version of the 'UncheckedExtrinsic' format. +extrinsic_version :: Word8 +extrinsic_version = 4 + +-- | A extrinsic right from the external world. This is unchecked and so +-- can contain a signature. +data UncheckedExtrinsic c a s e + = UncheckedExtrinsic + { extrinsicSignature :: !(Maybe (a, s, e)) + -- ^ The signature, address, number of extrinsics have come before from + -- the same signer and an era describing the longevity of this transaction, + -- if this is a signed extrinsic. + , extrinsicFunction :: !c + -- ^ The function that should be called. + } + +instance Encode c => Show (UncheckedExtrinsic c a b c) where + show (UncheckedExtrinsic _ call) = "UncheckedExtrinsic " ++ show encoded + where + encoded :: HexString + encoded = encode call + +instance (Encode c, Encode a, Encode s, Encode e) => Encode (UncheckedExtrinsic c a s e) where + put xt = put encoded + where + encoded :: ByteString + encoded = case xt of + UncheckedExtrinsic Nothing call + -> encode extrinsic_version <> encode call + UncheckedExtrinsic (Just s) call + -> encode (setBit extrinsic_version 7) <> encode s <> encode call + +instance (Decode c, Decode a, Decode s, Decode e) => Decode (UncheckedExtrinsic c a s e) where + get = do + (_v :: [()]) <- get + (signed, version) <- (flip testBit 7 &&& flip clearBit 7) <$> get + when (version /= extrinsic_version) $ fail "bad version" + UncheckedExtrinsic + <$> (if signed then fmap Just get else return Nothing) + <*> get + +-- | New instance of a signed extrinsic aka "transaction". +new_signed :: c -> a -> s -> e -> UncheckedExtrinsic c a s e +new_signed call address sig extra = UncheckedExtrinsic (Just (address, sig, extra)) call + +-- | New instance of an unsigned extrinsic aka "inherent". +new_unsigned :: f -> UncheckedExtrinsic f a b c +new_unsigned = UncheckedExtrinsic Nothing + +-- | Create and sign extrinsic by account. +sign_extrinsic :: (MultiPair a, Encode c, SignedExtension e, JsonRpc m) + => a + -- ^ Account to sign extrinsic. + -> c + -- ^ Function to call on runtime. + -> e + -- ^ Additional data to sign like nonce, blockhash, etc. + -> m (UncheckedExtrinsic c (MultiAddress a) (MultiSignature a) e) +sign_extrinsic a c e = do + sig <- sign_payload a (c, e) + return $ new_signed c (multi_address a) sig e diff --git a/packages/polkadot/src/Network/Polkadot/Metadata.hs b/packages/polkadot/src/Network/Polkadot/Metadata.hs new file mode 100644 index 00000000..32fa5b3f --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata.hs @@ -0,0 +1,119 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Node runtime type information. +-- + +module Network.Polkadot.Metadata where + +import Codec.Scale (Decode, Encode, + Generic) +import Data.Aeson (Options (constructorTagModifier, sumEncoding), + SumEncoding (ObjectWithSingleField), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.Char (toLower) +import Data.Set (Set) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import Network.Polkadot.Metadata.MagicNumber (MagicNumber (..)) +import Network.Polkadot.Metadata.Type (Type) +import Network.Polkadot.Metadata.Type.Discovery (runDiscovery) +import qualified Network.Polkadot.Metadata.V10 as V10 (Metadata (Metadata), + moduleName) +import qualified Network.Polkadot.Metadata.V11 as V11 (Metadata (Metadata), + moduleName) +import qualified Network.Polkadot.Metadata.V12 as V12 (Metadata (Metadata), + moduleName) +import qualified Network.Polkadot.Metadata.V13 as V13 (Metadata (Metadata), + moduleName) +import qualified Network.Polkadot.Metadata.V9 as V9 (Metadata (Metadata), + moduleName) + +-- | All supported metadata versions as enum. +-- +-- It could have troubles of decoding for metadata V9 because of hack: +-- https://github.com/polkadot-js/api/commit/a9211690be6b68ad6c6dad7852f1665cadcfa5b2 +data MetadataVersioned + = V0 | V1 | V2 | V3 | V4 | V5 | V6 | V7 | V8 -- Not defined + | V9 V9.Metadata + | V10 V10.Metadata + | V11 V11.Metadata + | V12 V12.Metadata + | V13 V13.Metadata + deriving (Eq, Show, Generic, GHC.Generic, Decode, Encode) + +$(deriveJSON (defaultOptions + { constructorTagModifier = over _head toLower, sumEncoding = ObjectWithSingleField }) ''MetadataVersioned) + +-- | The versioned runtime metadata as a decoded structure. +data Metadata = Metadata + { magicNumber :: MagicNumber + , metadata :: MetadataVersioned + } deriving (Eq, Show, Generic, GHC.Generic, Decode, Encode) + +$(deriveJSON defaultOptions ''Metadata) + +isV9 :: Metadata -> Bool +isV9 (Metadata _ (V9 _)) = True +isV9 _ = False + +isV10 :: Metadata -> Bool +isV10 (Metadata _ (V10 _)) = True +isV10 _ = False + +isV11 :: Metadata -> Bool +isV11 (Metadata _ (V11 _)) = True +isV11 _ = False + +isV12 :: Metadata -> Bool +isV12 (Metadata _ (V12 _)) = True +isV12 _ = False + +isV13 :: Metadata -> Bool +isV13 (Metadata _ (V13 _)) = True +isV13 _ = False + +isLatest :: Metadata -> Bool +{-# INLINE isLatest #-} +isLatest = isV13 + +toLatest :: Metadata -> V13.Metadata +toLatest (Metadata _ (V13 m)) = m +toLatest _ = undefined + +metadataTypes :: Metadata -> (Metadata, Set Type) +metadataTypes (Metadata _ (V9 (V9.Metadata modules))) = + let (modules', types) = runDiscovery V9.moduleName modules + in (Metadata MagicNumber (V9 (V9.Metadata modules')), types) + +metadataTypes (Metadata _ (V10 (V10.Metadata modules))) = + let (modules', types) = runDiscovery V10.moduleName modules + in (Metadata MagicNumber (V10 (V10.Metadata modules')), types) + +{- XXX: OOM compilation on my laptop +metadataTypes (Metadata _ (V11 (V11.Metadata modules extrinsics))) = + let (modules', types) = runDiscovery V11.moduleName modules + in (Metadata MagicNumber (V11 (V11.Metadata modules' extrinsics)), types) +-} + +metadataTypes (Metadata _ (V12 (V12.Metadata modules extrinsics))) = + let (modules', types) = runDiscovery V12.moduleName modules + in (Metadata MagicNumber (V12 (V12.Metadata modules' extrinsics)), types) + +metadataTypes (Metadata _ (V13 (V13.Metadata modules extrinsics))) = + let (modules', types) = runDiscovery V13.moduleName modules + in (Metadata MagicNumber (V13 (V13.Metadata modules' extrinsics)), types) + +metadataTypes m = (m, mempty) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/MagicNumber.hs b/packages/polkadot/src/Network/Polkadot/Metadata/MagicNumber.hs new file mode 100644 index 00000000..4c62b44e --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/MagicNumber.hs @@ -0,0 +1,50 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} + +-- | +-- Module : Network.Polkadot.Metadata.MagicNumber +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata V9 data type. +-- + +module Network.Polkadot.Metadata.MagicNumber where + +import Codec.Scale.Class (Decode (..), Encode (..)) +import Codec.Scale.Core () +import Control.Monad (when) +import Data.Aeson (FromJSON (..), ToJSON (..), Value (Number)) +import Data.Word (Word32) + +-- | `meta`, reversed for Little Endian encoding +magic_number :: Word32 +magic_number = 0x6174656d + +-- | 32-bit prefix magic sentence. +data MagicNumber = MagicNumber + deriving (Eq, Show) + +instance Decode MagicNumber where + get = do + n <- get + when (n /= magic_number) $ + fail "Bad magic number" + return MagicNumber + +instance Encode MagicNumber where + put _ = put magic_number + +instance FromJSON MagicNumber where + parseJSON (Number n) = do + when (n /= fromIntegral magic_number) $ + fail "Bad magic number" + return MagicNumber + parseJSON _ = fail "Magic number should be a number" + +instance ToJSON MagicNumber where + toJSON _ = toJSON magic_number diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/Type.hs b/packages/polkadot/src/Network/Polkadot/Metadata/Type.hs new file mode 100644 index 00000000..d7409885 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/Type.hs @@ -0,0 +1,40 @@ +-- | +-- Module : Network.Polkadot.Metadata.Type +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Runtime metadata type and encoding. +-- + +module Network.Polkadot.Metadata.Type where + +import Codec.Scale.Class (Decode (..), + Encode (..)) +import Codec.Scale.Core () +import Data.Aeson (FromJSON (..), + ToJSON (..), + Value (String)) +import Data.Text (Text) + +import Network.Polkadot.Metadata.Type.Parser (sanitizeM) + +-- | Sanitized name for metadata type. +newtype Type = Type { unType :: Text } + deriving (Eq, Ord, Show) + +instance FromJSON Type where + parseJSON (String s) = return (Type s) + parseJSON _ = fail "Type should be a string" + +instance ToJSON Type where + toJSON = toJSON . unType + +instance Decode Type where + get = fmap Type (sanitizeM =<< get) + +instance Encode Type where + put = put . unType diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/Type/Ast.hs b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Ast.hs new file mode 100644 index 00000000..77e17eda --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Ast.hs @@ -0,0 +1,39 @@ +-- | +-- Module : Network.Polkadot.Metadata.Type.Ast +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Runtime metadata type AST. +-- + +module Network.Polkadot.Metadata.Type.Ast where + +import Data.Text (Text) + +-- | Qualified type parameter, e.g., as SomeTrait>::SomeType. +type QSelf = (TypeAst, TypeAst) + +-- | A segment of a path: an identifier and a set of argument types. +type PathSegment = (Text, Maybe [TypeAst]) + +-- | Simple Rust type AST is used for Metadata type representation. +data TypeAst + = Slice !TypeAst + -- ^ A variable-length slice ([T]). + | Tuple ![TypeAst] + -- ^ A tuple ((A, B, C, D,...)). + | Array !TypeAst !Int + -- ^ A fixed length array ([T; n]). + | Path { qself :: !(Maybe QSelf) + -- ^ Two types of as Trait>. + , segments :: ![PathSegment] + -- ^ A segment of a path: an identifier and a set of types. + } + -- ^ A "Path" is essentially Rust's notion of a name. It's represented as a sequence of identifiers, + -- along with a bunch of supporting information. A path (module::module::...::Type), optionally "qualified", + -- e.g., as SomeTrait>::SomeType. + deriving (Eq, Ord, Read, Show) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/Type/Discovery.hs b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Discovery.hs new file mode 100644 index 00000000..c1deba04 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Discovery.hs @@ -0,0 +1,138 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeInType #-} +{-# LANGUAGE TypeOperators #-} +{-# LANGUAGE UndecidableInstances #-} + +-- | +-- Module : Network.Polkadot.Metadata.Type.Discovery +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Runtime type discovery for generic metadata structures. +-- + +module Network.Polkadot.Metadata.Type.Discovery + ( DiscoveryContext + , Discovery(..) + , runDiscovery + , prefix + , types + ) where + +import Control.Monad.State.Class (MonadState (..)) +import Control.Monad.State.Strict (runState) +import Data.ByteArray.HexString (HexString) +import Data.Set (Set, insert) +import Data.Text (Text) +import Data.Word (Word8) +import Generics.SOP +import Lens.Micro.Extras (view) +import Lens.Micro.Mtl (use, (%=), (.=)) +import Lens.Micro.TH (makeLenses) + +import Network.Polkadot.Metadata.Type (Type (..)) + +-- | Contains information about types and current context. +data DiscoveryContext = DiscoveryContext + { _prefix :: !Text + , _types :: !(Set Type) + } deriving (Eq, Show) + +instance Semigroup DiscoveryContext where + (DiscoveryContext p a) <> (DiscoveryContext _ b) = DiscoveryContext p (a <> b) + +instance Monoid DiscoveryContext where + mempty = DiscoveryContext mempty mempty + +makeLenses ''DiscoveryContext + +-- | Collects information about runtime types. +class Discovery a where + -- | Discover metadata structure for type information. + discovery :: MonadState DiscoveryContext m + => a + -- ^ Input data structure that contains type information. + -> m a + -- ^ Returns the same structure wrapped with registry state monad. + +-- | Skip 'Word8' when found. +instance {-# OVERLAPPING #-} Discovery Word8 where + discovery = return + +-- | Skip 'HexString' when found. +instance {-# OVERLAPPING #-} Discovery HexString where + discovery = return + +-- | Skip 'Text' when found. +instance {-# OVERLAPPING #-} Discovery Text where + discovery = return + +-- | Register 'Type' when found. +instance {-# OVERLAPPING #-} Discovery Type where + discovery t = update . maybe t Type . flip typeOverlap t =<< use prefix + where + update x = types %= insert x >> return x + +-- | Type overlapping hacks +typeOverlap :: Text + -- ^ Module name + -> Type + -- ^ Module type + -> Maybe Text + -- ^ New type name +typeOverlap "Society" (Type "Vote") = Just "SocietyVote" +typeOverlap "Treasury" (Type "Proposal") = Just "TreasuryProposal" +typeOverlap "Assets" (Type "Balance") = Just "TAssetBalance" +typeOverlap "Assets" (Type "Compact") = Just "Compact" +typeOverlap "Assets" (Type "Approval") = Just "AssetApproval" +typeOverlap "Assets" (Type "ApprovalKey") = Just "AssetApprovalKey" +typeOverlap "Assets" (Type "DestroyWitness") = Just "AssetDestroyWitness" +typeOverlap "Identity" (Type "Judgement") = Just "IdentityJudgement" +typeOverlap "ElectionProviderMultiPhase" (Type "Phase") = Just "ElectionPhase" +typeOverlap a (Type "Judgement") = Just (a <> "Judgement") +typeOverlap a (Type "EquivocationProof") = Just (a <> "EquivocationProof") +typeOverlap _ _ = Nothing + + +-- | If input type is generic structure, let's go deep using generics. +instance (Generic a, GDiscovery (NS (NP I) (Code a))) => Discovery a where + discovery = fmap (to . SOP) . gdiscovery . unSOP . from + +-- | Generic version of 'Discovery' type class. +class GDiscovery a where + gdiscovery :: MonadState DiscoveryContext m => a -> m a + +-- | Discovery all constructors of the sum. +instance ( GDiscovery (NP I xs) + , GDiscovery (NS (NP I) xss) + ) => GDiscovery (NS (NP I) (xs ': xss)) where + gdiscovery (Z xs) = Z <$> gdiscovery xs + gdiscovery (S xs) = S <$> gdiscovery xs + +-- | Finish when constructors will end. +instance GDiscovery (NS (NP I) '[]) where + gdiscovery = return + +-- | Discovery all fileds of constructors. +instance (Discovery a, GDiscovery (NP I as)) => GDiscovery (NP I (a ': as)) where + gdiscovery (I a :* as) = do + a' <- discovery a + (I a' :*) <$> gdiscovery as + +-- | Finish when fileds will end. +instance GDiscovery (NP I '[]) where + gdiscovery = return + +-- | Discovery types and returns sanitized metadata and set of discovered types. +runDiscovery :: (Discovery a, Traversable t) => (a -> Text) -> t a -> (t a, Set Type) +runDiscovery p = fmap (view types) + . flip runState mempty + . mapM (\m -> prefix .= p m >> discovery m) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/Type/Parser.hs b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Parser.hs new file mode 100644 index 00000000..232982c1 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/Type/Parser.hs @@ -0,0 +1,101 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Metadata.Type.Parser +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- This module parse and cleanup raw types given from runtime, +-- drop traits, generics, etc. +-- + +module Network.Polkadot.Metadata.Type.Parser + ( fromText + , fromTextM + , toText + , sanitize + , sanitizeM + ) where + +import Control.Monad.Fail (MonadFail) +import Data.Text (Text, + intercalate, + pack, + replace, + strip) +import Text.Parsec (ParseError, + parse) + +import Network.Polkadot.Metadata.Type.Ast +import Network.Polkadot.Metadata.Type.ParserCombinators (type') + +allowed_boxes :: [Text] +allowed_boxes = + [ "BTreeMap" + , "BTreeSet" + , "Compact" + , "DoNotConstruct" + , "HashMap" + , "Int" + , "Linkage" + , "Result" + , "Option" + , "UInt" + , "Vec" + ] + +render_box :: Text -> Maybe [TypeAst] -> Text +render_box name Nothing = name +render_box name (Just args) + | any (== name) allowed_boxes = name <> "<" <> intercalate "," (toText <$> args) <> ">" + | name == "BoundedVec" = "Vec<" <> intercalate "," (toText <$> args) <> ">" + | name == "Box" = toText (head args) + | otherwise = name + +aliases :: Maybe QSelf -> PathSegment -> Text -> Text +aliases _ _ "Vec" = "Bytes" +aliases _ _ "Announcement" = "ProxyAnnouncement" +aliases _ _ "Status" = "BalanceStatus" +aliases (Just (q, _)) _ "Source" = toText q <> "Source" +aliases (Just (q, _)) _ "Target" = toText q <> "Target" +aliases _ _ a = a + +-- | Render Metadata type to text. +-- +-- This function strongly sanitize type identifiers and paths, +-- removes generics and other Rust related staff. +toText :: TypeAst -> Text +toText (Slice (Path Nothing [("u8", Nothing)])) = "Bytes" +toText (Slice t) = "[" <> toText t <> "]" +toText (Tuple [t]) = toText t +toText (Tuple ts) = "(" <> intercalate "," (toText <$> ts) <> ")" +toText (Array t n) = "[" <> toText t <> ";" <> pack (show n) <> "]" +toText (Path _ []) = "()" +toText (Path q xs) = aliases q (last xs) $ render_box name args + where name = fst (last xs) + args = snd (last xs) + +-- | Parse metadata type (general Rust type) from text. +fromText :: Text -> Either ParseError TypeAst +fromText = parse type' "Metadata Type" + . strip + . replace "\n" "" + . replace "\n " "" + +-- | This variant of `fromText` fails when error happens. +fromTextM :: MonadFail m => Text -> m TypeAst +fromTextM t = either (fail . ((show t ++ ": ") ++) . show) return $ fromText t + +-- | Cleanup type or return error when syntax failure. +sanitize :: Text -> Either ParseError Text +{-# INLINE sanitize #-} +sanitize = fmap toText . fromText + +-- | Cleanup type or throw fail call when syntax failure. +sanitizeM :: MonadFail m => Text -> m Text +{-# INLINE sanitizeM #-} +sanitizeM = fmap toText . fromTextM diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/Type/ParserCombinators.hs b/packages/polkadot/src/Network/Polkadot/Metadata/Type/ParserCombinators.hs new file mode 100644 index 00000000..6167d653 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/Type/ParserCombinators.hs @@ -0,0 +1,62 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Metadata.Type.ParserCombinators +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Parser combinators for the metadata type. +-- + +module Network.Polkadot.Metadata.Type.ParserCombinators where + +import Data.Functor.Identity (Identity) +import Data.Text (pack) +import Text.Parsec +import Text.Parsec.Text () + +import Network.Polkadot.Metadata.Type.Ast (PathSegment, QSelf, + TypeAst (..)) + +type' :: Stream s Identity Char => Parsec s () TypeAst +type' = choice + [ Slice <$> try slice + , Tuple <$> tuple + , Array <$> arrayT <*> arrayN + , Path <$> optionMaybe pathQself <*> path + ] + +slice :: Stream s Identity Char => Parsec s () TypeAst +slice = (string "[" <|> string "&[") *> type' <* char ']' + +tuple :: Stream s Identity Char => Parsec s () [TypeAst] +tuple = char '(' *> type' `sepBy1` comma <* char ')' + +arrayT :: Stream s Identity Char => Parsec s () TypeAst +arrayT = char '[' *> type' <* dotcomma + where dotcomma = try (string "; ") <|> string ";" + +arrayN :: Stream s Identity Char => Parsec s () Int +arrayN = read <$> manyTill digit (char ']') + +pathQself :: Stream s Identity Char => Parsec s () QSelf +pathQself = (char '<' *> qselfP <* char '>') <* string "::" + where qselfP = (,) <$> (type' <* string " as ") <*> type' + +path :: Stream s Identity Char => Parsec s () [PathSegment] +path = path' `sepBy` string "::" + where + path' = (,) <$> ident + <*> optionMaybe (char '<' *> type' `sepBy1` comma <* char '>') + ident = do + c <- letter + cs <- many (alphaNum <|> char '_') + return $ pack (c : cs) + +comma :: Stream s Identity Char => Parsec s () String +comma = try (string ", ") <|> string "," diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/V10.hs b/packages/polkadot/src/Network/Polkadot/Metadata/V10.hs new file mode 100644 index 00000000..8cbed9c1 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/V10.hs @@ -0,0 +1,115 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata.V10 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata version 10 definitions. +-- + +module Network.Polkadot.Metadata.V10 where + +import Codec.Scale (Decode, Encode, Generic) +import Data.Aeson (Options (constructorTagModifier, fieldLabelModifier, sumEncoding), + SumEncoding (ObjectWithSingleField), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Text (Text) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import Network.Polkadot.Metadata.Type (Type) +import qualified Network.Polkadot.Metadata.V9 as V9 + +type StorageEntryModifier = V9.StorageEntryModifier +type FunctionMetadata = V9.FunctionMetadata +type EventMetadata = V9.EventMetadata +type ModuleConstantMetadata = V9.ModuleConstantMetadata +type ErrorMetadata = V9.ErrorMetadata + +data StorageHasher + = Blake2_128 + | Blake2_256 + | Blake2_128Concat + | Twox128 + | Twox256 + | Twox64Concat + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''StorageHasher) + +data MapType = MapType + { mapHasher :: !StorageHasher + , mapKey :: !Type + , mapValue :: !Type + , mapLinked :: !Bool + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 3 }) ''MapType) + +data DoubleMapType = DoubleMapType + { doubleMapHasher :: !StorageHasher + , doubleMapKey1 :: !Type + , doubleMapKey2 :: !Type + , doubleMapValue :: !Type + , doubleMapKey2Hasher :: !StorageHasher + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 9 }) ''DoubleMapType) + +data StorageEntryType + = Plain !Type + | Map !MapType + | DoubleMap !DoubleMapType + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { constructorTagModifier = over _head toLower, sumEncoding = ObjectWithSingleField }) ''StorageEntryType) + +data StorageEntryMetadata = StorageEntryMetadata + { entryName :: !Text + , entryModifier :: !StorageEntryModifier + , entryType :: !StorageEntryType + , entryFallback :: !HexString + , entryDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''StorageEntryMetadata) + +data StorageMetadata = StorageMetadata + { storagePrefix :: !Text + , storageItems :: ![StorageEntryMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''StorageMetadata) + +data ModuleMetadata = ModuleMetadata + { moduleName :: !Text + , moduleStorage :: !(Maybe StorageMetadata) + , moduleCalls :: !(Maybe [FunctionMetadata]) + , moduleEvents :: !(Maybe [EventMetadata]) + , moduleConstants :: ![ModuleConstantMetadata] + , moduleErrors :: ![ErrorMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''ModuleMetadata) + +data Metadata = Metadata + { modules :: ![ModuleMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''Metadata) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/V11.hs b/packages/polkadot/src/Network/Polkadot/Metadata/V11.hs new file mode 100644 index 00000000..8d4a6798 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/V11.hs @@ -0,0 +1,126 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata.V11 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata version 11 definitions. +-- + +module Network.Polkadot.Metadata.V11 where + +import Codec.Scale (Decode, Encode, Generic) +import Data.Aeson (Options (constructorTagModifier, fieldLabelModifier, sumEncoding), + SumEncoding (ObjectWithSingleField), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Text (Text) +import Data.Word (Word8) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import Network.Polkadot.Metadata.Type (Type) +import qualified Network.Polkadot.Metadata.V10 as V10 + +type StorageEntryModifier = V10.StorageEntryModifier +type FunctionMetadata = V10.FunctionMetadata +type EventMetadata = V10.EventMetadata +type ModuleConstantMetadata = V10.ModuleConstantMetadata +type ErrorMetadata = V10.ErrorMetadata + +data StorageHasher + = Blake2_128 + | Blake2_256 + | Blake2_128Concat + | Twox128 + | Twox256 + | Twox64Concat + | Identity + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''StorageHasher) + +data MapType = MapType + { mapHasher :: !StorageHasher + , mapKey :: !Type + , mapValue :: !Type + , mapLinked :: !Bool + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 3 }) ''MapType) + +data DoubleMapType = DoubleMapType + { doubleMapHasher :: !StorageHasher + , doubleMapKey1 :: !Type + , doubleMapKey2 :: !Type + , doubleMapValue :: !Type + , doubleMapKey2Hasher :: !StorageHasher + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 9 }) ''DoubleMapType) + +data StorageEntryType + = Plain !Type + | Map !MapType + | DoubleMap !DoubleMapType + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { constructorTagModifier = over _head toLower, sumEncoding = ObjectWithSingleField }) ''StorageEntryType) + +data StorageEntryMetadata = StorageEntryMetadata + { entryName :: !Text + , entryModifier :: !StorageEntryModifier + , entryType :: !StorageEntryType + , entryFallback :: !HexString + , entryDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''StorageEntryMetadata) + +data StorageMetadata = StorageMetadata + { storagePrefix :: !Text + , storageItems :: ![StorageEntryMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''StorageMetadata) + +data ModuleMetadata = ModuleMetadata + { moduleName :: !Text + , moduleStorage :: !(Maybe StorageMetadata) + , moduleCalls :: !(Maybe [FunctionMetadata]) + , moduleEvents :: !(Maybe [EventMetadata]) + , moduleConstants :: ![ModuleConstantMetadata] + , moduleErrors :: ![ErrorMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''ModuleMetadata) + +data ExtrinsicMetadata = ExtrinsicMetadata + { extrinsicVersion :: !Word8 + , extrinsicSignedExtensions :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 9 }) ''ExtrinsicMetadata) + +data Metadata = Metadata + { modules :: ![ModuleMetadata] + , extrinsics :: !ExtrinsicMetadata + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''Metadata) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/V12.hs b/packages/polkadot/src/Network/Polkadot/Metadata/V12.hs new file mode 100644 index 00000000..e01b94f2 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/V12.hs @@ -0,0 +1,60 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata.V12 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata version 12 definitions. +-- + +module Network.Polkadot.Metadata.V12 where + +import Codec.Scale (Decode, Encode, Generic) +import Data.Aeson (Options (fieldLabelModifier), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.Char (toLower) +import Data.Text (Text) +import Data.Word (Word8) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import qualified Network.Polkadot.Metadata.V11 as V11 + +type ExtrinsicMetadata = V11.ExtrinsicMetadata +type StorageMetadata = V11.StorageMetadata +type FunctionMetadata = V11.FunctionMetadata +type EventMetadata = V11.EventMetadata +type ModuleConstantMetadata = V11.ModuleConstantMetadata +type ErrorMetadata = V11.ErrorMetadata +type MapType = V11.MapType +type DoubleMapType = V11.DoubleMapType +type StorageHasher = V11.StorageHasher +type StorageEntryModifier = V11.StorageEntryModifier + +data ModuleMetadata = ModuleMetadata + { moduleName :: !Text + , moduleStorage :: !(Maybe StorageMetadata) + , moduleCalls :: !(Maybe [FunctionMetadata]) + , moduleEvents :: !(Maybe [EventMetadata]) + , moduleConstants :: ![ModuleConstantMetadata] + , moduleErrors :: ![ErrorMetadata] + , moduleIndex :: !Word8 + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''ModuleMetadata) + +data Metadata = Metadata + { modules :: ![ModuleMetadata] + , extrinsic :: !ExtrinsicMetadata + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''Metadata) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/V13.hs b/packages/polkadot/src/Network/Polkadot/Metadata/V13.hs new file mode 100644 index 00000000..b736a11b --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/V13.hs @@ -0,0 +1,99 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata.V13 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata version 13 definitions. +-- + +module Network.Polkadot.Metadata.V13 where + +import Codec.Scale (Decode, Encode, Generic) +import Data.Aeson (Options (constructorTagModifier, fieldLabelModifier, sumEncoding), + SumEncoding (ObjectWithSingleField), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Text (Text) +import Data.Word (Word8) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import Network.Polkadot.Metadata.Type (Type) +import qualified Network.Polkadot.Metadata.V12 as V12 + +type ExtrinsicMetadata = V12.ExtrinsicMetadata +type FunctionMetadata = V12.FunctionMetadata +type EventMetadata = V12.EventMetadata +type ModuleConstantMetadata = V12.ModuleConstantMetadata +type ErrorMetadata = V12.ErrorMetadata +type StorageHasher = V12.StorageHasher +type MapType = V12.MapType +type DoubleMapType = V12.DoubleMapType + +data NMapType = NMapType + { nmapKeyVec :: ![Type] + , nmapHashers :: ![StorageHasher] + , nmapValue :: !Type + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 4 }) ''NMapType) + +data StorageEntryType + = Plain !Type + | Map !MapType + | DoubleMap !DoubleMapType + | NMap !NMapType + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { constructorTagModifier = over _head toLower, sumEncoding = ObjectWithSingleField }) ''StorageEntryType) + +data StorageEntryMetadata = StorageEntryMetadata + { entryName :: !Text + , entryModifier :: !V12.StorageEntryModifier + , entryType :: !StorageEntryType + , entryFallback :: !HexString + , entryDocumentation :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''StorageEntryMetadata) + +data StorageMetadata = StorageMetadata + { storagePrefix :: !Text + , storageItems :: ![StorageEntryMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''StorageMetadata) + +data ModuleMetadata = ModuleMetadata + { moduleName :: !Text + , moduleStorage :: !(Maybe StorageMetadata) + , moduleCalls :: !(Maybe [FunctionMetadata]) + , moduleEvents :: !(Maybe [EventMetadata]) + , moduleConstants :: ![ModuleConstantMetadata] + , moduleErrors :: ![ErrorMetadata] + , moduleIndex :: !Word8 + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''ModuleMetadata) + +data Metadata = Metadata + { modules :: ![ModuleMetadata] + , extrinsic :: !ExtrinsicMetadata + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''Metadata) diff --git a/packages/polkadot/src/Network/Polkadot/Metadata/V9.hs b/packages/polkadot/src/Network/Polkadot/Metadata/V9.hs new file mode 100644 index 00000000..6250d002 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Metadata/V9.hs @@ -0,0 +1,157 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Metadata.V9 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Metadata version 9 definitions. +-- + +module Network.Polkadot.Metadata.V9 where + +import Codec.Scale (Decode, Encode, Generic) +import Data.Aeson (Options (constructorTagModifier, fieldLabelModifier, sumEncoding), + SumEncoding (ObjectWithSingleField), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Text (Text) +import qualified GHC.Generics as GHC (Generic) +import Lens.Micro (_head, over) + +import Network.Polkadot.Metadata.Type (Type) + +data FunctionArgumentMetadata = FunctionArgumentMetadata + { argumentName :: !Text + , argumentType :: !Type + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 8 }) ''FunctionArgumentMetadata) + +data FunctionMetadata = FunctionMetadata + { functionName :: !Text + , functionArgs :: ![FunctionArgumentMetadata] + , functionDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 8 }) ''FunctionMetadata) + +data EventMetadata = EventMetadata + { eventName :: !Text + , eventArgs :: ![Type] + , eventDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''EventMetadata) + +data ModuleConstantMetadata = ModuleConstantMetadata + { constantName :: !Text + , constantType :: !Type + , constantValue :: !HexString + , constantDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 8 }) ''ModuleConstantMetadata) + +data ErrorMetadata = ErrorMetadata + { errorName :: !Text + , errorDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''ErrorMetadata) + +data StorageHasher + = Blake2_128 + | Blake2_256 + | Twox128 + | Twox256 + | Twox64Concat + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''StorageHasher) + +data MapType = MapType + { mapHasher :: !StorageHasher + , mapKey :: !Type + , mapValue :: !Type + , mapLinked :: !Bool + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 3 }) ''MapType) + +data DoubleMapType = DoubleMapType + { doubleMapHasher :: !StorageHasher + , doubleMapKey1 :: !Type + , doubleMapKey2 :: !Type + , doubleMapValue :: !Type + , doubleMapKey2Hasher :: !StorageHasher + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 9 }) ''DoubleMapType) + +data StorageEntryType + = Plain !Type + | Map !MapType + | DoubleMap !DoubleMapType + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { constructorTagModifier = over _head toLower, sumEncoding = ObjectWithSingleField }) ''StorageEntryType) + +data StorageEntryModifier = Optional | Default | Required + deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''StorageEntryModifier) + +data StorageEntryMetadata = StorageEntryMetadata + { entryName :: !Text + , entryModifier :: !StorageEntryModifier + , entryType :: !StorageEntryType + , entryFallback :: !HexString + , entryDocs :: ![Text] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''StorageEntryMetadata) + +data StorageMetadata = StorageMetadata + { storagePrefix :: !Text + , storageItems :: ![StorageEntryMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''StorageMetadata) + +data ModuleMetadata = ModuleMetadata + { moduleName :: !Text + , moduleStorage :: !(Maybe StorageMetadata) + , moduleCalls :: !(Maybe [FunctionMetadata]) + , moduleEvents :: !(Maybe [EventMetadata]) + , moduleConstants :: ![ModuleConstantMetadata] + , moduleErrors :: ![ErrorMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''ModuleMetadata) + +data Metadata = Metadata + { modules :: ![ModuleMetadata] + } deriving (Eq, Show, Generic, GHC.Generic, Encode, Decode) + +$(deriveJSON defaultOptions ''Metadata) diff --git a/packages/polkadot/src/Network/Polkadot/Primitives.hs b/packages/polkadot/src/Network/Polkadot/Primitives.hs new file mode 100644 index 00000000..7926e781 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Primitives.hs @@ -0,0 +1,94 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} + +-- | +-- Module : Network.Polkadot.Primitives +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Polkadot primitive data types. +-- + +module Network.Polkadot.Primitives where + +import Codec.Scale (Decode, Encode) +import Codec.Scale.Compact (Compact) +import Data.BigNum (H160, H256, H512, Word128) +import Data.ByteArray.HexString (HexString) +import Data.Word (Word32, Word64, Word8) +import Generics.SOP (Generic) +import qualified GHC.Generics as GHC (Generic) + +-- | The user account balance, 'u128' type. +type Balance = Word128 + +-- | Block numbers is up to 2^32. +type BlockNumber = Word32 + +-- | Time moment is 64bit. +type Moment = Word64 + +-- | Transaction nonce value. +type Index = Word32 + +-- | The type for looking up accounts. We don't expect more than 4 billion of them. +type AccountIndex = Word32 + +-- | The user account identifier type for the runtime. +type AccountId = H256 + +-- | The type for runtime hashes. +type Hash = H256 + +-- | Account balances. +data AccountData = AccountData + { balanceFree :: !Balance + , balanceReserved :: !Balance + , miscFrozen :: !Balance + , feeFrozen :: !Balance + } deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +-- | General account information. +data AccountInfo = AccountInfo + { accountNonce :: !Index + , accountConsumers :: !Word32 + , accountProviders :: !Word32 + , accountSufficients :: !Word32 + , accountData :: !AccountData + } deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +-- | Multiple signatures support type. +data MultiSignature + = Ed25519Signature !H512 + | Sr25519Signature !H512 + | EcdsaSignature !H512 !Word8 + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +-- | Cryptographic key for any known crypto algorithm. +data MultiSigner + = Sr25519Signer + -- ^ sr25519 crypto has no support yet + | Ed25519Signer !H256 + -- ^ Ed25519 public key. + | EcdsaSigner !Word8 !H256 + -- ^ ECDSA public key. + deriving (Eq, Ord, GHC.Generic, Generic, Encode, Decode) + +-- | A multi-format address wrapper for on-chain accounts. +data MultiAddress + = MaId !AccountId + -- ^ It's an account ID (pubkey). + | MaIndex !(Compact AccountIndex) + -- ^ It's an account index. + | MaRaw !HexString + -- ^ It's some arbitrary raw bytes. + | MaAddress32 !H256 + -- ^ It's a 32 byte representation. + | MaAddress20 !H160 + -- ^ Its a 20 byte representation. + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) diff --git a/packages/polkadot/src/Network/Polkadot/Query.hs b/packages/polkadot/src/Network/Polkadot/Query.hs new file mode 100644 index 00000000..0824b743 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Query.hs @@ -0,0 +1,63 @@ +-- | +-- Module : Network.Polkadot.Query +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Query storage for internal data. +-- + +module Network.Polkadot.Query where + +import Codec.Scale (Decode, decode) +import Data.ByteArray.HexString (HexString) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc) + +import Network.Polkadot.Metadata (Metadata (Metadata), + metadataTypes, toLatest) +import Network.Polkadot.Rpc.State (getMetadata, getStorage) +import Network.Polkadot.Storage (Storage, fromMetadata, + storageKey) +import Network.Polkadot.Storage.Key (Argument) + +-- | Loads metadata from runtime and create storage type. +storage :: JsonRpc m => m (Either String Storage) +storage = (fmap go . decode) <$> getMetadata + where + go raw = let (meta, _) = metadataTypes raw in fromMetadata (toLatest meta) + +-- | Query data from blockchain via 'getStorage' RPC call. +query :: (JsonRpc m, Decode a) + => Text + -- ^ Module name. + -> Text + -- ^ Storage method name. + -> [Argument] + -- ^ Arguments (for mappings). + -> m (Either String a) + -- ^ Decoded storage item. +{-# INLINE query #-} +query = query' Nothing + +-- | Similar to 'query' but get block hash for query as an argument. +query' :: (JsonRpc m, Decode a) + => Maybe HexString + -- ^ Block hash for query ('Nothing' for best block). + -> Text + -- ^ Module name. + -> Text + -- ^ Storage method name. + -> [Argument] + -- ^ Arguments (for mappings). + -> m (Either String a) + -- ^ Decoded storage item. +query' blockHash section method args = go =<< storage + where + go (Right store) = case storageKey store section method args of + Just key -> decode <$> getStorage key blockHash + Nothing -> return (Left "Unable to find given section/method or wrong argument count") + go (Left err) = return (Left err) diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Account.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Account.hs new file mode 100644 index 00000000..8f1747e8 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Account.hs @@ -0,0 +1,27 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Account +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `account` prefix. +-- + +module Network.Polkadot.Rpc.Account where + +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Retrieves the next accountIndex as available on the node. +nextIndex :: JsonRpc m + => Text + -- ^ AccountId + -> m Int +{-# INLINE nextIndex #-} +nextIndex = remote "account_nextIndex" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Author.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Author.hs new file mode 100644 index 00000000..5931ee40 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Author.hs @@ -0,0 +1,77 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Author +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `author` prefix. +-- + +module Network.Polkadot.Rpc.Author where + +import Data.ByteArray.HexString (HexString) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Returns true if the keystore has private keys for the given public key and key type. +hasKey :: JsonRpc m + => HexString + -- ^ Public key + -> Text + -- ^ Key type + -> m Bool +{-# INLINE hasKey #-} +hasKey = remote "author_hasKey" + +-- | Returns true if the keystore has private keys for the given session public keys. +hasSessionKeys :: JsonRpc m + => HexString + -- ^ Session keys + -> m Bool +{-# INLINE hasSessionKeys #-} +hasSessionKeys = remote "author_hasSessionKeys" + +-- | Insert a key into the keystore. +insertKey :: JsonRpc m + => Text + -- ^ Key type + -> Text + -- ^ Key secret URI + -> HexString + -- ^ Public key + -> m HexString +{-# INLINE insertKey #-} +insertKey = remote "author_insertKey" + +-- | Returns all pending extrinsics, potentially grouped by sender. +pendingExtrinsics :: JsonRpc m => m [HexString] +{-# INLINE pendingExtrinsics #-} +pendingExtrinsics = remote "author_pendingExtrinsics" + +-- | Remove given extrinsic from the pool and temporarily ban it to prevent reimporting. +removeExtrinsic :: JsonRpc m + => [HexString] + -- ^ Extrinsic or hash + -> m HexString +{-# INLINE removeExtrinsic #-} +removeExtrinsic = remote "author_removeExtrinsic" + +-- | Generate new session keys and returns the corresponding public keys. +rotateKeys :: JsonRpc m => m HexString +{-# INLINE rotateKeys #-} +rotateKeys = remote "author_rotateKeys" + +-- | Submit a fully formatted extrinsic for block inclusion. +submitExtrinsic :: JsonRpc m + => HexString + -- ^ Extrinsic + -> m HexString + -- ^ Hash +{-# INLINE submitExtrinsic #-} +submitExtrinsic = remote "author_submitExtrinsic" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Babe.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Babe.hs new file mode 100644 index 00000000..74c89742 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Babe.hs @@ -0,0 +1,25 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Babe +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `babe` prefix. +-- + +module Network.Polkadot.Rpc.Babe where + +import Data.Aeson (Object) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Returns data about which slots (primary or secondary) can be claimed +-- in the current epoch with the keys in the keystore. +epochAuthorship :: JsonRpc m => m Object +{-# INLINE epochAuthorship #-} +epochAuthorship = remote "babe_epochAuthorship" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Chain.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Chain.hs new file mode 100644 index 00000000..05d364b2 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Chain.hs @@ -0,0 +1,50 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Chain +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `chain` prefix. +-- + +module Network.Polkadot.Rpc.Chain where + +import Data.ByteArray.HexString (HexString) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (Header, SignedBlock) + +-- | Get header and body of a relay chain block. +getBlock :: JsonRpc m + => Maybe HexString + -- ^ Block hash + -> m (Maybe SignedBlock) +{-# INLINE getBlock #-} +getBlock = remote "chain_getBlock" + +-- | Get the block hash for a specific block. +getBlockHash :: JsonRpc m + => Maybe Int + -- ^ Block number + -> m (Maybe HexString) +{-# INLINE getBlockHash #-} +getBlockHash = remote "chain_getBlockHash" + +-- | Get hash of the last finalized block in the canon chain. +getFinalizedHead :: JsonRpc m => m HexString +{-# INLINE getFinalizedHead #-} +getFinalizedHead = remote "chain_getFinalizedHead" + +-- | Retrieves the header for a specific block. +getHeader :: JsonRpc m + => Maybe HexString + -- ^ Block hash + -> m (Maybe Header) +{-# INLINE getHeader #-} +getHeader = remote "chain_getHeader" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Childstate.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Childstate.hs new file mode 100644 index 00000000..d1f3dfcf --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Childstate.hs @@ -0,0 +1,67 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Childstate +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `childstate` prefix. +-- + +module Network.Polkadot.Rpc.Childstate where + +import Data.ByteArray.HexString (HexString) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Returns the keys with prefix from a child storage, leave empty to get all the keys. +getKeys :: JsonRpc m + => HexString + -- ^ Prefixed storage key + -> HexString + -- ^ Storage key + -> Maybe HexString + -- ^ Block hash + -> m [HexString] +{-# INLINE getKeys #-} +getKeys = remote "childstate_getKeys" + +-- | Returns a child storage entry at a specific block state. +getStorage :: JsonRpc m + => HexString + -- ^ Prefixed storage key + -> HexString + -- ^ Storage key + -> Maybe HexString + -- ^ Block hash + -> m (Maybe HexString) +{-# INLINE getStorage #-} +getStorage = remote "childstate_getStorage" + +-- | Returns the hash of a child storage entry at a block state +getStorageHash :: JsonRpc m + => HexString + -- ^ Prefixed storage key + -> HexString + -- ^ Storage key + -> Maybe HexString + -- ^ Block hash + -> m (Maybe HexString) +{-# INLINE getStorageHash #-} +getStorageHash = remote "childstate_getStorageHash" + +-- | Returns the size of a child storage entry at a block state. +getStorageSize :: JsonRpc m + => HexString + -- ^ Prefixed storage key + -> HexString + -- ^ Storage key + -> Maybe HexString + -- ^ Block hash + -> m (Maybe Int) +{-# INLINE getStorageSize #-} +getStorageSize = remote "childstate_getStorageSize" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Contracts.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Contracts.hs new file mode 100644 index 00000000..cc0464bc --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Contracts.hs @@ -0,0 +1,54 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Contracts +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `contracts` prefix. +-- + +module Network.Polkadot.Rpc.Contracts where + +import Data.ByteArray.HexString (HexString) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (ContractCall, ContractExecResult) + +-- | Executes a call to a contract. +call :: JsonRpc m + => ContractCall + -- ^ Contract call + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m ContractExecResult +{-# INLINE call #-} +call = remote "contracts_call" + +-- | Returns the value under a specified storage key in a contract +getStorage :: JsonRpc m + => Text + -- ^ AccountId + -> HexString + -- ^ Storage key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m (Maybe HexString) +{-# INLINE getStorage #-} +getStorage = remote "contracts_getStorage" + +-- | Returns the projected time a given contract will be able to sustain paying its rent. +rentProjection :: JsonRpc m + => Text + -- ^ AccountId + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m (Maybe Int) +{-# INLINE rentProjection #-} +rentProjection = remote "contracts_rentProjection" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Engine.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Engine.hs new file mode 100644 index 00000000..2e63a774 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Engine.hs @@ -0,0 +1,43 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Engine +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `engine` prefix. +-- + +module Network.Polkadot.Rpc.Engine where + +import Data.ByteArray.HexString (HexString) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (CreatedBlock) + +-- | Instructs the manual-seal authorship task to create a new block. +createBlock :: JsonRpc m + => Bool + -- ^ Create empty + -> Bool + -- ^ Finalize + -> Maybe HexString + -- ^ Parent hash + -> m CreatedBlock +{-# INLINE createBlock #-} +createBlock = remote "engine_createBlock" + +-- | Instructs the manual-seal authorship task to finalize a block. +finalizeBlock :: JsonRpc m + => HexString + -- ^ Block hash + -> Maybe HexString + -- ^ Justification + -> m Bool +{-# INLINE finalizeBlock #-} +finalizeBlock = remote "engine_finalizeBlock" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Grandpa.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Grandpa.hs new file mode 100644 index 00000000..71b719b0 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Grandpa.hs @@ -0,0 +1,24 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Grandpa +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `grandpa` prefix. +-- + +module Network.Polkadot.Rpc.Grandpa where + +import Data.Aeson (Object) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Returns the state of the current best round state as well as the ongoing background rounds. +roundState :: JsonRpc m => m Object +{-# INLINE roundState #-} +roundState = remote "grandpa_roundState" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Offchain.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Offchain.hs new file mode 100644 index 00000000..bf28ed93 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Offchain.hs @@ -0,0 +1,43 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Offchain +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `offchain` prefix. +-- + +module Network.Polkadot.Rpc.Offchain where + +import Data.ByteArray.HexString (HexString) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (StorageKind) + +-- | Get offchain local storage under given key and prefix. +localStorageGet :: JsonRpc m + => StorageKind + -- ^ Offchain storage kind + -> HexString + -- ^ Key + -> m (Maybe HexString) +{-# INLINE localStorageGet #-} +localStorageGet = remote "offchain_localStorageGet" + +-- | Set offchain local storage under given key and prefix +localStorageSet :: JsonRpc m + => StorageKind + -- ^ Offchain storage kind + -> HexString + -- ^ Key + -> HexString + -- ^ Value + -> m () +{-# INLINE localStorageSet #-} +localStorageSet = remote "offchain_localStorageSet" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Payment.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Payment.hs new file mode 100644 index 00000000..d4c61cf0 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Payment.hs @@ -0,0 +1,31 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Payment +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `payment` prefix. +-- + +module Network.Polkadot.Rpc.Payment where + +import Data.ByteArray.HexString (HexString) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (RuntimeDispatchInfo) + +-- | Retrieves the fee information for an encoded extrinsic. +queryInfo :: JsonRpc m + => HexString + -- ^ Extrinsic + -> Maybe HexString + -- ^ Block hash or nothing for head block + -> m RuntimeDispatchInfo +{-# INLINE queryInfo #-} +queryInfo = remote "payment_queryInfo" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Rpc.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Rpc.hs new file mode 100644 index 00000000..5d8b2b18 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Rpc.hs @@ -0,0 +1,24 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.Rpc +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `rpc` prefix. +-- + +module Network.Polkadot.Rpc.Rpc where + +import Data.Aeson (Value) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +-- | Retrieves the list of RPC methods that are exposed by the node. +methods :: JsonRpc m => m Value +{-# INLINE methods #-} +methods = remote "rpc_methods" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/State.hs b/packages/polkadot/src/Network/Polkadot/Rpc/State.hs new file mode 100644 index 00000000..28fee2d0 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/State.hs @@ -0,0 +1,184 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.State +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `state` prefix. +-- + +module Network.Polkadot.Rpc.State where + +import Data.ByteArray.HexString (HexString) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (ReadProof, RuntimeVersion, + StorageChangeSet) + +-- | Perform a call to a builtin on the chain. +call :: JsonRpc m + => Text + -- ^ Call method + -> HexString + -- ^ Call data + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m HexString +{-# INLINE call #-} +call = remote "state_call" + +-- | Retrieves the keys with prefix of a specific child storage. +getChildKeys :: JsonRpc m + => HexString + -- ^ Child storage key + -> HexString + -- ^ Child definition + -> Int + -- ^ Child type + -> HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m [HexString] +{-# INLINE getChildKeys #-} +getChildKeys = remote "state_getChildKeys" + +-- | Retrieves the child storage for a key. +getChildStorage :: JsonRpc m + => HexString + -- ^ Child storage key + -> HexString + -- ^ Child definition + -> Int + -- ^ Child type + -> HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m HexString +{-# INLINE getChildStorage #-} +getChildStorage = remote "state_getChildStorage" + +-- | Retrieves the child storage hash. +getChildStorageHash :: JsonRpc m + => HexString + -- ^ Child storage key + -> HexString + -- ^ Child definition + -> Int + -- ^ Child type + -> HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m HexString +{-# INLINE getChildStorageHash #-} +getChildStorageHash = remote "state_getChildStorageHash" + +-- | Retrieves the child storage size. +getChildStorageSize :: JsonRpc m + => HexString + -- ^ Child storage key + -> HexString + -- ^ Child definition + -> Int + -- ^ Child type + -> HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m Int +{-# INLINE getChildStorageSize #-} +getChildStorageSize = remote "state_getChildStorageSize" + +-- | Retrieves the keys with a certain prefix. +getKeys :: JsonRpc m + => HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m [HexString] +{-# INLINE getKeys #-} +getKeys = remote "state_getKeys" + +-- | Returns the runtime metadata. +getMetadata :: JsonRpc m => m HexString +{-# INLINE getMetadata #-} +getMetadata = remote "state_getMetadata" + +-- | Returns proof of storage entries at a specific block state. +getReadProof :: JsonRpc m + => [HexString] + -- ^ Keys + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m ReadProof +{-# INLINE getReadProof #-} +getReadProof = remote "state_getReadProof" + +-- | Get runtime version. +getRuntimeVersion :: JsonRpc m + => Maybe HexString + -- ^ Block hash or nothing for head + -> m RuntimeVersion +{-# INLINE getRuntimeVersion #-} +getRuntimeVersion = remote "state_getRuntimeVersion" + +-- | Retrieves the storage for a key. +getStorage :: JsonRpc m + => HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m HexString +{-# INLINE getStorage #-} +getStorage = remote "state_getStorage" + +-- | Retrieves the storage hash. +getStorageHash :: JsonRpc m + => HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m HexString +{-# INLINE getStorageHash #-} +getStorageHash = remote "state_getStorageHash" + +-- | Retrieves the storage size. +getStorageSize :: JsonRpc m + => HexString + -- ^ Key + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m Int +{-# INLINE getStorageSize #-} +getStorageSize = remote "state_getStorageSize" + +-- | Query historical storage entries (by key) starting from a start block. +queryStorage :: JsonRpc m + => [HexString] + -- ^ Storage keys + -> HexString + -- ^ From block hash + -> Maybe HexString + -- ^ To block hash + -> m [StorageChangeSet] +{-# INLINE queryStorage #-} +queryStorage = remote "state_queryStorage" + +-- | Query storage entries (by key) starting at block hash given as the second parameter. +queryStorageAt :: JsonRpc m + => [HexString] + -- ^ Storage keys + -> Maybe HexString + -- ^ Block hash or nothing for head + -> m [StorageChangeSet] +{-# INLINE queryStorageAt #-} +queryStorageAt = remote "state_queryStorageAt" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/System.hs b/packages/polkadot/src/Network/Polkadot/Rpc/System.hs new file mode 100644 index 00000000..eb0aa336 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/System.hs @@ -0,0 +1,97 @@ +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Network.Polkadot.Rpc.System +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot RPC methods with `system` prefix. +-- + +module Network.Polkadot.Rpc.System where + +import Data.Aeson (Object) +import Data.Text (Text) +import Network.JsonRpc.TinyClient (JsonRpc (..)) + +import Network.Polkadot.Rpc.Types (ChainType, Health, NodeRole, + PeerInfo) + +-- | Adds a reserved peer. +addReservedPeer :: JsonRpc m + => Text + -- ^ Peer URI + -> m Text +{-# INLINE addReservedPeer #-} +addReservedPeer = remote "system_addReservedPeer" + +-- | Retrieves the chain. +chain :: JsonRpc m => m Text +{-# INLINE chain #-} +chain = remote "system_chain" + +-- | Retrieves the chain type. +chainType :: JsonRpc m => m ChainType +{-# INLINE chainType #-} +chainType = remote "system_chainType" + +-- | Return health status of the node. +health :: JsonRpc m => m Health +{-# INLINE health #-} +health = remote "system_health" + +-- | The addresses include a trailing /p2p/ with the local PeerId, +-- and are thus suitable to be passed to addReservedPeer or as a bootnode address. +localListenAddresses :: JsonRpc m => m [Text] +{-# INLINE localListenAddresses #-} +localListenAddresses = remote "system_localListenAddresses" + +-- | Returns the base58-encoded PeerId of the node. +localPeerId :: JsonRpc m => m Text +{-# INLINE localPeerId #-} +localPeerId = remote "system_localPeerId" + +-- | Retrieves the node name. +name :: JsonRpc m => m Text +{-# INLINE name #-} +name = remote "system_name" + +-- | Returns current state of the network. +-- +-- Warning: This API isn't stable. +networkState :: JsonRpc m => m Object +{-# INLINE networkState #-} +networkState = remote "system_networkState" + +-- | Returns the roles the node is running as. +nodeRoles :: JsonRpc m => m [NodeRole] +{-# INLINE nodeRoles #-} +nodeRoles = remote "system_nodeRoles" + +-- | Returns the currently connected peers. +peers :: JsonRpc m => m [PeerInfo] +{-# INLINE peers #-} +peers = remote "system_peers" + +-- | Get a custom set of properties as a JSON object, defined in the chain spec. +properties :: JsonRpc m => m Object +{-# INLINE properties #-} +properties = remote "system_properties" + +-- | Remove a reserved peer. +removeReservedPeer :: JsonRpc m + => Text + -- ^ Peer URI + -> m Text +{-# INLINE removeReservedPeer #-} +removeReservedPeer = remote "system_removeReservedPeer" + +-- | Retrieves the version of the node. +version :: JsonRpc m => m Text +{-# INLINE version #-} +version = remote "system_version" diff --git a/packages/polkadot/src/Network/Polkadot/Rpc/Types.hs b/packages/polkadot/src/Network/Polkadot/Rpc/Types.hs new file mode 100644 index 00000000..dcca5438 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Rpc/Types.hs @@ -0,0 +1,289 @@ +{-# LANGUAGE DeriveDataTypeable #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Network.Polkadot.Rpc.Types +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Polkadot JSON-RPC types. +-- + +module Network.Polkadot.Rpc.Types where + +import Data.Aeson (FromJSON (..), + Options (fieldLabelModifier), + ToJSON (..), Value (String), + defaultOptions) +import Data.Aeson.TH (deriveJSON) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Text (Text) +import Data.Word (Word32, Word64, Word8) +import GHC.Generics (Generic) +import Lens.Micro (_head, over) +import Numeric (readHex, showHex) + +-- | The role the node is running as. +data NodeRole = Full + | LightClient + | Authority + | Sentry + deriving (Eq, Generic, Show) + +$(deriveJSON defaultOptions ''NodeRole) + +-- | Type op a chain. +data ChainType = Development + | Local + | Live + | Custom Text + deriving (Eq, Generic, Show) + +instance FromJSON ChainType where + parseJSON (String v) = return $ case v of + "Development" -> Development + "Local" -> Local + "Live" -> Live + custom_name -> Custom custom_name + parseJSON _ = fail "ChainType should be a JSON String" + +instance ToJSON ChainType where + toJSON (Custom v) = toJSON v + toJSON v = toJSON (show v) + +-- | System health struct returned by the RPC +data Health = Health + { healthPeers :: Int + -- ^ Number of connected peers. + , healthIsSyncing :: Bool + -- ^ Is the node syncing. + , healthShouldHavePeers :: Bool + -- ^ Should this node have any peers. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''Health) + +-- | Network Peer information. +data PeerInfo = PeerInfo + { peerInfoPeerId :: Text + -- ^ Peer ID + , peerInfoRoles :: [NodeRole] + -- ^ Roles + , peerInfoProtocolVersion :: Int + -- ^ Protocol version. + , peerInfoBestHash :: Text + -- ^ Peer best block hash + , peerInfoBestNumber :: Int + -- ^ Peer best block number + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 8 }) ''PeerInfo) + +-- | Executes a call to a contract. +data ContractCall = ContractCall + { callOrigin :: HexString + , callDest :: HexString + , callValue :: Integer + , callGasLimit :: Integer + , callInputData :: HexString + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 4 }) ''ContractCall) + +-- | A result of execution of a contract. +data ContractExecResult = SuccessExec + { execStatus :: Word8 + -- ^ Status code returned by contract. + , execData :: Maybe HexString + -- ^ Output data returned by contract. Can be empty. + } + | ExecResultError + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 4 }) ''ContractExecResult) + +-- | ReadProof struct returned by RPC. +data ReadProof = ReadProof + { readProofAt :: HexString + -- ^ Block hash used to generate the proof. + , readProofProof :: [HexString] + -- ^ A proof used to prove that storage entries are included in the storage trie. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 9 }) ''ReadProof) + +-- | Runtime version. +-- This should not be thought of as classic Semver (major/minor/tiny). +-- This triplet have different semantics and mis-interpretation could cause problems. +-- In particular: bug fixes should result in an increment of `spec_version` and possibly `authoring_version`, +-- absolutely not `impl_version` since they change the semantics of the runtime. +data RuntimeVersion = RuntimeVersion + { runtimeSpecName :: Text + -- ^ Identifies the different Substrate runtimes. + , runtimeImplName :: Text + -- ^ Name of the implementation of the spec. + , runtimeAuthoringVersion :: Word32 + -- ^ `authoring_version` is the version of the authorship interface. + , runtimeSpecVersion :: Word32 + -- ^ Version of the runtime specification. + , runtimeImplVersion :: Word32 + -- ^ Version of the implementation of the specification. + , runtimeApis :: [(HexString, Word32)] + -- ^ List of supported API "features" along with their versions. + , runtimeTransactionVersion :: Word32 + -- ^ All existing dispatches are fully compatible when this number doesn't change. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''RuntimeVersion) + +-- | Type of supported offchain storages. +-- +-- 1: persistent storage is non-revertible and not fork-aware; +-- 2: local storage is revertible and fork-aware. +type StorageKind = Word8 + +-- | Storage changes. +data StorageChangeSet = StorageChangeSet + { storageBlock :: HexString + -- ^ Block hash. + , storageChanges :: [(HexString, Maybe HexString)] + -- ^ A list of changes. + } + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 7 }) ''StorageChangeSet) + +-- | Numeric range of transaction weight. +type Weight = Word64 + +-- | Generalized group of dispatch types. +data DispatchClass = Normal + | Operational + | Mandatory + deriving (Eq, Generic, Show) + +$(deriveJSON defaultOptions ''DispatchClass) + +-- | Some information related to a dispatchable that can be queried from the runtime. +data RuntimeDispatchInfo = RuntimeDispatchInfo + { dispatchWeight :: Weight + -- ^ Weight of this dispatch. + , dispatchClass :: DispatchClass + -- ^ Class of this dispatch. + , dispatchPartialFee :: Integer + -- ^ The partial inclusion fee of this dispatch. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 8 }) ''RuntimeDispatchInfo) + +-- | Auxiliary data associated with an imported block result. +data ImportedAux = ImportedAux + { auxHeaderOnly :: Bool + -- ^ Only the header has been imported. Block body verification was skipped. + , auxClearJustificationRequests :: Bool + -- ^ Clear all pending justification requests. + , auxNeedsJustification :: Bool + -- ^ Request a justification for the given block. + , auxBadJustification :: Bool + -- ^ Received a bad justification. + , auxNeedsFinalityProof :: Bool + -- ^ Request a finality proof for the given block. + , auxIsNewBest :: Bool + -- ^ Whether the block that was imported is the new best block. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 3 }) ''ImportedAux) + +data CreatedBlock = CreatedBlock + { createdBlockHash :: HexString + , createdBlockAux :: ImportedAux + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 12 }) ''CreatedBlock) + +-- | Generic header digest. +data Digest = Digest + { digestLogs :: ![HexString] + -- ^ A list of logs in the digest. + } + deriving (Eq, Generic, Show) + +-- | Hex-encoded block number. +newtype BlockNumber = BlockNumber { unBlockNumber :: Integer } + deriving (Eq, Ord, Show) + +instance FromJSON BlockNumber where + parseJSON = fmap (BlockNumber . fst . head . readHex . drop 2) . parseJSON + +instance ToJSON BlockNumber where + toJSON = toJSON . ("0x" <>) . flip showHex "" . unBlockNumber + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''Digest) + +-- | Abstraction over a block header for a substrate chain. +data Header = Header + { headerParentHash :: HexString + -- ^ The parent hash. + , headerNumber :: BlockNumber + -- ^ The block number. + , headerStateRoot :: HexString + -- ^ The state trie merkle root + , headerExtrinsicsRoot :: HexString + -- ^ The merkle root of the extrinsics. + , headerDigest :: Digest + -- ^ A chain-specific digest of data useful for light clients or referencing auxiliary data. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''Header) + +-- | Abstraction over a substrate block. +data Block = Block + { blockHeader :: !Header + -- ^ The block header. + , blockExtrinsics :: ![HexString] + -- ^ The accompanying extrinsics. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 5 }) ''Block) + +-- | Abstraction over a substrate block and justification. +data SignedBlock = SignedBlock + { signedBlock :: !Block + -- ^ Full block. + , signedJustification :: !(Maybe HexString) + -- ^ Block justification. + } + deriving (Eq, Generic, Show) + +$(deriveJSON (defaultOptions + { fieldLabelModifier = over _head toLower . drop 6 }) ''SignedBlock) diff --git a/packages/polkadot/src/Network/Polkadot/Storage.hs b/packages/polkadot/src/Network/Polkadot/Storage.hs new file mode 100644 index 00000000..b07d92c2 --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Storage.hs @@ -0,0 +1,81 @@ +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Network.Polkadot.Storage +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Substrate uses a simple key-value data store implemented as a database-backed, +-- modified Merkle tree. +-- +-- Blockchains that are built with Substrate expose a remote procedure call (RPC) +-- server that can be used to query runtime storage. +-- + +module Network.Polkadot.Storage where + +import Cases (camelize) +import Control.Arrow ((&&&)) +import Data.ByteArray (convert) +import Data.ByteArray.HexString (HexString) +import Data.Char (toLower) +import Data.Map.Strict (Map) +import qualified Data.Map.Strict as Map (fromList, lookup) +import Data.Maybe (mapMaybe) +import Data.Text (Text) +import qualified Data.Text as T (cons, head, tail) + +import Network.Polkadot.Metadata.V13 (Metadata (modules), + ModuleMetadata (..), + StorageEntryMetadata (..), + StorageMetadata (..)) +import Network.Polkadot.Storage.Key (Argument, StorageEntry (..), + newEntry) + +-- | Runtime storage is a set of named modules. +type Storage = Map Text ModuleStorage + +-- | Each module store data in a set of named entries. +type ModuleStorage = Map Text StorageEntry + +-- | Create 'Storage' abstraction from runtime metadata. +fromMetadata :: Metadata + -- ^ Runtime metadata (latest version). + -> Storage + -- ^ Storage entities. +fromMetadata = Map.fromList . mapMaybe go . modules + where + toLowerFirst = uncurry T.cons . (toLower . T.head &&& T.tail) + go ModuleMetadata{..} = do + StorageMetadata prefix items <- moduleStorage + let section = camelize moduleName + toEntry meta@StorageEntryMetadata{..} = + (toLowerFirst entryName, newEntry prefix meta) + return (toLowerFirst section, Map.fromList $ fmap toEntry items) + +-- | Create storage key for given parameters. +storageKey :: Storage + -- ^ Storage entities. + -> Text + -- ^ Module name. + -> Text + -- ^ Storage method name. + -> [Argument] + -- ^ Arguments (for mappings). + -> Maybe HexString + -- ^ Raw storage key. If module or method was not found + -- or wrong number of arguments - returns 'Nothing'. +storageKey store section method args = convert <$> do + entry <- Map.lookup method =<< Map.lookup section store + case entry of + PlainEntry x -> Just x + MapEntry f -> case args of + [a] -> Just (f a) + _ -> Nothing + DoubleMapEntry f -> case args of + [a, b] -> Just (f a b) + _ -> Nothing diff --git a/packages/polkadot/src/Network/Polkadot/Storage/Key.hs b/packages/polkadot/src/Network/Polkadot/Storage/Key.hs new file mode 100644 index 00000000..21d717ca --- /dev/null +++ b/packages/polkadot/src/Network/Polkadot/Storage/Key.hs @@ -0,0 +1,94 @@ +{-# LANGUAGE GADTs #-} +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Network.Polkadot.Storage.Key +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- When you use the Substrate RPC to access a storage item, +-- you only need to provide the key associated with that item. +-- + +module Network.Polkadot.Storage.Key where + +import Codec.Scale (encode) +import Codec.Scale.Class (Encode (..)) +import Control.Arrow ((&&&)) +import Data.ByteString (ByteString) +import Data.Digest.Blake2 (blake2_128, blake2_256) +import Data.Digest.XXHash (xxhash) +import Data.Text (Text) +import Data.Text.Encoding (encodeUtf8) + +import Network.Polkadot.Metadata.V11 (DoubleMapType (..), + MapType (..), + StorageHasher (..)) +import Network.Polkadot.Metadata.V13 (NMapType (..), + StorageEntryMetadata (..), + StorageEntryType (..)) + +-- | General type wrapper for SCALE encodable storage index argument. +data Argument where + Argument :: Encode a => a -> Argument + -- ^ Wrapped type should be encodable. + +instance Encode Argument where + put arg = case arg of Argument a -> put a + +-- | Hasher is a function that hash given argument. +type Hasher = Argument -> ByteString + +-- | Entry type describe storage prefix for different storage entity types. +data StorageEntry + = PlainEntry ByteString + -- ^ Simple storage type without arguments. + | MapEntry (Argument -> ByteString) + -- ^ Mapping with hashing for arguments. + | DoubleMapEntry (Argument -> Argument -> ByteString) + -- ^ Double map with two different hashers. + | NMapEntry ([Argument] -> ByteString) + -- ^ Map with array of hashers. + +instance Show StorageEntry where + show (PlainEntry _) = "PlainEntry" + show (MapEntry _) = "MapEntry" + show (DoubleMapEntry _) = "DoubleMapEntry" + show (NMapEntry _) = "NMapEntry" + +-- | Create storage key generator from metadata description. +newEntry :: Text + -- ^ Storage prefix (module name). + -> StorageEntryMetadata + -- ^ Storage key metadata, includes entry type, name, etc. + -> StorageEntry + -- ^ Storage key generator. +newEntry prefix meta = case entryType meta of + Plain _ -> PlainEntry plainKey + Map MapType{..} -> MapEntry (mapCodec mapHasher) + DoubleMap DoubleMapType{..} -> DoubleMapEntry (dMapCodec doubleMapHasher doubleMapKey2Hasher) + NMap NMapType{..} -> NMapEntry undefined -- TODO + where + method = entryName meta + -- To calculate the key for a simple Storage Value, + -- take the TwoX 128 hash of the name of the module that contains the Storage Value + -- and append to it the TwoX 128 hash of the name of the Storage Value itself. + plainKey = xxhash 128 (encodeUtf8 prefix) <> xxhash 128 (encodeUtf8 method) + -- Like Storage Values, the keys for Storage Maps are equal to the TwoX 128 hash + -- of the name of the module that contains the map prepended to the TwoX 128 hash + -- of the name of the Storage Map itself. + mapCodec h1 arg1 = plainKey <> getHasher h1 arg1 + dMapCodec h1 h2 arg1 arg2 = mapCodec h1 arg1 <> getHasher h2 arg2 + +getHasher :: StorageHasher -> Hasher +getHasher Blake2_128 = blake2_128 . encode +getHasher Blake2_256 = blake2_256 . encode +getHasher Blake2_128Concat = uncurry (<>) . (blake2_128 &&& id) . encode +getHasher Twox128 = xxhash 128 . encode +getHasher Twox256 = xxhash 256 . encode +getHasher Twox64Concat = uncurry (<>) . (xxhash 64 &&& id) . encode +getHasher Identity = encode diff --git a/packages/polkadot/tests/Network/Polkadot/Test/AccountSpec.hs b/packages/polkadot/tests/Network/Polkadot/Test/AccountSpec.hs new file mode 100644 index 00000000..f697e7c8 --- /dev/null +++ b/packages/polkadot/tests/Network/Polkadot/Test/AccountSpec.hs @@ -0,0 +1,42 @@ +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Polkadot.Test.AccountSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- + +module Network.Polkadot.Test.AccountSpec where + +import Data.ByteArray.HexString.TH (hex) +import Test.Hspec + +import Network.Polkadot.Account +import Network.Polkadot.Crypto + +spec :: Spec +spec = parallel $ do + let alice :: Ecdsa + Right alice = from_seed [hex|0x8beef718111d62174809fc2b332c14471f6038404c5cee7b33ac2573ba60ed06|] + let bob :: Ed25519 + Right bob = from_seed [hex|0xbd4e72a17a76b43ab59e7733cd0818d47c2e0ebcf88bfc5fb0192c8ee520c7d1|] + + describe "Public" $ do + it "Ecdsa" $ + show (public alice) `shouldBe` "(2,0xc96289d7426111e7ec5cbb90d7d201ab0b3d7ab17166826ae4ff27cb0c6d3f23)" + it "Ed25519" $ + show (public bob) `shouldBe` "0x8a016b9a1ca3709974ed7b1e1c79d6ed0f795899d212edc189cdb31318fec607" + + describe "Ss58Codec" $ do + it "Ecdsa" $ + to_ss58check (into_account $ multi_signer alice) + `shouldBe` "5EWfGfxVbLK2upe3Zfcqo9ZtALArwLgxkwcZaT3gMujmmFxU" + it "Ed25519" $ + to_ss58check (into_account $ multi_signer bob) + `shouldBe` "5FBetQhjRiJMfqqMU3f4cz8ho4majAPLzuZSdmxwxPtQTZ8V" diff --git a/packages/polkadot/tests/Network/Polkadot/Test/ExtrinsicSpec.hs b/packages/polkadot/tests/Network/Polkadot/Test/ExtrinsicSpec.hs new file mode 100644 index 00000000..399a45ae --- /dev/null +++ b/packages/polkadot/tests/Network/Polkadot/Test/ExtrinsicSpec.hs @@ -0,0 +1,42 @@ +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Polkadot.Test.ExtrinsicSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- + +module Network.Polkadot.Test.ExtrinsicSpec where + +import Codec.Scale (Compact (..), decode) +import Data.ByteArray.HexString.TH (hex) +import Test.Hspec + +import Network.Polkadot.Extrinsic.Era (Era (..), new_mortal_compact) + +spec :: Spec +spec = parallel $ do + describe "Era" $ do + it "decodes an Extrinsic Era with immortal" $ + decode [hex|0x00|] `shouldBe` Right ImmortalEra + + it "creates from an actual valid era" $ + new_mortal_compact 0xc503 `shouldBe` MortalEra 64 60 + + it "creates for an actual era (2)" $ + new_mortal_compact 0x8502 `shouldBe` MortalEra 64 40 + + it "creates form an actual era (3)" $ + new_mortal_compact 0x6502 `shouldBe` MortalEra 64 38 + + it "creates from a actual 100 block hash count" $ + new_mortal_compact 0xd607 `shouldBe` MortalEra 128 125 + + it "creates from a actual 2400 block hash count" $ + new_mortal_compact 0x9be3 `shouldBe` MortalEra 4096 3641 diff --git a/packages/polkadot/tests/Network/Polkadot/Test/MetadataSpec.hs b/packages/polkadot/tests/Network/Polkadot/Test/MetadataSpec.hs new file mode 100644 index 00000000..ec601aef --- /dev/null +++ b/packages/polkadot/tests/Network/Polkadot/Test/MetadataSpec.hs @@ -0,0 +1,77 @@ +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Polkadot.Test.MetadataSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Polkadot metadata tests ported from: +-- https://github.com/polkadot-js/api/tree/master/packages/metadata/src/Metadata +-- + +module Network.Polkadot.Test.MetadataSpec where + +import Codec.Scale (decode, encode) +import Data.Aeson (eitherDecodeFileStrict, + parseJSON, toJSON) +import Data.ByteArray.HexString (HexString) +import Data.ByteArray.HexString.TH (hexFrom) +import Test.Hspec +import Test.Hspec.Expectations.Json (shouldBeJson) + +import Network.Polkadot.Metadata (Metadata, metadataTypes) +import Network.Polkadot.Metadata.MagicNumber (MagicNumber (..)) + +spec :: Spec +spec = parallel $ do + describe "MagicNumber codec" $ do + let empty_metadata = "0x6d65746109" :: HexString + wrong_version = "0x6d657461ff" :: HexString + wrong_magic = "0x6d64746110" :: HexString + + it "succeeds when the magic number matches" $ + let magic = decode empty_metadata + in magic `shouldBe` Right MagicNumber + + it "fails when the magic number mismatches" $ + let error_str = decode wrong_magic :: Either String Metadata + in error_str `shouldBe` Left "Failed reading: Bad magic number\nEmpty call stack\n" + + it "fails when version out of scope" $ + let error_str = decode wrong_version :: Either String Metadata + in error_str `shouldBe` Left "Failed reading: index out of enum constructors count: 241\nEmpty call stack\n" + + describe "Metadata V9" $ do + it "succeeds decode from hex and json" $ do + let (Right hex) = decode [hexFrom|tests/meta/v9.hex|] :: Either String Metadata + (meta, _) = metadataTypes hex + Right json <- eitherDecodeFileStrict "tests/meta/v9.json" + toJSON meta `shouldBeJson` json + + describe "Metadata V10" $ do + it "succeeds decode from hex and json" $ do + let (Right hex) = decode [hexFrom|tests/meta/v10.hex|] :: Either String Metadata + (meta, _) = metadataTypes hex + Right json <- eitherDecodeFileStrict "tests/meta/v10.json" + toJSON meta `shouldBeJson` json + +{- + describe "Metadata V12" $ do + it "succeeds decode from hex and json" $ do + let (Right hex) = decode [hexFrom|tests/meta/v12.hex|] :: Either String Metadata + (meta, _) = metadataTypes hex + Right json <- eitherDecodeFileStrict "tests/meta/v12.json" + toJSON meta `shouldBeJson` json + + describe "Metadata V13" $ do + it "succeeds decode from hex and json" $ do + let (Right hex) = decode [hexFrom|tests/meta/v13.hex|] :: Either String Metadata + (meta, _) = metadataTypes hex + Right json <- eitherDecodeFileStrict "tests/meta/v13.json" + toJSON meta `shouldBeJson` json +-} diff --git a/packages/polkadot/tests/Network/Polkadot/Test/StorageSpec.hs b/packages/polkadot/tests/Network/Polkadot/Test/StorageSpec.hs new file mode 100644 index 00000000..748f75b6 --- /dev/null +++ b/packages/polkadot/tests/Network/Polkadot/Test/StorageSpec.hs @@ -0,0 +1,30 @@ +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE QuasiQuotes #-} + +-- | +-- Module : Network.Polkadot.Test.StorageSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- + +module Network.Polkadot.Test.StorageSpec where + +import Codec.Scale (decode) +import Data.ByteArray.HexString.TH (hexFrom) +import Test.Hspec + +import Network.Polkadot.Metadata (Metadata, metadataTypes, toLatest) +import Network.Polkadot.Storage (fromMetadata) + +spec :: Spec +spec = parallel $ do + describe "Metadata Storage" $ do + it "decode and parse storage entries" $ do + let (Right hex) = decode [hexFrom|tests/meta/v13.hex|] :: Either String Metadata + (meta, _) = metadataTypes hex + show (fromMetadata (toLatest meta)) `shouldBe` "fromList [(\"assets\",fromList [(\"account\",DoubleMapEntry),(\"approvals\",NMapEntry),(\"asset\",MapEntry),(\"metadata\",MapEntry)]),(\"authorship\",fromList [(\"author\",PlainEntry),(\"didSetUncles\",PlainEntry),(\"uncles\",PlainEntry)]),(\"babe\",fromList [(\"authorVrfRandomness\",PlainEntry),(\"authorities\",PlainEntry),(\"currentSlot\",PlainEntry),(\"epochConfig\",PlainEntry),(\"epochIndex\",PlainEntry),(\"epochStart\",PlainEntry),(\"genesisSlot\",PlainEntry),(\"initialized\",PlainEntry),(\"lateness\",PlainEntry),(\"nextAuthorities\",PlainEntry),(\"nextEpochConfig\",PlainEntry),(\"nextRandomness\",PlainEntry),(\"pendingEpochConfigChange\",PlainEntry),(\"randomness\",PlainEntry),(\"segmentIndex\",PlainEntry),(\"underConstruction\",MapEntry)]),(\"balances\",fromList [(\"account\",MapEntry),(\"locks\",MapEntry),(\"reserves\",MapEntry),(\"storageVersion\",PlainEntry),(\"totalIssuance\",PlainEntry)]),(\"bounties\",fromList [(\"bounties\",MapEntry),(\"bountyApprovals\",PlainEntry),(\"bountyCount\",PlainEntry),(\"bountyDescriptions\",MapEntry)]),(\"contracts\",fromList [(\"accountCounter\",PlainEntry),(\"codeStorage\",MapEntry),(\"contractInfoOf\",MapEntry),(\"deletionQueue\",PlainEntry),(\"pristineCode\",MapEntry)]),(\"council\",fromList [(\"members\",PlainEntry),(\"prime\",PlainEntry),(\"proposalCount\",PlainEntry),(\"proposalOf\",MapEntry),(\"proposals\",PlainEntry),(\"voting\",MapEntry)]),(\"democracy\",fromList [(\"blacklist\",MapEntry),(\"cancellations\",MapEntry),(\"depositOf\",MapEntry),(\"lastTabledWasExternal\",PlainEntry),(\"locks\",MapEntry),(\"lowestUnbaked\",PlainEntry),(\"nextExternal\",PlainEntry),(\"preimages\",MapEntry),(\"publicPropCount\",PlainEntry),(\"publicProps\",PlainEntry),(\"referendumCount\",PlainEntry),(\"referendumInfoOf\",MapEntry),(\"storageVersion\",PlainEntry),(\"votingOf\",MapEntry)]),(\"electionProviderMultiPhase\",fromList [(\"currentPhase\",PlainEntry),(\"desiredTargets\",PlainEntry),(\"minimumUntrustedScore\",PlainEntry),(\"queuedSolution\",PlainEntry),(\"round\",PlainEntry),(\"signedSubmissionIndices\",PlainEntry),(\"signedSubmissionNextIndex\",PlainEntry),(\"signedSubmissionsMap\",MapEntry),(\"snapshot\",PlainEntry),(\"snapshotMetadata\",PlainEntry)]),(\"elections\",fromList [(\"candidates\",PlainEntry),(\"electionRounds\",PlainEntry),(\"members\",PlainEntry),(\"runnersUp\",PlainEntry),(\"voting\",MapEntry)]),(\"gilt\",fromList [(\"active\",MapEntry),(\"activeTotal\",PlainEntry),(\"queueTotals\",PlainEntry),(\"queues\",MapEntry)]),(\"grandpa\",fromList [(\"currentSetId\",PlainEntry),(\"nextForced\",PlainEntry),(\"pendingChange\",PlainEntry),(\"setIdSession\",MapEntry),(\"stalled\",PlainEntry),(\"state\",PlainEntry)]),(\"identity\",fromList [(\"identityOf\",MapEntry),(\"registrars\",PlainEntry),(\"subsOf\",MapEntry),(\"superOf\",MapEntry)]),(\"imOnline\",fromList [(\"authoredBlocks\",DoubleMapEntry),(\"heartbeatAfter\",PlainEntry),(\"keys\",PlainEntry),(\"receivedHeartbeats\",DoubleMapEntry)]),(\"indices\",fromList [(\"accounts\",MapEntry)]),(\"lottery\",fromList [(\"callIndices\",PlainEntry),(\"lottery\",PlainEntry),(\"lotteryIndex\",PlainEntry),(\"participants\",MapEntry),(\"tickets\",MapEntry),(\"ticketsCount\",PlainEntry)]),(\"mmr\",fromList [(\"nodes\",MapEntry),(\"numberOfLeaves\",PlainEntry),(\"rootHash\",PlainEntry)]),(\"multisig\",fromList [(\"calls\",MapEntry),(\"multisigs\",DoubleMapEntry)]),(\"offences\",fromList [(\"concurrentReportsIndex\",DoubleMapEntry),(\"reports\",MapEntry),(\"reportsByKindIndex\",MapEntry)]),(\"proxy\",fromList [(\"announcements\",MapEntry),(\"proxies\",MapEntry)]),(\"randomnessCollectiveFlip\",fromList [(\"randomMaterial\",PlainEntry)]),(\"recovery\",fromList [(\"activeRecoveries\",DoubleMapEntry),(\"proxy\",MapEntry),(\"recoverable\",MapEntry)]),(\"scheduler\",fromList [(\"agenda\",MapEntry),(\"lookup\",MapEntry),(\"storageVersion\",PlainEntry)]),(\"session\",fromList [(\"currentIndex\",PlainEntry),(\"disabledValidators\",PlainEntry),(\"keyOwner\",MapEntry),(\"nextKeys\",MapEntry),(\"queuedChanged\",PlainEntry),(\"queuedKeys\",PlainEntry),(\"validators\",PlainEntry)]),(\"society\",fromList [(\"bids\",PlainEntry),(\"candidates\",PlainEntry),(\"defender\",PlainEntry),(\"defenderVotes\",MapEntry),(\"founder\",PlainEntry),(\"head\",PlainEntry),(\"maxMembers\",PlainEntry),(\"members\",PlainEntry),(\"payouts\",MapEntry),(\"pot\",PlainEntry),(\"rules\",PlainEntry),(\"strikes\",MapEntry),(\"suspendedCandidates\",MapEntry),(\"suspendedMembers\",MapEntry),(\"votes\",DoubleMapEntry),(\"vouching\",MapEntry)]),(\"staking\",fromList [(\"activeEra\",PlainEntry),(\"bonded\",MapEntry),(\"bondedEras\",PlainEntry),(\"canceledSlashPayout\",PlainEntry),(\"chillThreshold\",PlainEntry),(\"counterForNominators\",PlainEntry),(\"counterForValidators\",PlainEntry),(\"currentEra\",PlainEntry),(\"currentPlannedSession\",PlainEntry),(\"earliestUnappliedSlash\",PlainEntry),(\"erasRewardPoints\",MapEntry),(\"erasStakers\",DoubleMapEntry),(\"erasStakersClipped\",DoubleMapEntry),(\"erasStartSessionIndex\",MapEntry),(\"erasTotalStake\",MapEntry),(\"erasValidatorPrefs\",DoubleMapEntry),(\"erasValidatorReward\",MapEntry),(\"forceEra\",PlainEntry),(\"historyDepth\",PlainEntry),(\"invulnerables\",PlainEntry),(\"ledger\",MapEntry),(\"maxNominatorsCount\",PlainEntry),(\"maxValidatorsCount\",PlainEntry),(\"minNominatorBond\",PlainEntry),(\"minValidatorBond\",PlainEntry),(\"minimumValidatorCount\",PlainEntry),(\"nominatorSlashInEra\",DoubleMapEntry),(\"nominators\",MapEntry),(\"payee\",MapEntry),(\"slashRewardFraction\",PlainEntry),(\"slashingSpans\",MapEntry),(\"spanSlash\",MapEntry),(\"storageVersion\",PlainEntry),(\"unappliedSlashes\",MapEntry),(\"validatorCount\",PlainEntry),(\"validatorSlashInEra\",DoubleMapEntry),(\"validators\",MapEntry)]),(\"sudo\",fromList [(\"key\",PlainEntry)]),(\"system\",fromList [(\"account\",MapEntry),(\"allExtrinsicsLen\",PlainEntry),(\"blockHash\",MapEntry),(\"blockWeight\",PlainEntry),(\"digest\",PlainEntry),(\"eventCount\",PlainEntry),(\"eventTopics\",MapEntry),(\"events\",PlainEntry),(\"executionPhase\",PlainEntry),(\"extrinsicCount\",PlainEntry),(\"extrinsicData\",MapEntry),(\"lastRuntimeUpgrade\",PlainEntry),(\"number\",PlainEntry),(\"parentHash\",PlainEntry),(\"upgradedToTripleRefCount\",PlainEntry),(\"upgradedToU32RefCount\",PlainEntry)]),(\"technicalCommittee\",fromList [(\"members\",PlainEntry),(\"prime\",PlainEntry),(\"proposalCount\",PlainEntry),(\"proposalOf\",MapEntry),(\"proposals\",PlainEntry),(\"voting\",MapEntry)]),(\"technicalMembership\",fromList [(\"members\",PlainEntry),(\"prime\",PlainEntry)]),(\"timestamp\",fromList [(\"didUpdate\",PlainEntry),(\"now\",PlainEntry)]),(\"tips\",fromList [(\"reasons\",MapEntry),(\"tips\",MapEntry)]),(\"transactionPayment\",fromList [(\"nextFeeMultiplier\",PlainEntry),(\"storageVersion\",PlainEntry)]),(\"transactionStorage\",fromList [(\"blockTransactions\",PlainEntry),(\"byteFee\",PlainEntry),(\"chunkCount\",MapEntry),(\"entryFee\",PlainEntry),(\"maxBlockTransactions\",PlainEntry),(\"maxTransactionSize\",PlainEntry),(\"proofChecked\",PlainEntry),(\"storagePeriod\",PlainEntry),(\"transactions\",MapEntry)]),(\"treasury\",fromList [(\"approvals\",PlainEntry),(\"proposalCount\",PlainEntry),(\"proposals\",MapEntry)]),(\"uniques\",fromList [(\"account\",NMapEntry),(\"asset\",DoubleMapEntry),(\"attribute\",NMapEntry),(\"class\",MapEntry),(\"classMetadataOf\",MapEntry),(\"instanceMetadataOf\",DoubleMapEntry)]),(\"vesting\",fromList [(\"vesting\",MapEntry)])]" diff --git a/packages/polkadot/tests/Spec.hs b/packages/polkadot/tests/Spec.hs new file mode 100644 index 00000000..a824f8c3 --- /dev/null +++ b/packages/polkadot/tests/Spec.hs @@ -0,0 +1 @@ +{-# OPTIONS_GHC -F -pgmF hspec-discover #-} diff --git a/packages/polkadot/tests/meta/v10.hex b/packages/polkadot/tests/meta/v10.hex new file mode 100644 index 00000000..e403b831 --- /dev/null +++ b/packages/polkadot/tests/meta/v10.hex @@ -0,0 +1 @@ +0x6d6574610a6c1853797374656d011853797374656d34304163636f756e744e6f6e636501010130543a3a4163636f756e74496420543a3a496e646578001000000000047c2045787472696e73696373206e6f6e636520666f72206163636f756e74732e3845787472696e736963436f756e7400000c753332040004b820546f74616c2065787472696e7369637320636f756e7420666f72207468652063757272656e7420626c6f636b2e4c416c6c45787472696e73696373576569676874000018576569676874040004150120546f74616c2077656967687420666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e40416c6c45787472696e736963734c656e00000c753332040004410120546f74616c206c656e6774682028696e2062797465732920666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e24426c6f636b4861736801010138543a3a426c6f636b4e756d6265721c543a3a48617368008000000000000000000000000000000000000000000000000000000000000000000498204d6170206f6620626c6f636b206e756d6265727320746f20626c6f636b206861736865732e3445787472696e736963446174610101010c7533321c5665633c75383e000400043d012045787472696e73696373206461746120666f72207468652063757272656e7420626c6f636b20286d61707320616e2065787472696e736963277320696e64657820746f206974732064617461292e184e756d626572010038543a3a426c6f636b4e756d6265721000000000040901205468652063757272656e7420626c6f636b206e756d626572206265696e672070726f6365737365642e205365742062792060657865637574655f626c6f636b602e28506172656e744861736801001c543a3a4861736880000000000000000000000000000000000000000000000000000000000000000004702048617368206f66207468652070726576696f757320626c6f636b2e3845787472696e73696373526f6f7401001c543a3a486173688000000000000000000000000000000000000000000000000000000000000000000415012045787472696e7369637320726f6f74206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e1844696765737401002c4469676573744f663c543e040004f020446967657374206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e184576656e747301008c5665633c4576656e745265636f72643c543a3a4576656e742c20543a3a486173683e3e040004a0204576656e7473206465706f736974656420666f72207468652063757272656e7420626c6f636b2e284576656e74436f756e740100284576656e74496e646578100000000004b820546865206e756d626572206f66206576656e747320696e2074686520604576656e74733c543e60206c6973742e2c4576656e74546f706963730101011c543a3a48617368845665633c28543a3a426c6f636b4e756d6265722c204576656e74496e646578293e000400282501204d617070696e67206265747765656e206120746f7069632028726570726573656e74656420627920543a3a486173682920616e64206120766563746f72206f6620696e646578657394206f66206576656e747320696e2074686520603c4576656e74733c543e3e60206c6973742e00510120416c6c20746f70696320766563746f727320686176652064657465726d696e69737469632073746f72616765206c6f636174696f6e7320646570656e64696e67206f6e2074686520746f7069632e2054686973450120616c6c6f7773206c696768742d636c69656e747320746f206c6576657261676520746865206368616e67657320747269652073746f7261676520747261636b696e67206d656368616e69736d20616e64e420696e2063617365206f66206368616e67657320666574636820746865206c697374206f66206576656e7473206f6620696e7465726573742e004d01205468652076616c756520686173207468652074797065206028543a3a426c6f636b4e756d6265722c204576656e74496e646578296020626563617573652069662077652075736564206f6e6c79206a7573744d012074686520604576656e74496e64657860207468656e20696e20636173652069662074686520746f70696320686173207468652073616d6520636f6e74656e7473206f6e20746865206e65787420626c6f636b0101206e6f206e6f74696669636174696f6e2077696c6c20626520747269676765726564207468757320746865206576656e74206d69676874206265206c6f73742e01242866696c6c5f626c6f636b0004210120412062696720646973706174636820746861742077696c6c20646973616c6c6f7720616e79206f74686572207472616e73616374696f6e20746f20626520696e636c756465642e1872656d61726b041c5f72656d61726b1c5665633c75383e046c204d616b6520736f6d65206f6e2d636861696e2072656d61726b2e387365745f686561705f7061676573041470616765730c75363404fc2053657420746865206e756d626572206f6620706167657320696e2074686520576562417373656d626c7920656e7669726f6e6d656e74277320686561702e207365745f636f64650410636f64651c5665633c75383e04682053657420746865206e65772072756e74696d6520636f64652e5c7365745f636f64655f776974686f75745f636865636b730410636f64651c5665633c75383e041d012053657420746865206e65772072756e74696d6520636f646520776974686f757420646f696e6720616e7920636865636b73206f662074686520676976656e2060636f6465602e5c7365745f6368616e6765735f747269655f636f6e666967044c6368616e6765735f747269655f636f6e666967804f7074696f6e3c4368616e67657354726965436f6e66696775726174696f6e3e04a02053657420746865206e6577206368616e676573207472696520636f6e66696775726174696f6e2e2c7365745f73746f7261676504146974656d73345665633c4b657956616c75653e046c2053657420736f6d65206974656d73206f662073746f726167652e306b696c6c5f73746f7261676504106b657973205665633c4b65793e0478204b696c6c20736f6d65206974656d732066726f6d2073746f726167652e2c6b696c6c5f70726566697804187072656669780c4b6579041501204b696c6c20616c6c2073746f72616765206974656d7320776974682061206b657920746861742073746172747320776974682074686520676976656e207072656669782e01084045787472696e7369635375636365737304304469737061746368496e666f049420416e2065787472696e73696320636f6d706c65746564207375636365737366756c6c792e3c45787472696e7369634661696c6564083444697370617463684572726f72304469737061746368496e666f045420416e2065787472696e736963206661696c65642e00143c496e76616c6964537065634e616d6508150120546865206e616d65206f662073706563696669636174696f6e20646f6573206e6f74206d61746368206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e7c5370656356657273696f6e4e6f74416c6c6f776564546f4465637265617365084501205468652073706563696669636174696f6e2076657273696f6e206973206e6f7420616c6c6f77656420746f206465637265617365206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e7c496d706c56657273696f6e4e6f74416c6c6f776564546f44656372656173650849012054686520696d706c656d656e746174696f6e2076657273696f6e206973206e6f7420616c6c6f77656420746f206465637265617365206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e7c537065634f72496d706c56657273696f6e4e656564546f496e637265617365083501205468652073706563696669636174696f6e206f722074686520696d706c656d656e746174696f6e2076657273696f6e206e65656420746f20696e637265617365206265747765656e20746865942063757272656e742072756e74696d6520616e6420746865206e65772072756e74696d652e744661696c6564546f4578747261637452756e74696d6556657273696f6e0cf0204661696c656420746f2065787472616374207468652072756e74696d652076657273696f6e2066726f6d20746865206e65772072756e74696d652e000d01204569746865722063616c6c696e672060436f72655f76657273696f6e60206f72206465636f64696e67206052756e74696d6556657273696f6e60206661696c65642e1c5574696c697479011c5574696c69747904244d756c74697369677300020530543a3a4163636f756e744964205b75383b2033325dd04d756c74697369673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e02040004942054686520736574206f66206f70656e206d756c7469736967206f7065726174696f6e732e0114146261746368041463616c6c735c5665633c3c542061732054726169743e3a3a43616c6c3e48802053656e642061206261746368206f662064697370617463682063616c6c732e00ec20546869732077696c6c206578656375746520756e74696c20746865206669727374206f6e65206661696c7320616e64207468656e2073746f702e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e002c2023203c7765696768743ea4202d205468652073756d206f66207468652077656967687473206f6620746865206063616c6c73602e34202d204f6e65206576656e742e302023203c2f7765696768743e00590120546869732077696c6c2072657475726e20604f6b6020696e20616c6c2063697263756d7374616e6365732e20546f2064657465726d696e65207468652073756363657373206f66207468652062617463682c20616e3501206576656e74206973206465706f73697465642e20496620612063616c6c206661696c656420616e64207468652062617463682077617320696e7465727275707465642c207468656e20746865590120604261746368496e74657272757074656460206576656e74206973206465706f73697465642c20616c6f6e67207769746820746865206e756d626572206f66207375636365737366756c2063616c6c73206d616465510120616e6420746865206572726f72206f6620746865206661696c65642063616c6c2e20496620616c6c2077657265207375636365737366756c2c207468656e2074686520604261746368436f6d706c657465646050206576656e74206973206465706f73697465642e1861735f7375620814696e6465780c7531361063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e1ce02053656e6420612063616c6c207468726f75676820616e20696e64657865642070736575646f6e796d206f66207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e70202d2054686520776569676874206f6620746865206063616c6c602e302023203c2f7765696768743e2061735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e1063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3ea4590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e00b42049662074686572652061726520656e6f7567682c207468656e206469737061746368207468652063616c6c2e005101205061796d656e743a20604d756c74697369674465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573610120607468726573686f6c64602074696d657320604d756c74697369674465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e002101204e4f54453a20556e6c6573732074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2067656e6572616c6c792077616e7420746f207573651d012060617070726f76655f61735f6d756c74696020696e73746561642c2073696e6365206974206f6e6c7920726571756972657320612068617368206f66207468652063616c6c2e005d0120526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c7420696620607468726573686f6c64602069732065786163746c79206031602e204f74686572776973655901206f6e20737563636573732c20726573756c7420697320604f6b6020616e642074686520726573756c742066726f6d2074686520696e746572696f722063616c6c2c206966206974207761732065786563757465642ce0206d617920626520666f756e6420696e20746865206465706f736974656420604d756c7469736967457865637574656460206576656e742e002c2023203c7765696768743e54202d20604f2853202b205a202b2043616c6c29602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2e2501202d204f6e652063616c6c20656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285a296020776865726520605a602069732074782d6c656e2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e70202d2054686520776569676874206f6620746865206063616c6c602e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66f4202020604d756c74697369674465706f73697442617365202b207468726573686f6c64202a204d756c74697369674465706f736974466163746f72602e302023203c2f7765696768743e40617070726f76655f61735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e2463616c6c5f68617368205b75383b2033325d80590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e005101205061796d656e743a20604d756c74697369674465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573610120607468726573686f6c64602074696d657320604d756c74697369674465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e003901204e4f54453a2049662074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2077616e7420746f20757365206061735f6d756c74696020696e73746561642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66f4202020604d756c74697369674465706f73697442617365202b207468726573686f6c64202a204d756c74697369674465706f736974466163746f72602e302023203c2f7765696768743e3c63616e63656c5f61735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e2474696d65706f696e746454696d65706f696e743c543a3a426c6f636b4e756d6265723e2463616c6c5f68617368205b75383b2033325d5859012043616e63656c2061207072652d6578697374696e672c206f6e2d676f696e67206d756c7469736967207472616e73616374696f6e2e20416e79206465706f7369742072657365727665642070726576696f75736c79c820666f722074686973206f7065726174696f6e2077696c6c20626520756e7265736572766564206f6e20737563636573732e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e6101202d206074696d65706f696e74603a205468652074696d65706f696e742028626c6f636b206e756d62657220616e64207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c7c207472616e73616374696f6e20666f7220746869732064697370617463682ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602e34202d204f6e65206576656e742e88202d20492f4f3a2031207265616420604f285329602c206f6e652072656d6f76652e74202d2053746f726167653a2072656d6f766573206f6e65206974656d2e302023203c2f7765696768743e0118404261746368496e746572727570746564080c7533323444697370617463684572726f72085901204261746368206f66206469737061746368657320646964206e6f7420636f6d706c6574652066756c6c792e20496e646578206f66206669727374206661696c696e6720646973706174636820676976656e2c2061734c2077656c6c20617320746865206572726f722e384261746368436f6d706c657465640004cc204261746368206f66206469737061746368657320636f6d706c657465642066756c6c792077697468206e6f206572726f722e2c4e65774d756c746973696708244163636f756e744964244163636f756e7449640849012041206e6577206d756c7469736967206f7065726174696f6e2068617320626567756e2e20466972737420706172616d20697320746865206163636f756e74207468617420697320617070726f76696e672c80207365636f6e6420697320746865206d756c7469736967206163636f756e742e404d756c7469736967417070726f76616c0c244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449640859012041206d756c7469736967206f7065726174696f6e20686173206265656e20617070726f76656420627920736f6d656f6e652e20466972737420706172616d20697320746865206163636f756e742074686174206973a820617070726f76696e672c20746869726420697320746865206d756c7469736967206163636f756e742e404d756c7469736967457865637574656410244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e744964384469737061746368526573756c74082d012041206d756c7469736967206f7065726174696f6e20686173206265656e2065786563757465642e20466972737420706172616d20697320746865206163636f756e742074686174206973a820617070726f76696e672c20746869726420697320746865206d756c7469736967206163636f756e742e444d756c746973696743616e63656c6c65640c244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449640831012041206d756c7469736967206f7065726174696f6e20686173206265656e2063616e63656c6c65642e20466972737420706172616d20697320746865206163636f756e742074686174206973ac2063616e63656c6c696e672c20746869726420697320746865206d756c7469736967206163636f756e742e00001042616265011042616265242845706f6368496e64657801000c75363420000000000000000004542043757272656e742065706f636820696e6465782e2c417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e0400046c2043757272656e742065706f636820617574686f7269746965732e2c47656e65736973536c6f7401000c75363420000000000000000008f82054686520736c6f74206174207768696368207468652066697273742065706f63682061637475616c6c7920737461727465642e205468697320697320309020756e74696c2074686520666972737420626c6f636b206f662074686520636861696e2e2c43757272656e74536c6f7401000c75363420000000000000000004542043757272656e7420736c6f74206e756d6265722e2852616e646f6d6e6573730100205b75383b2033325d80000000000000000000000000000000000000000000000000000000000000000028b8205468652065706f63682072616e646f6d6e65737320666f7220746865202a63757272656e742a2065706f63682e002c20232053656375726974790005012054686973204d555354204e4f54206265207573656420666f722067616d626c696e672c2061732069742063616e20626520696e666c75656e6365642062792061f8206d616c6963696f75732076616c696461746f7220696e207468652073686f7274207465726d2e204974204d4159206265207573656420696e206d616e7915012063727970746f677261706869632070726f746f636f6c732c20686f77657665722c20736f206c6f6e67206173206f6e652072656d656d6265727320746861742074686973150120286c696b652065766572797468696e6720656c7365206f6e2d636861696e29206974206973207075626c69632e20466f72206578616d706c652c2069742063616e206265050120757365642077686572652061206e756d626572206973206e656564656420746861742063616e6e6f742068617665206265656e2063686f73656e20627920616e0d01206164766572736172792c20666f7220707572706f7365732073756368206173207075626c69632d636f696e207a65726f2d6b6e6f776c656467652070726f6f66732e384e65787452616e646f6d6e6573730100205b75383b2033325d800000000000000000000000000000000000000000000000000000000000000000045c204e6578742065706f63682072616e646f6d6e6573732e305365676d656e74496e64657801000c7533321000000000247c2052616e646f6d6e65737320756e64657220636f6e737472756374696f6e2e00f4205765206d616b6520612074726164656f6666206265747765656e2073746f7261676520616363657373657320616e64206c697374206c656e6774682e01012057652073746f72652074686520756e6465722d636f6e737472756374696f6e2072616e646f6d6e65737320696e207365676d656e7473206f6620757020746f942060554e4445525f434f4e535452554354494f4e5f5345474d454e545f4c454e475448602e00ec204f6e63652061207365676d656e7420726561636865732074686973206c656e6774682c20776520626567696e20746865206e657874206f6e652e090120576520726573657420616c6c207365676d656e747320616e642072657475726e20746f206030602061742074686520626567696e6e696e67206f662065766572791c2065706f63682e44556e646572436f6e737472756374696f6e0101010c753332345665633c5b75383b2033325d3e000400002c496e697469616c697a65640000204d6179626556726604000801012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e292077686963682069732060536f6d65601d01206966207065722d626c6f636b20696e697469616c697a6174696f6e2068617320616c7265616479206265656e2063616c6c656420666f722063757272656e7420626c6f636b2e010000083445706f63684475726174696f6e0c75363420c800000000000000080d0120546865206e756d626572206f66202a2a736c6f74732a2a207468617420616e2065706f63682074616b65732e20576520636f75706c652073657373696f6e7320746ffc2065706f6368732c20692e652e2077652073746172742061206e65772073657373696f6e206f6e636520746865206e65772065706f636820626567696e732e444578706563746564426c6f636b54696d6524543a3a4d6f6d656e7420b80b00000000000014050120546865206578706563746564206176657261676520626c6f636b2074696d6520617420776869636820424142452073686f756c64206265206372656174696e67110120626c6f636b732e2053696e636520424142452069732070726f626162696c6973746963206974206973206e6f74207472697669616c20746f20666967757265206f75740501207768617420746865206578706563746564206176657261676520626c6f636b2074696d652073686f756c64206265206261736564206f6e2074686520736c6f740901206475726174696f6e20616e642074686520736563757269747920706172616d657465722060636020287768657265206031202d20636020726570726573656e7473a0207468652070726f626162696c697479206f66206120736c6f74206265696e6720656d707479292e002454696d657374616d70012454696d657374616d70080c4e6f77010024543a3a4d6f6d656e7420000000000000000004902043757272656e742074696d6520666f72207468652063757272656e7420626c6f636b2e24446964557064617465010010626f6f6c040004b420446964207468652074696d657374616d7020676574207570646174656420696e207468697320626c6f636b3f01040c736574040c6e6f7748436f6d706163743c543a3a4d6f6d656e743e245820536574207468652063757272656e742074696d652e00590120546869732063616c6c2073686f756c6420626520696e766f6b65642065786163746c79206f6e63652070657220626c6f636b2e2049742077696c6c2070616e6963206174207468652066696e616c697a6174696f6ed82070686173652c20696620746869732063616c6c206861736e2774206265656e20696e766f6b656420627920746861742074696d652e004501205468652074696d657374616d702073686f756c642062652067726561746572207468616e207468652070726576696f7573206f6e652062792074686520616d6f756e74207370656369666965642062794420604d696e696d756d506572696f64602e00d820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060496e686572656e74602e0004344d696e696d756d506572696f6424543a3a4d6f6d656e7420dc0500000000000010690120546865206d696e696d756d20706572696f64206265747765656e20626c6f636b732e204265776172652074686174207468697320697320646966666572656e7420746f20746865202a65787065637465642a20706572696f64690120746861742074686520626c6f636b2070726f64756374696f6e206170706172617475732070726f76696465732e20596f75722063686f73656e20636f6e73656e7375732073797374656d2077696c6c2067656e6572616c6c79650120776f726b2077697468207468697320746f2064657465726d696e6520612073656e7369626c6520626c6f636b2074696d652e20652e672e20466f7220417572612c2069742077696c6c20626520646f75626c6520746869737020706572696f64206f6e2064656661756c742073657474696e67732e0028417574686f72736869700128417574686f72736869700c18556e636c65730100e85665633c556e636c65456e7472794974656d3c543a3a426c6f636b4e756d6265722c20543a3a486173682c20543a3a4163636f756e7449643e3e0400041c20556e636c657318417574686f72000030543a3a4163636f756e7449640400046420417574686f72206f662063757272656e7420626c6f636b2e30446964536574556e636c6573010010626f6f6c040004bc205768657468657220756e636c6573207765726520616c72656164792073657420696e207468697320626c6f636b2e0104287365745f756e636c657304286e65775f756e636c6573385665633c543a3a4865616465723e04642050726f76696465206120736574206f6620756e636c65732e00001c48496e76616c6964556e636c65506172656e74048c2054686520756e636c6520706172656e74206e6f7420696e2074686520636861696e2e40556e636c6573416c7265616479536574048420556e636c657320616c72656164792073657420696e2074686520626c6f636b2e34546f6f4d616e79556e636c6573044420546f6f206d616e7920756e636c65732e3047656e65736973556e636c6504582054686520756e636c652069732067656e657369732e30546f6f48696768556e636c6504802054686520756e636c6520697320746f6f206869676820696e20636861696e2e50556e636c65416c7265616479496e636c75646564047c2054686520756e636c6520697320616c726561647920696e636c756465642e204f6c64556e636c6504b82054686520756e636c652069736e277420726563656e7420656e6f75676820746f20626520696e636c756465642e1c496e6469636573011c496e6469636573082c4e657874456e756d53657401003c543a3a4163636f756e74496e6465781000000000047c20546865206e657874206672656520656e756d65726174696f6e207365742e1c456e756d5365740101013c543a3a4163636f756e74496e646578445665633c543a3a4163636f756e7449643e00040004582054686520656e756d65726174696f6e20736574732e010001043c4e65774163636f756e74496e64657808244163636f756e744964304163636f756e74496e64657810882041206e6577206163636f756e7420696e646578207761732061737369676e65642e0005012054686973206576656e74206973206e6f7420747269676765726564207768656e20616e206578697374696e6720696e64657820697320726561737369676e65646020746f20616e6f7468657220604163636f756e744964602e00002042616c616e636573012042616c616e6365731434546f74616c49737375616e6365010028543a3a42616c616e6365400000000000000000000000000000000004982054686520746f74616c20756e6974732069737375656420696e207468652073797374656d2e1c56657374696e6700010130543a3a4163636f756e744964ac56657374696e675363686564756c653c543a3a42616c616e63652c20543a3a426c6f636b4e756d6265723e00040004d820496e666f726d6174696f6e20726567617264696e67207468652076657374696e67206f66206120676976656e206163636f756e742e2c4672656542616c616e636501010130543a3a4163636f756e74496428543a3a42616c616e63650040000000000000000000000000000000002c9c20546865202766726565272062616c616e6365206f66206120676976656e206163636f756e742e004101205468697320697320746865206f6e6c792062616c616e63652074686174206d61747465727320696e207465726d73206f66206d6f7374206f7065726174696f6e73206f6e20746f6b656e732e204974750120616c6f6e65206973207573656420746f2064657465726d696e65207468652062616c616e6365207768656e20696e2074686520636f6e747261637420657865637574696f6e20656e7669726f6e6d656e742e205768656e207468697355012062616c616e63652066616c6c732062656c6f77207468652076616c7565206f6620604578697374656e7469616c4465706f736974602c207468656e20746865202763757272656e74206163636f756e74272069733d012064656c657465643a207370656369666963616c6c7920604672656542616c616e6365602e20467572746865722c2074686520604f6e4672656542616c616e63655a65726f602063616c6c6261636b450120697320696e766f6b65642c20676976696e672061206368616e636520746f2065787465726e616c206d6f64756c657320746f20636c65616e2075702064617461206173736f636961746564207769746854207468652064656c65746564206163636f756e742e00750120606672616d655f73797374656d3a3a4163636f756e744e6f6e63656020697320616c736f2064656c657465642069662060526573657276656442616c616e63656020697320616c736f207a65726f2028697420616c736f2067657473150120636f6c6c617073656420746f207a65726f2069662069742065766572206265636f6d6573206c657373207468616e20604578697374656e7469616c4465706f736974602e3c526573657276656442616c616e636501010130543a3a4163636f756e74496428543a3a42616c616e63650040000000000000000000000000000000002c75012054686520616d6f756e74206f66207468652062616c616e6365206f66206120676976656e206163636f756e7420746861742069732065787465726e616c6c792072657365727665643b20746869732063616e207374696c6c206765749c20736c61736865642c20627574206765747320736c6173686564206c617374206f6620616c6c2e006d0120546869732062616c616e63652069732061202772657365727665272062616c616e63652074686174206f746865722073756273797374656d732075736520696e206f7264657220746f2073657420617369646520746f6b656e732501207468617420617265207374696c6c20276f776e65642720627920746865206163636f756e7420686f6c6465722c20627574207768696368206172652073757370656e6461626c652e007501205768656e20746869732062616c616e63652066616c6c732062656c6f77207468652076616c7565206f6620604578697374656e7469616c4465706f736974602c207468656e2074686973202772657365727665206163636f756e7427b42069732064656c657465643a207370656369666963616c6c792c2060526573657276656442616c616e6365602e00650120606672616d655f73797374656d3a3a4163636f756e744e6f6e63656020697320616c736f2064656c6574656420696620604672656542616c616e63656020697320616c736f207a65726f2028697420616c736f2067657473190120636f6c6c617073656420746f207a65726f2069662069742065766572206265636f6d6573206c657373207468616e20604578697374656e7469616c4465706f736974602e29144c6f636b7301010130543a3a4163636f756e744964b05665633c42616c616e63654c6f636b3c543a3a42616c616e63652c20543a3a426c6f636b4e756d6265723e3e00040004b820416e79206c6971756964697479206c6f636b73206f6e20736f6d65206163636f756e742062616c616e6365732e0110207472616e736665720810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e64d8205472616e7366657220736f6d65206c697175696420667265652062616c616e636520746f20616e6f74686572206163636f756e742e00090120607472616e73666572602077696c6c207365742074686520604672656542616c616e636560206f66207468652073656e64657220616e642072656365697665722e21012049742077696c6c2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d2062792074686520605472616e73666572466565602e1501204966207468652073656e6465722773206163636f756e742069732062656c6f7720746865206578697374656e7469616c206465706f736974206173206120726573756c74b4206f6620746865207472616e736665722c20746865206163636f756e742077696c6c206265207265617065642e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605369676e65646020627920746865207472616e736163746f722e002c2023203c7765696768743e3101202d20446570656e64656e74206f6e20617267756d656e747320627574206e6f7420637269746963616c2c20676976656e2070726f70657220696d706c656d656e746174696f6e7320666f72cc202020696e70757420636f6e6669672074797065732e205365652072656c617465642066756e6374696f6e732062656c6f772e6901202d20497420636f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e642077726974657320696e7465726e616c6c7920616e64206e6f20636f6d706c657820636f6d7075746174696f6e2e004c2052656c617465642066756e6374696f6e733a0051012020202d2060656e737572655f63616e5f77697468647261776020697320616c776179732063616c6c656420696e7465726e616c6c792062757420686173206120626f756e64656420636f6d706c65786974792e2d012020202d205472616e7366657272696e672062616c616e63657320746f206163636f756e7473207468617420646964206e6f74206578697374206265666f72652077696c6c206361757365d420202020202060543a3a4f6e4e65774163636f756e743a3a6f6e5f6e65775f6163636f756e746020746f2062652063616c6c65642edc2020202d2052656d6f76696e6720656e6f7567682066756e64732066726f6d20616e206163636f756e742077696c6c20747269676765725901202020202060543a3a4475737452656d6f76616c3a3a6f6e5f756e62616c616e6365646020616e642060543a3a4f6e4672656542616c616e63655a65726f3a3a6f6e5f667265655f62616c616e63655f7a65726f602e49012020202d20607472616e736665725f6b6565705f616c6976656020776f726b73207468652073616d652077617920617320607472616e73666572602c206275742068617320616e206164646974696f6e616cf82020202020636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c20746865206f726967696e206163636f756e742e00302023203c2f7765696768743e2c7365745f62616c616e63650c0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365206e65775f667265654c436f6d706163743c543a3a42616c616e63653e306e65775f72657365727665644c436f6d706163743c543a3a42616c616e63653e349420536574207468652062616c616e636573206f66206120676976656e206163636f756e742e00210120546869732077696c6c20616c74657220604672656542616c616e63656020616e642060526573657276656442616c616e63656020696e2073746f726167652e2069742077696c6c090120616c736f2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d202860546f74616c49737375616e636560292e190120496620746865206e65772066726565206f722072657365727665642062616c616e63652069732062656c6f7720746865206578697374656e7469616c206465706f7369742c01012069742077696c6c20726573657420746865206163636f756e74206e6f6e63652028606672616d655f73797374656d3a3a4163636f756e744e6f6e636560292e00b420546865206469737061746368206f726967696e20666f7220746869732063616c6c2069732060726f6f74602e002c2023203c7765696768743e80202d20496e646570656e64656e74206f662074686520617267756d656e74732ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e302023203c2f7765696768743e38666f7263655f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e0851012045786163746c7920617320607472616e73666572602c2065786365707420746865206f726967696e206d75737420626520726f6f7420616e642074686520736f75726365206163636f756e74206d61792062652c207370656369666965642e4c7472616e736665725f6b6565705f616c6976650810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e1851012053616d6520617320746865205b607472616e73666572605d2063616c6c2c206275742077697468206120636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c2074686540206f726967696e206163636f756e742e00bc20393925206f66207468652074696d6520796f752077616e74205b607472616e73666572605d20696e73746561642e00c4205b607472616e73666572605d3a207374727563742e4d6f64756c652e68746d6c236d6574686f642e7472616e736665720114284e65774163636f756e7408244163636f756e7449641c42616c616e6365046c2041206e6577206163636f756e742077617320637265617465642e345265617065644163636f756e7408244163636f756e7449641c42616c616e6365045c20416e206163636f756e7420776173207265617065642e205472616e7366657210244163636f756e744964244163636f756e7449641c42616c616e63651c42616c616e636504b0205472616e7366657220737563636565646564202866726f6d2c20746f2c2076616c75652c2066656573292e2842616c616e63655365740c244163636f756e7449641c42616c616e63651c42616c616e636504c420412062616c616e6365207761732073657420627920726f6f74202877686f2c20667265652c207265736572766564292e1c4465706f73697408244163636f756e7449641c42616c616e636504dc20536f6d6520616d6f756e7420776173206465706f73697465642028652e672e20666f72207472616e73616374696f6e2066656573292e0c484578697374656e7469616c4465706f73697428543a3a42616c616e63654000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f206b65657020616e206163636f756e74206f70656e2e2c5472616e7366657246656528543a3a42616c616e6365400010a5d4e800000000000000000000000494205468652066656520726571756972656420746f206d616b652061207472616e736665722e2c4372656174696f6e46656528543a3a42616c616e6365400010a5d4e80000000000000000000000049c205468652066656520726571756972656420746f2063726561746520616e206163636f756e742e203856657374696e6742616c616e6365049c2056657374696e672062616c616e636520746f6f206869676820746f2073656e642076616c7565544c69717569646974795265737472696374696f6e7304c8204163636f756e74206c6971756964697479207265737472696374696f6e732070726576656e74207769746864726177616c204f766572666c6f77047420476f7420616e206f766572666c6f7720616674657220616464696e674c496e73756666696369656e7442616c616e636504782042616c616e636520746f6f206c6f7720746f2073656e642076616c7565484578697374656e7469616c4465706f73697404ec2056616c756520746f6f206c6f7720746f20637265617465206163636f756e742064756520746f206578697374656e7469616c206465706f736974244b656570416c6976650490205472616e736665722f7061796d656e7420776f756c64206b696c6c206163636f756e745c4578697374696e6756657374696e675363686564756c6504cc20412076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e742c446561644163636f756e74048c2042656e6566696369617279206163636f756e74206d757374207072652d6578697374485472616e73616374696f6e5061796d656e74012042616c616e63657304444e6578744665654d756c7469706c6965720100284d756c7469706c69657220000000000000000000000008485472616e73616374696f6e426173654665653042616c616e63654f663c543e400010a5d4e8000000000000000000000004dc205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b2074686520626173652e485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e001c5374616b696e67011c5374616b696e67683856616c696461746f72436f756e7401000c753332100000000004a82054686520696465616c206e756d626572206f66207374616b696e67207061727469636970616e74732e544d696e696d756d56616c696461746f72436f756e7401000c7533321004000000044101204d696e696d756d206e756d626572206f66207374616b696e67207061727469636970616e7473206265666f726520656d657267656e637920636f6e646974696f6e732061726520696d706f7365642e34496e76756c6e657261626c65730100445665633c543a3a4163636f756e7449643e04000c590120416e792076616c696461746f72732074686174206d6179206e6576657220626520736c6173686564206f7220666f726369626c79206b69636b65642e20497427732061205665632073696e636520746865792772654d01206561737920746f20696e697469616c697a6520616e642074686520706572666f726d616e636520686974206973206d696e696d616c2028776520657870656374206e6f206d6f7265207468616e20666f7572ac20696e76756c6e657261626c65732920616e64207265737472696374656420746f20746573746e6574732e18426f6e64656400010130543a3a4163636f756e74496430543a3a4163636f756e744964000400040101204d61702066726f6d20616c6c206c6f636b65642022737461736822206163636f756e747320746f2074686520636f6e74726f6c6c6572206163636f756e742e184c656467657200010130543a3a4163636f756e744964a45374616b696e674c65646765723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400044501204d61702066726f6d20616c6c2028756e6c6f636b6564292022636f6e74726f6c6c657222206163636f756e747320746f2074686520696e666f20726567617264696e6720746865207374616b696e672e14506179656501010130543a3a4163636f756e7449644452657761726444657374696e6174696f6e00040004e42057686572652074686520726577617264207061796d656e742073686f756c64206265206d6164652e204b657965642062792073746173682e2856616c696461746f727301010130543a3a4163636f756e7449643856616c696461746f72507265667301040004450120546865206d61702066726f6d202877616e6e616265292076616c696461746f72207374617368206b657920746f2074686520707265666572656e636573206f6620746861742076616c696461746f722e284e6f6d696e61746f727300010130543a3a4163636f756e744964644e6f6d696e6174696f6e733c543a3a4163636f756e7449643e01040010650120546865206d61702066726f6d206e6f6d696e61746f72207374617368206b657920746f2074686520736574206f66207374617368206b657973206f6620616c6c2076616c696461746f727320746f206e6f6d696e6174652e003501204e4f54453a206973207072697661746520736f20746861742077652063616e20656e73757265207570677261646564206265666f726520616c6c207479706963616c2061636365737365732ed8204469726563742073746f7261676520415049732063616e207374696c6c2062797061737320746869732070726f74656374696f6e2e1c5374616b65727301010130543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000c000000104d01204e6f6d696e61746f727320666f72206120706172746963756c6172206163636f756e74207468617420697320696e20616374696f6e207269676874206e6f772e20596f752063616e277420697465726174651901207468726f7567682076616c696461746f727320686572652c2062757420796f752063616e2066696e64207468656d20696e207468652053657373696f6e206d6f64756c652e00902054686973206973206b6579656420627920746865207374617368206163636f756e742e3843757272656e74456c65637465640100445665633c543a3a4163636f756e7449643e040004fc205468652063757272656e746c7920656c65637465642076616c696461746f7220736574206b65796564206279207374617368206163636f756e742049442e2843757272656e74457261010020457261496e6465781000000000045c205468652063757272656e742065726120696e6465782e3c43757272656e74457261537461727401002c4d6f6d656e744f663c543e200000000000000000047820546865207374617274206f66207468652063757272656e74206572612e6c43757272656e74457261537461727453657373696f6e496e64657801003053657373696f6e496e646578100000000004d0205468652073657373696f6e20696e646578206174207768696368207468652063757272656e742065726120737461727465642e5843757272656e74457261506f696e74734561726e6564010024457261506f696e7473140000000000040d01205265776172647320666f72207468652063757272656e74206572612e205573696e6720696e6469636573206f662063757272656e7420656c6563746564207365742e24536c6f745374616b6501003042616c616e63654f663c543e40000000000000000000000000000000000c31012054686520616d6f756e74206f662062616c616e6365206163746976656c79206174207374616b6520666f7220656163682076616c696461746f7220736c6f742c2063757272656e746c792e00c02054686973206973207573656420746f20646572697665207265776172647320616e642070756e6973686d656e74732e20466f72636545726101001c466f7263696e670400041d01205472756520696620746865206e6578742073657373696f6e206368616e67652077696c6c2062652061206e657720657261207265676172646c657373206f6620696e6465782e4c536c6173685265776172644672616374696f6e01001c50657262696c6c10000000000cf8205468652070657263656e74616765206f662074686520736c617368207468617420697320646973747269627574656420746f207265706f72746572732e00e4205468652072657374206f662074686520736c61736865642076616c75652069732068616e646c6564206279207468652060536c617368602e4c43616e63656c6564536c6173685061796f757401003042616c616e63654f663c543e40000000000000000000000000000000000815012054686520616d6f756e74206f662063757272656e637920676976656e20746f207265706f7274657273206f66206120736c617368206576656e7420776869636820776173ec2063616e63656c65642062792065787472616f7264696e6172792063697263756d7374616e6365732028652e672e20676f7665726e616e6365292e40556e6170706c696564536c617368657301010120457261496e646578bc5665633c556e6170706c696564536c6173683c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e00040004c420416c6c20756e6170706c69656420736c61736865732074686174206172652071756575656420666f72206c617465722e28426f6e646564457261730100745665633c28457261496e6465782c2053657373696f6e496e646578293e04000425012041206d617070696e672066726f6d207374696c6c2d626f6e646564206572617320746f207468652066697273742073657373696f6e20696e646578206f662074686174206572612e4c56616c696461746f72536c617368496e45726100020120457261496e64657830543a3a4163636f756e7449645c2850657262696c6c2c2042616c616e63654f663c543e2903040008450120416c6c20736c617368696e67206576656e7473206f6e2076616c696461746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682070726f706f7274696f6e7020616e6420736c6173682076616c7565206f6620746865206572612e4c4e6f6d696e61746f72536c617368496e45726100020120457261496e64657830543a3a4163636f756e7449643042616c616e63654f663c543e03040004610120416c6c20736c617368696e67206576656e7473206f6e206e6f6d696e61746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682076616c7565206f6620746865206572612e34536c617368696e675370616e7300010130543a3a4163636f756e7449645c736c617368696e673a3a536c617368696e675370616e73000400048c20536c617368696e67207370616e7320666f72207374617368206163636f756e74732e245370616e536c6173680101018c28543a3a4163636f756e7449642c20736c617368696e673a3a5370616e496e6465782988736c617368696e673a3a5370616e5265636f72643c42616c616e63654f663c543e3e00800000000000000000000000000000000000000000000000000000000000000000083d01205265636f72647320696e666f726d6174696f6e2061626f757420746865206d6178696d756d20736c617368206f6620612073746173682077697468696e206120736c617368696e67207370616e2cb82061732077656c6c20617320686f77206d7563682072657761726420686173206265656e2070616964206f75742e584561726c69657374556e6170706c696564536c617368000020457261496e646578040004fc20546865206561726c696573742065726120666f72207768696368207765206861766520612070656e64696e672c20756e6170706c69656420736c6173682e3853746f7261676556657273696f6e01000c75333210000000000490205468652076657273696f6e206f662073746f7261676520666f7220757067726164652e014410626f6e640c28636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e1470617965654452657761726444657374696e6174696f6e3c65012054616b6520746865206f726967696e206163636f756e74206173206120737461736820616e64206c6f636b207570206076616c756560206f66206974732062616c616e63652e2060636f6e74726f6c6c6572602077696c6c8420626520746865206163636f756e74207468617420636f6e74726f6c732069742e003101206076616c756560206d757374206265206d6f7265207468616e2074686520606d696e696d756d5f62616c616e636560207370656369666965642062792060543a3a43757272656e6379602e00250120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20627920746865207374617368206163636f756e742e002c2023203c7765696768743ed4202d20496e646570656e64656e74206f662074686520617267756d656e74732e204d6f64657261746520636f6d706c65786974792e20202d204f2831292e68202d20546872656520657874726120444220656e74726965732e006d01204e4f54453a2054776f206f66207468652073746f726167652077726974657320286053656c663a3a626f6e646564602c206053656c663a3a7061796565602920617265205f6e657665725f20636c65616e656420756e6c65737325012074686520606f726967696e602066616c6c732062656c6f77205f6578697374656e7469616c206465706f7369745f20616e6420676574732072656d6f76656420617320647573742e302023203c2f7765696768743e28626f6e645f657874726104386d61785f6164646974696f6e616c54436f6d706163743c42616c616e63654f663c543e3e3865012041646420736f6d6520657874726120616d6f756e742074686174206861766520617070656172656420696e207468652073746173682060667265655f62616c616e63656020696e746f207468652062616c616e63652075703420666f72207374616b696e672e00510120557365207468697320696620746865726520617265206164646974696f6e616c2066756e647320696e20796f7572207374617368206163636f756e74207468617420796f75207769736820746f20626f6e642e650120556e6c696b65205b60626f6e64605d206f72205b60756e626f6e64605d20746869732066756e6374696f6e20646f6573206e6f7420696d706f736520616e79206c696d69746174696f6e206f6e2074686520616d6f756e744c20746861742063616e2062652061646465642e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e20202d204f2831292e40202d204f6e6520444220656e7472792e302023203c2f7765696768743e18756e626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e5c5501205363686564756c65206120706f7274696f6e206f662074686520737461736820746f20626520756e6c6f636b656420726561647920666f72207472616e73666572206f75742061667465722074686520626f6e64010120706572696f6420656e64732e2049662074686973206c656176657320616e20616d6f756e74206163746976656c7920626f6e646564206c657373207468616e250120543a3a43757272656e63793a3a6d696e696d756d5f62616c616e636528292c207468656e20697420697320696e6372656173656420746f207468652066756c6c20616d6f756e742e004901204f6e63652074686520756e6c6f636b20706572696f6420697320646f6e652c20796f752063616e2063616c6c206077697468647261775f756e626f6e6465646020746f2061637475616c6c79206d6f7665c0207468652066756e6473206f7574206f66206d616e6167656d656e7420726561647920666f72207472616e736665722e003d01204e6f206d6f7265207468616e2061206c696d69746564206e756d626572206f6620756e6c6f636b696e67206368756e6b73202873656520604d41585f554e4c4f434b494e475f4348554e4b5360293d012063616e20636f2d657869737473206174207468652073616d652074696d652e20496e207468617420636173652c205b6043616c6c3a3a77697468647261775f756e626f6e646564605d206e656564fc20746f2062652063616c6c656420666972737420746f2072656d6f766520736f6d65206f6620746865206368756e6b732028696620706f737369626c65292e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e00982053656520616c736f205b6043616c6c3a3a77697468647261775f756e626f6e646564605d2e002c2023203c7765696768743e4101202d20496e646570656e64656e74206f662074686520617267756d656e74732e204c696d697465642062757420706f74656e7469616c6c79206578706c6f697461626c6520636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732e6501202d20456163682063616c6c20287265717569726573207468652072656d61696e646572206f662074686520626f6e6465642062616c616e636520746f2062652061626f766520606d696e696d756d5f62616c616e63656029710120202077696c6c2063617573652061206e657720656e74727920746f20626520696e73657274656420696e746f206120766563746f722028604c65646765722e756e6c6f636b696e676029206b65707420696e2073746f726167652ea501202020546865206f6e6c792077617920746f20636c65616e207468652061666f72656d656e74696f6e65642073746f72616765206974656d20697320616c736f20757365722d636f6e74726f6c6c656420766961206077697468647261775f756e626f6e646564602e40202d204f6e6520444220656e7472792e28203c2f7765696768743e4477697468647261775f756e626f6e64656400402d012052656d6f766520616e7920756e6c6f636b6564206368756e6b732066726f6d207468652060756e6c6f636b696e67602071756575652066726f6d206f7572206d616e6167656d656e742e003501205468697320657373656e7469616c6c7920667265657320757020746861742062616c616e636520746f206265207573656420627920746865207374617368206163636f756e7420746f20646f4c2077686174657665722069742077616e74732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e006c2053656520616c736f205b6043616c6c3a3a756e626f6e64605d2e002c2023203c7765696768743e5501202d20436f756c6420626520646570656e64656e74206f6e2074686520606f726967696e6020617267756d656e7420616e6420686f77206d7563682060756e6c6f636b696e6760206368756e6b732065786973742e45012020497420696d706c6965732060636f6e736f6c69646174655f756e6c6f636b656460207768696368206c6f6f7073206f76657220604c65646765722e756e6c6f636b696e67602c207768696368206973f42020696e6469726563746c7920757365722d636f6e74726f6c6c65642e20536565205b60756e626f6e64605d20666f72206d6f72652064657461696c2e7901202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732c20796574207468652073697a65206f6620776869636820636f756c64206265206c61726765206261736564206f6e20606c6564676572602ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e2076616c6964617465041470726566733856616c696461746f7250726566732ce8204465636c617265207468652064657369726520746f2076616c696461746520666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e206e6f6d696e617465041c74617267657473a05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e2c1101204465636c617265207468652064657369726520746f206e6f6d696e6174652060746172676574736020666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743e2501202d20546865207472616e73616374696f6e277320636f6d706c65786974792069732070726f706f7274696f6e616c20746f207468652073697a65206f66206074617267657473602c982077686963682069732063617070656420617420604d41585f4e4f4d494e4154494f4e53602ed8202d20426f74682074686520726561647320616e642077726974657320666f6c6c6f7720612073696d696c6172207061747465726e2e302023203c2f7765696768743e146368696c6c002cc8204465636c617265206e6f2064657369726520746f206569746865722076616c6964617465206f72206e6f6d696e6174652e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e54202d20436f6e7461696e73206f6e6520726561642ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e247365745f7061796565041470617965654452657761726444657374696e6174696f6e2cb8202852652d2973657420746865207061796d656e742074617267657420666f72206120636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e387365745f636f6e74726f6c6c65720428636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c90202852652d297365742074686520636f6e74726f6c6c6572206f6620612073746173682e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e4c7365745f76616c696461746f725f636f756e74040c6e657730436f6d706163743c7533323e04802054686520696465616c206e756d626572206f662076616c696461746f72732e34666f7263655f6e6f5f657261730014b020466f72636520746865726520746f206265206e6f206e6577206572617320696e646566696e6974656c792e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e302023203c2f7765696768743e34666f7263655f6e65775f65726100184d0120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f6620746865206e6578742073657373696f6e2e20416674657220746869732c2069742077696c6c206265a020726573657420746f206e6f726d616c20286e6f6e2d666f7263656429206265686176696f75722e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e302023203c2f7765696768743e447365745f696e76756c6e657261626c6573042876616c696461746f7273445665633c543a3a4163636f756e7449643e04cc20536574207468652076616c696461746f72732077686f2063616e6e6f7420626520736c61736865642028696620616e79292e34666f7263655f756e7374616b650414737461736830543a3a4163636f756e744964040d0120466f72636520612063757272656e74207374616b657220746f206265636f6d6520636f6d706c6574656c7920756e7374616b65642c20696d6d6564696174656c792e50666f7263655f6e65775f6572615f616c776179730014050120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f662073657373696f6e7320696e646566696e6974656c792e002c2023203c7765696768743e50202d204f6e652073746f72616765207772697465302023203c2f7765696768743e5463616e63656c5f64656665727265645f736c617368080c65726120457261496e64657834736c6173685f696e6469636573205665633c7533323e1c45012043616e63656c20656e6163746d656e74206f66206120646566657272656420736c6173682e2043616e2062652063616c6c6564206279206569746865722074686520726f6f74206f726967696e206f7270207468652060543a3a536c61736843616e63656c4f726967696e602e05012070617373696e67207468652065726120616e6420696e6469636573206f662074686520736c617368657320666f7220746861742065726120746f206b696c6c2e002c2023203c7765696768743e54202d204f6e652073746f726167652077726974652e302023203c2f7765696768743e187265626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e18e0205265626f6e64206120706f7274696f6e206f6620746865207374617368207363686564756c656420746f20626520756e6c6f636b65642e002c2023203c7765696768743ef0202d2054696d6520636f6d706c65786974793a204f2831292e20426f756e64656420627920604d41585f554e4c4f434b494e475f4348554e4b53602ef4202d2053746f72616765206368616e6765733a2043616e277420696e6372656173652073746f726167652c206f6e6c792064656372656173652069742e302023203c2f7765696768743e010c18526577617264081c42616c616e63651c42616c616e636508510120416c6c2076616c696461746f72732068617665206265656e207265776172646564206279207468652066697273742062616c616e63653b20746865207365636f6e64206973207468652072656d61696e6465728c2066726f6d20746865206d6178696d756d20616d6f756e74206f66207265776172642e14536c61736808244163636f756e7449641c42616c616e6365042501204f6e652076616c696461746f722028616e6420697473206e6f6d696e61746f72732920686173206265656e20736c61736865642062792074686520676976656e20616d6f756e742e684f6c64536c617368696e675265706f7274446973636172646564043053657373696f6e496e646578081d0120416e206f6c6420736c617368696e67207265706f72742066726f6d2061207072696f72206572612077617320646973636172646564206265636175736520697420636f756c6448206e6f742062652070726f6365737365642e083853657373696f6e735065724572613053657373696f6e496e64657810060000000470204e756d626572206f662073657373696f6e7320706572206572612e3c426f6e64696e674475726174696f6e20457261496e64657810a002000004e4204e756d626572206f6620657261732074686174207374616b65642066756e6473206d7573742072656d61696e20626f6e64656420666f722e28344e6f74436f6e74726f6c6c65720468204e6f74206120636f6e74726f6c6c6572206163636f756e742e204e6f7453746173680454204e6f742061207374617368206163636f756e742e34416c7265616479426f6e646564046420537461736820697320616c726561647920626f6e6465642e34416c7265616479506169726564047820436f6e74726f6c6c657220697320616c7265616479207061697265642e30456d70747954617267657473046420546172676574732063616e6e6f7420626520656d7074792e384475706c6963617465496e6465780444204475706c696361746520696e6465782e44496e76616c6964536c617368496e646578048820536c617368207265636f726420696e646578206f7574206f6620626f756e64732e44496e73756666696369656e7456616c756504cc2043616e206e6f7420626f6e6420776974682076616c7565206c657373207468616e206d696e696d756d2062616c616e63652e304e6f4d6f72654368756e6b7304942043616e206e6f74207363686564756c65206d6f726520756e6c6f636b206368756e6b732e344e6f556e6c6f636b4368756e6b04a42043616e206e6f74207265626f6e6420776974686f757420756e6c6f636b696e67206368756e6b732e1c53657373696f6e011c53657373696f6e1c2856616c696461746f727301004c5665633c543a3a56616c696461746f7249643e0400047c205468652063757272656e7420736574206f662076616c696461746f72732e3043757272656e74496e64657801003053657373696f6e496e646578100000000004782043757272656e7420696e646578206f66207468652073657373696f6e2e345175657565644368616e676564010010626f6f6c040008390120547275652069662074686520756e6465726c79696e672065636f6e6f6d6963206964656e746974696573206f7220776569676874696e6720626568696e64207468652076616c696461746f7273a420686173206368616e67656420696e20746865207175657565642076616c696461746f72207365742e285175657565644b6579730100785665633c28543a3a56616c696461746f7249642c20543a3a4b657973293e0400083d012054686520717565756564206b65797320666f7220746865206e6578742073657373696f6e2e205768656e20746865206e6578742073657373696f6e20626567696e732c207468657365206b657973e02077696c6c206265207573656420746f2064657465726d696e65207468652076616c696461746f7227732073657373696f6e206b6579732e4844697361626c656456616c696461746f72730100205665633c7533323e04000c8020496e6469636573206f662064697361626c65642076616c696461746f72732e003501205468652073657420697320636c6561726564207768656e20606f6e5f73657373696f6e5f656e64696e67602072657475726e732061206e657720736574206f66206964656e7469746965732e204e6578744b6579730002051c5665633c75383e38543a3a56616c696461746f7249641c543a3a4b657973010400109c20546865206e6578742073657373696f6e206b65797320666f7220612076616c696461746f722e00590120546865206669727374206b657920697320616c77617973206044454455505f4b45595f5052454649586020746f206861766520616c6c20746865206461746120696e207468652073616d65206272616e6368206f6661012074686520747269652e20486176696e6720616c6c206461746120696e207468652073616d65206272616e63682073686f756c642070726576656e7420736c6f77696e6720646f776e206f7468657220717565726965732e204b65794f776e65720002051c5665633c75383e50284b65795479706549642c205665633c75383e2938543a3a56616c696461746f72496401040010250120546865206f776e6572206f662061206b65792e20546865207365636f6e64206b65792069732074686520604b657954797065496460202b2074686520656e636f646564206b65792e00590120546865206669727374206b657920697320616c77617973206044454455505f4b45595f5052454649586020746f206861766520616c6c20746865206461746120696e207468652073616d65206272616e6368206f6661012074686520747269652e20486176696e6720616c6c206461746120696e207468652073616d65206272616e63682073686f756c642070726576656e7420736c6f77696e6720646f776e206f7468657220717565726965732e0104207365745f6b65797308106b6579731c543a3a4b6579731470726f6f661c5665633c75383e28e42053657473207468652073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c657220746f20606b6579602e210120416c6c6f777320616e206163636f756e7420746f20736574206974732073657373696f6e206b6579207072696f7220746f206265636f6d696e6720612076616c696461746f722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743e88202d204f286c6f67206e2920696e206e756d626572206f66206163636f756e74732e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e0104284e657753657373696f6e043053657373696f6e496e646578085501204e65772073657373696f6e206861732068617070656e65642e204e6f746520746861742074686520617267756d656e74206973207468652073657373696f6e20696e6465782c206e6f742074686520626c6f636b88206e756d626572206173207468652074797065206d6967687420737567676573742e044044454455505f4b45595f50524546495814265b75385d38343a73657373696f6e3a6b6579730865012055736564206173206669727374206b657920666f7220604e6578744b6579736020616e6420604b65794f776e65726020746f2070757420616c6c20746865206461746120696e746f207468652073616d65206272616e636834206f662074686520747269652e0c30496e76616c696450726f6f66046420496e76616c6964206f776e6572736869702070726f6f662e5c4e6f4173736f63696174656456616c696461746f72496404a0204e6f206173736f6369617465642076616c696461746f7220494420666f72206163636f756e742e344475706c6963617465644b657904682052656769737465726564206475706c6963617465206b65792e2444656d6f6372616379012444656d6f6372616379403c5075626c696350726f70436f756e7401002450726f70496e646578100000000004f420546865206e756d626572206f6620287075626c6963292070726f706f73616c7320746861742068617665206265656e206d61646520736f206661722e2c5075626c696350726f707301009c5665633c2850726f70496e6465782c20543a3a486173682c20543a3a4163636f756e744964293e040004210120546865207075626c69632070726f706f73616c732e20556e736f727465642e20546865207365636f6e64206974656d206973207468652070726f706f73616c277320686173682e24507265696d616765730001011c543a3a48617368d4285665633c75383e2c20543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d62657229000400086101204d6170206f662068617368657320746f207468652070726f706f73616c20707265696d6167652c20616c6f6e6720776974682077686f207265676973746572656420697420616e64207468656972206465706f7369742ee42054686520626c6f636b206e756d6265722069732074686520626c6f636b20617420776869636820697420776173206465706f73697465642e244465706f7369744f660001012450726f70496e646578842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e2900040004842054686f73652077686f2068617665206c6f636b65642061206465706f7369742e3c5265666572656e64756d436f756e7401003c5265666572656e64756d496e646578100000000004310120546865206e6578742066726565207265666572656e64756d20696e6465782c20616b6120746865206e756d626572206f66207265666572656e6461207374617274656420736f206661722e344c6f77657374556e62616b656401003c5265666572656e64756d496e646578100000000008250120546865206c6f77657374207265666572656e64756d20696e64657820726570726573656e74696e6720616e20756e62616b6564207265666572656e64756d2e20457175616c20746fdc20605265666572656e64756d436f756e74602069662074686572652069736e2774206120756e62616b6564207265666572656e64756d2e405265666572656e64756d496e666f4f660001013c5265666572656e64756d496e6465789c5265666572656e64756d496e666f3c543a3a426c6f636b4e756d6265722c20543a3a486173683e00040004b420496e666f726d6174696f6e20636f6e6365726e696e6720616e7920676976656e207265666572656e64756d2e34446973706174636851756575650100bc5665633c28543a3a426c6f636b4e756d6265722c20543a3a486173682c205265666572656e64756d496e646578293e0400044101205175657565206f66207375636365737366756c207265666572656e646120746f20626520646973706174636865642e2053746f726564206f72646572656420627920626c6f636b206e756d6265722e24566f74657273466f720101013c5265666572656e64756d496e646578445665633c543a3a4163636f756e7449643e00040004a4204765742074686520766f7465727320666f72207468652063757272656e742070726f706f73616c2e18566f74654f660101017c285265666572656e64756d496e6465782c20543a3a4163636f756e7449642910566f7465000400106101204765742074686520766f746520696e206120676976656e207265666572656e64756d206f66206120706172746963756c617220766f7465722e2054686520726573756c74206973206d65616e696e6766756c206f6e6c794d012069662060766f746572735f666f726020696e636c756465732074686520766f746572207768656e2063616c6c6564207769746820746865207265666572656e64756d2028796f75276c6c20676574207468655d012064656661756c742060566f7465602076616c7565206f7468657277697365292e20496620796f7520646f6e27742077616e7420746f20636865636b2060766f746572735f666f72602c207468656e20796f752063616ef420616c736f20636865636b20666f722073696d706c65206578697374656e636520776974682060566f74654f663a3a657869737473602066697273742e1450726f787900010130543a3a4163636f756e74496430543a3a4163636f756e7449640004000831012057686f2069732061626c6520746f20766f746520666f722077686f6d2e2056616c7565206973207468652066756e642d686f6c64696e67206163636f756e742c206b6579206973207468658820766f74652d7472616e73616374696f6e2d73656e64696e67206163636f756e742e2c44656c65676174696f6e7301010130543a3a4163636f756e7449646828543a3a4163636f756e7449642c20436f6e76696374696f6e2901840000000000000000000000000000000000000000000000000000000000000000000441012047657420746865206163636f756e742028616e64206c6f636b20706572696f64732920746f20776869636820616e6f74686572206163636f756e742069732064656c65676174696e6720766f74652e544c6173745461626c656457617345787465726e616c010010626f6f6c0400085901205472756520696620746865206c617374207265666572656e64756d207461626c656420776173207375626d69747465642065787465726e616c6c792e2046616c7365206966206974207761732061207075626c6963282070726f706f73616c2e304e65787445787465726e616c00006028543a3a486173682c20566f74655468726573686f6c6429040010590120546865207265666572656e64756d20746f206265207461626c6564207768656e6576657220697420776f756c642062652076616c696420746f207461626c6520616e2065787465726e616c2070726f706f73616c2e550120546869732068617070656e73207768656e2061207265666572656e64756d206e6565647320746f206265207461626c656420616e64206f6e65206f662074776f20636f6e646974696f6e7320617265206d65743aa4202d20604c6173745461626c656457617345787465726e616c60206973206066616c7365603b206f7268202d20605075626c696350726f70736020697320656d7074792e24426c61636b6c6973740001011c543a3a486173688c28543a3a426c6f636b4e756d6265722c205665633c543a3a4163636f756e7449643e290004000851012041207265636f7264206f662077686f207665746f656420776861742e204d6170732070726f706f73616c206861736820746f206120706f737369626c65206578697374656e7420626c6f636b206e756d626572e82028756e74696c207768656e206974206d6179206e6f742062652072657375626d69747465642920616e642077686f207665746f65642069742e3443616e63656c6c6174696f6e730101011c543a3a4861736810626f6f6c000400042901205265636f7264206f6620616c6c2070726f706f73616c7320746861742068617665206265656e207375626a65637420746f20656d657267656e63792063616e63656c6c6174696f6e2e01541c70726f706f7365083470726f706f73616c5f686173681c543a3a486173681476616c756554436f6d706163743c42616c616e63654f663c543e3e18a02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e002c2023203c7765696768743e20202d204f2831292e80202d2054776f204442206368616e6765732c206f6e6520444220656e7472792e302023203c2f7765696768743e187365636f6e64042070726f706f73616c48436f6d706163743c50726f70496e6465783e18a02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e002c2023203c7765696768743e20202d204f2831292e40202d204f6e6520444220656e7472792e302023203c2f7765696768743e10766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f746510566f74651c350120566f746520696e2061207265666572656e64756d2e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374207468652070726f706f73616c3bbc206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e002c2023203c7765696768743e20202d204f2831292e7c202d204f6e65204442206368616e67652c206f6e6520444220656e7472792e302023203c2f7765696768743e2870726f78795f766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f746510566f74651c510120566f746520696e2061207265666572656e64756d206f6e20626568616c66206f6620612073746173682e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374f4207468652070726f706f73616c3b206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e002c2023203c7765696768743e20202d204f2831292e7c202d204f6e65204442206368616e67652c206f6e6520444220656e7472792e302023203c2f7765696768743e40656d657267656e63795f63616e63656c04247265665f696e6465783c5265666572656e64756d496e646578085101205363686564756c6520616e20656d657267656e63792063616e63656c6c6174696f6e206f662061207265666572656e64756d2e2043616e6e6f742068617070656e20747769636520746f207468652073616d6530207265666572656e64756d2e4065787465726e616c5f70726f706f7365043470726f706f73616c5f686173681c543a3a48617368083101205363686564756c652061207265666572656e64756d20746f206265207461626c6564206f6e6365206974206973206c6567616c20746f207363686564756c6520616e2065787465726e616c30207265666572656e64756d2e6465787465726e616c5f70726f706f73655f6d616a6f72697479043470726f706f73616c5f686173681c543a3a48617368145901205363686564756c652061206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f207363686564756c656020616e2065787465726e616c207265666572656e64756d2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e6065787465726e616c5f70726f706f73655f64656661756c74043470726f706f73616c5f686173681c543a3a48617368144901205363686564756c652061206e656761746976652d7475726e6f75742d62696173207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f84207363686564756c6520616e2065787465726e616c207265666572656e64756d2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e28666173745f747261636b0c3470726f706f73616c5f686173681c543a3a4861736834766f74696e675f706572696f6438543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d626572245101205363686564756c65207468652063757272656e746c792065787465726e616c6c792d70726f706f736564206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564650120696d6d6564696174656c792e204966207468657265206973206e6f2065787465726e616c6c792d70726f706f736564207265666572656e64756d2063757272656e746c792c206f72206966207468657265206973206f6e65ec20627574206974206973206e6f742061206d616a6f726974792d63617272696573207265666572656e64756d207468656e206974206661696c732e00f8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652063757272656e742065787465726e616c2070726f706f73616c2e6101202d2060766f74696e675f706572696f64603a2054686520706572696f64207468617420697320616c6c6f77656420666f7220766f74696e67206f6e20746869732070726f706f73616c2e20496e6372656173656420746f9820202060456d657267656e6379566f74696e67506572696f646020696620746f6f206c6f772e5501202d206064656c6179603a20546865206e756d626572206f6620626c6f636b20616674657220766f74696e672068617320656e64656420696e20617070726f76616c20616e6420746869732073686f756c64206265bc202020656e61637465642e205468697320646f65736e277420686176652061206d696e696d756d20616d6f756e742e347665746f5f65787465726e616c043470726f706f73616c5f686173681c543a3a4861736804bc205665746f20616e6420626c61636b6c697374207468652065787465726e616c2070726f706f73616c20686173682e4463616e63656c5f7265666572656e64756d04247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e04542052656d6f76652061207265666572656e64756d2e3463616e63656c5f717565756564041477686963683c5265666572656e64756d496e64657804a02043616e63656c20612070726f706f73616c2071756575656420666f7220656e6163746d656e742e247365745f70726f7879041470726f787930543a3a4163636f756e7449641498205370656369667920612070726f78792e2043616c6c6564206279207468652073746173682e002c2023203c7765696768743e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e3072657369676e5f70726f787900149820436c656172207468652070726f78792e2043616c6c6564206279207468652070726f78792e002c2023203c7765696768743e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e3072656d6f76655f70726f7879041470726f787930543a3a4163636f756e744964149820436c656172207468652070726f78792e2043616c6c6564206279207468652073746173682e002c2023203c7765696768743e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e2064656c65676174650808746f30543a3a4163636f756e74496428636f6e76696374696f6e28436f6e76696374696f6e143c2044656c656761746520766f74652e002c2023203c7765696768743e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e28756e64656c656761746500144420556e64656c656761746520766f74652e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e58636c6561725f7075626c69635f70726f706f73616c7300040101205665746f20616e6420626c61636b6c697374207468652070726f706f73616c20686173682e204d7573742062652066726f6d20526f6f74206f726967696e2e346e6f74655f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e0861012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e205468697320646f65736e27742072657175697265207468652070726f706f73616c20746f206265250120696e207468652064697370617463682071756575652062757420646f657320726571756972652061206465706f7369742c2072657475726e6564206f6e636520656e61637465642e586e6f74655f696d6d696e656e745f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e0845012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e2054686973207265717569726573207468652070726f706f73616c20746f206265b420696e207468652064697370617463682071756575652e204e6f206465706f736974206973206e65656465642e34726561705f707265696d616765043470726f706f73616c5f686173681c543a3a4861736814f42052656d6f766520616e20657870697265642070726f706f73616c20707265696d61676520616e6420636f6c6c65637420746865206465706f7369742e00510120546869732077696c6c206f6e6c7920776f726b2061667465722060566f74696e67506572696f646020626c6f636b732066726f6d207468652074696d6520746861742074686520707265696d616765207761735d01206e6f7465642c2069662069742773207468652073616d65206163636f756e7420646f696e672069742e2049662069742773206120646966666572656e74206163636f756e742c207468656e206974276c6c206f6e6c79b020776f726b20616e206164646974696f6e616c2060456e6163746d656e74506572696f6460206c617465722e01402050726f706f736564082450726f70496e6465781c42616c616e636504c02041206d6f74696f6e20686173206265656e2070726f706f7365642062792061207075626c6963206163636f756e742e185461626c65640c2450726f70496e6465781c42616c616e6365385665633c4163636f756e7449643e04dc2041207075626c69632070726f706f73616c20686173206265656e207461626c656420666f72207265666572656e64756d20766f74652e3845787465726e616c5461626c656400049820416e2065787465726e616c2070726f706f73616c20686173206265656e207461626c65642e1c53746172746564083c5265666572656e64756d496e64657834566f74655468726573686f6c6404602041207265666572656e64756d2068617320626567756e2e18506173736564043c5265666572656e64756d496e64657804b020412070726f706f73616c20686173206265656e20617070726f766564206279207265666572656e64756d2e244e6f74506173736564043c5265666572656e64756d496e64657804b020412070726f706f73616c20686173206265656e2072656a6563746564206279207265666572656e64756d2e2443616e63656c6c6564043c5265666572656e64756d496e64657804842041207265666572656e64756d20686173206265656e2063616e63656c6c65642e204578656375746564083c5265666572656e64756d496e64657810626f6f6c047420412070726f706f73616c20686173206265656e20656e61637465642e2444656c65676174656408244163636f756e744964244163636f756e74496404e020416e206163636f756e74206861732064656c65676174656420746865697220766f746520746f20616e6f74686572206163636f756e742e2c556e64656c65676174656404244163636f756e74496404e820416e206163636f756e74206861732063616e63656c6c656420612070726576696f75732064656c65676174696f6e206f7065726174696f6e2e185665746f65640c244163636f756e74496410486173682c426c6f636b4e756d626572049820416e2065787465726e616c2070726f706f73616c20686173206265656e207665746f65642e34507265696d6167654e6f7465640c1048617368244163636f756e7449641c42616c616e636504e020412070726f706f73616c277320707265696d61676520776173206e6f7465642c20616e6420746865206465706f7369742074616b656e2e30507265696d616765557365640c1048617368244163636f756e7449641c42616c616e636504150120412070726f706f73616c20707265696d616765207761732072656d6f76656420616e6420757365642028746865206465706f736974207761732072657475726e6564292e3c507265696d616765496e76616c69640810486173683c5265666572656e64756d496e646578040d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d6167652077617320696e76616c69642e3c507265696d6167654d697373696e670810486173683c5265666572656e64756d496e646578040d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d61676520776173206d697373696e672e38507265696d616765526561706564101048617368244163636f756e7449641c42616c616e6365244163636f756e744964045d012041207265676973746572656420707265696d616765207761732072656d6f76656420616e6420746865206465706f73697420636f6c6c6563746564206279207468652072656170657220286c617374206974656d292e1c3c456e6163746d656e74506572696f6438543a3a426c6f636b4e756d62657210002f0d0014710120546865206d696e696d756d20706572696f64206f66206c6f636b696e6720616e642074686520706572696f64206265747765656e20612070726f706f73616c206265696e6720617070726f76656420616e6420656e61637465642e0031012049742073686f756c642067656e6572616c6c792062652061206c6974746c65206d6f7265207468616e2074686520756e7374616b6520706572696f6420746f20656e737572652074686174690120766f74696e67207374616b657273206861766520616e206f70706f7274756e69747920746f2072656d6f7665207468656d73656c7665732066726f6d207468652073797374656d20696e2074686520636173652077686572659c207468657920617265206f6e20746865206c6f73696e672073696465206f66206120766f74652e304c61756e6368506572696f6438543a3a426c6f636b4e756d62657210004e0c0004e420486f77206f6674656e2028696e20626c6f636b7329206e6577207075626c6963207265666572656e646120617265206c61756e636865642e30566f74696e67506572696f6438543a3a426c6f636b4e756d62657210004e0c0004b820486f77206f6674656e2028696e20626c6f636b732920746f20636865636b20666f72206e657720766f7465732e384d696e696d756d4465706f7369743042616c616e63654f663c543e400000c16ff2862300000000000000000004350120546865206d696e696d756d20616d6f756e7420746f20626520757365642061732061206465706f73697420666f722061207075626c6963207265666572656e64756d2070726f706f73616c2e54456d657267656e6379566f74696e67506572696f6438543a3a426c6f636b4e756d626572108051010004ec204d696e696d756d20766f74696e6720706572696f6420616c6c6f77656420666f7220616e20656d657267656e6379207265666572656e64756d2e34436f6f6c6f6666506572696f6438543a3a426c6f636b4e756d62657210004e0c0004610120506572696f6420696e20626c6f636b7320776865726520616e2065787465726e616c2070726f706f73616c206d6179206e6f742062652072652d7375626d6974746564206166746572206265696e67207665746f65642e4c507265696d616765427974654465706f7369743042616c616e63654f663c543e400010a5d4e800000000000000000000000429012054686520616d6f756e74206f662062616c616e63652074686174206d757374206265206465706f7369746564207065722062797465206f6620707265696d6167652073746f7265642e582056616c75654c6f7704382056616c756520746f6f206c6f773c50726f706f73616c4d697373696e6704602050726f706f73616c20646f6573206e6f74206578697374204e6f7450726f78790430204e6f7420612070726f787920426164496e646578043820556e6b6e6f776e20696e6465783c416c726561647943616e63656c656404982043616e6e6f742063616e63656c207468652073616d652070726f706f73616c207477696365444475706c696361746550726f706f73616c04582050726f706f73616c20616c7265616479206d6164654c50726f706f73616c426c61636b6c6973746564046c2050726f706f73616c207374696c6c20626c61636b6c6973746564444e6f7453696d706c654d616a6f7269747904ac204e6578742065787465726e616c2070726f706f73616c206e6f742073696d706c65206d616a6f726974792c496e76616c696448617368043420496e76616c69642068617368284e6f50726f706f73616c0454204e6f2065787465726e616c2070726f706f73616c34416c72656164795665746f6564049c204964656e74697479206d6179206e6f74207665746f20612070726f706f73616c20747769636530416c726561647950726f7879044020416c726561647920612070726f78792857726f6e6750726f787904302057726f6e672070726f7879304e6f7444656c6567617465640438204e6f742064656c656761746564444475706c6963617465507265696d616765045c20507265696d61676520616c7265616479206e6f7465642c4e6f74496d6d696e656e740434204e6f7420696d6d696e656e74144561726c79042820546f6f206561726c7920496d6d696e656e74042420496d6d696e656e743c507265696d6167654d697373696e67044c20507265696d616765206e6f7420666f756e64445265666572656e64756d496e76616c6964048820566f746520676976656e20666f7220696e76616c6964207265666572656e64756d3c507265696d616765496e76616c6964044420496e76616c696420707265696d6167652c4e6f6e6557616974696e670454204e6f2070726f706f73616c732077616974696e671c436f756e63696c014c496e7374616e636531436f6c6c656374697665142450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001011c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001011c543a3a486173684c566f7465733c543a3a4163636f756e7449643e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e01102c7365745f6d656d62657273042c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e105101205365742074686520636f6c6c6563746976652773206d656d62657273686970206d616e75616c6c7920746f20606e65775f6d656d62657273602e204265206e69636520746f2074686520636861696e20616e645c2070726f76696465206974207072652d736f727465642e005820526571756972657320726f6f74206f726967696e2e1c65786563757465042070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e0cf420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e1c70726f706f736508247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e102c2023203c7765696768743e90202d20426f756e6465642073746f7261676520726561647320616e64207772697465732eb8202d20417267756d656e7420607468726573686f6c6460206861732062656172696e67206f6e207765696768742e302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c102c2023203c7765696768743e8c202d20426f756e6465642073746f72616765207265616420616e64207772697465732e5501202d2057696c6c20626520736c696768746c792068656176696572206966207468652070726f706f73616c20697320617070726f766564202f20646973617070726f7665642061667465722074686520766f74652e302023203c2f7765696768743e01182050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e74084d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292e14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740809012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292e20417070726f76656404104861736804c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e2c446973617070726f76656404104861736804d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e20457865637574656408104861736810626f6f6c0405012041206d6f74696f6e207761732065786563757465643b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e384d656d626572457865637574656408104861736810626f6f6c042d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e0018244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642148546563686e6963616c436f6d6d6974746565014c496e7374616e636532436f6c6c656374697665142450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001011c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001011c543a3a486173684c566f7465733c543a3a4163636f756e7449643e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e01102c7365745f6d656d62657273042c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e105101205365742074686520636f6c6c6563746976652773206d656d62657273686970206d616e75616c6c7920746f20606e65775f6d656d62657273602e204265206e69636520746f2074686520636861696e20616e645c2070726f76696465206974207072652d736f727465642e005820526571756972657320726f6f74206f726967696e2e1c65786563757465042070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e0cf420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e1c70726f706f736508247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e102c2023203c7765696768743e90202d20426f756e6465642073746f7261676520726561647320616e64207772697465732eb8202d20417267756d656e7420607468726573686f6c6460206861732062656172696e67206f6e207765696768742e302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c102c2023203c7765696768743e8c202d20426f756e6465642073746f72616765207265616420616e64207772697465732e5501202d2057696c6c20626520736c696768746c792068656176696572206966207468652070726f706f73616c20697320617070726f766564202f20646973617070726f7665642061667465722074686520766f74652e302023203c2f7765696768743e01182050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e74084d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292e14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740809012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292e20417070726f76656404104861736804c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e2c446973617070726f76656404104861736804d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e20457865637574656408104861736810626f6f6c0405012041206d6f74696f6e207761732065786563757465643b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e384d656d626572457865637574656408104861736810626f6f6c042d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e0018244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642124456c656374696f6e73014050687261676d656e456c656374696f6e181c4d656d626572730100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e040004f0205468652063757272656e7420656c6563746564206d656d626572736869702e20536f72746564206261736564206f6e206163636f756e742069642e2452756e6e65727355700100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e0400044901205468652063757272656e742072756e6e6572735f75702e20536f72746564206261736564206f6e206c6f7720746f2068696768206d657269742028776f72736520746f20626573742072756e6e6572292e38456c656374696f6e526f756e647301000c75333210000000000441012054686520746f74616c206e756d626572206f6620766f746520726f756e6473207468617420686176652068617070656e65642c206578636c7564696e6720746865207570636f6d696e67206f6e652e1c566f7465734f6601010130543a3a4163636f756e744964445665633c543a3a4163636f756e7449643e01040004010120566f746573206f66206120706172746963756c617220766f7465722c20776974682074686520726f756e6420696e646578206f662074686520766f7465732e1c5374616b654f6601010130543a3a4163636f756e7449643042616c616e63654f663c543e0040000000000000000000000000000000000464204c6f636b6564207374616b65206f66206120766f7465722e2843616e646964617465730100445665633c543a3a4163636f756e7449643e0400086501205468652070726573656e742063616e646964617465206c6973742e20536f72746564206261736564206f6e206163636f756e742d69642e20412063757272656e74206d656d626572206f7220612072756e6e65722063616e3101206e6576657220656e746572207468697320766563746f7220616e6420697320616c7761797320696d706c696369746c7920617373756d656420746f20626520612063616e6469646174652e011810766f74650814766f746573445665633c543a3a4163636f756e7449643e1476616c756554436f6d706163743c42616c616e63654f663c543e3e3c050120566f746520666f72206120736574206f662063616e6469646174657320666f7220746865207570636f6d696e6720726f756e64206f6620656c656374696f6e2e0050205468652060766f746573602073686f756c643a482020202d206e6f7420626520656d7074792eac2020202d206265206c657373207468616e20746865206e756d626572206f662063616e646964617465732e005d012055706f6e20766f74696e672c206076616c75656020756e697473206f66206077686f6027732062616c616e6365206973206c6f636b656420616e64206120626f6e6420616d6f756e742069732072657365727665642e5d012049742069732074686520726573706f6e736962696c697479206f66207468652063616c6c657220746f206e6f7420706c61636520616c6c206f662074686569722062616c616e636520696e746f20746865206c6f636ba020616e64206b65657020736f6d6520666f722066757274686572207472616e73616374696f6e732e002c2023203c7765696768743e2c2023232323205374617465302052656164733a204f283129c8205772697465733a204f28562920676976656e2060566020766f7465732e205620697320626f756e6465642062792031362e302023203c2f7765696768743e3072656d6f76655f766f746572001c21012052656d6f766520606f726967696e60206173206120766f7465722e20546869732072656d6f76657320746865206c6f636b20616e642072657475726e732074686520626f6e642e002c2023203c7765696768743e2c2023232323205374617465302052656164733a204f28312934205772697465733a204f283129302023203c2f7765696768743e507265706f72745f646566756e63745f766f74657204187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365345d01205265706f727420607461726765746020666f72206265696e6720616e20646566756e637420766f7465722e20496e2063617365206f6620612076616c6964207265706f72742c20746865207265706f727465722069735d012072657761726465642062792074686520626f6e6420616d6f756e74206f662060746172676574602e204f74686572776973652c20746865207265706f7274657220697473656c662069732072656d6f76656420616e645c20746865697220626f6e6420697320736c61736865642e0088204120646566756e637420766f74657220697320646566696e656420746f2062653a4d012020202d206120766f7465722077686f73652063757272656e74207375626d697474656420766f7465732061726520616c6c20696e76616c69642e20692e652e20616c6c206f66207468656d20617265206e6fb420202020206c6f6e67657220612063616e646964617465206e6f7220616e20616374697665206d656d6265722e002c2023203c7765696768743e2c202323232320537461746515012052656164733a204f284e4c6f674d2920676976656e204d2063757272656e742063616e6469646174657320616e64204e20766f74657320666f722060746172676574602e34205772697465733a204f283129302023203c2f7765696768743e407375626d69745f63616e646964616379003478205375626d6974206f6e6573656c6620666f722063616e6469646163792e006420412063616e6469646174652077696c6c206569746865723aec2020202d204c6f73652061742074686520656e64206f6620746865207465726d20616e6420666f7266656974207468656972206465706f7369742e2d012020202d2057696e20616e64206265636f6d652061206d656d6265722e204d656d626572732077696c6c206576656e7475616c6c7920676574207468656972207374617368206261636b2e55012020202d204265636f6d6520612072756e6e65722d75702e2052756e6e6572732d75707320617265207265736572766564206d656d6265727320696e2063617365206f6e65206765747320666f72636566756c6c7934202020202072656d6f7665642e002c2023203c7765696768743e2c20232323232053746174658c2052656164733a204f284c6f674e2920476976656e204e2063616e646964617465732e34205772697465733a204f283129302023203c2f7765696768743e4872656e6f756e63655f63616e646964616379002451012052656e6f756e6365206f6e65277320696e74656e74696f6e20746f20626520612063616e64696461746520666f7220746865206e65787420656c656374696f6e20726f756e642e203320706f74656e7469616c40206f7574636f6d65732065786973743a4101202d20606f726967696e6020697320612063616e64696461746520616e64206e6f7420656c656374656420696e20616e79207365742e20496e207468697320636173652c2074686520626f6e64206973f4202020756e72657365727665642c2072657475726e656420616e64206f726967696e2069732072656d6f76656420617320612063616e6469646174652e5901202d20606f726967696e6020697320612063757272656e742072756e6e65722075702e20496e207468697320636173652c2074686520626f6e6420697320756e72657365727665642c2072657475726e656420616e64842020206f726967696e2069732072656d6f76656420617320612072756e6e65722e4d01202d20606f726967696e6020697320612063757272656e74206d656d6265722e20496e207468697320636173652c2074686520626f6e6420697320756e726573657276656420616e64206f726967696e206973590120202072656d6f7665642061732061206d656d6265722c20636f6e73657175656e746c79206e6f74206265696e6720612063616e64696461746520666f7220746865206e65787420726f756e6420616e796d6f72652e650120202053696d696c617220746f205b6072656d6f76655f766f746572605d2c206966207265706c6163656d656e742072756e6e657273206578697374732c20746865792061726520696d6d6564696174656c7920757365642e3472656d6f76655f6d656d626572040c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365345d012052656d6f7665206120706172746963756c6172206d656d6265722066726f6d20746865207365742e20546869732069732065666665637469766520696d6d6564696174656c7920616e642074686520626f6e64206f668020746865206f7574676f696e67206d656d62657220697320736c61736865642e00590120496620612072756e6e65722d757020697320617661696c61626c652c207468656e2074686520626573742072756e6e65722d75702077696c6c2062652072656d6f76656420616e64207265706c6163657320746865f4206f7574676f696e67206d656d6265722e204f74686572776973652c2061206e65772070687261676d656e20726f756e6420697320737461727465642e004501204e6f74652074686174207468697320646f6573206e6f7420616666656374207468652064657369676e6174656420626c6f636b206e756d626572206f6620746865206e65787420656c656374696f6e2e002c2023203c7765696768743e2c2023232323205374617465582052656164733a204f28646f5f70687261676d656e295c205772697465733a204f28646f5f70687261676d656e29302023203c2f7765696768743e01141c4e65775465726d04645665633c284163636f756e7449642c2042616c616e6365293e0855012041206e6577207465726d2077697468206e6577206d656d626572732e205468697320696e64696361746573207468617420656e6f7567682063616e6469646174657320657869737465642c206e6f742074686174450120656e6f756768206861766520686173206265656e20656c65637465642e2054686520696e6e65722076616c7565206d757374206265206578616d696e656420666f72207468697320707572706f73652e24456d7074795465726d0004d8204e6f20286f72206e6f7420656e6f756768292063616e64696461746573206578697374656420666f72207468697320726f756e642e304d656d6265724b69636b656404244163636f756e7449640845012041206d656d62657220686173206265656e2072656d6f7665642e20546869732073686f756c6420616c7761797320626520666f6c6c6f7765642062792065697468657220604e65775465726d60206f74342060456d7074795465726d602e3c4d656d62657252656e6f756e63656404244163636f756e74496404a02041206d656d626572206861732072656e6f756e6365642074686569722063616e6469646163792e34566f7465725265706f727465640c244163636f756e744964244163636f756e74496410626f6f6c086101204120766f7465722028666972737420656c656d656e742920776173207265706f72746564202862797420746865207365636f6e6420656c656d656e742920776974682074686520746865207265706f7274206265696e678c207375636365737366756c206f72206e6f742028746869726420656c656d656e74292e143443616e646964616379426f6e643042616c616e63654f663c543e400080c6a47e8d030000000000000000000028566f74696e67426f6e643042616c616e63654f663c543e4000407a10f35a000000000000000000000038446573697265644d656d626572730c753332100d00000000404465736972656452756e6e65727355700c753332100700000000305465726d4475726174696f6e38543a3a426c6f636b4e756d6265721080130300003830556e61626c65546f566f746504c42043616e6e6f7420766f7465207768656e206e6f2063616e64696461746573206f72206d656d626572732065786973742e1c4e6f566f7465730498204d75737420766f746520666f72206174206c65617374206f6e652063616e6469646174652e30546f6f4d616e79566f74657304882043616e6e6f7420766f7465206d6f7265207468616e2063616e646964617465732e504d6178696d756d566f7465734578636565646564049c2043616e6e6f7420766f7465206d6f7265207468616e206d6178696d756d20616c6c6f7765642e284c6f7742616c616e636504c82043616e6e6f7420766f74652077697468207374616b65206c657373207468616e206d696e696d756d2062616c616e63652e3c556e61626c65546f506179426f6e64047c20566f7465722063616e206e6f742070617920766f74696e6720626f6e642e2c4d7573744265566f7465720444204d757374206265206120766f7465722e285265706f727453656c6604502043616e6e6f74207265706f72742073656c662e4c4475706c69636174656443616e6469646174650484204475706c6963617465642063616e646964617465207375626d697373696f6e2e304d656d6265725375626d6974048c204d656d6265722063616e6e6f742072652d7375626d69742063616e6469646163792e3052756e6e65725375626d6974048c2052756e6e65722063616e6e6f742072652d7375626d69742063616e6469646163792e68496e73756666696369656e7443616e64696461746546756e647304982043616e64696461746520646f6573206e6f74206861766520656e6f7567682066756e64732e34496e76616c69644f726967696e04c8204f726967696e206973206e6f7420612063616e6469646174652c206d656d626572206f7220612072756e6e65722075702e244e6f744d656d6265720438204e6f742061206d656d6265722e4c546563686e6963616c4d656d62657273686970014c496e7374616e6365314d656d62657273686970041c4d656d626572730100445665633c543a3a4163636f756e7449643e040004c8205468652063757272656e74206d656d626572736869702c2073746f72656420617320616e206f726465726564205665632e0114286164645f6d656d626572040c77686f30543a3a4163636f756e7449640c7c204164642061206d656d626572206077686f6020746f20746865207365742e00b4204d6179206f6e6c792062652063616c6c65642066726f6d20604164644f726967696e60206f7220726f6f742e3472656d6f76655f6d656d626572040c77686f30543a3a4163636f756e7449640c902052656d6f76652061206d656d626572206077686f602066726f6d20746865207365742e00c0204d6179206f6e6c792062652063616c6c65642066726f6d206052656d6f76654f726967696e60206f7220726f6f742e2c737761705f6d656d626572081872656d6f766530543a3a4163636f756e7449640c61646430543a3a4163636f756e7449640cc02053776170206f7574206f6e65206d656d626572206072656d6f76656020666f7220616e6f746865722060616464602e00b8204d6179206f6e6c792062652063616c6c65642066726f6d2060537761704f726967696e60206f7220726f6f742e3472657365745f6d656d62657273041c6d656d62657273445665633c543a3a4163636f756e7449643e105901204368616e676520746865206d656d6265727368697020746f2061206e6577207365742c20646973726567617264696e6720746865206578697374696e67206d656d626572736869702e204265206e69636520616e646c207061737320606d656d6265727360207072652d736f727465642e00bc204d6179206f6e6c792062652063616c6c65642066726f6d206052657365744f726967696e60206f7220726f6f742e286368616e67655f6b6579040c6e657730543a3a4163636f756e7449640cd82053776170206f7574207468652073656e64696e67206d656d62657220666f7220736f6d65206f74686572206b657920606e6577602e00f4204d6179206f6e6c792062652063616c6c65642066726f6d20605369676e656460206f726967696e206f6620612063757272656e74206d656d6265722e01182c4d656d62657241646465640004e42054686520676976656e206d656d626572207761732061646465643b2073656520746865207472616e73616374696f6e20666f722077686f2e344d656d62657252656d6f7665640004ec2054686520676976656e206d656d626572207761732072656d6f7665643b2073656520746865207472616e73616374696f6e20666f722077686f2e384d656d62657273537761707065640004dc2054776f206d656d62657273207765726520737761707065643b2073656520746865207472616e73616374696f6e20666f722077686f2e304d656d6265727352657365740004190120546865206d656d62657273686970207761732072657365743b2073656520746865207472616e73616374696f6e20666f722077686f20746865206e6577207365742069732e284b65794368616e676564000488204f6e65206f6620746865206d656d6265727327206b657973206368616e6765642e1444756d6d7904bc73705f7374643a3a6d61726b65723a3a5068616e746f6d446174613c284163636f756e7449642c204576656e74293e0470205068616e746f6d206d656d6265722c206e6576657220757365642e00003c46696e616c697479547261636b65720001042866696e616c5f68696e74041068696e745c436f6d706163743c543a3a426c6f636b4e756d6265723e08f42048696e7420746861742074686520617574686f72206f66207468697320626c6f636b207468696e6b732074686520626573742066696e616c697a65646c20626c6f636b2069732074686520676976656e206e756d6265722e00082857696e646f7753697a6538543a3a426c6f636b4e756d626572106500000004190120546865206e756d626572206f6620726563656e742073616d706c657320746f206b6565702066726f6d207468697320636861696e2e2044656661756c74206973203130312e345265706f72744c6174656e637938543a3a426c6f636b4e756d62657210e8030000041d01205468652064656c617920616674657220776869636820706f696e74207468696e6773206265636f6d6520737573706963696f75732e2044656661756c7420697320313030302e0838416c72656164795570646174656404c82046696e616c2068696e74206d7573742062652075706461746564206f6e6c79206f6e636520696e2074686520626c6f636b1c42616448696e7404902046696e616c697a6564206865696768742061626f766520626c6f636b206e756d6265721c4772616e647061013c4772616e64706146696e616c6974791c2c417574686f726974696573010034417574686f726974794c6973740400102c20444550524543415445440061012054686973207573656420746f2073746f7265207468652063757272656e7420617574686f72697479207365742c20776869636820686173206265656e206d6967726174656420746f207468652077656c6c2d6b6e6f776e94204752414e4450415f415554484f52495445535f4b455920756e686173686564206b65792e14537461746501006c53746f72656453746174653c543a3a426c6f636b4e756d6265723e04000490205374617465206f66207468652063757272656e7420617574686f72697479207365742e3450656e64696e674368616e676500008c53746f72656450656e64696e674368616e67653c543a3a426c6f636b4e756d6265723e040004c42050656e64696e67206368616e67653a20287369676e616c65642061742c207363686564756c6564206368616e6765292e284e657874466f72636564000038543a3a426c6f636b4e756d626572040004bc206e65787420626c6f636b206e756d6265722077686572652077652063616e20666f7263652061206368616e67652e1c5374616c6c656400008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d626572290400049020607472756560206966207765206172652063757272656e746c79207374616c6c65642e3043757272656e7453657449640100145365744964200000000000000000085d0120546865206e756d626572206f66206368616e6765732028626f746820696e207465726d73206f66206b65797320616e6420756e6465726c79696e672065636f6e6f6d696320726573706f6e736962696c697469657329c420696e20746865202273657422206f66204772616e6470612076616c696461746f72732066726f6d2067656e657369732e30536574496453657373696f6e0001011453657449643053657373696f6e496e64657800040004c1012041206d617070696e672066726f6d206772616e6470612073657420494420746f2074686520696e646578206f6620746865202a6d6f737420726563656e742a2073657373696f6e20666f7220776869636820697473206d656d62657273207765726520726573706f6e7369626c652e0104487265706f72745f6d69736265686176696f72041c5f7265706f72741c5665633c75383e0464205265706f727420736f6d65206d69736265686176696f722e010c384e6577417574686f7269746965730434417574686f726974794c6973740490204e657720617574686f726974792073657420686173206265656e206170706c6965642e1850617573656400049c2043757272656e7420617574686f726974792073657420686173206265656e207061757365642e1c526573756d65640004a02043757272656e7420617574686f726974792073657420686173206265656e20726573756d65642e00102c50617573654661696c656408090120417474656d707420746f207369676e616c204752414e445041207061757365207768656e2074686520617574686f72697479207365742069736e2774206c697665a8202865697468657220706175736564206f7220616c72656164792070656e64696e67207061757365292e30526573756d654661696c656408150120417474656d707420746f207369676e616c204752414e44504120726573756d65207768656e2074686520617574686f72697479207365742069736e277420706175736564a42028656974686572206c697665206f7220616c72656164792070656e64696e6720726573756d65292e344368616e676550656e64696e6704ec20417474656d707420746f207369676e616c204752414e445041206368616e67652077697468206f6e6520616c72656164792070656e64696e672e1c546f6f536f6f6e04c02043616e6e6f74207369676e616c20666f72636564206368616e676520736f20736f6f6e206166746572206c6173742e20547265617375727901205472656173757279143450726f706f73616c436f756e7401003450726f706f73616c496e646578100000000004a4204e756d626572206f662070726f706f73616c7320746861742068617665206265656e206d6164652e2450726f706f73616c730001013450726f706f73616c496e6465789050726f706f73616c3c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400047c2050726f706f73616c7320746861742068617665206265656e206d6164652e24417070726f76616c730100485665633c50726f706f73616c496e6465783e040004f82050726f706f73616c20696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f742079657420617761726465642e10546970730001051c543a3a48617368f04f70656e5469703c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265722c20543a3a486173683e0004000c59012054697073207468617420617265206e6f742079657420636f6d706c657465642e204b65796564206279207468652068617368206f66206028726561736f6e2c2077686f29602066726f6d207468652076616c75652e3d012054686973206861732074686520696e73656375726520656e756d657261626c6520686173682066756e6374696f6e2073696e636520746865206b657920697473656c6620697320616c7265616479802067756172616e7465656420746f20626520612073656375726520686173682e1c526561736f6e730001051c543a3a486173681c5665633c75383e0004000849012053696d706c6520707265696d616765206c6f6f6b75702066726f6d2074686520726561736f6e2773206861736820746f20746865206f726967696e616c20646174612e20416761696e2c2068617320616e610120696e73656375726520656e756d657261626c6520686173682073696e636520746865206b65792069732067756172616e7465656420746f2062652074686520726573756c74206f6620612073656375726520686173682e01203470726f706f73655f7370656e64081476616c756554436f6d706163743c42616c616e63654f663c543e3e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365242d012050757420666f727761726420612073756767657374696f6e20666f72207370656e64696e672e2041206465706f7369742070726f706f7274696f6e616c20746f207468652076616c7565350120697320726573657276656420616e6420736c6173686564206966207468652070726f706f73616c2069732072656a65637465642e2049742069732072657475726e6564206f6e636520746865542070726f706f73616c20697320617761726465642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e94202d204f6e65204442206368616e67652c206f6e6520657874726120444220656e7472792e302023203c2f7765696768743e3c72656a6563745f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e1cfc2052656a65637420612070726f706f736564207370656e642e20546865206f726967696e616c206465706f7369742077696c6c20626520736c61736865642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e40617070726f76655f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e205d0120417070726f766520612070726f706f73616c2e2041742061206c617465722074696d652c207468652070726f706f73616c2077696c6c20626520616c6c6f636174656420746f207468652062656e6566696369617279ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e387265706f72745f617765736f6d650818726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e7449644c5d01205265706f727420736f6d657468696e672060726561736f6e60207468617420646573657276657320612074697020616e6420636c61696d20616e79206576656e7475616c207468652066696e6465722773206665652e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c206173d420605469705265706f72744465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743e9c202d20604f2852296020776865726520605260206c656e677468206f662060726561736f6e602e64202d204f6e652062616c616e6365206f7065726174696f6e2e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e2c726574726163745f7469700410686173681c543a3a486173684c550120526574726163742061207072696f72207469702d7265706f72742066726f6d20607265706f72745f617765736f6d65602c20616e642063616e63656c207468652070726f63657373206f662074697070696e672e00e0204966207375636365737366756c2c20746865206f726967696e616c206465706f7369742077696c6c20626520756e72657365727665642e00510120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642074686520746970206964656e746966696564206279206068617368604501206d7573742068617665206265656e207265706f7274656420627920746865207369676e696e67206163636f756e74207468726f75676820607265706f72745f617765736f6d65602028616e64206e6f7450207468726f75676820607469705f6e657760292e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e009020456d697473206054697052657472616374656460206966207375636365737366756c2e002c2023203c7765696768743e24202d20604f2854296064202d204f6e652062616c616e6365206f7065726174696f6e2ec4202d2054776f2073746f726167652072656d6f76616c7320286f6e6520726561642c20636f64656320604f28542960292e34202d204f6e65206576656e742e302023203c2f7765696768743e1c7469705f6e65770c18726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e744964247469705f76616c75653042616c616e63654f663c543e4cf4204769766520612074697020666f7220736f6d657468696e67206e65773b206e6f2066696e6465722773206665652077696c6c2062652074616b656e2e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743e4101202d20604f2852202b2054296020776865726520605260206c656e677468206f662060726561736f6e602c2060546020697320746865206e756d626572206f6620746970706572732e2060546020697345012020206e61747572616c6c79206361707065642061732061206d656d62657273686970207365742c20605260206973206c696d69746564207468726f756768207472616e73616374696f6e2d73697a652e0d01202d2054776f2073746f7261676520696e73657274696f6e732028636f6465637320604f285229602c20604f28542960292c206f6e65207265616420604f283129602e34202d204f6e65206576656e742e302023203c2f7765696768743e0c7469700810686173681c543a3a48617368247469705f76616c75653042616c616e63654f663c543e4cb4204465636c6172652061207469702076616c756520666f7220616e20616c72656164792d6f70656e207469702e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f66207468652068617368206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279382020206163636f756e742049442e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e00650120456d6974732060546970436c6f73696e676020696620746865207468726573686f6c64206f66207469707065727320686173206265656e207265616368656420616e642074686520636f756e74646f776e20706572696f64342068617320737461727465642e002c2023203c7765696768743e24202d20604f285429600101202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28542960292c206f6e652073746f72616765207265616420604f283129602e4c202d20557020746f206f6e65206576656e742e302023203c2f7765696768743e24636c6f73655f7469700410686173681c543a3a48617368386020436c6f736520616e64207061796f75742061207469702e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0019012054686520746970206964656e74696669656420627920606861736860206d75737420686176652066696e69736865642069747320636f756e74646f776e20706572696f642e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e002c2023203c7765696768743e24202d20604f28542960e4202d204f6e652073746f726167652072657472696576616c2028636f64656320604f285429602920616e642074776f2072656d6f76616c732e88202d20557020746f2074687265652062616c616e6365206f7065726174696f6e732e302023203c2f7765696768743e012c2050726f706f736564043450726f706f73616c496e6465780438204e65772070726f706f73616c2e205370656e64696e67041c42616c616e636504e8205765206861766520656e6465642061207370656e6420706572696f6420616e642077696c6c206e6f7720616c6c6f636174652066756e64732e1c417761726465640c3450726f706f73616c496e6465781c42616c616e6365244163636f756e744964048020536f6d652066756e64732068617665206265656e20616c6c6f63617465642e2052656a6563746564083450726f706f73616c496e6465781c42616c616e636504b420412070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e144275726e74041c42616c616e6365048c20536f6d65206f66206f75722066756e64732068617665206265656e206275726e742e20526f6c6c6f766572041c42616c616e6365043101205370656e64696e67206861732066696e69736865643b20746869732069732074686520616d6f756e74207468617420726f6c6c73206f76657220756e74696c206e657874207370656e642e1c4465706f736974041c42616c616e6365048020536f6d652066756e64732068617665206265656e206465706f73697465642e184e657754697004104861736804982041206e6577207469702073756767657374696f6e20686173206265656e206f70656e65642e28546970436c6f73696e6704104861736804dc2041207469702073756767657374696f6e206861732072656163686564207468726573686f6c6420616e6420697320636c6f73696e672e24546970436c6f7365640c1048617368244163636f756e7449641c42616c616e636504882041207469702073756767657374696f6e20686173206265656e20636c6f7365642e3054697052657472616374656404104861736804942041207469702073756767657374696f6e20686173206265656e207265747261637465642e203050726f706f73616c426f6e641c5065726d696c6c1050c30000085501204672616374696f6e206f6620612070726f706f73616c27732076616c756520746861742073686f756c6420626520626f6e64656420696e206f7264657220746f20706c616365207468652070726f706f73616c2e110120416e2061636365707465642070726f706f73616c2067657473207468657365206261636b2e20412072656a65637465642070726f706f73616c20646f6573206e6f742e4c50726f706f73616c426f6e644d696e696d756d3042616c616e63654f663c543e4000407a10f35a00000000000000000000044901204d696e696d756d20616d6f756e74206f662066756e647320746861742073686f756c6420626520706c6163656420696e2061206465706f73697420666f72206d616b696e6720612070726f706f73616c2e2c5370656e64506572696f6438543a3a426c6f636b4e756d6265721080700000048820506572696f64206265747765656e2073756363657373697665207370656e64732e104275726e1c5065726d696c6c1020a107000411012050657263656e74616765206f662073706172652066756e64732028696620616e7929207468617420617265206275726e7420706572207370656e6420706572696f642e30546970436f756e74646f776e38543a3a426c6f636b4e756d62657210807000000445012054686520706572696f6420666f722077686963682061207469702072656d61696e73206f70656e20616674657220697320686173206163686965766564207468726573686f6c6420746970706572732e3454697046696e646572734665651c50657263656e7404140431012054686520616d6f756e74206f66207468652066696e616c2074697020776869636820676f657320746f20746865206f726967696e616c207265706f72746572206f6620746865207469702e505469705265706f72744465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004d42054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120746970207265706f72742e5c5469705265706f72744465706f736974506572427974653042616c616e63654f663c543e400010a5d4e800000000000000000000000409012054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e2074686520746970207265706f727420726561736f6e2e2070496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e50496e76616c696450726f706f73616c496e646578046c204e6f2070726f706f73616c206174207468617420696e6465782e30526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e30416c72656164794b6e6f776e048c20546865207469702077617320616c726561647920666f756e642f737461727465642e28556e6b6e6f776e54697004642054686520746970206861736820697320756e6b6e6f776e2e244e6f7446696e64657204210120546865206163636f756e7420617474656d7074696e6720746f20726574726163742074686520746970206973206e6f74207468652066696e646572206f6620746865207469702e245374696c6c4f70656e042d0120546865207469702063616e6e6f7420626520636c61696d65642f636c6f736564206265636175736520746865726520617265206e6f7420656e6f7567682074697070657273207965742e245072656d617475726504350120546865207469702063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e24436f6e7472616374730120436f6e74726163741c204761735370656e7401000c476173200000000000000000048020476173207370656e7420736f2066617220696e207468697320626c6f636b2e3c43757272656e745363686564756c650100205363686564756c65c5010000000001000000000000000100000000000000010000000000000001000000000000000100000000000000010000000000000001000000000000008700000000000000af000000000000000100000000000000010000000000000004000000000001001000000000400000002000000004942043757272656e7420636f7374207363686564756c6520666f7220636f6e7472616374732e305072697374696e65436f64650001012c436f6465486173683c543e1c5665633c75383e0004000465012041206d617070696e672066726f6d20616e206f726967696e616c20636f6465206861736820746f20746865206f726967696e616c20636f64652c20756e746f756368656420627920696e737472756d656e746174696f6e2e2c436f646553746f726167650001012c436f6465486173683c543e587761736d3a3a5072656661625761736d4d6f64756c650004000465012041206d617070696e67206265747765656e20616e206f726967696e616c20636f6465206861736820616e6420696e737472756d656e746564207761736d20636f64652c20726561647920666f7220657865637574696f6e2e384163636f756e74436f756e74657201000c753634200000000000000000045420546865207375627472696520636f756e7465722e38436f6e7472616374496e666f4f6600010130543a3a4163636f756e7449643c436f6e7472616374496e666f3c543e00040004a82054686520636f6465206173736f6369617465642077697468206120676976656e206163636f756e742e20476173507269636501003042616c616e63654f663c543e4001000000000000000000000000000000047820546865207072696365206f66206f6e6520756e6974206f66206761732e01143c7570646174655f7363686564756c6504207363686564756c65205363686564756c650cb4205570646174657320746865207363686564756c6520666f72206d65746572696e6720636f6e7472616374732e000d0120546865207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652073746f726564207363686564756c652e207075745f636f646508246761735f6c696d697430436f6d706163743c4761733e10636f64651c5665633c75383e085d012053746f7265732074686520676976656e2062696e617279205761736d20636f646520696e746f2074686520636861696e27732073746f7261676520616e642072657475726e73206974732060636f646568617368602ed420596f752063616e20696e7374616e746961746520636f6e747261637473206f6e6c7920776974682073746f72656420636f64652e1063616c6c1010646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e10646174611c5665633c75383e1c0901204d616b657320612063616c6c20746f20616e206163636f756e742c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e002901202a20496620746865206163636f756e74206973206120736d6172742d636f6e7472616374206163636f756e742c20746865206173736f63696174656420636f64652077696c6c206265b020657865637574656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e1901202a20496620746865206163636f756e74206973206120726567756c6172206163636f756e742c20616e792076616c75652077696c6c206265207472616e736665727265642e4901202a204966206e6f206163636f756e742065786973747320616e64207468652063616c6c2076616c7565206973206e6f74206c657373207468616e20606578697374656e7469616c5f6465706f736974602c1501206120726567756c6172206163636f756e742077696c6c206265206372656174656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e2c696e7374616e74696174651024656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e24636f64655f686173682c436f6465486173683c543e10646174611c5665633c75383e28bd0120496e7374616e7469617465732061206e657720636f6e74726163742066726f6d207468652060636f646568617368602067656e65726174656420627920607075745f636f6465602c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e009820496e7374616e74696174696f6e20697320657865637574656420617320666f6c6c6f77733a004101202d205468652064657374696e6174696f6e206164647265737320697320636f6d7075746564206261736564206f6e207468652073656e64657220616e642068617368206f662074686520636f64652e0501202d2054686520736d6172742d636f6e7472616374206163636f756e7420697320637265617465642061742074686520636f6d707574656420616464726573732e6d01202d20546865206063746f725f636f64656020697320657865637574656420696e2074686520636f6e74657874206f6620746865206e65776c792d63726561746564206163636f756e742e204275666665722072657475726e65645d0120202061667465722074686520657865637574696f6e206973207361766564206173207468652060636f646560206f6620746865206163636f756e742e205468617420636f64652077696c6c20626520696e766f6b6564a820202075706f6e20616e792063616c6c2072656365697665642062792074686973206163636f756e742e7c202d2054686520636f6e747261637420697320696e697469616c697a65642e3c636c61696d5f73757263686172676508106465737430543a3a4163636f756e744964286175785f73656e646572504f7074696f6e3c543a3a4163636f756e7449643e14710120416c6c6f777320626c6f636b2070726f64756365727320746f20636c61696d206120736d616c6c2072657761726420666f72206576696374696e67206120636f6e74726163742e204966206120626c6f636b2070726f64756365721501206661696c7320746f20646f20736f2c206120726567756c61722075736572732077696c6c20626520616c6c6f77656420746f20636c61696d20746865207265776172642e00390120496620636f6e7472616374206973206e6f742065766963746564206173206120726573756c74206f6620746869732063616c6c2c206e6f20616374696f6e73206172652074616b656e20616e64ac207468652073656e646572206973206e6f7420656c696769626c6520666f7220746865207265776172642e0118205472616e736665720c244163636f756e744964244163636f756e7449641c42616c616e6365046901205472616e736665722068617070656e6564206066726f6d6020746f2060746f60207769746820676976656e206076616c7565602061732070617274206f662061206063616c6c60206f722060696e7374616e7469617465602e30496e7374616e74696174656408244163636f756e744964244163636f756e74496404dc20436f6e7472616374206465706c6f7965642062792061646472657373206174207468652073706563696669656420616464726573732e28436f646553746f72656404104861736804b820436f646520776974682074686520737065636966696564206861736820686173206265656e2073746f7265642e3c5363686564756c6555706461746564040c75333204c020547269676765726564207768656e207468652063757272656e74207363686564756c6520697320757064617465642e284469737061746368656408244163636f756e74496410626f6f6c08390120412063616c6c2077617320646973706174636865642066726f6d2074686520676976656e206163636f756e742e2054686520626f6f6c207369676e616c7320776865746865722069742077617374207375636365737366756c20657865637574696f6e206f72206e6f742e20436f6e747261637408244163636f756e7449641c5665633c75383e048c20416e206576656e742066726f6d20636f6e7472616374206f66206163636f756e742e404c5369676e6564436c61696d48616e646963617038543a3a426c6f636b4e756d626572100200000010e0204e756d626572206f6620626c6f636b2064656c617920616e2065787472696e73696320636c61696d20737572636861726765206861732e000d01205768656e20636c61696d207375726368617267652069732063616c6c656420627920616e2065787472696e736963207468652072656e7420697320636865636b65646820666f722063757272656e745f626c6f636b202d2064656c617940546f6d6273746f6e654465706f7369743042616c616e63654f663c543e4000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f2067656e6572617465206120746f6d6273746f6e652e4453746f7261676553697a654f66667365740c75333210080000000851012053697a65206f66206120636f6e7472616374206174207468652074696d65206f6620696e7374616e746961696f6e2e205468697320697320612073696d706c652077617920746f20656e737572652074686174a420656d70747920636f6e747261637473206576656e7475616c6c7920676574732064656c657465642e2c52656e74427974654665653042616c616e63654f663c543e4000407a10f35a00000000000000000000043501205072696365206f6620612062797465206f662073746f7261676520706572206f6e6520626c6f636b20696e74657276616c2e2053686f756c642062652067726561746572207468616e20302e4452656e744465706f7369744f66667365743042616c616e63654f663c543e4000008a5d7845630100000000000000001c05012054686520616d6f756e74206f662066756e6473206120636f6e74726163742073686f756c64206465706f73697420696e206f7264657220746f206f6666736574582074686520636f7374206f66206f6e6520627974652e006901204c6574277320737570706f736520746865206465706f73697420697320312c303030204255202862616c616e636520756e697473292f6279746520616e64207468652072656e7420697320312042552f627974652f6461792c5901207468656e206120636f6e7472616374207769746820312c3030302c3030302042552074686174207573657320312c303030206279746573206f662073746f7261676520776f756c6420706179206e6f2072656e742e4d0120427574206966207468652062616c616e6365207265647563656420746f203530302c30303020425520616e64207468652073746f7261676520737461796564207468652073616d6520617420312c3030302c78207468656e20697420776f756c6420706179203530302042552f6461792e3c5375726368617267655265776172643042616c616e63654f663c543e400080a1a76b4a3500000000000000000008e4205265776172642074686174206973207265636569766564206279207468652070617274792077686f736520746f75636820686173206c65646820746f2072656d6f76616c206f66206120636f6e74726163742e2c5472616e736665724665653042616c616e63654f663c543e400010a5d4e800000000000000000000000494205468652066656520726571756972656420746f206d616b652061207472616e736665722e2c4372656174696f6e4665653042616c616e63654f663c543e400010a5d4e80000000000000000000000049c205468652066656520726571756972656420746f2063726561746520616e206163636f756e742e485472616e73616374696f6e426173654665653042616c616e63654f663c543e400010a5d4e8000000000000000000000004dc205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b2074686520626173652e485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e2c436f6e74726163744665653042616c616e63654f663c543e400010a5d4e80000000000000000000000084101205468652066656520726571756972656420746f20696e7374616e7469617465206120636f6e747261637420696e7374616e63652e204120726561736f6e61626c652064656661756c742076616c75651c2069732032312e2c43616c6c426173654665650c47617320e803000000000000081d0120546865206261736520666565206368617267656420666f722063616c6c696e6720696e746f206120636f6e74726163742e204120726561736f6e61626c652064656661756c74382076616c7565206973203133352e48496e7374616e7469617465426173654665650c47617320e80300000000000008390120546865206261736520666565206368617267656420666f7220696e7374616e74696174696e67206120636f6e74726163742e204120726561736f6e61626c652064656661756c742076616c756520206973203137352e204d617844657074680c753332102000000008310120546865206d6178696d756d206e657374696e67206c6576656c206f6620612063616c6c2f696e7374616e746961746520737461636b2e204120726561736f6e61626c652064656661756c74382076616c7565206973203130302e304d617856616c756553697a650c753332100040000004390120546865206d6178696d756d2073697a65206f6620612073746f726167652076616c756520696e2062797465732e204120726561736f6e61626c652064656661756c74206973203136204b69422e34426c6f636b4761734c696d69740c47617320809698000000000008250120546865206d6178696d756d20616d6f756e74206f6620676173207468617420636f756c6420626520657870656e6465642070657220626c6f636b2e204120726561736f6e61626c65742064656661756c742076616c75652069732031305f3030305f3030302e1858496e76616c69645363686564756c6556657273696f6e0405012041206e6577207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652063757272656e74206f6e652e54496e76616c6964537572636861726765436c61696d04550120416e206f726967696e206d757374206265207369676e6564206f7220696e686572656e7420616e6420617578696c696172792073656e646572206f6e6c792070726f7669646564206f6e20696e686572656e742e54496e76616c6964536f75726365436f6e747261637404dc2043616e6e6f7420726573746f72652066726f6d206e6f6e6578697374696e67206f7220746f6d6273746f6e6520636f6e74726163742e68496e76616c696444657374696e6174696f6e436f6e747261637404c42043616e6e6f7420726573746f726520746f206e6f6e6578697374696e67206f7220616c69766520636f6e74726163742e40496e76616c6964546f6d6273746f6e65046020546f6d6273746f6e657320646f6e2774206d617463682e54496e76616c6964436f6e74726163744f726967696e04bc20416e206f726967696e20547269654964207772697474656e20696e207468652063757272656e7420626c6f636b2e105375646f01105375646f040c4b6579010030543a3a4163636f756e74496480000000000000000000000000000000000000000000000000000000000000000004842054686520604163636f756e74496460206f6620746865207375646f206b65792e010c107375646f042070726f706f73616c40426f783c543a3a50726f706f73616c3e2839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ed4202d20556e6b6e6f776e20776569676874206f662064657269766174697665206070726f706f73616c6020657865637574696f6e2e302023203c2f7765696768743e1c7365745f6b6579040c6e65778c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652475012041757468656e74696361746573207468652063757272656e74207375646f206b657920616e6420736574732074686520676976656e204163636f756e7449642028606e6577602920617320746865206e6577207375646f206b65792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e1c7375646f5f6173080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652070726f706f73616c40426f783c543a3a50726f706f73616c3e2c51012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c207769746820605369676e656460206f726967696e2066726f6d44206120676976656e206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ed4202d20556e6b6e6f776e20776569676874206f662064657269766174697665206070726f706f73616c6020657865637574696f6e2e302023203c2f7765696768743e010c1453756469640410626f6f6c04602041207375646f206a75737420746f6f6b20706c6163652e284b65794368616e67656404244163636f756e74496404f020546865207375646f6572206a757374207377697463686564206964656e746974793b20746865206f6c64206b657920697320737570706c6965642e285375646f4173446f6e650410626f6f6c04602041207375646f206a75737420746f6f6b20706c6163652e00042c526571756972655375646f04802053656e646572206d75737420626520746865205375646f206163636f756e7420496d4f6e6c696e650120496d4f6e6c696e651020476f737369704174010038543a3a426c6f636b4e756d626572100000000004a02054686520626c6f636b206e756d626572207768656e2077652073686f756c6420676f737369702e104b65797301004c5665633c543a3a417574686f7269747949643e040004d0205468652063757272656e7420736574206f66206b6579732074686174206d61792069737375652061206865617274626561742e485265636569766564486561727462656174730002013053657373696f6e496e6465782441757468496e6465781c5665633c75383e01040008e420466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206041757468496e646578608c20746f20606f6666636861696e3a3a4f70617175654e6574776f726b5374617465602e38417574686f726564426c6f636b730102013053657373696f6e496e64657838543a3a56616c696461746f7249640c75333201100000000008150120466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f662060543a3a56616c696461746f7249646020746f20746865c8206e756d626572206f6620626c6f636b7320617574686f7265642062792074686520676976656e20617574686f726974792e0104246865617274626561740824686561727462656174644865617274626561743c543a3a426c6f636b4e756d6265723e285f7369676e6174757265bc3c543a3a417574686f7269747949642061732052756e74696d654170705075626c69633e3a3a5369676e617475726500010c444865617274626561745265636569766564042c417574686f72697479496404c02041206e657720686561727462656174207761732072656365697665642066726f6d2060417574686f726974794964601c416c6c476f6f640004d42041742074686520656e64206f66207468652073657373696f6e2c206e6f206f6666656e63652077617320636f6d6d69747465642e2c536f6d654f66666c696e6504605665633c4964656e74696669636174696f6e5475706c653e0431012041742074686520656e64206f66207468652073657373696f6e2c206174206c65617374206f6e63652076616c696461746f722077617320666f756e6420746f206265206f66666c696e652e000828496e76616c69644b65790464204e6f6e206578697374656e74207075626c6963206b65792e4c4475706c6963617465644865617274626561740458204475706c696361746564206865617274626561742e48417574686f72697479446973636f76657279000100000000204f6666656e63657301204f6666656e6365730c1c5265706f727473000101345265706f727449644f663c543ed04f6666656e636544657461696c733c543a3a4163636f756e7449642c20543a3a4964656e74696669636174696f6e5475706c653e00040004490120546865207072696d61727920737472756374757265207468617420686f6c647320616c6c206f6666656e6365207265636f726473206b65796564206279207265706f7274206964656e746966696572732e58436f6e63757272656e745265706f727473496e646578010201104b696e64384f706171756554696d65536c6f74485665633c5265706f727449644f663c543e3e010400042901204120766563746f72206f66207265706f727473206f66207468652073616d65206b696e6420746861742068617070656e6564206174207468652073616d652074696d6520736c6f742e485265706f72747342794b696e64496e646578010101104b696e641c5665633c75383e00040018110120456e756d65726174657320616c6c207265706f727473206f662061206b696e6420616c6f6e672077697468207468652074696d6520746865792068617070656e65642e00bc20416c6c207265706f7274732061726520736f72746564206279207468652074696d65206f66206f6666656e63652e004901204e6f74652074686174207468652061637475616c2074797065206f662074686973206d617070696e6720697320605665633c75383e602c207468697320697320626563617573652076616c756573206f66690120646966666572656e7420747970657320617265206e6f7420737570706f7274656420617420746865206d6f6d656e7420736f2077652061726520646f696e6720746865206d616e75616c2073657269616c697a6174696f6e2e010001041c4f6666656e636508104b696e64384f706171756554696d65536c6f7408550120546865726520697320616e206f6666656e6365207265706f72746564206f662074686520676976656e20606b696e64602068617070656e656420617420746865206073657373696f6e5f696e6465786020616e64390120286b696e642d7370656369666963292074696d6520736c6f742e2054686973206576656e74206973206e6f74206465706f736974656420666f72206475706c696361746520736c61736865732e00006052616e646f6d6e657373436f6c6c656374697665466c6970016052616e646f6d6e657373436f6c6c656374697665466c6970043852616e646f6d4d6174657269616c0100305665633c543a3a486173683e04000c610120536572696573206f6620626c6f636b20686561646572732066726f6d20746865206c61737420383120626c6f636b73207468617420616374732061732072616e646f6d2073656564206d6174657269616c2e2054686973610120697320617272616e67656420617320612072696e672062756666657220776974682060626c6f636b5f6e756d626572202520383160206265696e672074686520696e64657820696e746f20746865206056656360206f664420746865206f6c6465737420686173682e0100000000204964656e7469747901105375646f10284964656e746974794f6600010130543a3a4163636f756e74496468526567697374726174696f6e3c42616c616e63654f663c543e3e00040004210120496e666f726d6174696f6e20746861742069732070657274696e656e7420746f206964656e746966792074686520656e7469747920626568696e6420616e206163636f756e742e1c53757065724f6600010130543a3a4163636f756e7449645028543a3a4163636f756e7449642c204461746129000400086101205468652073757065722d6964656e74697479206f6620616e20616c7465726e6174697665202273756222206964656e7469747920746f676574686572207769746820697473206e616d652c2077697468696e2074686174510120636f6e746578742e20496620746865206163636f756e74206973206e6f7420736f6d65206f74686572206163636f756e742773207375622d6964656e746974792c207468656e206a75737420604e6f6e65602e18537562734f6601010130543a3a4163636f756e744964842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e29004400000000000000000000000000000000000cb820416c7465726e6174697665202273756222206964656e746974696573206f662074686973206163636f756e742e001d0120546865206669727374206974656d20697320746865206465706f7369742c20746865207365636f6e64206973206120766563746f72206f6620746865206163636f756e74732e28526567697374726172730100d85665633c4f7074696f6e3c526567697374726172496e666f3c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e3e0400104d012054686520736574206f6620726567697374726172732e204e6f7420657870656374656420746f206765742076657279206269672061732063616e206f6e6c79206265206164646564207468726f7567682061a8207370656369616c206f726967696e20286c696b656c79206120636f756e63696c206d6f74696f6e292e0029012054686520696e64657820696e746f20746869732063616e206265206361737420746f2060526567697374726172496e6465786020746f2067657420612076616c69642076616c75652e012c346164645f726567697374726172041c6163636f756e7430543a3a4163636f756e744964347c2041646420612072656769737472617220746f207468652073797374656d2e001d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605265676973747261724f726967696e60206f722060526f6f74602e00ac202d20606163636f756e74603a20746865206163636f756e74206f6620746865207265676973747261722e009820456d6974732060526567697374726172416464656460206966207375636365737366756c2e002c2023203c7765696768743ee4202d20604f2852296020776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e646564292e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e307365745f6964656e746974790410696e666f304964656e74697479496e666f482d012053657420616e206163636f756e742773206964656e7469747920696e666f726d6174696f6e20616e6420726573657276652074686520617070726f707269617465206465706f7369742e00590120496620746865206163636f756e7420616c726561647920686173206964656e7469747920696e666f726d6174696f6e2c20746865206465706f7369742069732074616b656e2061732070617274207061796d656e745420666f7220746865206e6577206465706f7369742e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e0090202d2060696e666f603a20546865206964656e7469747920696e666f726d6174696f6e2e008c20456d69747320604964656e7469747953657460206966207375636365737366756c2e002c2023203c7765696768743e0501202d20604f2858202b2052296020776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e646564292e88202d204174206d6f73742074776f2062616c616e6365206f7065726174696f6e732eac202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f2858202b20522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e207365745f73756273041073756273645665633c28543a3a4163636f756e7449642c2044617461293e40902053657420746865207375622d6163636f756e7473206f66207468652073656e6465722e005901205061796d656e743a20416e79206167677265676174652062616c616e63652072657365727665642062792070726576696f757320607365745f73756273602063616c6c732077696c6c2062652072657475726e6564310120616e6420616e20616d6f756e7420605375624163636f756e744465706f736974602077696c6c20626520726573657276656420666f722065616368206974656d20696e206073756273602e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e009c202d206073756273603a20546865206964656e746974792773207375622d6163636f756e74732e002c2023203c7765696768743eec202d20604f285329602077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e88202d204174206d6f73742074776f2062616c616e6365206f7065726174696f6e732e4101202d204174206d6f7374204f2832202a2053202b2031292073746f72616765206d75746174696f6e733b20636f64656320636f6d706c657869747920604f2831202a2053202b2053202a20312960293b582020206f6e652073746f726167652d6578697374732e302023203c2f7765696768743e38636c6561725f6964656e74697479003c390120436c65617220616e206163636f756e742773206964656e7469747920696e666f20616e6420616c6c207375622d6163636f756e7420616e642072657475726e20616c6c206465706f736974732e00f0205061796d656e743a20416c6c2072657365727665642062616c616e636573206f6e20746865206163636f756e74206172652072657475726e65642e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e009c20456d69747320604964656e74697479436c656172656460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2852202b2053202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e74202d206053202b2032602073746f726167652064656c6574696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e44726571756573745f6a756467656d656e7408247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e1c6d61785f66656554436f6d706163743c42616c616e63654f663c543e3e5c9820526571756573742061206a756467656d656e742066726f6d2061207265676973747261722e005901205061796d656e743a204174206d6f737420606d61785f666565602077696c6c20626520726573657276656420666f72207061796d656e7420746f2074686520726567697374726172206966206a756467656d656e741c20676976656e2e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e002101202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973207265717565737465642e5901202d20606d61785f666565603a20546865206d6178696d756d206665652074686174206d617920626520706169642e20546869732073686f756c64206a757374206265206175746f2d706f70756c617465642061733a0034206060606e6f636f6d70696c65a42053656c663a3a72656769737472617273287265675f696e646578292e75776e72617028292e666565102060606000a820456d69747320604a756467656d656e7452657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2858202b205229602e34202d204f6e65206576656e742e302023203c2f7765696768743e3863616e63656c5f7265717565737404247265675f696e64657838526567697374726172496e646578446c2043616e63656c20612070726576696f757320726571756573742e00fc205061796d656e743a20412070726576696f75736c79207265736572766564206465706f7369742069732072657475726e6564206f6e20737563636573732e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e004901202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206e6f206c6f6e676572207265717565737465642e00b020456d69747320604a756467656d656e74556e72657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e8c202d204f6e652073746f72616765206d75746174696f6e20604f2852202b205829602e34202d204f6e65206576656e742e302023203c2f7765696768743e1c7365745f6665650814696e6465785c436f6d706163743c526567697374726172496e6465783e0c66656554436f6d706163743c42616c616e63654f663c543e3e301d0120536574207468652066656520726571756972656420666f722061206a756467656d656e7420746f206265207265717565737465642066726f6d2061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e58202d2060666565603a20746865206e6577206665652e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602e302023203c2f7765696768743e387365745f6163636f756e745f69640814696e6465785c436f6d706163743c526567697374726172496e6465783e0c6e657730543a3a4163636f756e74496430c0204368616e676520746865206163636f756e74206173736f63696174656420776974682061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e74202d20606e6577603a20746865206e6577206163636f756e742049442e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602e302023203c2f7765696768743e287365745f6669656c64730814696e6465785c436f6d706163743c526567697374726172496e6465783e186669656c6473384964656e746974794669656c647330ac2053657420746865206669656c6420696e666f726d6174696f6e20666f722061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e1101202d20606669656c6473603a20746865206669656c64732074686174207468652072656769737472617220636f6e6365726e73207468656d73656c76657320776974682e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602e302023203c2f7765696768743e4470726f766964655f6a756467656d656e740c247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365246a756467656d656e745c4a756467656d656e743c42616c616e63654f663c543e3e4cbc2050726f766964652061206a756467656d656e7420666f7220616e206163636f756e742773206964656e746974792e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74b4206f6620746865207265676973747261722077686f736520696e64657820697320607265675f696e646578602e002501202d20607265675f696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206265696e67206d6164652e5901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e4d01202d20606a756467656d656e74603a20746865206a756467656d656e74206f662074686520726567697374726172206f6620696e64657820607265675f696e646578602061626f75742060746172676574602e009820456d69747320604a756467656d656e74476976656e60206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e88202d204f6e652062616c616e63652d7472616e73666572206f7065726174696f6e2e98202d20557020746f206f6e65206163636f756e742d6c6f6f6b7570206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2852202b205829602e34202d204f6e65206576656e742e302023203c2f7765696768743e346b696c6c5f6964656e7469747904187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654c45012052656d6f766520616e206163636f756e742773206964656e7469747920616e64207375622d6163636f756e7420696e666f726d6174696f6e20616e6420736c61736820746865206465706f736974732e006501205061796d656e743a2052657365727665642062616c616e6365732066726f6d20607365745f737562736020616e6420607365745f6964656e74697479602061726520736c617368656420616e642068616e646c656420627949012060536c617368602e20566572696669636174696f6e2072657175657374206465706f7369747320617265206e6f742072657475726e65643b20746865792073686f756c642062652063616e63656c6c656484206d616e75616c6c79207573696e67206063616e63656c5f72657175657374602e00310120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f206f72206d617463682060543a3a466f7263654f726967696e602e005901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e009820456d69747320604964656e746974794b696c6c656460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2852202b2053202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e74202d206053202b2032602073746f72616765206d75746174696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e011c2c4964656e7469747953657404244163636f756e74496404f02041206e616d652077617320736574206f72207265736574202877686963682077696c6c2072656d6f766520616c6c206a756467656d656e7473292e3c4964656e74697479436c656172656408244163636f756e7449641c42616c616e636504d02041206e616d652077617320636c65617265642c20616e642074686520676976656e2062616c616e63652072657475726e65642e384964656e746974794b696c6c656408244163636f756e7449641c42616c616e636504c82041206e616d65207761732072656d6f76656420616e642074686520676976656e2062616c616e636520736c61736865642e484a756467656d656e7452657175657374656408244163636f756e74496438526567697374726172496e64657804a02041206a756467656d656e74207761732061736b65642066726f6d2061207265676973747261722e504a756467656d656e74556e72657175657374656408244163636f756e74496438526567697374726172496e646578048c2041206a756467656d656e74207265717565737420776173207265747261637465642e384a756467656d656e74476976656e08244163636f756e74496438526567697374726172496e64657804982041206a756467656d656e742077617320676976656e2062792061207265676973747261722e3852656769737472617241646465640438526567697374726172496e646578045c204120726567697374726172207761732061646465642e002c48546f6f4d616e795375624163636f756e7473046020546f6f206d616e7920737562732d6163636f756e74732e204e6f74466f756e640454204163636f756e742069736e277420666f756e642e204e6f744e616d65640454204163636f756e742069736e2774206e616d65642e28456d707479496e646578043420456d70747920696e6465782e284665654368616e676564044020466565206973206368616e6765642e284e6f4964656e74697479044c204e6f206964656e7469747920666f756e642e3c537469636b794a756467656d656e74044820537469636b79206a756467656d656e742e384a756467656d656e74476976656e0444204a756467656d656e7420676976656e2e40496e76616c69644a756467656d656e74044c20496e76616c6964206a756467656d656e742e30496e76616c6964496e64657804582054686520696e64657820697320696e76616c69642e34496e76616c6964546172676574045c205468652074617267657420697320696e76616c69642e1c536f6369657479011c536f6369657479401c466f756e646572000030543a3a4163636f756e7449640400044820546865206669727374206d656d6265722e1452756c657300001c543a3a48617368040008510120412068617368206f66207468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e2043616e206f6e6c7920626520736574206f6e636520616e6454206f6e6c792062792074686520666f756e6465722e2843616e6469646174657301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e0400043901205468652063757272656e7420736574206f662063616e646964617465733b206269646465727320746861742061726520617474656d7074696e6720746f206265636f6d65206d656d626572732e4c53757370656e64656443616e6469646174657300010130543a3a4163636f756e744964e42842616c616e63654f663c542c20493e2c204269644b696e643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e2900040004842054686520736574206f662073757370656e6465642063616e646964617465732e0c506f7401003c42616c616e63654f663c542c20493e400000000000000000000000000000000004410120416d6f756e74206f66206f7572206163636f756e742062616c616e63652074686174206973207370656369666963616c6c7920666f7220746865206e65787420726f756e642773206269642873292e1048656164000030543a3a4163636f756e744964040004e820546865206d6f7374207072696d6172792066726f6d20746865206d6f737420726563656e746c7920617070726f766564206d656d626572732e1c4d656d626572730100445665633c543a3a4163636f756e7449643e04000494205468652063757272656e7420736574206f66206d656d626572732c206f7264657265642e4053757370656e6465644d656d6265727301010130543a3a4163636f756e74496410626f6f6c00040004782054686520736574206f662073757370656e646564206d656d626572732e104269647301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e040004e8205468652063757272656e7420626964732c2073746f726564206f726465726564206279207468652076616c7565206f6620746865206269642e20566f756368696e6700010130543a3a4163636f756e74496438566f756368696e6753746174757300040004e4204d656d626572732063757272656e746c7920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e1c5061796f75747301010130543a3a4163636f756e744964985665633c28543a3a426c6f636b4e756d6265722c2042616c616e63654f663c542c20493e293e000400044d012050656e64696e67207061796f7574733b206f72646572656420627920626c6f636b206e756d6265722c20776974682074686520616d6f756e7420746861742073686f756c642062652070616964206f75742e1c537472696b657301010130543a3a4163636f756e7449642c537472696b65436f756e7400100000000004dc20546865206f6e676f696e67206e756d626572206f66206c6f73696e6720766f746573206361737420627920746865206d656d6265722e14566f74657300020530543a3a4163636f756e74496430543a3a4163636f756e74496410566f746505040004d020446f75626c65206d61702066726f6d2043616e646964617465202d3e20566f746572202d3e20284d617962652920566f74652e20446566656e646572000030543a3a4163636f756e744964040004c42054686520646566656e64696e67206d656d6265722063757272656e746c79206265696e67206368616c6c656e6765642e34446566656e646572566f74657300010530543a3a4163636f756e74496410566f7465000400046020566f74657320666f722074686520646566656e6465722e284d61784d656d6265727301000c753332100000000004dc20546865206d6178206e756d626572206f66206d656d6265727320666f722074686520736f6369657479206174206f6e652074696d652e01300c626964041476616c75653c42616c616e63654f663c542c20493e84e020412075736572206f757473696465206f662074686520736f63696574792063616e206d616b6520612062696420666f7220656e7472792e003901205061796d656e743a206043616e6469646174654465706f736974602077696c6c20626520726573657276656420666f72206d616b696e672061206269642e2049742069732072657475726e6564f0207768656e2074686520626964206265636f6d65732061206d656d6265722c206f7220696620746865206269642063616c6c732060756e626964602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a5901202d206076616c7565603a2041206f6e652074696d65207061796d656e74207468652062696420776f756c64206c696b6520746f2072656365697665207768656e206a6f696e696e672074686520736f63696574792e002c2023203c7765696768743e5501204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520726573657276652944202d2053746f726167652052656164733aec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f284329c820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d2948202d2053746f72616765205772697465733a810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3a2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6820092d204f6e65206576656e7420666f72206e6577206269642efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e14756e626964040c706f730c7533324cd82041206269646465722063616e2072656d6f76652074686569722062696420666f7220656e74727920696e746f20736f63696574792e010120427920646f696e6720736f2c20746865792077696c6c20686176652074686569722063616e646964617465206465706f7369742072657475726e6564206f728420746865792077696c6c20756e766f75636820746865697220766f75636865722e00fc205061796d656e743a2054686520626964206465706f73697420697320756e7265736572766564206966207468652075736572206d6164652061206269642e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206269646465722e003020506172616d65746572733a1901202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2077616e747320746f20756e6269642e002c2023203c7765696768743eb0204b65793a204220286c656e206f662062696473292c2058202862616c616e636520756e72657365727665290d01202d204f6e652073746f72616765207265616420616e6420777269746520746f20726574726965766520616e64207570646174652074686520626964732e204f2842294501202d20456974686572206f6e6520756e726573657276652062616c616e636520616374696f6e204f285829206f72206f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2842202b205829302023203c2f7765696768743e14766f7563680c0c77686f30543a3a4163636f756e7449641476616c75653c42616c616e63654f663c542c20493e0c7469703c42616c616e63654f663c542c20493eb045012041732061206d656d6265722c20766f75636820666f7220736f6d656f6e6520746f206a6f696e20736f636965747920627920706c6163696e67206120626964206f6e20746865697220626568616c662e005501205468657265206973206e6f206465706f73697420726571756972656420746f20766f75636820666f722061206e6577206269642c206275742061206d656d6265722063616e206f6e6c7920766f75636820666f725d01206f6e652062696420617420612074696d652e2049662074686520626964206265636f6d657320612073757370656e6465642063616e64696461746520616e6420756c74696d6174656c792072656a65637465642062794101207468652073757370656e73696f6e206a756467656d656e74206f726967696e2c20746865206d656d6265722077696c6c2062652062616e6e65642066726f6d20766f756368696e6720616761696e2e005901204173206120766f756368696e67206d656d6265722c20796f752063616e20636c61696d206120746970206966207468652063616e6469646174652069732061636365707465642e2054686973207469702077696c6c51012062652070616964206173206120706f7274696f6e206f66207468652072657761726420746865206d656d6265722077696c6c207265636569766520666f72206a6f696e696e672074686520736f63696574792e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733acc202d206077686f603a2054686520757365722077686f20796f7520776f756c64206c696b6520746f20766f75636820666f722e5101202d206076616c7565603a2054686520746f74616c2072657761726420746f2062652070616964206265747765656e20796f7520616e64207468652063616e6469646174652069662074686579206265636f6d65642061206d656d62657220696e2074686520736f63696574792e4901202d2060746970603a20596f757220637574206f662074686520746f74616c206076616c756560207061796f7574207768656e207468652063616e64696461746520697320696e64756374656420696e746f15012074686520736f63696574792e2054697073206c6172676572207468616e206076616c7565602077696c6c206265207361747572617465642075706f6e207061796f75742e002c2023203c7765696768743e0101204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d626572732944202d2053746f726167652052656164733ac820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d29090120092d204f6e652073746f72616765207265616420746f20636865636b206d656d626572206973206e6f7420616c726561647920766f756368696e672e204f283129ec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f28432948202d2053746f72616765205772697465733a0d0120092d204f6e652073746f7261676520777269746520746f20696e7365727420766f756368696e672073746174757320746f20746865206d656d6265722e204f283129810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3ac020092d204f286c6f67204d292073656172636820746f20636865636b2073656e6465722069732061206d656d6265722e2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6020092d204f6e65206576656e7420666f7220766f7563682efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e1c756e766f756368040c706f730c753332442d01204173206120766f756368696e67206d656d6265722c20756e766f7563682061206269642e2054686973206f6e6c7920776f726b73207768696c6520766f7563686564207573657220697394206f6e6c792061206269646465722028616e64206e6f7420612063616e646964617465292e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206120766f756368696e67206d656d6265722e003020506172616d65746572733a2d01202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2073686f756c6420626520756e766f75636865642e002c2023203c7765696768743e54204b65793a204220286c656e206f662062696473290901202d204f6e652073746f726167652072656164204f28312920746f20636865636b20746865207369676e6572206973206120766f756368696e67206d656d6265722eec202d204f6e652073746f72616765206d757461746520746f20726574726965766520616e64207570646174652074686520626964732e204f28422994202d204f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f284229302023203c2f7765696768743e10766f7465082463616e6469646174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c617070726f766510626f6f6c4c882041732061206d656d6265722c20766f7465206f6e20612063616e6469646174652e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733a0d01202d206063616e646964617465603a205468652063616e646964617465207468617420746865206d656d62657220776f756c64206c696b6520746f20626964206f6e2ef4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265d82020202020202020202020202020617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743ebc204b65793a204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722e58202d204f6e65206163636f756e74206c6f6f6b75702e2d01202d204f6e652073746f726167652072656164204f28432920616e64204f2843292073656172636820746f20636865636b2074686174207573657220697320612063616e6469646174652ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204329302023203c2f7765696768743e34646566656e6465725f766f7465041c617070726f766510626f6f6c408c2041732061206d656d6265722c20766f7465206f6e2074686520646566656e6465722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733af4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265a420617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743e68202d204b65793a204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e007820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d29302023203c2f7765696768743e187061796f757400504501205472616e7366657220746865206669727374206d617475726564207061796f757420666f72207468652073656e64657220616e642072656d6f76652069742066726f6d20746865207265636f7264732e006901204e4f54453a20546869732065787472696e736963206e6565647320746f2062652063616c6c6564206d756c7469706c652074696d657320746f20636c61696d206d756c7469706c65206d617475726564207061796f7574732e002101205061796d656e743a20546865206d656d6265722077696c6c20726563656976652061207061796d656e7420657175616c20746f207468656972206669727374206d61747572656478207061796f757420746f20746865697220667265652062616c616e63652e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d62657220776974684c207061796f7574732072656d61696e696e672e002c2023203c7765696768743e1d01204b65793a204d20286c656e206f66206d656d62657273292c205020286e756d626572206f66207061796f75747320666f72206120706172746963756c6172206d656d626572292501202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b207369676e65722069732061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28502920746f2067657420616c6c207061796f75747320666f722061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28312920746f20676574207468652063757272656e7420626c6f636b206e756d6265722e8c202d204f6e652063757272656e6379207472616e736665722063616c6c2e204f2858291101202d204f6e652073746f72616765207772697465206f722072656d6f76616c20746f2075706461746520746865206d656d6265722773207061796f7574732e204f285029009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2050202b205829302023203c2f7765696768743e14666f756e640c1c666f756e64657230543a3a4163636f756e7449642c6d61785f6d656d626572730c7533321472756c65731c5665633c75383e4c4c20466f756e642074686520736f63696574792e00f0205468697320697320646f6e65206173206120646973637265746520616374696f6e20696e206f7264657220746f20616c6c6f7720666f72207468651901206d6f64756c6520746f20626520696e636c7564656420696e746f20612072756e6e696e6720636861696e20616e642063616e206f6e6c7920626520646f6e65206f6e63652e001d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f466f756e6465725365744f726967696e5f2e003020506172616d65746572733a1901202d2060666f756e64657260202d20546865206669727374206d656d62657220616e642068656164206f6620746865206e65776c7920666f756e64656420736f63696574792e1501202d20606d61785f6d656d6265727360202d2054686520696e697469616c206d6178206e756d626572206f66206d656d6265727320666f722074686520736f63696574792ef4202d206072756c657360202d205468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e002c2023203c7765696768743ee0202d2054776f2073746f72616765206d75746174657320746f207365742060486561646020616e642060466f756e646572602e204f283129f4202d204f6e652073746f7261676520777269746520746f2061646420746865206669727374206d656d62657220746f20736f63696574792e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e1c756e666f756e6400348c20416e756c6c2074686520666f756e64696e67206f662074686520736f63696574792e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205369676e65642c20616e6420746865207369676e696e67206163636f756e74206d75737420626520626f74685901207468652060466f756e6465726020616e6420746865206048656164602e205468697320696d706c6965732074686174206974206d6179206f6e6c7920626520646f6e65207768656e207468657265206973206f6e6520206d656d6265722e002c2023203c7765696768743e68202d2054776f2073746f72616765207265616473204f2831292e78202d20466f75722073746f726167652072656d6f76616c73204f2831292e34202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e586a756467655f73757370656e6465645f6d656d626572080c77686f30543a3a4163636f756e7449641c666f726769766510626f6f6c6c2d0120416c6c6f772073757370656e73696f6e206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e646564206d656d6265722e00590120496620612073757370656e646564206d656d62657220697320666f72676976656e2c2077652073696d706c7920616464207468656d206261636b2061732061206d656d6265722c206e6f7420616666656374696e67cc20616e79206f6620746865206578697374696e672073746f72616765206974656d7320666f722074686174206d656d6265722e00490120496620612073757370656e646564206d656d6265722069732072656a65637465642c2072656d6f766520616c6c206173736f6369617465642073746f72616765206974656d732c20696e636c7564696e670101207468656972207061796f7574732c20616e642072656d6f766520616e7920766f7563686564206269647320746865792063757272656e746c7920686176652e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ab4202d206077686f60202d205468652073757370656e646564206d656d62657220746f206265206a75646765642e3501202d2060666f726769766560202d204120626f6f6c65616e20726570726573656e74696e672077686574686572207468652073757370656e73696f6e206a756467656d656e74206f726967696e2501202020202020202020202020202020666f726769766573202860747275656029206f722072656a6563747320286066616c7365602920612073757370656e646564206d656d6265722e002c2023203c7765696768743ea4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d6265727329f8202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e646564206d656d6265722e204f2831297101202d20557020746f206f6e652073746f72616765207772697465204f284d292077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d626572206261636b20746f20736f63696574792ef8202d20557020746f20332073746f726167652072656d6f76616c73204f28312920746f20636c65616e20757020612072656d6f766564206d656d6265722e4501202d20557020746f206f6e652073746f72616765207772697465204f2842292077697468204f2842292073656172636820746f2072656d6f766520766f7563686564206269642066726f6d20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e70202d204f6e652073746f726167652072656d6f76616c2e204f2831297c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204229302023203c2f7765696768743e646a756467655f73757370656e6465645f63616e646964617465080c77686f30543a3a4163636f756e744964246a756467656d656e74244a756467656d656e74a0350120416c6c6f772073757370656e646564206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e6465642063616e6469646174652e005d0120496620746865206a756467656d656e742069732060417070726f7665602c20776520616464207468656d20746f20736f63696574792061732061206d656d62657220776974682074686520617070726f70726961746574207061796d656e7420666f72206a6f696e696e6720736f63696574792e00550120496620746865206a756467656d656e74206973206052656a656374602c2077652065697468657220736c61736820746865206465706f736974206f6620746865206269642c20676976696e67206974206261636b110120746f2074686520736f63696574792074726561737572792c206f722077652062616e2074686520766f75636865722066726f6d20766f756368696e6720616761696e2e005d0120496620746865206a756467656d656e7420697320605265626964602c20776520707574207468652063616e646964617465206261636b20696e207468652062696420706f6f6c20616e64206c6574207468656d20676f94207468726f7567682074686520696e64756374696f6e2070726f6365737320616761696e2e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ac0202d206077686f60202d205468652073757370656e6465642063616e64696461746520746f206265206a75646765642ec4202d20606a756467656d656e7460202d2060417070726f7665602c206052656a656374602c206f7220605265626964602e002c2023203c7765696768743ef4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520616374696f6e29f0202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e6465642063616e6469646174652ec8202d204f6e652073746f726167652072656d6f76616c206f66207468652073757370656e6465642063616e6469646174652e40202d20417070726f7665204c6f676963150120092d204f6e652073746f72616765207265616420746f206765742074686520617661696c61626c6520706f7420746f2070617920757365727320776974682e204f283129dc20092d204f6e652073746f7261676520777269746520746f207570646174652074686520617661696c61626c6520706f742e204f283129e820092d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f283129b420092d204f6e652073746f72616765207265616420746f2067657420616c6c206d656d626572732e204f284d29a020092d20557020746f206f6e6520756e726573657276652063757272656e637920616374696f6e2eb020092d20557020746f2074776f206e65772073746f726167652077726974657320746f207061796f7574732e4d0120092d20557020746f206f6e652073746f726167652077726974652077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d62657220746f20736f63696574792e3c202d2052656a656374204c6f676963dc20092d20557020746f206f6e6520726570617472696174652072657365727665642063757272656e637920616374696f6e2e204f2858292d0120092d20557020746f206f6e652073746f7261676520777269746520746f2062616e2074686520766f756368696e67206d656d6265722066726f6d20766f756368696e6720616761696e2e38202d205265626964204c6f676963410120092d2053746f72616765206d75746174652077697468204f286c6f672042292062696e6172792073656172636820746f20706c616365207468652075736572206261636b20696e746f20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e5c202d204f6e652073746f726167652072656d6f76616c2e7c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2042202b205829302023203c2f7765696768743e3c7365745f6d61785f6d656d62657273040c6d61780c753332381d0120416c6c6f777320726f6f74206f726967696e20746f206368616e676520746865206d6178696d756d206e756d626572206f66206d656d6265727320696e20736f63696574792eb4204d6178206d656d6265727368697020636f756e74206d7573742062652067726561746572207468616e20312e00dc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d205f524f4f545f2e003020506172616d65746572733ae4202d20606d617860202d20546865206d6178696d756d206e756d626572206f66206d656d6265727320666f722074686520736f63696574792e002c2023203c7765696768743eb0202d204f6e652073746f7261676520777269746520746f2075706461746520746865206d61782e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e013c1c466f756e64656404244163636f756e74496404b82054686520736f636965747920697320666f756e6465642062792074686520676976656e206964656e746974792e0c42696408244163636f756e7449641c42616c616e63650861012041206d656d6265727368697020626964206a7573742068617070656e65642e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e64207468656972206f666665723c20697320746865207365636f6e642e14566f7563680c244163636f756e7449641c42616c616e6365244163636f756e7449640861012041206d656d6265727368697020626964206a7573742068617070656e656420627920766f756368696e672e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e64f0207468656972206f6666657220697320746865207365636f6e642e2054686520766f756368696e67207061727479206973207468652074686972642e244175746f556e62696404244163636f756e74496404090120412063616e646964617465207761732064726f70706564202864756520746f20616e20657863657373206f66206269647320696e207468652073797374656d292e14556e62696404244163636f756e74496404b020412063616e646964617465207761732064726f70706564202862792074686569722072657175657374292e1c556e766f75636804244163636f756e74496404f820412063616e646964617465207761732064726f70706564202862792072657175657374206f662077686f20766f756368656420666f72207468656d292e20496e64756374656408244163636f756e744964385665633c4163636f756e7449643e08590120412067726f7570206f662063616e646964617465732068617665206265656e20696e6475637465642e205468652062617463682773207072696d617279206973207468652066697273742076616c75652c207468657420626174636820696e2066756c6c20697320746865207365636f6e642e6053757370656e6465644d656d6265724a756467656d656e7408244163636f756e74496410626f6f6c048c20412073757370656e646564206d656d62657220686173206265656e206a75646765644843616e64696461746553757370656e64656404244163636f756e744964047c20412063616e64696461746520686173206265656e2073757370656e6465643c4d656d62657253757370656e64656404244163636f756e74496404702041206d656d62657220686173206265656e2073757370656e646564284368616c6c656e67656404244163636f756e74496404742041206d656d62657220686173206265656e206368616c6c656e67656410566f74650c244163636f756e744964244163636f756e74496410626f6f6c04c0204120766f746520686173206265656e20706c61636564202863616e6469646174652c20766f7465722c20766f74652930446566656e646572566f746508244163636f756e74496410626f6f6c04f0204120766f746520686173206265656e20706c6163656420666f72206120646566656e64696e67206d656d6265722028766f7465722c20766f746529344e65774d61784d656d62657273040c75333204902041206e6577206d6178206d656d62657220636f756e7420686173206265656e2073657424556e666f756e64656404244163636f756e744964045820536f636965747920697320756e666f756e6465642e184043616e6469646174654465706f7369743c42616c616e63654f663c542c20493e400080c6a47e8d0300000000000000000004fc20546865206d696e696d756d20616d6f756e74206f662061206465706f73697420726571756972656420666f7220612062696420746f206265206d6164652e4857726f6e6753696465446564756374696f6e3c42616c616e63654f663c542c20493e400080f420e6b5000000000000000000000855012054686520616d6f756e74206f662074686520756e70616964207265776172642074686174206765747320646564756374656420696e207468652063617365207468617420656974686572206120736b6570746963c020646f65736e277420766f7465206f7220736f6d656f6e6520766f74657320696e207468652077726f6e67207761792e284d6178537472696b65730c753332100a00000008750120546865206e756d626572206f662074696d65732061206d656d626572206d617920766f7465207468652077726f6e672077617920286f72206e6f7420617420616c6c2c207768656e207468657920617265206120736b65707469632978206265666f72652074686579206265636f6d652073757370656e6465642e2c506572696f645370656e643c42616c616e63654f663c542c20493e400000c52ebca2b1000000000000000000042d012054686520616d6f756e74206f6620696e63656e7469766520706169642077697468696e206561636820706572696f642e20446f65736e277420696e636c75646520566f7465725469702e38526f746174696f6e506572696f6438543a3a426c6f636b4e756d626572100077010004110120546865206e756d626572206f6620626c6f636b73206265747765656e2063616e6469646174652f6d656d6265727368697020726f746174696f6e20706572696f64732e3c4368616c6c656e6765506572696f6438543a3a426c6f636b4e756d626572108013030004d020546865206e756d626572206f6620626c6f636b73206265747765656e206d656d62657273686970206368616c6c656e6765732e482c426164506f736974696f6e049020416e20696e636f727265637420706f736974696f6e207761732070726f76696465642e244e6f744d656d62657204582055736572206973206e6f742061206d656d6265722e34416c72656164794d656d6265720468205573657220697320616c72656164792061206d656d6265722e2453757370656e646564044c20557365722069732073757370656e6465642e304e6f7453757370656e646564045c2055736572206973206e6f742073757370656e6465642e204e6f5061796f7574044c204e6f7468696e6720746f207061796f75742e38416c7265616479466f756e646564046420536f636965747920616c726561647920666f756e6465642e3c496e73756666696369656e74506f74049c204e6f7420656e6f75676820696e20706f7420746f206163636570742063616e6469646174652e3c416c7265616479566f756368696e6704e8204d656d62657220697320616c726561647920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e2e2c4e6f74566f756368696e670460204d656d626572206973206e6f7420766f756368696e672e104865616404942043616e6e6f742072656d6f7665207468652068656164206f662074686520636861696e2e1c466f756e646572046c2043616e6e6f742072656d6f76652074686520666f756e6465722e28416c7265616479426964047420557365722068617320616c7265616479206d6164652061206269642e40416c726561647943616e6469646174650474205573657220697320616c726561647920612063616e6469646174652e304e6f7443616e64696461746504642055736572206973206e6f7420612063616e6469646174652e284d61784d656d62657273048420546f6f206d616e79206d656d6265727320696e2074686520736f63696574792e284e6f74466f756e646572047c205468652063616c6c6572206973206e6f742074686520666f756e6465722e1c4e6f74486561640470205468652063616c6c6572206973206e6f742074686520686561642e205265636f7665727901205265636f766572790c2c5265636f76657261626c6500010130543a3a4163636f756e744964e85265636f76657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e0004000409012054686520736574206f66207265636f76657261626c65206163636f756e747320616e64207468656972207265636f7665727920636f6e66696775726174696f6e2e404163746976655265636f76657269657300020530543a3a4163636f756e74496430543a3a4163636f756e744964e84163746976655265636f766572793c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e050400106820416374697665207265636f7665727920617474656d7074732e001501204669727374206163636f756e7420697320746865206163636f756e7420746f206265207265636f76657265642c20616e6420746865207365636f6e64206163636f756e74ac20697320746865207573657220747279696e6720746f207265636f76657220746865206163636f756e742e245265636f766572656400010130543a3a4163636f756e74496430543a3a4163636f756e7449640004000c98205468652066696e616c206c697374206f66207265636f7665726564206163636f756e74732e00f8204d61702066726f6d20746865207265636f7665726564206163636f756e7420746f2074686520757365722077686f2063616e206163636573732069742e01203061735f7265636f7665726564081c6163636f756e7430543a3a4163636f756e7449641063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e34a42053656e6420612063616c6c207468726f7567682061207265636f7665726564206163636f756e742e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a2501202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f752077616e7420746f206d616b6520612063616c6c206f6e2d626568616c662d6f662e0101202d206063616c6c603a205468652063616c6c20796f752077616e7420746f206d616b65207769746820746865207265636f7665726564206163636f756e742e002c2023203c7765696768743e70202d2054686520776569676874206f6620746865206063616c6c602e0901202d204f6e652073746f72616765206c6f6f6b757020746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e347365745f7265636f766572656408106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e744964341d0120416c6c6f7720524f4f5420746f2062797061737320746865207265636f766572792070726f6365737320616e642073657420616e20612072657363756572206163636f756e747420666f722061206c6f7374206163636f756e74206469726563746c792e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f524f4f545f2e003020506172616d65746572733ab8202d20606c6f7374603a2054686520226c6f7374206163636f756e742220746f206265207265636f76657265642e1d01202d206072657363756572603a20546865202272657363756572206163636f756e74222077686963682063616e2063616c6c20617320746865206c6f7374206163636f756e742e002c2023203c7765696768743e64202d204f6e652073746f72616765207772697465204f28312930202d204f6e65206576656e74302023203c2f7765696768743e3c6372656174655f7265636f766572790c1c667269656e6473445665633c543a3a4163636f756e7449643e247468726573686f6c640c7531363064656c61795f706572696f6438543a3a426c6f636b4e756d6265726c5d01204372656174652061207265636f7665727920636f6e66696775726174696f6e20666f7220796f7572206163636f756e742e2054686973206d616b657320796f7572206163636f756e74207265636f76657261626c652e003101205061796d656e743a2060436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732062616c616e636549012077696c6c20626520726573657276656420666f722073746f72696e6720746865207265636f7665727920636f6e66696775726174696f6e2e2054686973206465706f7369742069732072657475726e6564bc20696e2066756c6c207768656e2074686520757365722063616c6c73206072656d6f76655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2501202d2060667269656e6473603a2041206c697374206f6620667269656e647320796f7520747275737420746f20766f75636820666f72207265636f7665727920617474656d7074732ed420202053686f756c64206265206f72646572656420616e6420636f6e7461696e206e6f206475706c69636174652076616c7565732e3101202d20607468726573686f6c64603a20546865206e756d626572206f6620667269656e64732074686174206d75737420766f75636820666f722061207265636f7665727920617474656d70741d012020206265666f726520746865206163636f756e742063616e206265207265636f76657265642e2053686f756c64206265206c657373207468616e206f7220657175616c20746f94202020746865206c656e677468206f6620746865206c697374206f6620667269656e64732e3d01202d206064656c61795f706572696f64603a20546865206e756d626572206f6620626c6f636b732061667465722061207265636f7665727920617474656d707420697320696e697469616c697a6564e820202074686174206e6565647320746f2070617373206265666f726520746865206163636f756e742063616e206265207265636f76657265642e002c2023203c7765696768743e68202d204b65793a204620286c656e206f6620667269656e6473292d01202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973206e6f7420616c7265616479207265636f76657261626c652e204f2831292eec202d204120636865636b20746861742074686520667269656e6473206c69737420697320736f7274656420616e6420756e697175652e204f2846299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f2858299c202d204f6e652073746f726167652077726974652e204f2831292e20436f646563204f2846292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e44696e6974696174655f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496458ec20496e697469617465207468652070726f6365737320666f72207265636f766572696e672061207265636f76657261626c65206163636f756e742e001d01205061796d656e743a20605265636f766572794465706f736974602062616c616e63652077696c6c20626520726573657276656420666f7220696e6974696174696e67207468652501207265636f766572792070726f636573732e2054686973206465706f7369742077696c6c20616c7761797320626520726570617472696174656420746f20746865206163636f756e74b820747279696e6720746f206265207265636f76657265642e205365652060636c6f73655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e2054686973206163636f756e7401012020206e6565647320746f206265207265636f76657261626c652028692e652e20686176652061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743ef8202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973207265636f76657261626c652e204f2846295101202d204f6e652073746f72616765207265616420746f20636865636b20746861742074686973207265636f766572792070726f63657373206861736e277420616c726561647920737461727465642e204f2831299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f285829e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831296c202d204f6e652073746f726167652077726974652e204f2831292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e38766f7563685f7265636f7665727908106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e74496464290120416c6c6f7720612022667269656e6422206f662061207265636f76657261626c65206163636f756e7420746f20766f75636820666f7220616e20616374697665207265636f76657279682070726f6365737320666f722074686174206163636f756e742e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d75737420626520612022667269656e64227420666f7220746865207265636f76657261626c65206163636f756e742e003020506172616d65746572733ad4202d20606c6f7374603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f2072657363756520746865206c6f7374206163636f756e74207468617420796f755420202077616e7420746f20766f75636820666f722e0025012054686520636f6d62696e6174696f6e206f662074686573652074776f20706172616d6574657273206d75737420706f696e7420746f20616e20616374697665207265636f76657279242070726f636573732e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629ec202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c6572206973206120667269656e642e204f286c6f6746291d01202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c657220686173206e6f7420616c726561647920766f75636865642e204f286c6f6756299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e00a420546f74616c20436f6d706c65786974793a204f2846202b206c6f6746202b2056202b206c6f675629302023203c2f7765696768743e38636c61696d5f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496450f420416c6c6f772061207375636365737366756c207265736375657220746f20636c61696d207468656972207265636f7665726564206163636f756e742e002d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061202272657363756572221d012077686f20686173207375636365737366756c6c7920636f6d706c6574656420746865206163636f756e74207265636f766572792070726f636573733a20636f6c6c6563746564310120607468726573686f6c6460206f72206d6f726520766f75636865732c20776169746564206064656c61795f706572696f646020626c6f636b732073696e636520696e6974696174696f6e2e003020506172616d65746572733a2d01202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f20636c61696d20686173206265656e207375636365737366756c6c79502020207265636f766572656420627920796f752e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205629302023203c2f7765696768743e38636c6f73655f7265636f76657279041c7265736375657230543a3a4163636f756e7449645015012041732074686520636f6e74726f6c6c6572206f662061207265636f76657261626c65206163636f756e742c20636c6f736520616e20616374697665207265636f76657279682070726f6365737320666f7220796f7572206163636f756e742e002101205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e2c20746865207265636f76657261626c65206163636f756e742077696c6c2072656365697665f820746865207265636f76657279206465706f73697420605265636f766572794465706f7369746020706c616365642062792074686520726573637565722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061f0207265636f76657261626c65206163636f756e74207769746820616e20616374697665207265636f766572792070726f6365737320666f722069742e003020506172616d65746572733a1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f207265736375652074686973207265636f76657261626c65206163636f756e742e002c2023203c7765696768743e84204b65793a205620286c656e206f6620766f756368696e6720667269656e6473293d01202d204f6e652073746f7261676520726561642f72656d6f766520746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629c0202d204f6e652062616c616e63652063616c6c20746f20726570617472696174652072657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2856202b205829302023203c2f7765696768743e3c72656d6f76655f7265636f766572790054b82052656d6f766520746865207265636f766572792070726f6365737320666f7220796f7572206163636f756e742e001501204e4f54453a205468652075736572206d757374206d616b65207375726520746f2063616c6c2060636c6f73655f7265636f7665727960206f6e20616c6c206163746976650901207265636f7665727920617474656d707473206265666f72652063616c6c696e6720746869732066756e6374696f6e20656c73652069742077696c6c206661696c2e002501205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e20746865207265636f76657261626c65206163636f756e742077696c6c20756e7265736572766598207468656972207265636f7665727920636f6e66696775726174696f6e206465706f7369742ef4202860436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732900050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061e4207265636f76657261626c65206163636f756e742028692e652e206861732061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743e60204b65793a204620286c656e206f6620667269656e6473292901202d204f6e652073746f72616765207265616420746f206765742074686520707265666978206974657261746f7220666f7220616374697665207265636f7665726965732e204f2831293901202d204f6e652073746f7261676520726561642f72656d6f766520746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846299c202d204f6e652062616c616e63652063616c6c20746f20756e72657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e01183c5265636f766572794372656174656404244163636f756e74496404c82041207265636f766572792070726f6365737320686173206265656e2073657420757020666f7220616e206163636f756e74445265636f76657279496e6974696174656408244163636f756e744964244163636f756e7449640405012041207265636f766572792070726f6365737320686173206265656e20696e6974696174656420666f72206163636f756e745f31206279206163636f756e745f323c5265636f76657279566f75636865640c244163636f756e744964244163636f756e744964244163636f756e7449640441012041207265636f766572792070726f6365737320666f72206163636f756e745f31206279206163636f756e745f3220686173206265656e20766f756368656420666f72206279206163636f756e745f33385265636f76657279436c6f73656408244163636f756e744964244163636f756e74496404f82041207265636f766572792070726f6365737320666f72206163636f756e745f31206279206163636f756e745f3220686173206265656e20636c6f736564404163636f756e745265636f766572656408244163636f756e744964244163636f756e74496404dc204163636f756e745f3120686173206265656e207375636365737366756c6c79207265636f7665726564206279206163636f756e745f323c5265636f7665727952656d6f76656404244163636f756e74496404cc2041207265636f766572792070726f6365737320686173206265656e2072656d6f76656420666f7220616e206163636f756e740000 \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v10.json b/packages/polkadot/tests/meta/v10.json new file mode 100644 index 00000000..66a3d548 --- /dev/null +++ b/packages/polkadot/tests/meta/v10.json @@ -0,0 +1,7821 @@ +{ + "magicNumber": 1635018093, + "metadata": { + "v10": { + "modules": [ + { + "name": "System", + "storage": { + "prefix": "System", + "items": [ + { + "name": "AccountNonce", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Index", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " Extrinsics nonce for accounts." + ] + }, + { + "name": "ExtrinsicCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total extrinsics count for the current block." + ] + }, + { + "name": "AllExtrinsicsWeight", + "modifier": "Optional", + "type": { + "plain": "Weight" + }, + "fallback": "0x00", + "docs": [ + " Total weight for all extrinsics put together, for the current block." + ] + }, + { + "name": "AllExtrinsicsLen", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total length (in bytes) for all extrinsics put together, for the current block." + ] + }, + { + "name": "BlockHash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "BlockNumber", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Map of block numbers to block hashes." + ] + }, + { + "name": "ExtrinsicData", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "u32", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Extrinsics data for the current block (maps an extrinsic's index to its data)." + ] + }, + { + "name": "Number", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The current block number being processed. Set by `execute_block`." + ] + }, + { + "name": "ParentHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Hash of the previous block." + ] + }, + { + "name": "ExtrinsicsRoot", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Extrinsics root of the current block, also part of the block header." + ] + }, + { + "name": "Digest", + "modifier": "Default", + "type": { + "plain": "DigestOf" + }, + "fallback": "0x00", + "docs": [ + " Digest of the current block, also part of the block header." + ] + }, + { + "name": "Events", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Events deposited for the current block." + ] + }, + { + "name": "EventCount", + "modifier": "Default", + "type": { + "plain": "EventIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of events in the `Events` list." + ] + }, + { + "name": "EventTopics", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Vec<(BlockNumber,EventIndex)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Mapping between a topic (represented by T::Hash) and a vector of indexes", + " of events in the `>` list.", + "", + " All topic vectors have deterministic storage locations depending on the topic. This", + " allows light-clients to leverage the changes trie storage tracking mechanism and", + " in case of changes fetch the list of events of interest.", + "", + " The value has the type `(T::BlockNumber, EventIndex)` because if we used only just", + " the `EventIndex` then in case if the topic has the same contents on the next block", + " no notification will be triggered thus the event might be lost." + ] + } + ] + }, + "calls": [ + { + "name": "fill_block", + "args": [], + "docs": [ + " A big dispatch that will disallow any other transaction to be included." + ] + }, + { + "name": "remark", + "args": [ + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark." + ] + }, + { + "name": "set_heap_pages", + "args": [ + { + "name": "pages", + "type": "u64" + } + ], + "docs": [ + " Set the number of pages in the WebAssembly environment's heap." + ] + }, + { + "name": "set_code", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code." + ] + }, + { + "name": "set_code_without_checks", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code without doing any checks of the given `code`." + ] + }, + { + "name": "set_changes_trie_config", + "args": [ + { + "name": "changes_trie_config", + "type": "Option" + } + ], + "docs": [ + " Set the new changes trie configuration." + ] + }, + { + "name": "set_storage", + "args": [ + { + "name": "items", + "type": "Vec" + } + ], + "docs": [ + " Set some items of storage." + ] + }, + { + "name": "kill_storage", + "args": [ + { + "name": "keys", + "type": "Vec" + } + ], + "docs": [ + " Kill some items from storage." + ] + }, + { + "name": "kill_prefix", + "args": [ + { + "name": "prefix", + "type": "Key" + } + ], + "docs": [ + " Kill all storage items with a key that starts with the given prefix." + ] + } + ], + "events": [ + { + "name": "ExtrinsicSuccess", + "args": [ + "DispatchInfo" + ], + "docs": [ + " An extrinsic completed successfully." + ] + }, + { + "name": "ExtrinsicFailed", + "args": [ + "DispatchError", + "DispatchInfo" + ], + "docs": [ + " An extrinsic failed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidSpecName", + "docs": [ + " The name of specification does not match between the current runtime", + " and the new runtime." + ] + }, + { + "name": "SpecVersionNotAllowedToDecrease", + "docs": [ + " The specification version is not allowed to decrease between the current runtime", + " and the new runtime." + ] + }, + { + "name": "ImplVersionNotAllowedToDecrease", + "docs": [ + " The implementation version is not allowed to decrease between the current runtime", + " and the new runtime." + ] + }, + { + "name": "SpecOrImplVersionNeedToIncrease", + "docs": [ + " The specification or the implementation version need to increase between the", + " current runtime and the new runtime." + ] + }, + { + "name": "FailedToExtractRuntimeVersion", + "docs": [ + " Failed to extract the runtime version from the new runtime.", + "", + " Either calling `Core_version` or decoding `RuntimeVersion` failed." + ] + } + ] + }, + { + "name": "Utility", + "storage": { + "prefix": "Utility", + "items": [ + { + "name": "Multisigs", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "[u8;32]", + "value": "Multisig", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " The set of open multisig operations." + ] + } + ] + }, + "calls": [ + { + "name": "batch", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls.", + "", + " This will execute until the first one fails and then stop.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " # ", + " - The sum of the weights of the `calls`.", + " - One event.", + " # ", + "", + " This will return `Ok` in all circumstances. To determine the success of the batch, an", + " event is deposited. If a call failed and the batch was interrupted, then the", + " `BatchInterrupted` event is deposited, along with the number of successful calls made", + " and the error of the failed call. If all were successful, then the `BatchCompleted`", + " event is deposited." + ] + }, + { + "name": "as_sub", + "args": [ + { + "name": "index", + "type": "u16" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through an indexed pseudonym of the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - The weight of the `call`.", + " # " + ] + }, + { + "name": "as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " If there are enough, then dispatch the call.", + "", + " Payment: `MultisigDepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `MultisigDepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call`: The call to be executed.", + "", + " NOTE: Unless this is the final approval, you will generally want to use", + " `approve_as_multi` instead, since it only requires a hash of the call.", + "", + " Result is equivalent to the dispatched result if `threshold` is exactly `1`. Otherwise", + " on success, result is `Ok` and the result from the interior call, if it was executed,", + " may be found in the deposited `MultisigExecuted` event.", + "", + " # ", + " - `O(S + Z + Call)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One call encode & hash, both of complexity `O(Z)` where `Z` is tx-len.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - The weight of the `call`.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `MultisigDepositBase + threshold * MultisigDepositFactor`.", + " # " + ] + }, + { + "name": "approve_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call_hash", + "type": "[u8;32]" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " Payment: `MultisigDepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `MultisigDepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call_hash`: The hash of the call to be executed.", + "", + " NOTE: If this is the final approval, you will want to use `as_multi` instead.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `MultisigDepositBase + threshold * MultisigDepositFactor`.", + " # " + ] + }, + { + "name": "cancel_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "timepoint", + "type": "Timepoint" + }, + { + "name": "call_hash", + "type": "[u8;32]" + } + ], + "docs": [ + " Cancel a pre-existing, on-going multisig transaction. Any deposit reserved previously", + " for this operation will be unreserved on success.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `timepoint`: The timepoint (block number and transaction index) of the first approval", + " transaction for this dispatch.", + " - `call_hash`: The hash of the call to be executed.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - One event.", + " - I/O: 1 read `O(S)`, one remove.", + " - Storage: removes one item.", + " # " + ] + } + ], + "events": [ + { + "name": "BatchInterrupted", + "args": [ + "u32", + "DispatchError" + ], + "docs": [ + " Batch of dispatches did not complete fully. Index of first failing dispatch given, as", + " well as the error." + ] + }, + { + "name": "BatchCompleted", + "args": [], + "docs": [ + " Batch of dispatches completed fully with no error." + ] + }, + { + "name": "NewMultisig", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A new multisig operation has begun. First param is the account that is approving,", + " second is the multisig account." + ] + }, + { + "name": "MultisigApproval", + "args": [ + "AccountId", + "Timepoint", + "AccountId" + ], + "docs": [ + " A multisig operation has been approved by someone. First param is the account that is", + " approving, third is the multisig account." + ] + }, + { + "name": "MultisigExecuted", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "DispatchResult" + ], + "docs": [ + " A multisig operation has been executed. First param is the account that is", + " approving, third is the multisig account." + ] + }, + { + "name": "MultisigCancelled", + "args": [ + "AccountId", + "Timepoint", + "AccountId" + ], + "docs": [ + " A multisig operation has been cancelled. First param is the account that is", + " cancelling, third is the multisig account." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Babe", + "storage": { + "prefix": "Babe", + "items": [ + { + "name": "EpochIndex", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current epoch index." + ] + }, + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Current epoch authorities." + ] + }, + { + "name": "GenesisSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The slot at which the first epoch actually started. This is 0", + " until the first block of the chain." + ] + }, + { + "name": "CurrentSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current slot number." + ] + }, + { + "name": "Randomness", + "modifier": "Default", + "type": { + "plain": "[u8;32]" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The epoch randomness for the *current* epoch.", + "", + " # Security", + "", + " This MUST NOT be used for gambling, as it can be influenced by a", + " malicious validator in the short term. It MAY be used in many", + " cryptographic protocols, however, so long as one remembers that this", + " (like everything else on-chain) it is public. For example, it can be", + " used where a number is needed that cannot have been chosen by an", + " adversary, for purposes such as public-coin zero-knowledge proofs." + ] + }, + { + "name": "NextRandomness", + "modifier": "Default", + "type": { + "plain": "[u8;32]" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Next epoch randomness." + ] + }, + { + "name": "SegmentIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Randomness under construction.", + "", + " We make a tradeoff between storage accesses and list length.", + " We store the under-construction randomness in segments of up to", + " `UNDER_CONSTRUCTION_SEGMENT_LENGTH`.", + "", + " Once a segment reaches this length, we begin the next one.", + " We reset all segments and return to `0` at the beginning of every", + " epoch." + ] + }, + { + "name": "UnderConstruction", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "u32", + "value": "Vec<[u8;32]>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [] + }, + { + "name": "Initialized", + "modifier": "Optional", + "type": { + "plain": "MaybeVrf" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) which is `Some`", + " if per-block initialization has already been called for current block." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [ + { + "name": "EpochDuration", + "type": "u64", + "value": "0xc800000000000000", + "docs": [ + " The number of **slots** that an epoch takes. We couple sessions to", + " epochs, i.e. we start a new session once the new epoch begins." + ] + }, + { + "name": "ExpectedBlockTime", + "type": "Moment", + "value": "0xb80b000000000000", + "docs": [ + " The expected average block time at which BABE should be creating", + " blocks. Since BABE is probabilistic it is not trivial to figure out", + " what the expected average block time should be based on the slot", + " duration and the security parameter `c` (where `1 - c` represents", + " the probability of a slot being empty)." + ] + } + ], + "errors": [] + }, + { + "name": "Timestamp", + "storage": { + "prefix": "Timestamp", + "items": [ + { + "name": "Now", + "modifier": "Default", + "type": { + "plain": "Moment" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current time for the current block." + ] + }, + { + "name": "DidUpdate", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Did the timestamp get updated in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "set", + "args": [ + { + "name": "now", + "type": "Compact" + } + ], + "docs": [ + " Set the current time.", + "", + " This call should be invoked exactly once per block. It will panic at the finalization", + " phase, if this call hasn't been invoked by that time.", + "", + " The timestamp should be greater than the previous one by the amount specified by", + " `MinimumPeriod`.", + "", + " The dispatch origin for this call must be `Inherent`." + ] + } + ], + "events": null, + "constants": [ + { + "name": "MinimumPeriod", + "type": "Moment", + "value": "0xdc05000000000000", + "docs": [ + " The minimum period between blocks. Beware that this is different to the *expected* period", + " that the block production apparatus provides. Your chosen consensus system will generally", + " work with this to determine a sensible block time. e.g. For Aura, it will be double this", + " period on default settings." + ] + } + ], + "errors": [] + }, + { + "name": "Authorship", + "storage": { + "prefix": "Authorship", + "items": [ + { + "name": "Uncles", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Uncles" + ] + }, + { + "name": "Author", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " Author of current block." + ] + }, + { + "name": "DidSetUncles", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Whether uncles were already set in this block." + ] + } + ] + }, + "calls": [ + { + "name": "set_uncles", + "args": [ + { + "name": "new_uncles", + "type": "Vec
" + } + ], + "docs": [ + " Provide a set of uncles." + ] + } + ], + "events": null, + "constants": [], + "errors": [ + { + "name": "InvalidUncleParent", + "docs": [ + " The uncle parent not in the chain." + ] + }, + { + "name": "UnclesAlreadySet", + "docs": [ + " Uncles already set in the block." + ] + }, + { + "name": "TooManyUncles", + "docs": [ + " Too many uncles." + ] + }, + { + "name": "GenesisUncle", + "docs": [ + " The uncle is genesis." + ] + }, + { + "name": "TooHighUncle", + "docs": [ + " The uncle is too high in chain." + ] + }, + { + "name": "UncleAlreadyIncluded", + "docs": [ + " The uncle is already included." + ] + }, + { + "name": "OldUncle", + "docs": [ + " The uncle isn't recent enough to be included." + ] + } + ] + }, + { + "name": "Indices", + "storage": { + "prefix": "Indices", + "items": [ + { + "name": "NextEnumSet", + "modifier": "Default", + "type": { + "plain": "AccountIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free enumeration set." + ] + }, + { + "name": "EnumSet", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The enumeration sets." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "NewAccountIndex", + "args": [ + "AccountId", + "AccountIndex" + ], + "docs": [ + " A new account index was assigned.", + "", + " This event is not triggered when an existing index is reassigned", + " to another `AccountId`." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Balances", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "TotalIssuance", + "modifier": "Default", + "type": { + "plain": "Balance" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total units issued in the system." + ] + }, + { + "name": "Vesting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "VestingSchedule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information regarding the vesting of a given account." + ] + }, + { + "name": "FreeBalance", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Balance", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The 'free' balance of a given account.", + "", + " This is the only balance that matters in terms of most operations on tokens. It", + " alone is used to determine the balance when in the contract execution environment. When this", + " balance falls below the value of `ExistentialDeposit`, then the 'current account' is", + " deleted: specifically `FreeBalance`. Further, the `OnFreeBalanceZero` callback", + " is invoked, giving a chance to external modules to clean up data associated with", + " the deleted account.", + "", + " `frame_system::AccountNonce` is also deleted if `ReservedBalance` is also zero (it also gets", + " collapsed to zero if it ever becomes less than `ExistentialDeposit`." + ] + }, + { + "name": "ReservedBalance", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Balance", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of the balance of a given account that is externally reserved; this can still get", + " slashed, but gets slashed last of all.", + "", + " This balance is a 'reserve' balance that other subsystems use in order to set aside tokens", + " that are still 'owned' by the account holder, but which are suspendable.", + "", + " When this balance falls below the value of `ExistentialDeposit`, then this 'reserve account'", + " is deleted: specifically, `ReservedBalance`.", + "", + " `frame_system::AccountNonce` is also deleted if `FreeBalance` is also zero (it also gets", + " collapsed to zero if it ever becomes less than `ExistentialDeposit`.)" + ] + }, + { + "name": "Locks", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Any liquidity locks on some account balances." + ] + } + ] + }, + "calls": [ + { + "name": "transfer", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Transfer some liquid free balance to another account.", + "", + " `transfer` will set the `FreeBalance` of the sender and receiver.", + " It will decrease the total issuance of the system by the `TransferFee`.", + " If the sender's account is below the existential deposit as a result", + " of the transfer, the account will be reaped.", + "", + " The dispatch origin for this call must be `Signed` by the transactor.", + "", + " # ", + " - Dependent on arguments but not critical, given proper implementations for", + " input config types. See related functions below.", + " - It contains a limited number of reads and writes internally and no complex computation.", + "", + " Related functions:", + "", + " - `ensure_can_withdraw` is always called internally but has a bounded complexity.", + " - Transferring balances to accounts that did not exist before will cause", + " `T::OnNewAccount::on_new_account` to be called.", + " - Removing enough funds from an account will trigger", + " `T::DustRemoval::on_unbalanced` and `T::OnFreeBalanceZero::on_free_balance_zero`.", + " - `transfer_keep_alive` works the same way as `transfer`, but has an additional", + " check that the transfer will not kill the origin account.", + "", + " # " + ] + }, + { + "name": "set_balance", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "new_free", + "type": "Compact" + }, + { + "name": "new_reserved", + "type": "Compact" + } + ], + "docs": [ + " Set the balances of a given account.", + "", + " This will alter `FreeBalance` and `ReservedBalance` in storage. it will", + " also decrease the total issuance of the system (`TotalIssuance`).", + " If the new free or reserved balance is below the existential deposit,", + " it will reset the account nonce (`frame_system::AccountNonce`).", + "", + " The dispatch origin for this call is `root`.", + "", + " # ", + " - Independent of the arguments.", + " - Contains a limited number of reads and writes.", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Exactly as `transfer`, except the origin must be root and the source account may be", + " specified." + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Same as the [`transfer`] call, but with a check that the transfer will not kill the", + " origin account.", + "", + " 99% of the time you want [`transfer`] instead.", + "", + " [`transfer`]: struct.Module.html#method.transfer" + ] + } + ], + "events": [ + { + "name": "NewAccount", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A new account was created." + ] + }, + { + "name": "ReapedAccount", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was reaped." + ] + }, + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " Transfer succeeded (from, to, value, fees)." + ] + }, + { + "name": "BalanceSet", + "args": [ + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " A balance was set by root (who, free, reserved)." + ] + }, + { + "name": "Deposit", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some amount was deposited (e.g. for transaction fees)." + ] + } + ], + "constants": [ + { + "name": "ExistentialDeposit", + "type": "Balance", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to keep an account open." + ] + }, + { + "name": "TransferFee", + "type": "Balance", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to make a transfer." + ] + }, + { + "name": "CreationFee", + "type": "Balance", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to create an account." + ] + } + ], + "errors": [ + { + "name": "VestingBalance", + "docs": [ + " Vesting balance too high to send value" + ] + }, + { + "name": "LiquidityRestrictions", + "docs": [ + " Account liquidity restrictions prevent withdrawal" + ] + }, + { + "name": "Overflow", + "docs": [ + " Got an overflow after adding" + ] + }, + { + "name": "InsufficientBalance", + "docs": [ + " Balance too low to send value" + ] + }, + { + "name": "ExistentialDeposit", + "docs": [ + " Value too low to create account due to existential deposit" + ] + }, + { + "name": "KeepAlive", + "docs": [ + " Transfer/payment would kill account" + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " A vesting schedule already exists for this account" + ] + }, + { + "name": "DeadAccount", + "docs": [ + " Beneficiary account must pre-exist" + ] + } + ] + }, + { + "name": "TransactionPayment", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "NextFeeMultiplier", + "modifier": "Default", + "type": { + "plain": "Multiplier" + }, + "fallback": "0x0000000000000000", + "docs": [] + } + ] + }, + "calls": null, + "events": null, + "constants": [ + { + "name": "TransactionBaseFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the base." + ] + }, + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + } + ], + "errors": [] + }, + { + "name": "Staking", + "storage": { + "prefix": "Staking", + "items": [ + { + "name": "ValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The ideal number of staking participants." + ] + }, + { + "name": "MinimumValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x04000000", + "docs": [ + " Minimum number of staking participants before emergency conditions are imposed." + ] + }, + { + "name": "Invulnerables", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Any validators that may never be slashed or forcibly kicked. It's a Vec since they're", + " easy to initialize and the performance hit is minimal (we expect no more than four", + " invulnerables) and restricted to testnets." + ] + }, + { + "name": "Bonded", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all locked \"stash\" accounts to the controller account." + ] + }, + { + "name": "Ledger", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "StakingLedger", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all (unlocked) \"controller\" accounts to the info regarding the staking." + ] + }, + { + "name": "Payee", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "RewardDestination", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Where the reward payment should be made. Keyed by stash." + ] + }, + { + "name": "Validators", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "ValidatorPrefs", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " The map from (wannabe) validator stash key to the preferences of that validator." + ] + }, + { + "name": "Nominators", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Nominations", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " The map from nominator stash key to the set of stash keys of all validators to nominate.", + "", + " NOTE: is private so that we can ensure upgraded before all typical accesses.", + " Direct storage APIs can still bypass this protection." + ] + }, + { + "name": "Stakers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Exposure", + "linked": false + } + }, + "fallback": "0x000000", + "docs": [ + " Nominators for a particular account that is in action right now. You can't iterate", + " through validators here, but you can find them in the Session module.", + "", + " This is keyed by the stash account." + ] + }, + { + "name": "CurrentElected", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The currently elected validator set keyed by stash account ID." + ] + }, + { + "name": "CurrentEra", + "modifier": "Default", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The current era index." + ] + }, + { + "name": "CurrentEraStart", + "modifier": "Default", + "type": { + "plain": "MomentOf" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The start of the current era." + ] + }, + { + "name": "CurrentEraStartSessionIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The session index at which the current era started." + ] + }, + { + "name": "CurrentEraPointsEarned", + "modifier": "Default", + "type": { + "plain": "EraPoints" + }, + "fallback": "0x0000000000", + "docs": [ + " Rewards for the current era. Using indices of current elected set." + ] + }, + { + "name": "SlotStake", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of balance actively at stake for each validator slot, currently.", + "", + " This is used to derive rewards and punishments." + ] + }, + { + "name": "ForceEra", + "modifier": "Default", + "type": { + "plain": "Forcing" + }, + "fallback": "0x00", + "docs": [ + " True if the next session change will be a new era regardless of index." + ] + }, + { + "name": "SlashRewardFraction", + "modifier": "Default", + "type": { + "plain": "Perbill" + }, + "fallback": "0x00000000", + "docs": [ + " The percentage of the slash that is distributed to reporters.", + "", + " The rest of the slashed value is handled by the `Slash`." + ] + }, + { + "name": "CanceledSlashPayout", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of currency given to reporters of a slash event which was", + " canceled by extraordinary circumstances (e.g. governance)." + ] + }, + { + "name": "UnappliedSlashes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "EraIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " All unapplied slashes that are queued for later." + ] + }, + { + "name": "BondedEras", + "modifier": "Default", + "type": { + "plain": "Vec<(EraIndex,SessionIndex)>" + }, + "fallback": "0x00", + "docs": [ + " A mapping from still-bonded eras to the first session index of that era." + ] + }, + { + "name": "ValidatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "EraIndex", + "key2": "AccountId", + "value": "(Perbill,BalanceOf)", + "key2Hasher": "Twox128" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on validators, mapped by era to the highest slash proportion", + " and slash value of the era." + ] + }, + { + "name": "NominatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "EraIndex", + "key2": "AccountId", + "value": "BalanceOf", + "key2Hasher": "Twox128" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on nominators, mapped by era to the highest slash value of the era." + ] + }, + { + "name": "SlashingSpans", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "SlashingSpans", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Slashing spans for stash accounts." + ] + }, + { + "name": "SpanSlash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "(AccountId,SpanIndex)", + "value": "SpanRecord", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Records information about the maximum slash of a stash within a slashing span,", + " as well as how much reward has been paid out." + ] + }, + { + "name": "EarliestUnappliedSlash", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The earliest era for which we have a pending, unapplied slash." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The version of storage for upgrade." + ] + } + ] + }, + "calls": [ + { + "name": "bond", + "args": [ + { + "name": "controller", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " Take the origin account as a stash and lock up `value` of its balance. `controller` will", + " be the account that controls it.", + "", + " `value` must be more than the `minimum_balance` specified by `T::Currency`.", + "", + " The dispatch origin for this call must be _Signed_ by the stash account.", + "", + " # ", + " - Independent of the arguments. Moderate complexity.", + " - O(1).", + " - Three extra DB entries.", + "", + " NOTE: Two of the storage writes (`Self::bonded`, `Self::payee`) are _never_ cleaned unless", + " the `origin` falls below _existential deposit_ and gets removed as dust.", + " # " + ] + }, + { + "name": "bond_extra", + "args": [ + { + "name": "max_additional", + "type": "Compact" + } + ], + "docs": [ + " Add some extra amount that have appeared in the stash `free_balance` into the balance up", + " for staking.", + "", + " Use this if there are additional funds in your stash account that you wish to bond.", + " Unlike [`bond`] or [`unbond`] this function does not impose any limitation on the amount", + " that can be added.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - O(1).", + " - One DB entry.", + " # " + ] + }, + { + "name": "unbond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Schedule a portion of the stash to be unlocked ready for transfer out after the bond", + " period ends. If this leaves an amount actively bonded less than", + " T::Currency::minimum_balance(), then it is increased to the full amount.", + "", + " Once the unlock period is done, you can call `withdraw_unbonded` to actually move", + " the funds out of management ready for transfer.", + "", + " No more than a limited number of unlocking chunks (see `MAX_UNLOCKING_CHUNKS`)", + " can co-exists at the same time. In that case, [`Call::withdraw_unbonded`] need", + " to be called first to remove some of the chunks (if possible).", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " See also [`Call::withdraw_unbonded`].", + "", + " # ", + " - Independent of the arguments. Limited but potentially exploitable complexity.", + " - Contains a limited number of reads.", + " - Each call (requires the remainder of the bonded balance to be above `minimum_balance`)", + " will cause a new entry to be inserted into a vector (`Ledger.unlocking`) kept in storage.", + " The only way to clean the aforementioned storage item is also user-controlled via `withdraw_unbonded`.", + " - One DB entry.", + " " + ] + }, + { + "name": "withdraw_unbonded", + "args": [], + "docs": [ + " Remove any unlocked chunks from the `unlocking` queue from our management.", + "", + " This essentially frees up that balance to be used by the stash account to do", + " whatever it wants.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " See also [`Call::unbond`].", + "", + " # ", + " - Could be dependent on the `origin` argument and how much `unlocking` chunks exist.", + " It implies `consolidate_unlocked` which loops over `Ledger.unlocking`, which is", + " indirectly user-controlled. See [`unbond`] for more detail.", + " - Contains a limited number of reads, yet the size of which could be large based on `ledger`.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "validate", + "args": [ + { + "name": "prefs", + "type": "ValidatorPrefs" + } + ], + "docs": [ + " Declare the desire to validate for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "nominate", + "args": [ + { + "name": "targets", + "type": "Vec" + } + ], + "docs": [ + " Declare the desire to nominate `targets` for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - The transaction's complexity is proportional to the size of `targets`,", + " which is capped at `MAX_NOMINATIONS`.", + " - Both the reads and writes follow a similar pattern.", + " # " + ] + }, + { + "name": "chill", + "args": [], + "docs": [ + " Declare no desire to either validate or nominate.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains one read.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_payee", + "args": [ + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " (Re-)set the payment target for a controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_controller", + "args": [ + { + "name": "controller", + "type": "LookupSource" + } + ], + "docs": [ + " (Re-)set the controller of a stash.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_validator_count", + "args": [ + { + "name": "new", + "type": "Compact" + } + ], + "docs": [ + " The ideal number of validators." + ] + }, + { + "name": "force_no_eras", + "args": [], + "docs": [ + " Force there to be no new eras indefinitely.", + "", + " # ", + " - No arguments.", + " # " + ] + }, + { + "name": "force_new_era", + "args": [], + "docs": [ + " Force there to be a new era at the end of the next session. After this, it will be", + " reset to normal (non-forced) behaviour.", + "", + " # ", + " - No arguments.", + " # " + ] + }, + { + "name": "set_invulnerables", + "args": [ + { + "name": "validators", + "type": "Vec" + } + ], + "docs": [ + " Set the validators who cannot be slashed (if any)." + ] + }, + { + "name": "force_unstake", + "args": [ + { + "name": "stash", + "type": "AccountId" + } + ], + "docs": [ + " Force a current staker to become completely unstaked, immediately." + ] + }, + { + "name": "force_new_era_always", + "args": [], + "docs": [ + " Force there to be a new era at the end of sessions indefinitely.", + "", + " # ", + " - One storage write", + " # " + ] + }, + { + "name": "cancel_deferred_slash", + "args": [ + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "slash_indices", + "type": "Vec" + } + ], + "docs": [ + " Cancel enactment of a deferred slash. Can be called by either the root origin or", + " the `T::SlashCancelOrigin`.", + " passing the era and indices of the slashes for that era to kill.", + "", + " # ", + " - One storage write.", + " # " + ] + }, + { + "name": "rebond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Rebond a portion of the stash scheduled to be unlocked.", + "", + " # ", + " - Time complexity: O(1). Bounded by `MAX_UNLOCKING_CHUNKS`.", + " - Storage changes: Can't increase storage, only decrease it.", + " # " + ] + } + ], + "events": [ + { + "name": "Reward", + "args": [ + "Balance", + "Balance" + ], + "docs": [ + " All validators have been rewarded by the first balance; the second is the remainder", + " from the maximum amount of reward." + ] + }, + { + "name": "Slash", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " One validator (and its nominators) has been slashed by the given amount." + ] + }, + { + "name": "OldSlashingReportDiscarded", + "args": [ + "SessionIndex" + ], + "docs": [ + " An old slashing report from a prior era was discarded because it could", + " not be processed." + ] + } + ], + "constants": [ + { + "name": "SessionsPerEra", + "type": "SessionIndex", + "value": "0x06000000", + "docs": [ + " Number of sessions per era." + ] + }, + { + "name": "BondingDuration", + "type": "EraIndex", + "value": "0xa0020000", + "docs": [ + " Number of eras that staked funds must remain bonded for." + ] + } + ], + "errors": [ + { + "name": "NotController", + "docs": [ + " Not a controller account." + ] + }, + { + "name": "NotStash", + "docs": [ + " Not a stash account." + ] + }, + { + "name": "AlreadyBonded", + "docs": [ + " Stash is already bonded." + ] + }, + { + "name": "AlreadyPaired", + "docs": [ + " Controller is already paired." + ] + }, + { + "name": "EmptyTargets", + "docs": [ + " Targets cannot be empty." + ] + }, + { + "name": "DuplicateIndex", + "docs": [ + " Duplicate index." + ] + }, + { + "name": "InvalidSlashIndex", + "docs": [ + " Slash record index out of bounds." + ] + }, + { + "name": "InsufficientValue", + "docs": [ + " Can not bond with value less than minimum balance." + ] + }, + { + "name": "NoMoreChunks", + "docs": [ + " Can not schedule more unlock chunks." + ] + }, + { + "name": "NoUnlockChunk", + "docs": [ + " Can not rebond without unlocking chunks." + ] + } + ] + }, + { + "name": "Session", + "storage": { + "prefix": "Session", + "items": [ + { + "name": "Validators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of validators." + ] + }, + { + "name": "CurrentIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Current index of the session." + ] + }, + { + "name": "QueuedChanged", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the underlying economic identities or weighting behind the validators", + " has changed in the queued validator set." + ] + }, + { + "name": "QueuedKeys", + "modifier": "Default", + "type": { + "plain": "Vec<(ValidatorId,Keys)>" + }, + "fallback": "0x00", + "docs": [ + " The queued keys for the next session. When the next session begins, these keys", + " will be used to determine the validator's session keys." + ] + }, + { + "name": "DisabledValidators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Indices of disabled validators.", + "", + " The set is cleared when `on_session_ending` returns a new set of identities." + ] + }, + { + "name": "NextKeys", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Bytes", + "key2": "ValidatorId", + "value": "Keys", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " The next session keys for a validator.", + "", + " The first key is always `DEDUP_KEY_PREFIX` to have all the data in the same branch of", + " the trie. Having all data in the same branch should prevent slowing down other queries." + ] + }, + { + "name": "KeyOwner", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Bytes", + "key2": "(KeyTypeId,Bytes)", + "value": "ValidatorId", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " The owner of a key. The second key is the `KeyTypeId` + the encoded key.", + "", + " The first key is always `DEDUP_KEY_PREFIX` to have all the data in the same branch of", + " the trie. Having all data in the same branch should prevent slowing down other queries." + ] + } + ] + }, + "calls": [ + { + "name": "set_keys", + "args": [ + { + "name": "keys", + "type": "Keys" + }, + { + "name": "proof", + "type": "Bytes" + } + ], + "docs": [ + " Sets the session key(s) of the function caller to `key`.", + " Allows an account to set its session key prior to becoming a validator.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - O(log n) in number of accounts.", + " - One extra DB entry.", + " # " + ] + } + ], + "events": [ + { + "name": "NewSession", + "args": [ + "SessionIndex" + ], + "docs": [ + " New session has happened. Note that the argument is the session index, not the block", + " number as the type might suggest." + ] + } + ], + "constants": [ + { + "name": "DEDUP_KEY_PREFIX", + "type": "Bytes", + "value": "0x343a73657373696f6e3a6b657973", + "docs": [ + " Used as first key for `NextKeys` and `KeyOwner` to put all the data into the same branch", + " of the trie." + ] + } + ], + "errors": [ + { + "name": "InvalidProof", + "docs": [ + " Invalid ownership proof." + ] + }, + { + "name": "NoAssociatedValidatorId", + "docs": [ + " No associated validator ID for account." + ] + }, + { + "name": "DuplicatedKey", + "docs": [ + " Registered duplicate key." + ] + } + ] + }, + { + "name": "Democracy", + "storage": { + "prefix": "Democracy", + "items": [ + { + "name": "PublicPropCount", + "modifier": "Default", + "type": { + "plain": "PropIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of (public) proposals that have been made so far." + ] + }, + { + "name": "PublicProps", + "modifier": "Default", + "type": { + "plain": "Vec<(PropIndex,Hash,AccountId)>" + }, + "fallback": "0x00", + "docs": [ + " The public proposals. Unsorted. The second item is the proposal's hash." + ] + }, + { + "name": "Preimages", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "(Bytes,AccountId,BalanceOf,BlockNumber)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map of hashes to the proposal preimage, along with who registered it and their deposit.", + " The block number is the block at which it was deposited." + ] + }, + { + "name": "DepositOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "PropIndex", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Those who have locked a deposit." + ] + }, + { + "name": "ReferendumCount", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free referendum index, aka the number of referenda started so far." + ] + }, + { + "name": "LowestUnbaked", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The lowest referendum index representing an unbaked referendum. Equal to", + " `ReferendumCount` if there isn't a unbaked referendum." + ] + }, + { + "name": "ReferendumInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReferendumIndex", + "value": "ReferendumInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information concerning any given referendum." + ] + }, + { + "name": "DispatchQueue", + "modifier": "Default", + "type": { + "plain": "Vec<(BlockNumber,Hash,ReferendumIndex)>" + }, + "fallback": "0x00", + "docs": [ + " Queue of successful referenda to be dispatched. Stored ordered by block number." + ] + }, + { + "name": "VotersFor", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReferendumIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Get the voters for the current proposal." + ] + }, + { + "name": "VoteOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "(ReferendumIndex,AccountId)", + "value": "Vote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Get the vote in a given referendum of a particular voter. The result is meaningful only", + " if `voters_for` includes the voter when called with the referendum (you'll get the", + " default `Vote` value otherwise). If you don't want to check `voters_for`, then you can", + " also check for simple existence with `VoteOf::exists` first." + ] + }, + { + "name": "Proxy", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Who is able to vote for whom. Value is the fund-holding account, key is the", + " vote-transaction-sending account." + ] + }, + { + "name": "Delegations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(AccountId,Conviction)", + "linked": true + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Get the account (and lock periods) to which another account is delegating vote." + ] + }, + { + "name": "LastTabledWasExternal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the last referendum tabled was submitted externally. False if it was a public", + " proposal." + ] + }, + { + "name": "NextExternal", + "modifier": "Optional", + "type": { + "plain": "(Hash,VoteThreshold)" + }, + "fallback": "0x00", + "docs": [ + " The referendum to be tabled whenever it would be valid to table an external proposal.", + " This happens when a referendum needs to be tabled and one of two conditions are met:", + " - `LastTabledWasExternal` is `false`; or", + " - `PublicProps` is empty." + ] + }, + { + "name": "Blacklist", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "(BlockNumber,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A record of who vetoed what. Maps proposal hash to a possible existent block number", + " (until when it may not be resubmitted) and who vetoed it." + ] + }, + { + "name": "Cancellations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Record of all proposals that have been subject to emergency cancellation." + ] + } + ] + }, + "calls": [ + { + "name": "propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " # ", + " - O(1).", + " - Two DB changes, one DB entry.", + " # " + ] + }, + { + "name": "second", + "args": [ + { + "name": "proposal", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " # ", + " - O(1).", + " - One DB entry.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "Vote" + } + ], + "docs": [ + " Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;", + " otherwise it is a vote to keep the status quo.", + "", + " # ", + " - O(1).", + " - One DB change, one DB entry.", + " # " + ] + }, + { + "name": "proxy_vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "Vote" + } + ], + "docs": [ + " Vote in a referendum on behalf of a stash. If `vote.is_aye()`, the vote is to enact", + " the proposal; otherwise it is a vote to keep the status quo.", + "", + " # ", + " - O(1).", + " - One DB change, one DB entry.", + " # " + ] + }, + { + "name": "emergency_cancel", + "args": [ + { + "name": "ref_index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Schedule an emergency cancellation of a referendum. Cannot happen twice to the same", + " referendum." + ] + }, + { + "name": "external_propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a referendum to be tabled once it is legal to schedule an external", + " referendum." + ] + }, + { + "name": "external_propose_majority", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a majority-carries referendum to be tabled next once it is legal to schedule", + " an external referendum.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call." + ] + }, + { + "name": "external_propose_default", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a negative-turnout-bias referendum to be tabled next once it is legal to", + " schedule an external referendum.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call." + ] + }, + { + "name": "fast_track", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "voting_period", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Schedule the currently externally-proposed majority-carries referendum to be tabled", + " immediately. If there is no externally-proposed referendum currently, or if there is one", + " but it is not a majority-carries referendum then it fails.", + "", + " - `proposal_hash`: The hash of the current external proposal.", + " - `voting_period`: The period that is allowed for voting on this proposal. Increased to", + " `EmergencyVotingPeriod` if too low.", + " - `delay`: The number of block after voting has ended in approval and this should be", + " enacted. This doesn't have a minimum amount." + ] + }, + { + "name": "veto_external", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Veto and blacklist the external proposal hash." + ] + }, + { + "name": "cancel_referendum", + "args": [ + { + "name": "ref_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a referendum." + ] + }, + { + "name": "cancel_queued", + "args": [ + { + "name": "which", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Cancel a proposal queued for enactment." + ] + }, + { + "name": "set_proxy", + "args": [ + { + "name": "proxy", + "type": "AccountId" + } + ], + "docs": [ + " Specify a proxy. Called by the stash.", + "", + " # ", + " - One extra DB entry.", + " # " + ] + }, + { + "name": "resign_proxy", + "args": [], + "docs": [ + " Clear the proxy. Called by the proxy.", + "", + " # ", + " - One DB clear.", + " # " + ] + }, + { + "name": "remove_proxy", + "args": [ + { + "name": "proxy", + "type": "AccountId" + } + ], + "docs": [ + " Clear the proxy. Called by the stash.", + "", + " # ", + " - One DB clear.", + " # " + ] + }, + { + "name": "delegate", + "args": [ + { + "name": "to", + "type": "AccountId" + }, + { + "name": "conviction", + "type": "Conviction" + } + ], + "docs": [ + " Delegate vote.", + "", + " # ", + " - One extra DB entry.", + " # " + ] + }, + { + "name": "undelegate", + "args": [], + "docs": [ + " Undelegate vote.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "clear_public_proposals", + "args": [], + "docs": [ + " Veto and blacklist the proposal hash. Must be from Root origin." + ] + }, + { + "name": "note_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This doesn't require the proposal to be", + " in the dispatch queue but does require a deposit, returned once enacted." + ] + }, + { + "name": "note_imminent_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This requires the proposal to be", + " in the dispatch queue. No deposit is needed." + ] + }, + { + "name": "reap_preimage", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Remove an expired proposal preimage and collect the deposit.", + "", + " This will only work after `VotingPeriod` blocks from the time that the preimage was", + " noted, if it's the same account doing it. If it's a different account, then it'll only", + " work an additional `EnactmentPeriod` later." + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "PropIndex", + "Balance" + ], + "docs": [ + " A motion has been proposed by a public account." + ] + }, + { + "name": "Tabled", + "args": [ + "PropIndex", + "Balance", + "Vec" + ], + "docs": [ + " A public proposal has been tabled for referendum vote." + ] + }, + { + "name": "ExternalTabled", + "args": [], + "docs": [ + " An external proposal has been tabled." + ] + }, + { + "name": "Started", + "args": [ + "ReferendumIndex", + "VoteThreshold" + ], + "docs": [ + " A referendum has begun." + ] + }, + { + "name": "Passed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been approved by referendum." + ] + }, + { + "name": "NotPassed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been rejected by referendum." + ] + }, + { + "name": "Cancelled", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A referendum has been cancelled." + ] + }, + { + "name": "Executed", + "args": [ + "ReferendumIndex", + "bool" + ], + "docs": [ + " A proposal has been enacted." + ] + }, + { + "name": "Delegated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " An account has delegated their vote to another account." + ] + }, + { + "name": "Undelegated", + "args": [ + "AccountId" + ], + "docs": [ + " An account has cancelled a previous delegation operation." + ] + }, + { + "name": "Vetoed", + "args": [ + "AccountId", + "Hash", + "BlockNumber" + ], + "docs": [ + " An external proposal has been vetoed." + ] + }, + { + "name": "PreimageNoted", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal's preimage was noted, and the deposit taken." + ] + }, + { + "name": "PreimageUsed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal preimage was removed and used (the deposit was returned)." + ] + }, + { + "name": "PreimageInvalid", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was invalid." + ] + }, + { + "name": "PreimageMissing", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was missing." + ] + }, + { + "name": "PreimageReaped", + "args": [ + "Hash", + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A registered preimage was removed and the deposit collected by the reaper (last item)." + ] + } + ], + "constants": [ + { + "name": "EnactmentPeriod", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The minimum period of locking and the period between a proposal being approved and enacted.", + "", + " It should generally be a little more than the unstake period to ensure that", + " voting stakers have an opportunity to remove themselves from the system in the case where", + " they are on the losing side of a vote." + ] + }, + { + "name": "LaunchPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) new public referenda are launched." + ] + }, + { + "name": "VotingPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) to check for new votes." + ] + }, + { + "name": "MinimumDeposit", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be used as a deposit for a public referendum proposal." + ] + }, + { + "name": "EmergencyVotingPeriod", + "type": "BlockNumber", + "value": "0x80510100", + "docs": [ + " Minimum voting period allowed for an emergency referendum." + ] + }, + { + "name": "CooloffPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " Period in blocks where an external proposal may not be re-submitted after being vetoed." + ] + }, + { + "name": "PreimageByteDeposit", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of balance that must be deposited per byte of preimage stored." + ] + } + ], + "errors": [ + { + "name": "ValueLow", + "docs": [ + " Value too low" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal does not exist" + ] + }, + { + "name": "NotProxy", + "docs": [ + " Not a proxy" + ] + }, + { + "name": "BadIndex", + "docs": [ + " Unknown index" + ] + }, + { + "name": "AlreadyCanceled", + "docs": [ + " Cannot cancel the same proposal twice" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Proposal already made" + ] + }, + { + "name": "ProposalBlacklisted", + "docs": [ + " Proposal still blacklisted" + ] + }, + { + "name": "NotSimpleMajority", + "docs": [ + " Next external proposal not simple majority" + ] + }, + { + "name": "InvalidHash", + "docs": [ + " Invalid hash" + ] + }, + { + "name": "NoProposal", + "docs": [ + " No external proposal" + ] + }, + { + "name": "AlreadyVetoed", + "docs": [ + " Identity may not veto a proposal twice" + ] + }, + { + "name": "AlreadyProxy", + "docs": [ + " Already a proxy" + ] + }, + { + "name": "WrongProxy", + "docs": [ + " Wrong proxy" + ] + }, + { + "name": "NotDelegated", + "docs": [ + " Not delegated" + ] + }, + { + "name": "DuplicatePreimage", + "docs": [ + " Preimage already noted" + ] + }, + { + "name": "NotImminent", + "docs": [ + " Not imminent" + ] + }, + { + "name": "Early", + "docs": [ + " Too early" + ] + }, + { + "name": "Imminent", + "docs": [ + " Imminent" + ] + }, + { + "name": "PreimageMissing", + "docs": [ + " Preimage not found" + ] + }, + { + "name": "ReferendumInvalid", + "docs": [ + " Vote given for invalid referendum" + ] + }, + { + "name": "PreimageInvalid", + "docs": [ + " Invalid preimage" + ] + }, + { + "name": "NoneWaiting", + "docs": [ + " No proposals waiting" + ] + } + ] + }, + { + "name": "Council", + "storage": { + "prefix": "Instance1Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + } + ], + "docs": [ + " Set the collective's membership manually to `new_members`. Be nice to the chain and", + " provide it pre-sorted.", + "", + " Requires root origin." + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective." + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " # ", + " - Bounded storage reads and writes.", + " - Argument `threshold` has bearing on weight.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " # ", + " - Bounded storage read and writes.", + " - Will be slightly heavier if the proposal is approved / disapproved after the vote.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`)." + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`)." + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold." + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold." + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A motion was executed; `bool` is true if returned without error." + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A single member did some action; `bool` is true if returned without error." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + } + ] + }, + { + "name": "TechnicalCommittee", + "storage": { + "prefix": "Instance2Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + } + ], + "docs": [ + " Set the collective's membership manually to `new_members`. Be nice to the chain and", + " provide it pre-sorted.", + "", + " Requires root origin." + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective." + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " # ", + " - Bounded storage reads and writes.", + " - Argument `threshold` has bearing on weight.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " # ", + " - Bounded storage read and writes.", + " - Will be slightly heavier if the proposal is approved / disapproved after the vote.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`)." + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`)." + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold." + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold." + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A motion was executed; `bool` is true if returned without error." + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A single member did some action; `bool` is true if returned without error." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + } + ] + }, + { + "name": "Elections", + "storage": { + "prefix": "PhragmenElection", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current elected membership. Sorted based on account id." + ] + }, + { + "name": "RunnersUp", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current runners_up. Sorted based on low to high merit (worse to best runner)." + ] + }, + { + "name": "ElectionRounds", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The total number of vote rounds that have happened, excluding the upcoming one." + ] + }, + { + "name": "VotesOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Vec", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " Votes of a particular voter, with the round index of the votes." + ] + }, + { + "name": "StakeOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Locked stake of a voter." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The present candidate list. Sorted based on account-id. A current member or a runner can", + " never enter this vector and is always implicitly assumed to be a candidate." + ] + } + ] + }, + "calls": [ + { + "name": "vote", + "args": [ + { + "name": "votes", + "type": "Vec" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Vote for a set of candidates for the upcoming round of election.", + "", + " The `votes` should:", + " - not be empty.", + " - be less than the number of candidates.", + "", + " Upon voting, `value` units of `who`'s balance is locked and a bond amount is reserved.", + " It is the responsibility of the caller to not place all of their balance into the lock", + " and keep some for further transactions.", + "", + " # ", + " #### State", + " Reads: O(1)", + " Writes: O(V) given `V` votes. V is bounded by 16.", + " # " + ] + }, + { + "name": "remove_voter", + "args": [], + "docs": [ + " Remove `origin` as a voter. This removes the lock and returns the bond.", + "", + " # ", + " #### State", + " Reads: O(1)", + " Writes: O(1)", + " # " + ] + }, + { + "name": "report_defunct_voter", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Report `target` for being an defunct voter. In case of a valid report, the reporter is", + " rewarded by the bond amount of `target`. Otherwise, the reporter itself is removed and", + " their bond is slashed.", + "", + " A defunct voter is defined to be:", + " - a voter whose current submitted votes are all invalid. i.e. all of them are no", + " longer a candidate nor an active member.", + "", + " # ", + " #### State", + " Reads: O(NLogM) given M current candidates and N votes for `target`.", + " Writes: O(1)", + " # " + ] + }, + { + "name": "submit_candidacy", + "args": [], + "docs": [ + " Submit oneself for candidacy.", + "", + " A candidate will either:", + " - Lose at the end of the term and forfeit their deposit.", + " - Win and become a member. Members will eventually get their stash back.", + " - Become a runner-up. Runners-ups are reserved members in case one gets forcefully", + " removed.", + "", + " # ", + " #### State", + " Reads: O(LogN) Given N candidates.", + " Writes: O(1)", + " # " + ] + }, + { + "name": "renounce_candidacy", + "args": [], + "docs": [ + " Renounce one's intention to be a candidate for the next election round. 3 potential", + " outcomes exist:", + " - `origin` is a candidate and not elected in any set. In this case, the bond is", + " unreserved, returned and origin is removed as a candidate.", + " - `origin` is a current runner up. In this case, the bond is unreserved, returned and", + " origin is removed as a runner.", + " - `origin` is a current member. In this case, the bond is unreserved and origin is", + " removed as a member, consequently not being a candidate for the next round anymore.", + " Similar to [`remove_voter`], if replacement runners exists, they are immediately used." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Remove a particular member from the set. This is effective immediately and the bond of", + " the outgoing member is slashed.", + "", + " If a runner-up is available, then the best runner-up will be removed and replaces the", + " outgoing member. Otherwise, a new phragmen round is started.", + "", + " Note that this does not affect the designated block number of the next election.", + "", + " # ", + " #### State", + " Reads: O(do_phragmen)", + " Writes: O(do_phragmen)", + " # " + ] + } + ], + "events": [ + { + "name": "NewTerm", + "args": [ + "Vec<(AccountId,Balance)>" + ], + "docs": [ + " A new term with new members. This indicates that enough candidates existed, not that", + " enough have has been elected. The inner value must be examined for this purpose." + ] + }, + { + "name": "EmptyTerm", + "args": [], + "docs": [ + " No (or not enough) candidates existed for this round." + ] + }, + { + "name": "MemberKicked", + "args": [ + "AccountId" + ], + "docs": [ + " A member has been removed. This should always be followed by either `NewTerm` ot", + " `EmptyTerm`." + ] + }, + { + "name": "MemberRenounced", + "args": [ + "AccountId" + ], + "docs": [ + " A member has renounced their candidacy." + ] + }, + { + "name": "VoterReported", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A voter (first element) was reported (byt the second element) with the the report being", + " successful or not (third element)." + ] + } + ], + "constants": [ + { + "name": "CandidacyBond", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [] + }, + { + "name": "VotingBond", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [] + }, + { + "name": "DesiredMembers", + "type": "u32", + "value": "0x0d000000", + "docs": [] + }, + { + "name": "DesiredRunnersUp", + "type": "u32", + "value": "0x07000000", + "docs": [] + }, + { + "name": "TermDuration", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [] + } + ], + "errors": [ + { + "name": "UnableToVote", + "docs": [ + " Cannot vote when no candidates or members exist." + ] + }, + { + "name": "NoVotes", + "docs": [ + " Must vote for at least one candidate." + ] + }, + { + "name": "TooManyVotes", + "docs": [ + " Cannot vote more than candidates." + ] + }, + { + "name": "MaximumVotesExceeded", + "docs": [ + " Cannot vote more than maximum allowed." + ] + }, + { + "name": "LowBalance", + "docs": [ + " Cannot vote with stake less than minimum balance." + ] + }, + { + "name": "UnableToPayBond", + "docs": [ + " Voter can not pay voting bond." + ] + }, + { + "name": "MustBeVoter", + "docs": [ + " Must be a voter." + ] + }, + { + "name": "ReportSelf", + "docs": [ + " Cannot report self." + ] + }, + { + "name": "DuplicatedCandidate", + "docs": [ + " Duplicated candidate submission." + ] + }, + { + "name": "MemberSubmit", + "docs": [ + " Member cannot re-submit candidacy." + ] + }, + { + "name": "RunnerSubmit", + "docs": [ + " Runner cannot re-submit candidacy." + ] + }, + { + "name": "InsufficientCandidateFunds", + "docs": [ + " Candidate does not have enough funds." + ] + }, + { + "name": "InvalidOrigin", + "docs": [ + " Origin is not a candidate, member or a runner up." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + } + ] + }, + { + "name": "TechnicalMembership", + "storage": { + "prefix": "Instance1Membership", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current membership, stored as an ordered Vec." + ] + } + ] + }, + "calls": [ + { + "name": "add_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Add a member `who` to the set.", + "", + " May only be called from `AddOrigin` or root." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Remove a member `who` from the set.", + "", + " May only be called from `RemoveOrigin` or root." + ] + }, + { + "name": "swap_member", + "args": [ + { + "name": "remove", + "type": "AccountId" + }, + { + "name": "add", + "type": "AccountId" + } + ], + "docs": [ + " Swap out one member `remove` for another `add`.", + "", + " May only be called from `SwapOrigin` or root." + ] + }, + { + "name": "reset_members", + "args": [ + { + "name": "members", + "type": "Vec" + } + ], + "docs": [ + " Change the membership to a new set, disregarding the existing membership. Be nice and", + " pass `members` pre-sorted.", + "", + " May only be called from `ResetOrigin` or root." + ] + }, + { + "name": "change_key", + "args": [ + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Swap out the sending member for some other key `new`.", + "", + " May only be called from `Signed` origin of a current member." + ] + } + ], + "events": [ + { + "name": "MemberAdded", + "args": [], + "docs": [ + " The given member was added; see the transaction for who." + ] + }, + { + "name": "MemberRemoved", + "args": [], + "docs": [ + " The given member was removed; see the transaction for who." + ] + }, + { + "name": "MembersSwapped", + "args": [], + "docs": [ + " Two members were swapped; see the transaction for who." + ] + }, + { + "name": "MembersReset", + "args": [], + "docs": [ + " The membership was reset; see the transaction for who the new set is." + ] + }, + { + "name": "KeyChanged", + "args": [], + "docs": [ + " One of the members' keys changed." + ] + }, + { + "name": "Dummy", + "args": [ + "PhantomData" + ], + "docs": [ + " Phantom member, never used." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "FinalityTracker", + "storage": null, + "calls": [ + { + "name": "final_hint", + "args": [ + { + "name": "hint", + "type": "Compact" + } + ], + "docs": [ + " Hint that the author of this block thinks the best finalized", + " block is the given number." + ] + } + ], + "events": null, + "constants": [ + { + "name": "WindowSize", + "type": "BlockNumber", + "value": "0x65000000", + "docs": [ + " The number of recent samples to keep from this chain. Default is 101." + ] + }, + { + "name": "ReportLatency", + "type": "BlockNumber", + "value": "0xe8030000", + "docs": [ + " The delay after which point things become suspicious. Default is 1000." + ] + } + ], + "errors": [ + { + "name": "AlreadyUpdated", + "docs": [ + " Final hint must be updated only once in the block" + ] + }, + { + "name": "BadHint", + "docs": [ + " Finalized height above block number" + ] + } + ] + }, + { + "name": "Grandpa", + "storage": { + "prefix": "GrandpaFinality", + "items": [ + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "AuthorityList" + }, + "fallback": "0x00", + "docs": [ + " DEPRECATED", + "", + " This used to store the current authority set, which has been migrated to the well-known", + " GRANDPA_AUTHORITES_KEY unhashed key." + ] + }, + { + "name": "State", + "modifier": "Default", + "type": { + "plain": "StoredState" + }, + "fallback": "0x00", + "docs": [ + " State of the current authority set." + ] + }, + { + "name": "PendingChange", + "modifier": "Optional", + "type": { + "plain": "StoredPendingChange" + }, + "fallback": "0x00", + "docs": [ + " Pending change: (signaled at, scheduled change)." + ] + }, + { + "name": "NextForced", + "modifier": "Optional", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00", + "docs": [ + " next block number where we can force a change." + ] + }, + { + "name": "Stalled", + "modifier": "Optional", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x00", + "docs": [ + " `true` if we are currently stalled." + ] + }, + { + "name": "CurrentSetId", + "modifier": "Default", + "type": { + "plain": "SetId" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The number of changes (both in terms of keys and underlying economic responsibilities)", + " in the \"set\" of Grandpa validators from genesis." + ] + }, + { + "name": "SetIdSession", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "SetId", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from grandpa set ID to the index of the *most recent* session for which its members were responsible." + ] + } + ] + }, + "calls": [ + { + "name": "report_misbehavior", + "args": [ + { + "name": "_report", + "type": "Bytes" + } + ], + "docs": [ + " Report some misbehavior." + ] + } + ], + "events": [ + { + "name": "NewAuthorities", + "args": [ + "AuthorityList" + ], + "docs": [ + " New authority set has been applied." + ] + }, + { + "name": "Paused", + "args": [], + "docs": [ + " Current authority set has been paused." + ] + }, + { + "name": "Resumed", + "args": [], + "docs": [ + " Current authority set has been resumed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "PauseFailed", + "docs": [ + " Attempt to signal GRANDPA pause when the authority set isn't live", + " (either paused or already pending pause)." + ] + }, + { + "name": "ResumeFailed", + "docs": [ + " Attempt to signal GRANDPA resume when the authority set isn't paused", + " (either live or already pending resume)." + ] + }, + { + "name": "ChangePending", + "docs": [ + " Attempt to signal GRANDPA change with one already pending." + ] + }, + { + "name": "TooSoon", + "docs": [ + " Cannot signal forced change so soon after last." + ] + } + ] + }, + { + "name": "Treasury", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "ProposalIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of proposals that have been made." + ] + }, + { + "name": "Proposals", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ProposalIndex", + "value": "TreasuryProposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Proposals that have been made." + ] + }, + { + "name": "Approvals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Proposal indices that have been approved but not yet awarded." + ] + }, + { + "name": "Tips", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Hash", + "value": "OpenTip", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Tips that are not yet completed. Keyed by the hash of `(reason, who)` from the value.", + " This has the insecure enumerable hash function since the key itself is already", + " guaranteed to be a secure hash." + ] + }, + { + "name": "Reasons", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Hash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Simple preimage lookup from the reason's hash to the original data. Again, has an", + " insecure enumerable hash since the key is guaranteed to be the result of a secure hash." + ] + } + ] + }, + "calls": [ + { + "name": "propose_spend", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Put forward a suggestion for spending. A deposit proportional to the value", + " is reserved and slashed if the proposal is rejected. It is returned once the", + " proposal is awarded.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change, one extra DB entry.", + " # " + ] + }, + { + "name": "reject_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Reject a proposed spend. The original deposit will be slashed.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB clear.", + " # " + ] + }, + { + "name": "approve_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a proposal. At a later time, the proposal will be allocated to the beneficiary", + " and the original deposit will be returned.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "report_awesome", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Report something `reason` that deserves a tip and claim any eventual the finder's fee.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `TipReportDepositPerByte` for each byte in `reason`.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - `O(R)` where `R` length of `reason`.", + " - One balance operation.", + " - One storage mutation (codec `O(R)`).", + " - One event.", + " # " + ] + }, + { + "name": "retract_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Retract a prior tip-report from `report_awesome`, and cancel the process of tipping.", + "", + " If successful, the original deposit will be unreserved.", + "", + " The dispatch origin for this call must be _Signed_ and the tip identified by `hash`", + " must have been reported by the signing account through `report_awesome` (and not", + " through `tip_new`).", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " Emits `TipRetracted` if successful.", + "", + " # ", + " - `O(T)`", + " - One balance operation.", + " - Two storage removals (one read, codec `O(T)`).", + " - One event.", + " # " + ] + }, + { + "name": "tip_new", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + }, + { + "name": "tip_value", + "type": "BalanceOf" + } + ], + "docs": [ + " Give a tip for something new; no finder's fee will be taken.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - `O(R + T)` where `R` length of `reason`, `T` is the number of tippers. `T` is", + " naturally capped as a membership set, `R` is limited through transaction-size.", + " - Two storage insertions (codecs `O(R)`, `O(T)`), one read `O(1)`.", + " - One event.", + " # " + ] + }, + { + "name": "tip", + "args": [ + { + "name": "hash", + "type": "Hash" + }, + { + "name": "tip_value", + "type": "BalanceOf" + } + ], + "docs": [ + " Declare a tip value for an already-open tip.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the hash of the original tip `reason` and the beneficiary", + " account ID.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `TipClosing` if the threshold of tippers has been reached and the countdown period", + " has started.", + "", + " # ", + " - `O(T)`", + " - One storage mutation (codec `O(T)`), one storage read `O(1)`.", + " - Up to one event.", + " # " + ] + }, + { + "name": "close_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Close and payout a tip.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " The tip identified by `hash` must have finished its countdown period.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " # ", + " - `O(T)`", + " - One storage retrieval (codec `O(T)`) and two removals.", + " - Up to three balance operations.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "ProposalIndex" + ], + "docs": [ + " New proposal." + ] + }, + { + "name": "Spending", + "args": [ + "Balance" + ], + "docs": [ + " We have ended a spend period and will now allocate funds." + ] + }, + { + "name": "Awarded", + "args": [ + "ProposalIndex", + "Balance", + "AccountId" + ], + "docs": [ + " Some funds have been allocated." + ] + }, + { + "name": "Rejected", + "args": [ + "ProposalIndex", + "Balance" + ], + "docs": [ + " A proposal was rejected; funds were slashed." + ] + }, + { + "name": "Burnt", + "args": [ + "Balance" + ], + "docs": [ + " Some of our funds have been burnt." + ] + }, + { + "name": "Rollover", + "args": [ + "Balance" + ], + "docs": [ + " Spending has finished; this is the amount that rolls over until next spend." + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds have been deposited." + ] + }, + { + "name": "NewTip", + "args": [ + "Hash" + ], + "docs": [ + " A new tip suggestion has been opened." + ] + }, + { + "name": "TipClosing", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has reached threshold and is closing." + ] + }, + { + "name": "TipClosed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been closed." + ] + }, + { + "name": "TipRetracted", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has been retracted." + ] + } + ], + "constants": [ + { + "name": "ProposalBond", + "type": "Permill", + "value": "0x50c30000", + "docs": [ + " Fraction of a proposal's value that should be bonded in order to place the proposal.", + " An accepted proposal gets these back. A rejected proposal does not." + ] + }, + { + "name": "ProposalBondMinimum", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Minimum amount of funds that should be placed in a deposit for making a proposal." + ] + }, + { + "name": "SpendPeriod", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " Period between successive spends." + ] + }, + { + "name": "Burn", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of spare funds (if any) that are burnt per spend period." + ] + }, + { + "name": "TipCountdown", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The period for which a tip remains open after is has achieved threshold tippers." + ] + }, + { + "name": "TipFindersFee", + "type": "Percent", + "value": "0x14", + "docs": [ + " The amount of the final tip which goes to the original reporter of the tip." + ] + }, + { + "name": "TipReportDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a tip report." + ] + }, + { + "name": "TipReportDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within the tip report reason." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidProposalIndex", + "docs": [ + " No proposal at that index." + ] + }, + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "AlreadyKnown", + "docs": [ + " The tip was already found/started." + ] + }, + { + "name": "UnknownTip", + "docs": [ + " The tip hash is unknown." + ] + }, + { + "name": "NotFinder", + "docs": [ + " The account attempting to retract the tip is not the finder of the tip." + ] + }, + { + "name": "StillOpen", + "docs": [ + " The tip cannot be claimed/closed because there are not enough tippers yet." + ] + }, + { + "name": "Premature", + "docs": [ + " The tip cannot be claimed/closed because it's still in the countdown period." + ] + } + ] + }, + { + "name": "Contracts", + "storage": { + "prefix": "Contract", + "items": [ + { + "name": "GasSpent", + "modifier": "Default", + "type": { + "plain": "Gas" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Gas spent so far in this block." + ] + }, + { + "name": "CurrentSchedule", + "modifier": "Default", + "type": { + "plain": "Schedule" + }, + "fallback": "0x0000000001000000000000000100000000000000010000000000000001000000000000000100000000000000010000000000000001000000000000008700000000000000af0000000000000001000000000000000100000000000000040000000000010010000000004000000020000000", + "docs": [ + " Current cost schedule for contracts." + ] + }, + { + "name": "PristineCode", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "CodeHash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from an original code hash to the original code, untouched by instrumentation." + ] + }, + { + "name": "CodeStorage", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "CodeHash", + "value": "PrefabWasmModule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping between an original code hash and instrumented wasm code, ready for execution." + ] + }, + { + "name": "AccountCounter", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The subtrie counter." + ] + }, + { + "name": "ContractInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "ContractInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The code associated with a given account." + ] + }, + { + "name": "GasPrice", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x01000000000000000000000000000000", + "docs": [ + " The price of one unit of gas." + ] + } + ] + }, + "calls": [ + { + "name": "update_schedule", + "args": [ + { + "name": "schedule", + "type": "Schedule" + } + ], + "docs": [ + " Updates the schedule for metering contracts.", + "", + " The schedule must have a greater version than the stored schedule." + ] + }, + { + "name": "put_code", + "args": [ + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Stores the given binary Wasm code into the chain's storage and returns its `codehash`.", + " You can instantiate contracts only with stored code." + ] + }, + { + "name": "call", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Makes a call to an account, optionally transferring some balance.", + "", + " * If the account is a smart-contract account, the associated code will be", + " executed and any value will be transferred.", + " * If the account is a regular account, any value will be transferred.", + " * If no account exists and the call value is not less than `existential_deposit`,", + " a regular account will be created and any value will be transferred." + ] + }, + { + "name": "instantiate", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code_hash", + "type": "CodeHash" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a new contract from the `codehash` generated by `put_code`, optionally transferring some balance.", + "", + " Instantiation is executed as follows:", + "", + " - The destination address is computed based on the sender and hash of the code.", + " - The smart-contract account is created at the computed address.", + " - The `ctor_code` is executed in the context of the newly-created account. Buffer returned", + " after the execution is saved as the `code` of the account. That code will be invoked", + " upon any call received by this account.", + " - The contract is initialized." + ] + }, + { + "name": "claim_surcharge", + "args": [ + { + "name": "dest", + "type": "AccountId" + }, + { + "name": "aux_sender", + "type": "Option" + } + ], + "docs": [ + " Allows block producers to claim a small reward for evicting a contract. If a block producer", + " fails to do so, a regular users will be allowed to claim the reward.", + "", + " If contract is not evicted as a result of this call, no actions are taken and", + " the sender is not eligible for the reward." + ] + } + ], + "events": [ + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " Transfer happened `from` to `to` with given `value` as part of a `call` or `instantiate`." + ] + }, + { + "name": "Instantiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract deployed by address at the specified address." + ] + }, + { + "name": "CodeStored", + "args": [ + "Hash" + ], + "docs": [ + " Code with the specified hash has been stored." + ] + }, + { + "name": "ScheduleUpdated", + "args": [ + "u32" + ], + "docs": [ + " Triggered when the current schedule is updated." + ] + }, + { + "name": "Dispatched", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A call was dispatched from the given account. The bool signals whether it was", + " successful execution or not." + ] + }, + { + "name": "Contract", + "args": [ + "AccountId", + "Bytes" + ], + "docs": [ + " An event from contract of account." + ] + } + ], + "constants": [ + { + "name": "SignedClaimHandicap", + "type": "BlockNumber", + "value": "0x02000000", + "docs": [ + " Number of block delay an extrinsic claim surcharge has.", + "", + " When claim surcharge is called by an extrinsic the rent is checked", + " for current_block - delay" + ] + }, + { + "name": "TombstoneDeposit", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to generate a tombstone." + ] + }, + { + "name": "StorageSizeOffset", + "type": "u32", + "value": "0x08000000", + "docs": [ + " Size of a contract at the time of instantiaion. This is a simple way to ensure that", + " empty contracts eventually gets deleted." + ] + }, + { + "name": "RentByteFee", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Price of a byte of storage per one block interval. Should be greater than 0." + ] + }, + { + "name": "RentDepositOffset", + "type": "BalanceOf", + "value": "0x00008a5d784563010000000000000000", + "docs": [ + " The amount of funds a contract should deposit in order to offset", + " the cost of one byte.", + "", + " Let's suppose the deposit is 1,000 BU (balance units)/byte and the rent is 1 BU/byte/day,", + " then a contract with 1,000,000 BU that uses 1,000 bytes of storage would pay no rent.", + " But if the balance reduced to 500,000 BU and the storage stayed the same at 1,000,", + " then it would pay 500 BU/day." + ] + }, + { + "name": "SurchargeReward", + "type": "BalanceOf", + "value": "0x0080a1a76b4a35000000000000000000", + "docs": [ + " Reward that is received by the party whose touch has led", + " to removal of a contract." + ] + }, + { + "name": "TransferFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to make a transfer." + ] + }, + { + "name": "CreationFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to create an account." + ] + }, + { + "name": "TransactionBaseFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the base." + ] + }, + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + }, + { + "name": "ContractFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to instantiate a contract instance. A reasonable default value", + " is 21." + ] + }, + { + "name": "CallBaseFee", + "type": "Gas", + "value": "0xe803000000000000", + "docs": [ + " The base fee charged for calling into a contract. A reasonable default", + " value is 135." + ] + }, + { + "name": "InstantiateBaseFee", + "type": "Gas", + "value": "0xe803000000000000", + "docs": [ + " The base fee charged for instantiating a contract. A reasonable default value", + " is 175." + ] + }, + { + "name": "MaxDepth", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum nesting level of a call/instantiate stack. A reasonable default", + " value is 100." + ] + }, + { + "name": "MaxValueSize", + "type": "u32", + "value": "0x00400000", + "docs": [ + " The maximum size of a storage value in bytes. A reasonable default is 16 KiB." + ] + }, + { + "name": "BlockGasLimit", + "type": "Gas", + "value": "0x8096980000000000", + "docs": [ + " The maximum amount of gas that could be expended per block. A reasonable", + " default value is 10_000_000." + ] + } + ], + "errors": [ + { + "name": "InvalidScheduleVersion", + "docs": [ + " A new schedule must have a greater version than the current one." + ] + }, + { + "name": "InvalidSurchargeClaim", + "docs": [ + " An origin must be signed or inherent and auxiliary sender only provided on inherent." + ] + }, + { + "name": "InvalidSourceContract", + "docs": [ + " Cannot restore from nonexisting or tombstone contract." + ] + }, + { + "name": "InvalidDestinationContract", + "docs": [ + " Cannot restore to nonexisting or alive contract." + ] + }, + { + "name": "InvalidTombstone", + "docs": [ + " Tombstones don't match." + ] + }, + { + "name": "InvalidContractOrigin", + "docs": [ + " An origin TrieId written in the current block." + ] + } + ] + }, + { + "name": "Sudo", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "Key", + "modifier": "Default", + "type": { + "plain": "AccountId" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The `AccountId` of the sudo key." + ] + } + ] + }, + "calls": [ + { + "name": "sudo", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Unknown weight of derivative `proposal` execution.", + " # " + ] + }, + { + "name": "set_key", + "args": [ + { + "name": "new", + "type": "LookupSource" + } + ], + "docs": [ + " Authenticates the current sudo key and sets the given AccountId (`new`) as the new sudo key.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "sudo_as", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Signed` origin from", + " a given account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Unknown weight of derivative `proposal` execution.", + " # " + ] + } + ], + "events": [ + { + "name": "Sudid", + "args": [ + "bool" + ], + "docs": [ + " A sudo just took place." + ] + }, + { + "name": "KeyChanged", + "args": [ + "AccountId" + ], + "docs": [ + " The sudoer just switched identity; the old key is supplied." + ] + }, + { + "name": "SudoAsDone", + "args": [ + "bool" + ], + "docs": [ + " A sudo just took place." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "RequireSudo", + "docs": [ + " Sender must be the Sudo account" + ] + } + ] + }, + { + "name": "ImOnline", + "storage": { + "prefix": "ImOnline", + "items": [ + { + "name": "GossipAt", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The block number when we should gossip." + ] + }, + { + "name": "Keys", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of keys that may issue a heartbeat." + ] + }, + { + "name": "ReceivedHeartbeats", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "SessionIndex", + "key2": "AuthIndex", + "value": "Bytes", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " For each session index, we keep a mapping of `AuthIndex`", + " to `offchain::OpaqueNetworkState`." + ] + }, + { + "name": "AuthoredBlocks", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "SessionIndex", + "key2": "ValidatorId", + "value": "u32", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00000000", + "docs": [ + " For each session index, we keep a mapping of `T::ValidatorId` to the", + " number of blocks authored by the given authority." + ] + } + ] + }, + "calls": [ + { + "name": "heartbeat", + "args": [ + { + "name": "heartbeat", + "type": "Heartbeat" + }, + { + "name": "_signature", + "type": "Signature" + } + ], + "docs": [] + } + ], + "events": [ + { + "name": "HeartbeatReceived", + "args": [ + "AuthorityId" + ], + "docs": [ + " A new heartbeat was received from `AuthorityId`" + ] + }, + { + "name": "AllGood", + "args": [], + "docs": [ + " At the end of the session, no offence was committed." + ] + }, + { + "name": "SomeOffline", + "args": [ + "Vec" + ], + "docs": [ + " At the end of the session, at least once validator was found to be offline." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidKey", + "docs": [ + " Non existent public key." + ] + }, + { + "name": "DuplicatedHeartbeat", + "docs": [ + " Duplicated heartbeat." + ] + } + ] + }, + { + "name": "AuthorityDiscovery", + "storage": null, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Offences", + "storage": { + "prefix": "Offences", + "items": [ + { + "name": "Reports", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReportIdOf", + "value": "OffenceDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The primary structure that holds all offence records keyed by report identifiers." + ] + }, + { + "name": "ConcurrentReportsIndex", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "Kind", + "key2": "OpaqueTimeSlot", + "value": "Vec", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " A vector of reports of the same kind that happened at the same time slot." + ] + }, + { + "name": "ReportsByKindIndex", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Kind", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Enumerates all reports of a kind along with the time they happened.", + "", + " All reports are sorted by the time of offence.", + "", + " Note that the actual type of this mapping is `Vec`, this is because values of", + " different types are not supported at the moment so we are doing the manual serialization." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "Offence", + "args": [ + "Kind", + "OpaqueTimeSlot" + ], + "docs": [ + " There is an offence reported of the given `kind` happened at the `session_index` and", + " (kind-specific) time slot. This event is not deposited for duplicate slashes." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "RandomnessCollectiveFlip", + "storage": { + "prefix": "RandomnessCollectiveFlip", + "items": [ + { + "name": "RandomMaterial", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Series of block headers from the last 81 blocks that acts as random seed material. This", + " is arranged as a ring buffer with `block_number % 81` being the index into the `Vec` of", + " the oldest hash." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Identity", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "IdentityOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Registration", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information that is pertinent to identify the entity behind an account." + ] + }, + { + "name": "SuperOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(AccountId,Data)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The super-identity of an alternative \"sub\" identity together with its name, within that", + " context. If the account is not some other account's sub-identity, then just `None`." + ] + }, + { + "name": "SubsOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " Alternative \"sub\" identities of this account.", + "", + " The first item is the deposit, the second is a vector of the accounts." + ] + }, + { + "name": "Registrars", + "modifier": "Default", + "type": { + "plain": "Vec>" + }, + "fallback": "0x00", + "docs": [ + " The set of registrars. Not expected to get very big as can only be added through a", + " special origin (likely a council motion).", + "", + " The index into this can be cast to `RegistrarIndex` to get a valid value." + ] + } + ] + }, + "calls": [ + { + "name": "add_registrar", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Add a registrar to the system.", + "", + " The dispatch origin for this call must be `RegistrarOrigin` or `Root`.", + "", + " - `account`: the account of the registrar.", + "", + " Emits `RegistrarAdded` if successful.", + "", + " # ", + " - `O(R)` where `R` registrar-count (governance-bounded).", + " - One storage mutation (codec `O(R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_identity", + "args": [ + { + "name": "info", + "type": "IdentityInfo" + } + ], + "docs": [ + " Set an account's identity information and reserve the appropriate deposit.", + "", + " If the account already has identity information, the deposit is taken as part payment", + " for the new deposit.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " - `info`: The identity information.", + "", + " Emits `IdentitySet` if successful.", + "", + " # ", + " - `O(X + R)` where `X` additional-field-count (deposit-bounded).", + " - At most two balance operations.", + " - One storage mutation (codec `O(X + R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_subs", + "args": [ + { + "name": "subs", + "type": "Vec<(AccountId,Data)>" + } + ], + "docs": [ + " Set the sub-accounts of the sender.", + "", + " Payment: Any aggregate balance reserved by previous `set_subs` calls will be returned", + " and an amount `SubAccountDeposit` will be reserved for each item in `subs`.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " - `subs`: The identity's sub-accounts.", + "", + " # ", + " - `O(S)` where `S` subs-count (hard- and deposit-bounded).", + " - At most two balance operations.", + " - At most O(2 * S + 1) storage mutations; codec complexity `O(1 * S + S * 1)`);", + " one storage-exists.", + " # " + ] + }, + { + "name": "clear_identity", + "args": [], + "docs": [ + " Clear an account's identity info and all sub-account and return all deposits.", + "", + " Payment: All reserved balances on the account are returned.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " Emits `IdentityCleared` if successful.", + "", + " # ", + " - `O(R + S + X)`.", + " - One balance-reserve operation.", + " - `S + 2` storage deletions.", + " - One event.", + " # " + ] + }, + { + "name": "request_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "max_fee", + "type": "Compact" + } + ], + "docs": [ + " Request a judgement from a registrar.", + "", + " Payment: At most `max_fee` will be reserved for payment to the registrar if judgement", + " given.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is requested.", + " - `max_fee`: The maximum fee that may be paid. This should just be auto-populated as:", + "", + " ```nocompile", + " Self::registrars(reg_index).uwnrap().fee", + " ```", + "", + " Emits `JudgementRequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(X + R)`.", + " - One event.", + " # " + ] + }, + { + "name": "cancel_request", + "args": [ + { + "name": "reg_index", + "type": "RegistrarIndex" + } + ], + "docs": [ + " Cancel a previous request.", + "", + " Payment: A previously reserved deposit is returned on success.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is no longer requested.", + "", + " Emits `JudgementUnrequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - One storage mutation `O(R + X)`.", + " - One event.", + " # " + ] + }, + { + "name": "set_fee", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Set the fee required for a judgement to be requested from a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fee`: the new fee.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " # " + ] + }, + { + "name": "set_account_id", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Change the account associated with a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `new`: the new account ID.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " # " + ] + }, + { + "name": "set_fields", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fields", + "type": "IdentityFields" + } + ], + "docs": [ + " Set the field information for a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fields`: the fields that the registrar concerns themselves with.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " # " + ] + }, + { + "name": "provide_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "judgement", + "type": "IdentityJudgement" + } + ], + "docs": [ + " Provide a judgement for an account's identity.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `reg_index`.", + "", + " - `reg_index`: the index of the registrar whose judgement is being made.", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + " - `judgement`: the judgement of the registrar of index `reg_index` about `target`.", + "", + " Emits `JudgementGiven` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-transfer operation.", + " - Up to one account-lookup operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(R + X)`.", + " - One event.", + " # " + ] + }, + { + "name": "kill_identity", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Remove an account's identity and sub-account information and slash the deposits.", + "", + " Payment: Reserved balances from `set_subs` and `set_identity` are slashed and handled by", + " `Slash`. Verification request deposits are not returned; they should be cancelled", + " manually using `cancel_request`.", + "", + " The dispatch origin for this call must be _Root_ or match `T::ForceOrigin`.", + "", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + "", + " Emits `IdentityKilled` if successful.", + "", + " # ", + " - `O(R + S + X)`.", + " - One balance-reserve operation.", + " - `S + 2` storage mutations.", + " - One event.", + " # " + ] + } + ], + "events": [ + { + "name": "IdentitySet", + "args": [ + "AccountId" + ], + "docs": [ + " A name was set or reset (which will remove all judgements)." + ] + }, + { + "name": "IdentityCleared", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was cleared, and the given balance returned." + ] + }, + { + "name": "IdentityKilled", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was removed and the given balance slashed." + ] + }, + { + "name": "JudgementRequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was asked from a registrar." + ] + }, + { + "name": "JudgementUnrequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement request was retracted." + ] + }, + { + "name": "JudgementGiven", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was given by a registrar." + ] + }, + { + "name": "RegistrarAdded", + "args": [ + "RegistrarIndex" + ], + "docs": [ + " A registrar was added." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "TooManySubAccounts", + "docs": [ + " Too many subs-accounts." + ] + }, + { + "name": "NotFound", + "docs": [ + " Account isn't found." + ] + }, + { + "name": "NotNamed", + "docs": [ + " Account isn't named." + ] + }, + { + "name": "EmptyIndex", + "docs": [ + " Empty index." + ] + }, + { + "name": "FeeChanged", + "docs": [ + " Fee is changed." + ] + }, + { + "name": "NoIdentity", + "docs": [ + " No identity found." + ] + }, + { + "name": "StickyJudgement", + "docs": [ + " Sticky judgement." + ] + }, + { + "name": "JudgementGiven", + "docs": [ + " Judgement given." + ] + }, + { + "name": "InvalidJudgement", + "docs": [ + " Invalid judgement." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " The index is invalid." + ] + }, + { + "name": "InvalidTarget", + "docs": [ + " The target is invalid." + ] + } + ] + }, + { + "name": "Society", + "storage": { + "prefix": "Society", + "items": [ + { + "name": "Founder", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The first member." + ] + }, + { + "name": "Rules", + "modifier": "Optional", + "type": { + "plain": "Hash" + }, + "fallback": "0x00", + "docs": [ + " A hash of the rules of this society concerning membership. Can only be set once and", + " only by the founder." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of candidates; bidders that are attempting to become members." + ] + }, + { + "name": "SuspendedCandidates", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(BalanceOf,BidKind)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended candidates." + ] + }, + { + "name": "Pot", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Amount of our account balance that is specifically for the next round's bid(s)." + ] + }, + { + "name": "Head", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The most primary from the most recently approved members." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of members, ordered." + ] + }, + { + "name": "SuspendedMembers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended members." + ] + }, + { + "name": "Bids", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current bids, stored ordered by the value of the bid." + ] + }, + { + "name": "Vouching", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "VouchingStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Members currently vouching or banned from vouching again" + ] + }, + { + "name": "Payouts", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Vec<(BlockNumber,BalanceOf)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Pending payouts; ordered by block number, with the amount that should be paid out." + ] + }, + { + "name": "Strikes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "StrikeCount", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " The ongoing number of losing votes cast by the member." + ] + }, + { + "name": "Votes", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "SocietyVote", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Double map from Candidate -> Voter -> (Maybe) Vote." + ] + }, + { + "name": "Defender", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The defending member currently being challenged." + ] + }, + { + "name": "DefenderVotes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SocietyVote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes for the defender." + ] + }, + { + "name": "MaxMembers", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The max number of members for the society at one time." + ] + } + ] + }, + "calls": [ + { + "name": "bid", + "args": [ + { + "name": "value", + "type": "BalanceOf" + } + ], + "docs": [ + " A user outside of the society can make a bid for entry.", + "", + " Payment: `CandidateDeposit` will be reserved for making a bid. It is returned", + " when the bid becomes a member, or if the bid calls `unbid`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `value`: A one time payment the bid would like to receive when joining the society.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members), X (balance reserve)", + " - Storage Reads:", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " \t- One storage read to retrieve all members. O(M)", + " - Storage Writes:", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for new bid.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unbid", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " A bidder can remove their bid for entry into society.", + " By doing so, they will have their candidate deposit returned or", + " they will unvouch their voucher.", + "", + " Payment: The bid deposit is unreserved if the user made a bid.", + "", + " The dispatch origin for this call must be _Signed_ and a bidder.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who wants to unbid.", + "", + " # ", + " Key: B (len of bids), X (balance unreserve)", + " - One storage read and write to retrieve and update the bids. O(B)", + " - Either one unreserve balance action O(X) or one vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B + X)", + " # " + ] + }, + { + "name": "vouch", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "value", + "type": "BalanceOf" + }, + { + "name": "tip", + "type": "BalanceOf" + } + ], + "docs": [ + " As a member, vouch for someone to join society by placing a bid on their behalf.", + "", + " There is no deposit required to vouch for a new bid, but a member can only vouch for", + " one bid at a time. If the bid becomes a suspended candidate and ultimately rejected by", + " the suspension judgement origin, the member will be banned from vouching again.", + "", + " As a vouching member, you can claim a tip if the candidate is accepted. This tip will", + " be paid as a portion of the reward the member will receive for joining the society.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `who`: The user who you would like to vouch for.", + " - `value`: The total reward to be paid between you and the candidate if they become", + " a member in the society.", + " - `tip`: Your cut of the total `value` payout when the candidate is inducted into", + " the society. Tips larger than `value` will be saturated upon payout.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members)", + " - Storage Reads:", + " \t- One storage read to retrieve all members. O(M)", + " \t- One storage read to check member is not already vouching. O(1)", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " - Storage Writes:", + " \t- One storage write to insert vouching status to the member. O(1)", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(log M) search to check sender is a member.", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for vouch.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unvouch", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " As a vouching member, unvouch a bid. This only works while vouched user is", + " only a bidder (and not a candidate).", + "", + " The dispatch origin for this call must be _Signed_ and a vouching member.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who should be unvouched.", + "", + " # ", + " Key: B (len of bids)", + " - One storage read O(1) to check the signer is a vouching member.", + " - One storage mutate to retrieve and update the bids. O(B)", + " - One vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B)", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "candidate", + "type": "LookupSource" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on a candidate.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `candidate`: The candidate that the member would like to bid on.", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " Key: C (len of candidates), M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One account lookup.", + " - One storage read O(C) and O(C) search to check that user is a candidate.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM + C)", + " # " + ] + }, + { + "name": "defender_vote", + "args": [ + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on the defender.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " - Key: M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM)", + " # " + ] + }, + { + "name": "payout", + "args": [], + "docs": [ + " Transfer the first matured payout for the sender and remove it from the records.", + "", + " NOTE: This extrinsic needs to be called multiple times to claim multiple matured payouts.", + "", + " Payment: The member will receive a payment equal to their first matured", + " payout to their free balance.", + "", + " The dispatch origin for this call must be _Signed_ and a member with", + " payouts remaining.", + "", + " # ", + " Key: M (len of members), P (number of payouts for a particular member)", + " - One storage read O(M) and O(log M) search to check signer is a member.", + " - One storage read O(P) to get all payouts for a member.", + " - One storage read O(1) to get the current block number.", + " - One currency transfer call. O(X)", + " - One storage write or removal to update the member's payouts. O(P)", + "", + " Total Complexity: O(M + logM + P + X)", + " # " + ] + }, + { + "name": "found", + "args": [ + { + "name": "founder", + "type": "AccountId" + }, + { + "name": "max_members", + "type": "u32" + }, + { + "name": "rules", + "type": "Bytes" + } + ], + "docs": [ + " Found the society.", + "", + " This is done as a discrete action in order to allow for the", + " module to be included into a running chain and can only be done once.", + "", + " The dispatch origin for this call must be from the _FounderSetOrigin_.", + "", + " Parameters:", + " - `founder` - The first member and head of the newly founded society.", + " - `max_members` - The initial max number of members for the society.", + " - `rules` - The rules of this society concerning membership.", + "", + " # ", + " - Two storage mutates to set `Head` and `Founder`. O(1)", + " - One storage write to add the first member to society. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "unfound", + "args": [], + "docs": [ + " Anull the founding of the society.", + "", + " The dispatch origin for this call must be Signed, and the signing account must be both", + " the `Founder` and the `Head`. This implies that it may only be done when there is one", + " member.", + "", + " # ", + " - Two storage reads O(1).", + " - Four storage removals O(1).", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "judge_suspended_member", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "forgive", + "type": "bool" + } + ], + "docs": [ + " Allow suspension judgement origin to make judgement on a suspended member.", + "", + " If a suspended member is forgiven, we simply add them back as a member, not affecting", + " any of the existing storage items for that member.", + "", + " If a suspended member is rejected, remove all associated storage items, including", + " their payouts, and remove any vouched bids they currently have.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended member to be judged.", + " - `forgive` - A boolean representing whether the suspension judgement origin", + " forgives (`true`) or rejects (`false`) a suspended member.", + "", + " # ", + " Key: B (len of bids), M (len of members)", + " - One storage read to check `who` is a suspended member. O(1)", + " - Up to one storage write O(M) with O(log M) binary search to add a member back to society.", + " - Up to 3 storage removals O(1) to clean up a removed member.", + " - Up to one storage write O(B) with O(B) search to remove vouched bid from bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal. O(1)", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B)", + " # " + ] + }, + { + "name": "judge_suspended_candidate", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "judgement", + "type": "SocietyJudgement" + } + ], + "docs": [ + " Allow suspended judgement origin to make judgement on a suspended candidate.", + "", + " If the judgement is `Approve`, we add them to society as a member with the appropriate", + " payment for joining society.", + "", + " If the judgement is `Reject`, we either slash the deposit of the bid, giving it back", + " to the society treasury, or we ban the voucher from vouching again.", + "", + " If the judgement is `Rebid`, we put the candidate back in the bid pool and let them go", + " through the induction process again.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended candidate to be judged.", + " - `judgement` - `Approve`, `Reject`, or `Rebid`.", + "", + " # ", + " Key: B (len of bids), M (len of members), X (balance action)", + " - One storage read to check `who` is a suspended candidate.", + " - One storage removal of the suspended candidate.", + " - Approve Logic", + " \t- One storage read to get the available pot to pay users with. O(1)", + " \t- One storage write to update the available pot. O(1)", + " \t- One storage read to get the current block number. O(1)", + " \t- One storage read to get all members. O(M)", + " \t- Up to one unreserve currency action.", + " \t- Up to two new storage writes to payouts.", + " \t- Up to one storage write with O(log M) binary search to add a member to society.", + " - Reject Logic", + " \t- Up to one repatriate reserved currency action. O(X)", + " \t- Up to one storage write to ban the vouching member from vouching again.", + " - Rebid Logic", + " \t- Storage mutate with O(log B) binary search to place the user back into bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal.", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B + X)", + " # " + ] + }, + { + "name": "set_max_members", + "args": [ + { + "name": "max", + "type": "u32" + } + ], + "docs": [ + " Allows root origin to change the maximum number of members in society.", + " Max membership count must be greater than 1.", + "", + " The dispatch origin for this call must be from _ROOT_.", + "", + " Parameters:", + " - `max` - The maximum number of members for the society.", + "", + " # ", + " - One storage write to update the max. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "Founded", + "args": [ + "AccountId" + ], + "docs": [ + " The society is founded by the given identity." + ] + }, + { + "name": "Bid", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A membership bid just happened. The given account is the candidate's ID and their offer", + " is the second." + ] + }, + { + "name": "Vouch", + "args": [ + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A membership bid just happened by vouching. The given account is the candidate's ID and", + " their offer is the second. The vouching party is the third." + ] + }, + { + "name": "AutoUnbid", + "args": [ + "AccountId" + ], + "docs": [ + " A candidate was dropped (due to an excess of bids in the system)." + ] + }, + { + "name": "Unbid", + "args": [ + "AccountId" + ], + "docs": [ + " A candidate was dropped (by their request)." + ] + }, + { + "name": "Unvouch", + "args": [ + "AccountId" + ], + "docs": [ + " A candidate was dropped (by request of who vouched for them)." + ] + }, + { + "name": "Inducted", + "args": [ + "AccountId", + "Vec" + ], + "docs": [ + " A group of candidates have been inducted. The batch's primary is the first value, the", + " batch in full is the second." + ] + }, + { + "name": "SuspendedMemberJudgement", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A suspended member has been judged" + ] + }, + { + "name": "CandidateSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A candidate has been suspended" + ] + }, + { + "name": "MemberSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A member has been suspended" + ] + }, + { + "name": "Challenged", + "args": [ + "AccountId" + ], + "docs": [ + " A member has been challenged" + ] + }, + { + "name": "Vote", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed (candidate, voter, vote)" + ] + }, + { + "name": "DefenderVote", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed for a defending member (voter, vote)" + ] + }, + { + "name": "NewMaxMembers", + "args": [ + "u32" + ], + "docs": [ + " A new max member count has been set" + ] + }, + { + "name": "Unfounded", + "args": [ + "AccountId" + ], + "docs": [ + " Society is unfounded." + ] + } + ], + "constants": [ + { + "name": "CandidateDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The minimum amount of a deposit required for a bid to be made." + ] + }, + { + "name": "WrongSideDeduction", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount of the unpaid reward that gets deducted in the case that either a skeptic", + " doesn't vote or someone votes in the wrong way." + ] + }, + { + "name": "MaxStrikes", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The number of times a member may vote the wrong way (or not at all, when they are a skeptic)", + " before they become suspended." + ] + }, + { + "name": "PeriodSpend", + "type": "BalanceOf", + "value": "0x0000c52ebca2b1000000000000000000", + "docs": [ + " The amount of incentive paid within each period. Doesn't include VoterTip." + ] + }, + { + "name": "RotationPeriod", + "type": "BlockNumber", + "value": "0x00770100", + "docs": [ + " The number of blocks between candidate/membership rotation periods." + ] + }, + { + "name": "ChallengePeriod", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " The number of blocks between membership challenges." + ] + } + ], + "errors": [ + { + "name": "BadPosition", + "docs": [ + " An incorrect position was provided." + ] + }, + { + "name": "NotMember", + "docs": [ + " User is not a member." + ] + }, + { + "name": "AlreadyMember", + "docs": [ + " User is already a member." + ] + }, + { + "name": "Suspended", + "docs": [ + " User is suspended." + ] + }, + { + "name": "NotSuspended", + "docs": [ + " User is not suspended." + ] + }, + { + "name": "NoPayout", + "docs": [ + " Nothing to payout." + ] + }, + { + "name": "AlreadyFounded", + "docs": [ + " Society already founded." + ] + }, + { + "name": "InsufficientPot", + "docs": [ + " Not enough in pot to accept candidate." + ] + }, + { + "name": "AlreadyVouching", + "docs": [ + " Member is already vouching or banned from vouching again." + ] + }, + { + "name": "NotVouching", + "docs": [ + " Member is not vouching." + ] + }, + { + "name": "Head", + "docs": [ + " Cannot remove the head of the chain." + ] + }, + { + "name": "Founder", + "docs": [ + " Cannot remove the founder." + ] + }, + { + "name": "AlreadyBid", + "docs": [ + " User has already made a bid." + ] + }, + { + "name": "AlreadyCandidate", + "docs": [ + " User is already a candidate." + ] + }, + { + "name": "NotCandidate", + "docs": [ + " User is not a candidate." + ] + }, + { + "name": "MaxMembers", + "docs": [ + " Too many members in the society." + ] + }, + { + "name": "NotFounder", + "docs": [ + " The caller is not the founder." + ] + }, + { + "name": "NotHead", + "docs": [ + " The caller is not the head." + ] + } + ] + }, + { + "name": "Recovery", + "storage": { + "prefix": "Recovery", + "items": [ + { + "name": "Recoverable", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "RecoveryConfig", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of recoverable accounts and their recovery configuration." + ] + }, + { + "name": "ActiveRecoveries", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "ActiveRecovery", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Active recovery attempts.", + "", + " First account is the account to be recovered, and the second account", + " is the user trying to recover the account." + ] + }, + { + "name": "Recovered", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The final list of recovered accounts.", + "", + " Map from the recovered account to the user who can access it." + ] + } + ] + }, + "calls": [ + { + "name": "as_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through a recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you want to make a call on-behalf-of.", + " - `call`: The call you want to make with the recovered account.", + "", + " # ", + " - The weight of the `call`.", + " - One storage lookup to check account is recovered by `who`. O(1)", + " # " + ] + }, + { + "name": "set_recovered", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow ROOT to bypass the recovery process and set an a rescuer account", + " for a lost account directly.", + "", + " The dispatch origin for this call must be _ROOT_.", + "", + " Parameters:", + " - `lost`: The \"lost account\" to be recovered.", + " - `rescuer`: The \"rescuer account\" which can call as the lost account.", + "", + " # ", + " - One storage write O(1)", + " - One event", + " # " + ] + }, + { + "name": "create_recovery", + "args": [ + { + "name": "friends", + "type": "Vec" + }, + { + "name": "threshold", + "type": "u16" + }, + { + "name": "delay_period", + "type": "BlockNumber" + } + ], + "docs": [ + " Create a recovery configuration for your account. This makes your account recoverable.", + "", + " Payment: `ConfigDepositBase` + `FriendDepositFactor` * #_of_friends balance", + " will be reserved for storing the recovery configuration. This deposit is returned", + " in full when the user calls `remove_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `friends`: A list of friends you trust to vouch for recovery attempts.", + " Should be ordered and contain no duplicate values.", + " - `threshold`: The number of friends that must vouch for a recovery attempt", + " before the account can be recovered. Should be less than or equal to", + " the length of the list of friends.", + " - `delay_period`: The number of blocks after a recovery attempt is initialized", + " that needs to pass before the account can be recovered.", + "", + " # ", + " - Key: F (len of friends)", + " - One storage read to check that account is not already recoverable. O(1).", + " - A check that the friends list is sorted and unique. O(F)", + " - One currency reserve operation. O(X)", + " - One storage write. O(1). Codec O(F).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "initiate_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Initiate the process for recovering a recoverable account.", + "", + " Payment: `RecoveryDeposit` balance will be reserved for initiating the", + " recovery process. This deposit will always be repatriated to the account", + " trying to be recovered. See `close_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `account`: The lost account that you want to recover. This account", + " needs to be recoverable (i.e. have a recovery configuration).", + "", + " # ", + " - One storage read to check that account is recoverable. O(F)", + " - One storage read to check that this recovery process hasn't already started. O(1)", + " - One currency reserve operation. O(X)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "vouch_recovery", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow a \"friend\" of a recoverable account to vouch for an active recovery", + " process for that account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"friend\"", + " for the recoverable account.", + "", + " Parameters:", + " - `lost`: The lost account that you want to recover.", + " - `rescuer`: The account trying to rescue the lost account that you", + " want to vouch for.", + "", + " The combination of these two parameters must point to an active recovery", + " process.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One binary search to confirm caller is a friend. O(logF)", + " - One binary search to confirm caller has not already vouched. O(logV)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + logF + V + logV)", + " # " + ] + }, + { + "name": "claim_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Allow a successful rescuer to claim their recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"rescuer\"", + " who has successfully completed the account recovery process: collected", + " `threshold` or more vouches, waited `delay_period` blocks since initiation.", + "", + " Parameters:", + " - `account`: The lost account that you want to claim has been successfully", + " recovered by you.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + V)", + " # " + ] + }, + { + "name": "close_recovery", + "args": [ + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " As the controller of a recoverable account, close an active recovery", + " process for your account.", + "", + " Payment: By calling this function, the recoverable account will receive", + " the recovery deposit `RecoveryDeposit` placed by the rescuer.", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account with an active recovery process for it.", + "", + " Parameters:", + " - `rescuer`: The account trying to rescue this recoverable account.", + "", + " # ", + " Key: V (len of vouching friends)", + " - One storage read/remove to get the active recovery process. O(1), Codec O(V)", + " - One balance call to repatriate reserved. O(X)", + " - One event.", + "", + " Total Complexity: O(V + X)", + " # " + ] + }, + { + "name": "remove_recovery", + "args": [], + "docs": [ + " Remove the recovery process for your account.", + "", + " NOTE: The user must make sure to call `close_recovery` on all active", + " recovery attempts before calling this function else it will fail.", + "", + " Payment: By calling this function the recoverable account will unreserve", + " their recovery configuration deposit.", + " (`ConfigDepositBase` + `FriendDepositFactor` * #_of_friends)", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account (i.e. has a recovery configuration).", + "", + " # ", + " Key: F (len of friends)", + " - One storage read to get the prefix iterator for active recoveries. O(1)", + " - One storage read/remove to get the recovery configuration. O(1), Codec O(F)", + " - One balance call to unreserved. O(X)", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + } + ], + "events": [ + { + "name": "RecoveryCreated", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been set up for an account" + ] + }, + { + "name": "RecoveryInitiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process has been initiated for account_1 by account_2" + ] + }, + { + "name": "RecoveryVouched", + "args": [ + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for account_1 by account_2 has been vouched for by account_3" + ] + }, + { + "name": "RecoveryClosed", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for account_1 by account_2 has been closed" + ] + }, + { + "name": "AccountRecovered", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Account_1 has been successfully recovered by account_2" + ] + }, + { + "name": "RecoveryRemoved", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been removed for an account" + ] + } + ], + "constants": [], + "errors": [] + } + ] + } + } +} diff --git a/packages/polkadot/tests/meta/v11.hex b/packages/polkadot/tests/meta/v11.hex new file mode 100644 index 00000000..65a31332 --- /dev/null +++ b/packages/polkadot/tests/meta/v11.hex @@ -0,0 +1 @@ +0x6d6574610b801853797374656d011853797374656d3c1c4163636f756e7401010230543a3a4163636f756e744964944163636f756e74496e666f3c543a3a496e6465782c20543a3a4163636f756e74446174613e00150100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004e8205468652066756c6c206163636f756e7420696e666f726d6174696f6e20666f72206120706172746963756c6172206163636f756e742049442e3845787472696e736963436f756e7400000c753332040004b820546f74616c2065787472696e7369637320636f756e7420666f72207468652063757272656e7420626c6f636b2e2c426c6f636b576569676874010064776569676874733a3a45787472696e7369637357656967687440000000000000000000000000000000000488205468652063757272656e742077656967687420666f722074686520626c6f636b2e40416c6c45787472696e736963734c656e00000c753332040004410120546f74616c206c656e6774682028696e2062797465732920666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e24426c6f636b4861736801010538543a3a426c6f636b4e756d6265721c543a3a48617368008000000000000000000000000000000000000000000000000000000000000000000498204d6170206f6620626c6f636b206e756d6265727320746f20626c6f636b206861736865732e3445787472696e736963446174610101050c7533321c5665633c75383e000400043d012045787472696e73696373206461746120666f72207468652063757272656e7420626c6f636b20286d61707320616e2065787472696e736963277320696e64657820746f206974732064617461292e184e756d626572010038543a3a426c6f636b4e756d6265721000000000040901205468652063757272656e7420626c6f636b206e756d626572206265696e672070726f6365737365642e205365742062792060657865637574655f626c6f636b602e28506172656e744861736801001c543a3a4861736880000000000000000000000000000000000000000000000000000000000000000004702048617368206f66207468652070726576696f757320626c6f636b2e3845787472696e73696373526f6f7401001c543a3a486173688000000000000000000000000000000000000000000000000000000000000000000415012045787472696e7369637320726f6f74206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e1844696765737401002c4469676573744f663c543e040004f020446967657374206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e184576656e747301008c5665633c4576656e745265636f72643c543a3a4576656e742c20543a3a486173683e3e040004a0204576656e7473206465706f736974656420666f72207468652063757272656e7420626c6f636b2e284576656e74436f756e740100284576656e74496e646578100000000004b820546865206e756d626572206f66206576656e747320696e2074686520604576656e74733c543e60206c6973742e2c4576656e74546f706963730101021c543a3a48617368845665633c28543a3a426c6f636b4e756d6265722c204576656e74496e646578293e000400282501204d617070696e67206265747765656e206120746f7069632028726570726573656e74656420627920543a3a486173682920616e64206120766563746f72206f6620696e646578657394206f66206576656e747320696e2074686520603c4576656e74733c543e3e60206c6973742e00510120416c6c20746f70696320766563746f727320686176652064657465726d696e69737469632073746f72616765206c6f636174696f6e7320646570656e64696e67206f6e2074686520746f7069632e2054686973450120616c6c6f7773206c696768742d636c69656e747320746f206c6576657261676520746865206368616e67657320747269652073746f7261676520747261636b696e67206d656368616e69736d20616e64e420696e2063617365206f66206368616e67657320666574636820746865206c697374206f66206576656e7473206f6620696e7465726573742e004d01205468652076616c756520686173207468652074797065206028543a3a426c6f636b4e756d6265722c204576656e74496e646578296020626563617573652069662077652075736564206f6e6c79206a7573744d012074686520604576656e74496e64657860207468656e20696e20636173652069662074686520746f70696320686173207468652073616d6520636f6e74656e7473206f6e20746865206e65787420626c6f636b0101206e6f206e6f74696669636174696f6e2077696c6c20626520747269676765726564207468757320746865206576656e74206d69676874206265206c6f73742e484c61737452756e74696d65557067726164650000584c61737452756e74696d6555706772616465496e666f04000455012053746f726573207468652060737065635f76657273696f6e6020616e642060737065635f6e616d6560206f66207768656e20746865206c6173742072756e74696d6520757067726164652068617070656e65642e38457865637574696f6e50686173650000145068617365040004882054686520657865637574696f6e207068617365206f662074686520626c6f636b2e01282866696c6c5f626c6f636b04185f726174696f1c50657262696c6c040901204120646973706174636820746861742077696c6c2066696c6c2074686520626c6f636b2077656967687420757020746f2074686520676976656e20726174696f2e1872656d61726b041c5f72656d61726b1c5665633c75383e1c6c204d616b6520736f6d65206f6e2d636861696e2072656d61726b2e002c2023203c7765696768743e24202d20604f28312960e0202d2042617365205765696768743a20302e36363520c2b5732c20696e646570656e64656e74206f662072656d61726b206c656e6774682e50202d204e6f204442206f7065726174696f6e732e302023203c2f7765696768743e387365745f686561705f7061676573041470616765730c75363420fc2053657420746865206e756d626572206f6620706167657320696e2074686520576562417373656d626c7920656e7669726f6e6d656e74277320686561702e002c2023203c7765696768743e24202d20604f283129604c202d20312073746f726167652077726974652e64202d2042617365205765696768743a20312e34303520c2b57360202d203120777269746520746f20484541505f5041474553302023203c2f7765696768743e207365745f636f64650410636f64651c5665633c75383e28682053657420746865206e65772072756e74696d6520636f64652e002c2023203c7765696768743e3501202d20604f2843202b2053296020776865726520604360206c656e677468206f662060636f64656020616e642060536020636f6d706c6578697479206f66206063616e5f7365745f636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e7901202d20312063616c6c20746f206063616e5f7365745f636f6465603a20604f28532960202863616c6c73206073705f696f3a3a6d6973633a3a72756e74696d655f76657273696f6e6020776869636820697320657870656e73697665292e2c202d2031206576656e742e7d012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652c206275742067656e6572616c6c792074686973206973207665727920657870656e736976652e902057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f636f64655f776974686f75745f636865636b730410636f64651c5665633c75383e201d012053657420746865206e65772072756e74696d6520636f646520776974686f757420646f696e6720616e7920636865636b73206f662074686520676976656e2060636f6465602e002c2023203c7765696768743e90202d20604f2843296020776865726520604360206c656e677468206f662060636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e2c202d2031206576656e742e75012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652e2057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f6368616e6765735f747269655f636f6e666967044c6368616e6765735f747269655f636f6e666967804f7074696f6e3c4368616e67657354726965436f6e66696775726174696f6e3e28a02053657420746865206e6577206368616e676573207472696520636f6e66696775726174696f6e2e002c2023203c7765696768743e24202d20604f28312960b0202d20312073746f72616765207772697465206f722064656c6574652028636f64656320604f28312960292ed8202d20312063616c6c20746f20606465706f7369745f6c6f67603a20557365732060617070656e6460204150492c20736f204f28312964202d2042617365205765696768743a20372e32313820c2b57334202d204442205765696768743aa820202020202d205772697465733a204368616e67657320547269652c2053797374656d20446967657374302023203c2f7765696768743e2c7365745f73746f7261676504146974656d73345665633c4b657956616c75653e206c2053657420736f6d65206974656d73206f662073746f726167652e002c2023203c7765696768743e94202d20604f2849296020776865726520604960206c656e677468206f6620606974656d73607c202d206049602073746f72616765207772697465732028604f28312960292e74202d2042617365205765696768743a20302e353638202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e306b696c6c5f73746f7261676504106b657973205665633c4b65793e2078204b696c6c20736f6d65206974656d732066726f6d2073746f726167652e002c2023203c7765696768743efc202d20604f28494b296020776865726520604960206c656e677468206f6620606b6579736020616e6420604b60206c656e677468206f66206f6e65206b657964202d206049602073746f726167652064656c6574696f6e732e70202d2042617365205765696768743a202e333738202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e2c6b696c6c5f70726566697808187072656669780c4b6579205f7375626b6579730c7533322c1501204b696c6c20616c6c2073746f72616765206974656d7320776974682061206b657920746861742073746172747320776974682074686520676976656e207072656669782e003d01202a2a4e4f54453a2a2a2057652072656c79206f6e2074686520526f6f74206f726967696e20746f2070726f7669646520757320746865206e756d626572206f66207375626b65797320756e64657241012074686520707265666978207765206172652072656d6f76696e6720746f2061636375726174656c792063616c63756c6174652074686520776569676874206f6620746869732066756e6374696f6e2e002c2023203c7765696768743edc202d20604f285029602077686572652060506020616d6f756e74206f66206b65797320776974682070726566697820607072656669786064202d206050602073746f726167652064656c6574696f6e732e74202d2042617365205765696768743a20302e383334202a205020c2b57380202d205772697465733a204e756d626572206f66207375626b657973202b2031302023203c2f7765696768743e1c7375696369646500286501204b696c6c207468652073656e64696e67206163636f756e742c20617373756d696e6720746865726520617265206e6f207265666572656e636573206f75747374616e64696e6720616e642074686520636f6d706f7369746590206461746120697320657175616c20746f206974732064656661756c742076616c75652e002c2023203c7765696768743e24202d20604f283129607c202d20312073746f72616765207265616420616e642064656c6574696f6e2e54202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a20382e36323620c2b5731101204e6f2044422052656164206f72205772697465206f7065726174696f6e7320626563617573652063616c6c657220697320616c726561647920696e206f7665726c6179302023203c2f7765696768743e01144045787472696e7369635375636365737304304469737061746368496e666f04b020416e2065787472696e73696320636f6d706c65746564207375636365737366756c6c792e205b696e666f5d3c45787472696e7369634661696c6564083444697370617463684572726f72304469737061746368496e666f048c20416e2065787472696e736963206661696c65642e205b6572726f722c20696e666f5d2c436f64655570646174656400045420603a636f6465602077617320757064617465642e284e65774163636f756e7404244163636f756e74496404742041206e6577205b6163636f756e745d2077617320637265617465642e344b696c6c65644163636f756e7404244163636f756e744964046420416e205b6163636f756e745d20776173207265617065642e1838426c6f636b48617368436f756e7438543a3a426c6f636b4e756d626572106009000004d820546865206d6178696d756d206e756d626572206f6620626c6f636b7320746f20616c6c6f7720696e206d6f7274616c20657261732e484d6178696d756d426c6f636b576569676874185765696768742000204aa9d1010000047c20546865206d6178696d756d20776569676874206f66206120626c6f636b2e2044625765696768743c52756e74696d6544625765696768744040787d010000000000e1f505000000000409012054686520776569676874206f662072756e74696d65206461746162617365206f7065726174696f6e73207468652072756e74696d652063616e20696e766f6b652e50426c6f636b457865637574696f6e576569676874185765696768742000f2052a0100000004510120546865206261736520776569676874206f6620657865637574696e67206120626c6f636b2c20696e646570656e64656e74206f6620746865207472616e73616374696f6e7320696e2074686520626c6f636b2e4c45787472696e736963426173655765696768741857656967687420405973070000000004790120546865206261736520776569676874206f6620616e2045787472696e73696320696e2074686520626c6f636b2c20696e646570656e64656e74206f6620746865206f662065787472696e736963206265696e672065786563757465642e484d6178696d756d426c6f636b4c656e6774680c753332100000500004a820546865206d6178696d756d206c656e677468206f66206120626c6f636b2028696e206279746573292e143c496e76616c6964537065634e616d6508150120546865206e616d65206f662073706563696669636174696f6e20646f6573206e6f74206d61746368206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e685370656356657273696f6e4e65656473546f496e637265617365084501205468652073706563696669636174696f6e2076657273696f6e206973206e6f7420616c6c6f77656420746f206465637265617365206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e744661696c6564546f4578747261637452756e74696d6556657273696f6e0cf0204661696c656420746f2065787472616374207468652072756e74696d652076657273696f6e2066726f6d20746865206e65772072756e74696d652e000d01204569746865722063616c6c696e672060436f72655f76657273696f6e60206f72206465636f64696e67206052756e74696d6556657273696f6e60206661696c65642e4c4e6f6e44656661756c74436f6d706f7369746504010120537569636964652063616c6c6564207768656e20746865206163636f756e7420686173206e6f6e2d64656661756c7420636f6d706f7369746520646174612e3c4e6f6e5a65726f526566436f756e740439012054686572652069732061206e6f6e2d7a65726f207265666572656e636520636f756e742070726576656e74696e6720746865206163636f756e742066726f6d206265696e67207075726765642e1c5574696c697479000108146261746368041463616c6c735c5665633c3c542061732054726169743e3a3a43616c6c3e50802053656e642061206261746368206f662064697370617463682063616c6c732e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e006101204966206f726967696e20697320726f6f74207468656e2063616c6c2061726520646973706174636820776974686f757420636865636b696e67206f726967696e2066696c7465722e20285468697320696e636c75646573c820627970617373696e6720606672616d655f73797374656d3a3a54726169743a3a4261736543616c6c46696c74657260292e002c2023203c7765696768743e90202d2042617365207765696768743a2031342e3339202b202e393837202a206320c2b573b8202d20506c7573207468652073756d206f66207468652077656967687473206f6620746865206063616c6c73602ec4202d20506c7573206f6e65206164646974696f6e616c206576656e742e202872657065617420726561642f777269746529302023203c2f7765696768743e00590120546869732077696c6c2072657475726e20604f6b6020696e20616c6c2063697263756d7374616e6365732e20546f2064657465726d696e65207468652073756363657373206f66207468652062617463682c20616e3501206576656e74206973206465706f73697465642e20496620612063616c6c206661696c656420616e64207468652062617463682077617320696e7465727275707465642c207468656e20746865590120604261746368496e74657272757074656460206576656e74206973206465706f73697465642c20616c6f6e67207769746820746865206e756d626572206f66207375636365737366756c2063616c6c73206d616465510120616e6420746865206572726f72206f6620746865206661696c65642063616c6c2e20496620616c6c2077657265207375636365737366756c2c207468656e2074686520604261746368436f6d706c657465646050206576656e74206973206465706f73697465642e3461735f646572697661746976650814696e6465780c7531361063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e34e02053656e6420612063616c6c207468726f75676820616e20696e64657865642070736575646f6e796d206f66207468652073656e6465722e0059012046696c7465722066726f6d206f726967696e206172652070617373656420616c6f6e672e205468652063616c6c2077696c6c2062652064697370617463686564207769746820616e206f726967696e207768696368c020757365207468652073616d652066696c74657220617320746865206f726967696e206f6620746869732063616c6c2e004901204e4f54453a20496620796f75206e65656420746f20656e73757265207468617420616e79206163636f756e742d62617365642066696c746572696e67206973206e6f7420686f6e6f7265642028692e652e6501206265636175736520796f7520657870656374206070726f78796020746f2068617665206265656e2075736564207072696f7220696e207468652063616c6c20737461636b20616e6420796f7520646f206e6f742077616e745501207468652063616c6c207265737472696374696f6e7320746f206170706c7920746f20616e79207375622d6163636f756e7473292c207468656e20757365206061735f6d756c74695f7468726573686f6c645f31608020696e20746865204d756c74697369672070616c6c657420696e73746561642e00f8204e4f54453a205072696f7220746f2076657273696f6e202a31322c2074686973207761732063616c6c6564206061735f6c696d697465645f737562602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0108404261746368496e746572727570746564080c7533323444697370617463684572726f72085901204261746368206f66206469737061746368657320646964206e6f7420636f6d706c6574652066756c6c792e20496e646578206f66206669727374206661696c696e6720646973706174636820676976656e2c206173882077656c6c20617320746865206572726f722e205b696e6465782c206572726f725d384261746368436f6d706c657465640004cc204261746368206f66206469737061746368657320636f6d706c657465642066756c6c792077697468206e6f206572726f722e000010426162650110426162652c2845706f6368496e64657801000c75363420000000000000000004542043757272656e742065706f636820696e6465782e2c417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e0400046c2043757272656e742065706f636820617574686f7269746965732e2c47656e65736973536c6f7401000c75363420000000000000000008f82054686520736c6f74206174207768696368207468652066697273742065706f63682061637475616c6c7920737461727465642e205468697320697320309020756e74696c2074686520666972737420626c6f636b206f662074686520636861696e2e2c43757272656e74536c6f7401000c75363420000000000000000004542043757272656e7420736c6f74206e756d6265722e2852616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e65737380000000000000000000000000000000000000000000000000000000000000000028b8205468652065706f63682072616e646f6d6e65737320666f7220746865202a63757272656e742a2065706f63682e002c20232053656375726974790005012054686973204d555354204e4f54206265207573656420666f722067616d626c696e672c2061732069742063616e20626520696e666c75656e6365642062792061f8206d616c6963696f75732076616c696461746f7220696e207468652073686f7274207465726d2e204974204d4159206265207573656420696e206d616e7915012063727970746f677261706869632070726f746f636f6c732c20686f77657665722c20736f206c6f6e67206173206f6e652072656d656d6265727320746861742074686973150120286c696b652065766572797468696e6720656c7365206f6e2d636861696e29206974206973207075626c69632e20466f72206578616d706c652c2069742063616e206265050120757365642077686572652061206e756d626572206973206e656564656420746861742063616e6e6f742068617665206265656e2063686f73656e20627920616e0d01206164766572736172792c20666f7220707572706f7365732073756368206173207075626c69632d636f696e207a65726f2d6b6e6f776c656467652070726f6f66732e3c4e65787445706f6368436f6e6669670000504e657874436f6e66696744657363726970746f7204000498204e6578742065706f636820636f6e66696775726174696f6e2c206966206368616e6765642e384e65787452616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e657373800000000000000000000000000000000000000000000000000000000000000000045c204e6578742065706f63682072616e646f6d6e6573732e305365676d656e74496e64657801000c7533321000000000247c2052616e646f6d6e65737320756e64657220636f6e737472756374696f6e2e00f4205765206d616b6520612074726164656f6666206265747765656e2073746f7261676520616363657373657320616e64206c697374206c656e6774682e01012057652073746f72652074686520756e6465722d636f6e737472756374696f6e2072616e646f6d6e65737320696e207365676d656e7473206f6620757020746f942060554e4445525f434f4e535452554354494f4e5f5345474d454e545f4c454e475448602e00ec204f6e63652061207365676d656e7420726561636865732074686973206c656e6774682c20776520626567696e20746865206e657874206f6e652e090120576520726573657420616c6c207365676d656e747320616e642072657475726e20746f206030602061742074686520626567696e6e696e67206f662065766572791c2065706f63682e44556e646572436f6e737472756374696f6e0101050c7533326c5665633c7363686e6f72726b656c3a3a52616e646f6d6e6573733e0004000415012054574f582d4e4f54453a20605365676d656e74496e6465786020697320616e20696e6372656173696e6720696e74656765722c20736f2074686973206973206f6b61792e2c496e697469616c697a656400003c4d6179626552616e646f6d6e65737304000801012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e292077686963682069732060536f6d65601d01206966207065722d626c6f636b20696e697469616c697a6174696f6e2068617320616c7265616479206265656e2063616c6c656420666f722063757272656e7420626c6f636b2e204c6174656e657373010038543a3a426c6f636b4e756d626572100000000014d820486f77206c617465207468652063757272656e7420626c6f636b20697320636f6d706172656420746f2069747320706172656e742e001501205468697320656e74727920697320706f70756c617465642061732070617274206f6620626c6f636b20657865637574696f6e20616e6420697320636c65616e65642075701101206f6e20626c6f636b2066696e616c697a6174696f6e2e205175657279696e6720746869732073746f7261676520656e747279206f757473696465206f6620626c6f636bb020657865637574696f6e20636f6e746578742073686f756c6420616c77617973207969656c64207a65726f2e01084c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66200d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e00083445706f63684475726174696f6e0c75363420c800000000000000080d0120546865206e756d626572206f66202a2a736c6f74732a2a207468617420616e2065706f63682074616b65732e20576520636f75706c652073657373696f6e7320746ffc2065706f6368732c20692e652e2077652073746172742061206e65772073657373696f6e206f6e636520746865206e65772065706f636820626567696e732e444578706563746564426c6f636b54696d6524543a3a4d6f6d656e7420b80b00000000000014050120546865206578706563746564206176657261676520626c6f636b2074696d6520617420776869636820424142452073686f756c64206265206372656174696e67110120626c6f636b732e2053696e636520424142452069732070726f626162696c6973746963206974206973206e6f74207472697669616c20746f20666967757265206f75740501207768617420746865206578706563746564206176657261676520626c6f636b2074696d652073686f756c64206265206261736564206f6e2074686520736c6f740901206475726174696f6e20616e642074686520736563757269747920706172616d657465722060636020287768657265206031202d20636020726570726573656e7473a0207468652070726f626162696c697479206f66206120736c6f74206265696e6720656d707479292e002454696d657374616d70012454696d657374616d70080c4e6f77010024543a3a4d6f6d656e7420000000000000000004902043757272656e742074696d6520666f72207468652063757272656e7420626c6f636b2e24446964557064617465010010626f6f6c040004b420446964207468652074696d657374616d7020676574207570646174656420696e207468697320626c6f636b3f01040c736574040c6e6f7748436f6d706163743c543a3a4d6f6d656e743e3c5820536574207468652063757272656e742074696d652e00590120546869732063616c6c2073686f756c6420626520696e766f6b65642065786163746c79206f6e63652070657220626c6f636b2e2049742077696c6c2070616e6963206174207468652066696e616c697a6174696f6ed82070686173652c20696620746869732063616c6c206861736e2774206265656e20696e766f6b656420627920746861742074696d652e004501205468652074696d657374616d702073686f756c642062652067726561746572207468616e207468652070726576696f7573206f6e652062792074686520616d6f756e74207370656369666965642062794420604d696e696d756d506572696f64602e00d820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060496e686572656e74602e002c2023203c7765696768743ed0202d20604f285429602077686572652060546020636f6d706c6578697479206f6620606f6e5f74696d657374616d705f73657460a101202d20312073746f72616765207265616420616e6420312073746f72616765206d75746174696f6e2028636f64656320604f28312960292e202862656361757365206f6620604469645570646174653a3a74616b656020696e20606f6e5f66696e616c697a656029b4202d2031206576656e742068616e646c657220606f6e5f74696d657374616d705f7365746020604f285429602e302023203c2f7765696768743e0004344d696e696d756d506572696f6424543a3a4d6f6d656e7420dc0500000000000010690120546865206d696e696d756d20706572696f64206265747765656e20626c6f636b732e204265776172652074686174207468697320697320646966666572656e7420746f20746865202a65787065637465642a20706572696f64690120746861742074686520626c6f636b2070726f64756374696f6e206170706172617475732070726f76696465732e20596f75722063686f73656e20636f6e73656e7375732073797374656d2077696c6c2067656e6572616c6c79650120776f726b2077697468207468697320746f2064657465726d696e6520612073656e7369626c6520626c6f636b2074696d652e20652e672e20466f7220417572612c2069742077696c6c20626520646f75626c6520746869737020706572696f64206f6e2064656661756c742073657474696e67732e0028417574686f72736869700128417574686f72736869700c18556e636c65730100e85665633c556e636c65456e7472794974656d3c543a3a426c6f636b4e756d6265722c20543a3a486173682c20543a3a4163636f756e7449643e3e0400041c20556e636c657318417574686f72000030543a3a4163636f756e7449640400046420417574686f72206f662063757272656e7420626c6f636b2e30446964536574556e636c6573010010626f6f6c040004bc205768657468657220756e636c6573207765726520616c72656164792073657420696e207468697320626c6f636b2e0104287365745f756e636c657304286e65775f756e636c6573385665633c543a3a4865616465723e04642050726f76696465206120736574206f6620756e636c65732e00001c48496e76616c6964556e636c65506172656e74048c2054686520756e636c6520706172656e74206e6f7420696e2074686520636861696e2e40556e636c6573416c7265616479536574048420556e636c657320616c72656164792073657420696e2074686520626c6f636b2e34546f6f4d616e79556e636c6573044420546f6f206d616e7920756e636c65732e3047656e65736973556e636c6504582054686520756e636c652069732067656e657369732e30546f6f48696768556e636c6504802054686520756e636c6520697320746f6f206869676820696e20636861696e2e50556e636c65416c7265616479496e636c75646564047c2054686520756e636c6520697320616c726561647920696e636c756465642e204f6c64556e636c6504b82054686520756e636c652069736e277420726563656e7420656e6f75676820746f20626520696e636c756465642e1c496e6469636573011c496e646963657304204163636f756e74730001023c543a3a4163636f756e74496e6465788828543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20626f6f6c29000400048820546865206c6f6f6b75702066726f6d20696e64657820746f206163636f756e742e011414636c61696d0414696e6465783c543a3a4163636f756e74496e6465784c9c2041737369676e20616e2070726576696f75736c7920756e61737369676e656420696e6465782e00e0205061796d656e743a20604465706f736974602069732072657365727665642066726f6d207468652073656e646572206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e00f4202d2060696e646578603a2074686520696e64657820746f20626520636c61696d65642e2054686973206d757374206e6f7420626520696e207573652e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2032382e363920c2b57394202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e207472616e73666572080c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e6465785461012041737369676e20616e20696e64657820616c7265616479206f776e6564206279207468652073656e64657220746f20616e6f74686572206163636f756e742e205468652062616c616e6365207265736572766174696f6ebc206973206566666563746976656c79207472616e7366657272656420746f20746865206e6577206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002901202d2060696e646578603a2074686520696e64657820746f2062652072652d61737369676e65642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e68202d204f6e65207472616e73666572206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2033332e373420c2b57334202d204442205765696768743ae4202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429e8202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429302023203c2f7765696768743e10667265650414696e6465783c543a3a4163636f756e74496e6465784c98204672656520757020616e20696e646578206f776e6564206279207468652073656e6465722e006101205061796d656e743a20416e792070726576696f7573206465706f73697420706c6163656420666f722074686520696e64657820697320756e726573657276656420696e207468652073656e646572206163636f756e742e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206f776e2074686520696e6465782e001101202d2060696e646578603a2074686520696e64657820746f2062652066726565642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e008820456d6974732060496e646578467265656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2032352e353320c2b57394202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e38666f7263655f7472616e736665720c0c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e64657818667265657a6510626f6f6c58590120466f72636520616e20696e64657820746f20616e206163636f756e742e205468697320646f65736e277420726571756972652061206465706f7369742e2049662074686520696e64657820697320616c7265616479ec2068656c642c207468656e20616e79206465706f736974206973207265696d62757273656420746f206974732063757272656e74206f776e65722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00a8202d2060696e646578603a2074686520696e64657820746f206265202872652d2961737369676e65642e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e4501202d2060667265657a65603a2069662073657420746f206074727565602c2077696c6c20667265657a652074686520696e64657820736f2069742063616e6e6f74206265207472616e736665727265642e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e7c202d20557020746f206f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2032362e383320c2b57334202d204442205765696768743af8202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229fc202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229302023203c2f7765696768743e18667265657a650414696e6465783c543a3a4163636f756e74496e64657848690120467265657a6520616e20696e64657820736f2069742077696c6c20616c7761797320706f696e7420746f207468652073656e646572206163636f756e742e205468697320636f6e73756d657320746865206465706f7369742e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d7573742068617665206170206e6f6e2d66726f7a656e206163636f756e742060696e646578602e00b0202d2060696e646578603a2074686520696e64657820746f2062652066726f7a656e20696e20706c6163652e008c20456d6974732060496e64657846726f7a656e60206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e74202d20557020746f206f6e6520736c617368206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2033302e383620c2b57394202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e010c34496e64657841737369676e656408244163636f756e744964304163636f756e74496e64657804ac2041206163636f756e7420696e646578207761732061737369676e65642e205b77686f2c20696e6465785d28496e646578467265656404304163636f756e74496e64657804e02041206163636f756e7420696e64657820686173206265656e2066726565642075702028756e61737369676e6564292e205b696e6465785d2c496e64657846726f7a656e08304163636f756e74496e646578244163636f756e7449640421012041206163636f756e7420696e64657820686173206265656e2066726f7a656e20746f206974732063757272656e74206163636f756e742049442e205b77686f2c20696e6465785d041c4465706f7369743042616c616e63654f663c543e4000407a10f35a0000000000000000000004ac20546865206465706f736974206e656564656420666f7220726573657276696e6720616e20696e6465782e002042616c616e636573012042616c616e6365731034546f74616c49737375616e6365010028543a3a42616c616e6365400000000000000000000000000000000004982054686520746f74616c20756e6974732069737375656420696e207468652073797374656d2e1c4163636f756e7401010230543a3a4163636f756e7449645c4163636f756e74446174613c543a3a42616c616e63653e000101000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c6c205468652062616c616e6365206f6620616e206163636f756e742e004101204e4f54453a2054686973206973206f6e6c79207573656420696e20746865206361736520746861742074686973206d6f64756c65206973207573656420746f2073746f72652062616c616e6365732e144c6f636b7301010230543a3a4163636f756e744964705665633c42616c616e63654c6f636b3c543a3a42616c616e63653e3e00040008b820416e79206c6971756964697479206c6f636b73206f6e20736f6d65206163636f756e742062616c616e6365732e2501204e4f54453a2053686f756c64206f6e6c79206265206163636573736564207768656e2073657474696e672c206368616e67696e6720616e642066726565696e672061206c6f636b2e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076322e302e3020666f72206e6577206e6574776f726b732e0110207472616e736665720810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e6cd8205472616e7366657220736f6d65206c697175696420667265652062616c616e636520746f20616e6f74686572206163636f756e742e00090120607472616e73666572602077696c6c207365742074686520604672656542616c616e636560206f66207468652073656e64657220616e642072656365697665722e21012049742077696c6c2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d2062792074686520605472616e73666572466565602e1501204966207468652073656e6465722773206163636f756e742069732062656c6f7720746865206578697374656e7469616c206465706f736974206173206120726573756c74b4206f6620746865207472616e736665722c20746865206163636f756e742077696c6c206265207265617065642e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605369676e65646020627920746865207472616e736163746f722e002c2023203c7765696768743e3101202d20446570656e64656e74206f6e20617267756d656e747320627574206e6f7420637269746963616c2c20676976656e2070726f70657220696d706c656d656e746174696f6e7320666f72cc202020696e70757420636f6e6669672074797065732e205365652072656c617465642066756e6374696f6e732062656c6f772e6901202d20497420636f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e642077726974657320696e7465726e616c6c7920616e64206e6f20636f6d706c657820636f6d7075746174696f6e2e004c2052656c617465642066756e6374696f6e733a0051012020202d2060656e737572655f63616e5f77697468647261776020697320616c776179732063616c6c656420696e7465726e616c6c792062757420686173206120626f756e64656420636f6d706c65786974792e2d012020202d205472616e7366657272696e672062616c616e63657320746f206163636f756e7473207468617420646964206e6f74206578697374206265666f72652077696c6c206361757365d420202020202060543a3a4f6e4e65774163636f756e743a3a6f6e5f6e65775f6163636f756e746020746f2062652063616c6c65642e61012020202d2052656d6f76696e6720656e6f7567682066756e64732066726f6d20616e206163636f756e742077696c6c20747269676765722060543a3a4475737452656d6f76616c3a3a6f6e5f756e62616c616e636564602e49012020202d20607472616e736665725f6b6565705f616c6976656020776f726b73207468652073616d652077617920617320607472616e73666572602c206275742068617320616e206164646974696f6e616cf82020202020636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c20746865206f726967696e206163636f756e742e88202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d4501202d2042617365205765696768743a2037332e363420c2b5732c20776f7273742063617365207363656e6172696f20286163636f756e7420637265617465642c206163636f756e742072656d6f76656429dc202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374696e6174696f6e206163636f756e741501202d204f726967696e206163636f756e7420697320616c726561647920696e206d656d6f72792c20736f206e6f204442206f7065726174696f6e7320666f72207468656d2e302023203c2f7765696768743e2c7365745f62616c616e63650c0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365206e65775f667265654c436f6d706163743c543a3a42616c616e63653e306e65775f72657365727665644c436f6d706163743c543a3a42616c616e63653e489420536574207468652062616c616e636573206f66206120676976656e206163636f756e742e00210120546869732077696c6c20616c74657220604672656542616c616e63656020616e642060526573657276656442616c616e63656020696e2073746f726167652e2069742077696c6c090120616c736f2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d202860546f74616c49737375616e636560292e190120496620746865206e65772066726565206f722072657365727665642062616c616e63652069732062656c6f7720746865206578697374656e7469616c206465706f7369742c01012069742077696c6c20726573657420746865206163636f756e74206e6f6e63652028606672616d655f73797374656d3a3a4163636f756e744e6f6e636560292e00b420546865206469737061746368206f726967696e20666f7220746869732063616c6c2069732060726f6f74602e002c2023203c7765696768743e80202d20496e646570656e64656e74206f662074686520617267756d656e74732ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e58202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d3c202d2042617365205765696768743a6820202020202d204372656174696e673a2032372e353620c2b5736420202020202d204b696c6c696e673a2033352e313120c2b57398202d204442205765696768743a203120526561642c203120577269746520746f206077686f60302023203c2f7765696768743e38666f7263655f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e1851012045786163746c7920617320607472616e73666572602c2065786365707420746865206f726967696e206d75737420626520726f6f7420616e642074686520736f75726365206163636f756e74206d61792062652c207370656369666965642e2c2023203c7765696768743e4101202d2053616d65206173207472616e736665722c20627574206164646974696f6e616c207265616420616e6420777269746520626563617573652074686520736f75726365206163636f756e74206973902020206e6f7420617373756d656420746f20626520696e20746865206f7665726c61792e302023203c2f7765696768743e4c7472616e736665725f6b6565705f616c6976650810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e2c51012053616d6520617320746865205b607472616e73666572605d2063616c6c2c206275742077697468206120636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c2074686540206f726967696e206163636f756e742e00bc20393925206f66207468652074696d6520796f752077616e74205b607472616e73666572605d20696e73746561642e00c4205b607472616e73666572605d3a207374727563742e4d6f64756c652e68746d6c236d6574686f642e7472616e736665722c2023203c7765696768743ee8202d2043686561706572207468616e207472616e736665722062656361757365206163636f756e742063616e6e6f74206265206b696c6c65642e60202d2042617365205765696768743a2035312e3420c2b5731d01202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374202873656e64657220697320696e206f7665726c617920616c7265616479292c20233c2f7765696768743e01201c456e646f77656408244163636f756e7449641c42616c616e6365041d0120416e206163636f756e74207761732063726561746564207769746820736f6d6520667265652062616c616e63652e205b6163636f756e742c20667265655f62616c616e63655d20447573744c6f737408244163636f756e7449641c42616c616e636508410120416e206163636f756e74207761732072656d6f7665642077686f73652062616c616e636520776173206e6f6e2d7a65726f206275742062656c6f77204578697374656e7469616c4465706f7369742cc820726573756c74696e6720696e20616e206f75747269676874206c6f73732e205b6163636f756e742c2062616c616e63655d205472616e736665720c244163636f756e744964244163636f756e7449641c42616c616e63650498205472616e73666572207375636365656465642e205b66726f6d2c20746f2c2076616c75655d2842616c616e63655365740c244163636f756e7449641c42616c616e63651c42616c616e636504c420412062616c616e6365207761732073657420627920726f6f742e205b77686f2c20667265652c2072657365727665645d1c4465706f73697408244163636f756e7449641c42616c616e636504190120536f6d6520616d6f756e7420776173206465706f73697465642028652e672e20666f72207472616e73616374696f6e2066656573292e205b77686f2c206465706f7369745d20526573657276656408244163636f756e7449641c42616c616e636504190120536f6d652062616c616e63652077617320726573657276656420286d6f7665642066726f6d206672656520746f207265736572766564292e205b77686f2c2076616c75655d28556e726573657276656408244163636f756e7449641c42616c616e636504210120536f6d652062616c616e63652077617320756e726573657276656420286d6f7665642066726f6d20726573657276656420746f2066726565292e205b77686f2c2076616c75655d4852657365727665526570617472696174656410244163636f756e744964244163636f756e7449641c42616c616e6365185374617475730c510120536f6d652062616c616e636520776173206d6f7665642066726f6d207468652072657365727665206f6620746865206669727374206163636f756e7420746f20746865207365636f6e64206163636f756e742edc2046696e616c20617267756d656e7420696e64696361746573207468652064657374696e6174696f6e2062616c616e636520747970652ea0205b66726f6d2c20746f2c2062616c616e63652c2064657374696e6174696f6e5f7374617475735d04484578697374656e7469616c4465706f73697428543a3a42616c616e63654000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f206b65657020616e206163636f756e74206f70656e2e203856657374696e6742616c616e6365049c2056657374696e672062616c616e636520746f6f206869676820746f2073656e642076616c7565544c69717569646974795265737472696374696f6e7304c8204163636f756e74206c6971756964697479207265737472696374696f6e732070726576656e74207769746864726177616c204f766572666c6f77047420476f7420616e206f766572666c6f7720616674657220616464696e674c496e73756666696369656e7442616c616e636504782042616c616e636520746f6f206c6f7720746f2073656e642076616c7565484578697374656e7469616c4465706f73697404ec2056616c756520746f6f206c6f7720746f20637265617465206163636f756e742064756520746f206578697374656e7469616c206465706f736974244b656570416c6976650490205472616e736665722f7061796d656e7420776f756c64206b696c6c206163636f756e745c4578697374696e6756657374696e675363686564756c6504cc20412076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e742c446561644163636f756e74048c2042656e6566696369617279206163636f756e74206d757374207072652d6578697374485472616e73616374696f6e5061796d656e7401485472616e73616374696f6e5061796d656e7408444e6578744665654d756c7469706c6965720100284d756c7469706c69657240000064a7b3b6e00d0000000000000000003853746f7261676556657273696f6e01002052656c6561736573040000000008485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e2c576569676874546f466565a45665633c576569676874546f466565436f656666696369656e743c42616c616e63654f663c543e3e3e5c0401000000000000000000000000000000000000000001040d012054686520706f6c796e6f6d69616c2074686174206973206170706c69656420696e206f7264657220746f20646572697665206665652066726f6d207765696768742e001c5374616b696e67011c5374616b696e678c30486973746f7279446570746801000c75333210540000001c8c204e756d626572206f66206572617320746f206b65657020696e20686973746f72792e00390120496e666f726d6174696f6e206973206b65707420666f72206572617320696e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e006101204d757374206265206d6f7265207468616e20746865206e756d626572206f6620657261732064656c617965642062792073657373696f6e206f74686572776973652e20492e652e2061637469766520657261206d757374390120616c7761797320626520696e20686973746f72792e20492e652e20606163746976655f657261203e2063757272656e745f657261202d20686973746f72795f646570746860206d757374206265302067756172616e746565642e3856616c696461746f72436f756e7401000c753332100000000004a82054686520696465616c206e756d626572206f66207374616b696e67207061727469636970616e74732e544d696e696d756d56616c696461746f72436f756e7401000c7533321000000000044101204d696e696d756d206e756d626572206f66207374616b696e67207061727469636970616e7473206265666f726520656d657267656e637920636f6e646974696f6e732061726520696d706f7365642e34496e76756c6e657261626c65730100445665633c543a3a4163636f756e7449643e04000c590120416e792076616c696461746f72732074686174206d6179206e6576657220626520736c6173686564206f7220666f726369626c79206b69636b65642e20497427732061205665632073696e636520746865792772654d01206561737920746f20696e697469616c697a6520616e642074686520706572666f726d616e636520686974206973206d696e696d616c2028776520657870656374206e6f206d6f7265207468616e20666f7572ac20696e76756c6e657261626c65732920616e64207265737472696374656420746f20746573746e6574732e18426f6e64656400010530543a3a4163636f756e74496430543a3a4163636f756e744964000400040101204d61702066726f6d20616c6c206c6f636b65642022737461736822206163636f756e747320746f2074686520636f6e74726f6c6c6572206163636f756e742e184c656467657200010230543a3a4163636f756e744964a45374616b696e674c65646765723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400044501204d61702066726f6d20616c6c2028756e6c6f636b6564292022636f6e74726f6c6c657222206163636f756e747320746f2074686520696e666f20726567617264696e6720746865207374616b696e672e14506179656501010530543a3a4163636f756e7449647c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e00040004e42057686572652074686520726577617264207061796d656e742073686f756c64206265206d6164652e204b657965642062792073746173682e2856616c696461746f727301010530543a3a4163636f756e7449643856616c696461746f72507265667300040004450120546865206d61702066726f6d202877616e6e616265292076616c696461746f72207374617368206b657920746f2074686520707265666572656e636573206f6620746861742076616c696461746f722e284e6f6d696e61746f727300010530543a3a4163636f756e744964644e6f6d696e6174696f6e733c543a3a4163636f756e7449643e00040004650120546865206d61702066726f6d206e6f6d696e61746f72207374617368206b657920746f2074686520736574206f66207374617368206b657973206f6620616c6c2076616c696461746f727320746f206e6f6d696e6174652e2843757272656e74457261000020457261496e6465780400105c205468652063757272656e742065726120696e6465782e006501205468697320697320746865206c617465737420706c616e6e6564206572612c20646570656e64696e67206f6e20686f77207468652053657373696f6e2070616c6c657420717565756573207468652076616c696461746f7280207365742c206974206d6967687420626520616374697665206f72206e6f742e24416374697665457261000034416374697665457261496e666f040010d820546865206163746976652065726120696e666f726d6174696f6e2c20697420686f6c647320696e64657820616e642073746172742e00b820546865206163746976652065726120697320746865206572612063757272656e746c792072657761726465642e2d012056616c696461746f7220736574206f66207468697320657261206d75737420626520657175616c20746f206053657373696f6e496e746572666163653a3a76616c696461746f7273602e5445726173537461727453657373696f6e496e64657800010520457261496e6465783053657373696f6e496e646578000400043101205468652073657373696f6e20696e646578206174207768696368207468652065726120737461727420666f7220746865206c6173742060484953544f52595f44455054486020657261732e2c457261735374616b65727301020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000001878204578706f73757265206f662076616c696461746f72206174206572612e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e48457261735374616b657273436c697070656401020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000002c9820436c6970706564204578706f73757265206f662076616c696461746f72206174206572612e00590120546869732069732073696d696c617220746f205b60457261735374616b657273605d20627574206e756d626572206f66206e6f6d696e61746f7273206578706f736564206973207265647563656420746f20746865dc2060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732e1d0120284e6f74653a20746865206669656c642060746f74616c6020616e6420606f776e60206f6620746865206578706f737572652072656d61696e7320756e6368616e676564292ef42054686973206973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e005d012054686973206973206b657965642066697374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e484572617356616c696461746f72507265667301020520457261496e64657830543a3a4163636f756e7449643856616c696461746f7250726566730504001411012053696d696c617220746f2060457261735374616b657273602c207468697320686f6c64732074686520707265666572656e636573206f662076616c696461746f72732e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4c4572617356616c696461746f7252657761726400010520457261496e6465783042616c616e63654f663c543e0004000c09012054686520746f74616c2076616c696461746f7220657261207061796f757420666f7220746865206c6173742060484953544f52595f44455054486020657261732e0021012045726173207468617420686176656e27742066696e697368656420796574206f7220686173206265656e2072656d6f76656420646f65736e27742068617665207265776172642e4045726173526577617264506f696e747301010520457261496e64657874457261526577617264506f696e74733c543a3a4163636f756e7449643e0014000000000008ac205265776172647320666f7220746865206c6173742060484953544f52595f44455054486020657261732e250120496620726577617264206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207265776172642069732072657475726e65642e3845726173546f74616c5374616b6501010520457261496e6465783042616c616e63654f663c543e00400000000000000000000000000000000008ec2054686520746f74616c20616d6f756e74207374616b656420666f7220746865206c6173742060484953544f52595f44455054486020657261732e1d0120496620746f74616c206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207374616b652069732072657475726e65642e20466f72636545726101001c466f7263696e6704000454204d6f6465206f662065726120666f7263696e672e4c536c6173685265776172644672616374696f6e01001c50657262696c6c10000000000cf8205468652070657263656e74616765206f662074686520736c617368207468617420697320646973747269627574656420746f207265706f72746572732e00e4205468652072657374206f662074686520736c61736865642076616c75652069732068616e646c6564206279207468652060536c617368602e4c43616e63656c6564536c6173685061796f757401003042616c616e63654f663c543e40000000000000000000000000000000000815012054686520616d6f756e74206f662063757272656e637920676976656e20746f207265706f7274657273206f66206120736c617368206576656e7420776869636820776173ec2063616e63656c65642062792065787472616f7264696e6172792063697263756d7374616e6365732028652e672e20676f7665726e616e6365292e40556e6170706c696564536c617368657301010520457261496e646578bc5665633c556e6170706c696564536c6173683c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e00040004c420416c6c20756e6170706c69656420736c61736865732074686174206172652071756575656420666f72206c617465722e28426f6e646564457261730100745665633c28457261496e6465782c2053657373696f6e496e646578293e04001025012041206d617070696e672066726f6d207374696c6c2d626f6e646564206572617320746f207468652066697273742073657373696f6e20696e646578206f662074686174206572612e00c8204d75737420636f6e7461696e7320696e666f726d6174696f6e20666f72206572617320666f72207468652072616e67653abc20605b6163746976655f657261202d20626f756e64696e675f6475726174696f6e3b206163746976655f6572615d604c56616c696461746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449645c2850657262696c6c2c2042616c616e63654f663c543e2905040008450120416c6c20736c617368696e67206576656e7473206f6e2076616c696461746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682070726f706f7274696f6e7020616e6420736c6173682076616c7565206f6620746865206572612e4c4e6f6d696e61746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449643042616c616e63654f663c543e05040004610120416c6c20736c617368696e67206576656e7473206f6e206e6f6d696e61746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682076616c7565206f6620746865206572612e34536c617368696e675370616e7300010530543a3a4163636f756e7449645c736c617368696e673a3a536c617368696e675370616e73000400048c20536c617368696e67207370616e7320666f72207374617368206163636f756e74732e245370616e536c6173680101058c28543a3a4163636f756e7449642c20736c617368696e673a3a5370616e496e6465782988736c617368696e673a3a5370616e5265636f72643c42616c616e63654f663c543e3e00800000000000000000000000000000000000000000000000000000000000000000083d01205265636f72647320696e666f726d6174696f6e2061626f757420746865206d6178696d756d20736c617368206f6620612073746173682077697468696e206120736c617368696e67207370616e2cb82061732077656c6c20617320686f77206d7563682072657761726420686173206265656e2070616964206f75742e584561726c69657374556e6170706c696564536c617368000020457261496e646578040004fc20546865206561726c696573742065726120666f72207768696368207765206861766520612070656e64696e672c20756e6170706c69656420736c6173682e48536e617073686f7456616c696461746f72730000445665633c543a3a4163636f756e7449643e040008650120536e617073686f74206f662076616c696461746f72732061742074686520626567696e6e696e67206f66207468652063757272656e7420656c656374696f6e2077696e646f772e20546869732073686f756c64206f6e6c791901206861766520612076616c7565207768656e205b60457261456c656374696f6e537461747573605d203d3d2060456c656374696f6e5374617475733a3a4f70656e285f29602e48536e617073686f744e6f6d696e61746f72730000445665633c543a3a4163636f756e7449643e040008650120536e617073686f74206f66206e6f6d696e61746f72732061742074686520626567696e6e696e67206f66207468652063757272656e7420656c656374696f6e2077696e646f772e20546869732073686f756c64206f6e6c791901206861766520612076616c7565207768656e205b60457261456c656374696f6e537461747573605d203d3d2060456c656374696f6e5374617475733a3a4f70656e285f29602e34517565756564456c65637465640000a8456c656374696f6e526573756c743c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e04000c650120546865206e6578742076616c696461746f72207365742e2041742074686520656e64206f6620616e206572612c206966207468697320697320617661696c61626c652028706f74656e7469616c6c792066726f6d20746865610120726573756c74206f6620616e206f6666636861696e20776f726b6572292c20697420697320696d6d6564696174656c7920757365642e204f74686572776973652c20746865206f6e2d636861696e20656c656374696f6e342069732065786563757465642e2c51756575656453636f7265000034456c656374696f6e53636f7265040004b0205468652073636f7265206f66207468652063757272656e74205b60517565756564456c6563746564605d2e44457261456c656374696f6e537461747573010078456c656374696f6e5374617475733c543a3a426c6f636b4e756d6265723e040008490120466c616720746f20636f6e74726f6c2074686520657865637574696f6e206f6620746865206f6666636861696e20656c656374696f6e2e205768656e20604f70656e285f29602c207765206163636570746c20736f6c7574696f6e7320746f206265207375626d69747465642e54497343757272656e7453657373696f6e46696e616c010010626f6f6c0400084d012054727565206966207468652063757272656e74202a2a706c616e6e65642a2a2073657373696f6e2069732066696e616c2e204e6f74652074686174207468697320646f6573206e6f742074616b65206572615820666f7263696e6720696e746f206163636f756e742e3853746f7261676556657273696f6e01002052656c6561736573040310cc2054727565206966206e6574776f726b20686173206265656e20757067726164656420746f20746869732076657273696f6e2e7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076332e302e3020666f72206e6577206e6574776f726b732e016010626f6e640c28636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e1470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e5865012054616b6520746865206f726967696e206163636f756e74206173206120737461736820616e64206c6f636b207570206076616c756560206f66206974732062616c616e63652e2060636f6e74726f6c6c6572602077696c6c8420626520746865206163636f756e74207468617420636f6e74726f6c732069742e003101206076616c756560206d757374206265206d6f7265207468616e2074686520606d696e696d756d5f62616c616e636560207370656369666965642062792060543a3a43757272656e6379602e00250120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20627920746865207374617368206163636f756e742e004020456d6974732060426f6e646564602e002c2023203c7765696768743ed4202d20496e646570656e64656e74206f662074686520617267756d656e74732e204d6f64657261746520636f6d706c65786974792e20202d204f2831292e68202d20546872656520657874726120444220656e74726965732e005101204e4f54453a2054776f206f66207468652073746f726167652077726974657320286053656c663a3a626f6e646564602c206053656c663a3a7061796565602920617265205f6e657665725f20636c65616e6564410120756e6c6573732074686520606f726967696e602066616c6c732062656c6f77205f6578697374656e7469616c206465706f7369745f20616e6420676574732072656d6f76656420617320647573742e4c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a2036372e383720c2b5732c204442205765696768743a3101202d20526561643a20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c2043757272656e74204572612c20486973746f72792044657074682c204c6f636b73e0202d2057726974653a20426f6e6465642c2050617965652c205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e28626f6e645f657874726104386d61785f6164646974696f6e616c54436f6d706163743c42616c616e63654f663c543e3e5865012041646420736f6d6520657874726120616d6f756e742074686174206861766520617070656172656420696e207468652073746173682060667265655f62616c616e63656020696e746f207468652062616c616e63652075703420666f72207374616b696e672e00510120557365207468697320696620746865726520617265206164646974696f6e616c2066756e647320696e20796f7572207374617368206163636f756e74207468617420796f75207769736820746f20626f6e642e650120556e6c696b65205b60626f6e64605d206f72205b60756e626f6e64605d20746869732066756e6374696f6e20646f6573206e6f7420696d706f736520616e79206c696d69746174696f6e206f6e2074686520616d6f756e744c20746861742063616e2062652061646465642e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c657220616e64f82069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004020456d6974732060426f6e646564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e20202d204f2831292e40202d204f6e6520444220656e7472792e34202d2d2d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a2035342e383820c2b5732c204442205765696768743a1501202d20526561643a2045726120456c656374696f6e205374617475732c20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c204c6f636b73a4202d2057726974653a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e18756e626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e805501205363686564756c65206120706f7274696f6e206f662074686520737461736820746f20626520756e6c6f636b656420726561647920666f72207472616e73666572206f75742061667465722074686520626f6e64010120706572696f6420656e64732e2049662074686973206c656176657320616e20616d6f756e74206163746976656c7920626f6e646564206c657373207468616e250120543a3a43757272656e63793a3a6d696e696d756d5f62616c616e636528292c207468656e20697420697320696e6372656173656420746f207468652066756c6c20616d6f756e742e004901204f6e63652074686520756e6c6f636b20706572696f6420697320646f6e652c20796f752063616e2063616c6c206077697468647261775f756e626f6e6465646020746f2061637475616c6c79206d6f7665c0207468652066756e6473206f7574206f66206d616e6167656d656e7420726561647920666f72207472616e736665722e003d01204e6f206d6f7265207468616e2061206c696d69746564206e756d626572206f6620756e6c6f636b696e67206368756e6b73202873656520604d41585f554e4c4f434b494e475f4348554e4b5360293d012063616e20636f2d657869737473206174207468652073616d652074696d652e20496e207468617420636173652c205b6043616c6c3a3a77697468647261775f756e626f6e646564605d206e656564fc20746f2062652063616c6c656420666972737420746f2072656d6f766520736f6d65206f6620746865206368756e6b732028696620706f737369626c65292e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004820456d6974732060556e626f6e646564602e00982053656520616c736f205b6043616c6c3a3a77697468647261775f756e626f6e646564605d2e002c2023203c7765696768743e4101202d20496e646570656e64656e74206f662074686520617267756d656e74732e204c696d697465642062757420706f74656e7469616c6c79206578706c6f697461626c6520636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732e6501202d20456163682063616c6c20287265717569726573207468652072656d61696e646572206f662074686520626f6e6465642062616c616e636520746f2062652061626f766520606d696e696d756d5f62616c616e63656029710120202077696c6c2063617573652061206e657720656e74727920746f20626520696e73657274656420696e746f206120766563746f722028604c65646765722e756e6c6f636b696e676029206b65707420696e2073746f726167652e5101202020546865206f6e6c792077617920746f20636c65616e207468652061666f72656d656e74696f6e65642073746f72616765206974656d20697320616c736f20757365722d636f6e74726f6c6c6564207669615c2020206077697468647261775f756e626f6e646564602e40202d204f6e6520444220656e7472792e2c202d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a2035302e333420c2b5732c204442205765696768743a2901202d20526561643a2045726120456c656374696f6e205374617475732c204c65646765722c2043757272656e74204572612c204c6f636b732c205b4f726967696e204163636f756e745da4202d2057726974653a205b4f726967696e204163636f756e745d2c204c6f636b732c204c656467657228203c2f7765696768743e4477697468647261775f756e626f6e64656404486e756d5f736c617368696e675f7370616e730c753332782d012052656d6f766520616e7920756e6c6f636b6564206368756e6b732066726f6d207468652060756e6c6f636b696e67602071756575652066726f6d206f7572206d616e6167656d656e742e003501205468697320657373656e7469616c6c7920667265657320757020746861742062616c616e636520746f206265207573656420627920746865207374617368206163636f756e7420746f20646f4c2077686174657665722069742077616e74732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004c20456d697473206057697468647261776e602e006c2053656520616c736f205b6043616c6c3a3a756e626f6e64605d2e002c2023203c7765696768743e5501202d20436f756c6420626520646570656e64656e74206f6e2074686520606f726967696e6020617267756d656e7420616e6420686f77206d7563682060756e6c6f636b696e6760206368756e6b732065786973742e45012020497420696d706c6965732060636f6e736f6c69646174655f756e6c6f636b656460207768696368206c6f6f7073206f76657220604c65646765722e756e6c6f636b696e67602c207768696368206973f42020696e6469726563746c7920757365722d636f6e74726f6c6c65642e20536565205b60756e626f6e64605d20666f72206d6f72652064657461696c2e7901202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732c20796574207468652073697a65206f6620776869636820636f756c64206265206c61726765206261736564206f6e20606c6564676572602ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d090120436f6d706c6578697479204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2072656d6f7665342042617365205765696768743a74205570646174653a2035302e3532202b202e303238202a205320c2b5732501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c204c6f636b732c205b4f726967696e204163636f756e745da8202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c656467657270204b696c6c3a2037392e3431202b20322e333636202a205320c2b5738501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c20426f6e6465642c20536c617368696e67205370616e732c205b4f726967696e204163636f756e745d2c204c6f636b73b101202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c205b4f726967696e204163636f756e745d2c204c6f636b7374202d2057726974657320456163683a205370616e536c617368202a20530d01204e4f54453a2057656967687420616e6e6f746174696f6e20697320746865206b696c6c207363656e6172696f2c20776520726566756e64206f74686572776973652e302023203c2f7765696768743e2076616c6964617465041470726566733856616c696461746f72507265667344e8204465636c617265207468652064657369726520746f2076616c696461746520666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e30202d2d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a2031372e313320c2b5732c204442205765696768743a90202d20526561643a2045726120456c656374696f6e205374617475732c204c656467657280202d2057726974653a204e6f6d696e61746f72732c2056616c696461746f7273302023203c2f7765696768743e206e6f6d696e617465041c74617267657473a05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e4c1101204465636c617265207468652064657369726520746f206e6f6d696e6174652060746172676574736020666f7220746865206f726967696e20636f6e74726f6c6c65722e00510120456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e20546869732063616e206f6e6c792062652063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e3101202d20546865207472616e73616374696f6e277320636f6d706c65786974792069732070726f706f7274696f6e616c20746f207468652073697a65206f662060746172676574736020284e2901012077686963682069732063617070656420617420436f6d7061637441737369676e6d656e74733a3a4c494d495420284d41585f4e4f4d494e4154494f4e53292ed8202d20426f74682074686520726561647320616e642077726974657320666f6c6c6f7720612073696d696c6172207061747465726e2e28202d2d2d2d2d2d2d2d2d842042617365205765696768743a2032322e3334202b202e3336202a204e20c2b57384207768657265204e20697320746865206e756d626572206f6620746172676574732c204442205765696768743ac8202d2052656164733a2045726120456c656374696f6e205374617475732c204c65646765722c2043757272656e742045726184202d205772697465733a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e146368696c6c0044c8204465636c617265206e6f2064657369726520746f206569746865722076616c6964617465206f72206e6f6d696e6174652e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e54202d20436f6e7461696e73206f6e6520726561642ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e24202d2d2d2d2d2d2d2d5c2042617365205765696768743a2031362e353320c2b5732c204442205765696768743a88202d20526561643a20457261456c656374696f6e5374617475732c204c656467657280202d2057726974653a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e247365745f7061796565041470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e40b8202852652d2973657420746865207061796d656e742074617267657420666f72206120636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e28202d2d2d2d2d2d2d2d2d64202d2042617365205765696768743a2031312e333320c2b57334202d204442205765696768743a4c20202020202d20526561643a204c65646765724c20202020202d2057726974653a205061796565302023203c2f7765696768743e387365745f636f6e74726f6c6c65720428636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654090202852652d297365742074686520636f6e74726f6c6c6572206f6620612073746173682e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e2c202d2d2d2d2d2d2d2d2d2d5c2042617365205765696768743a2032352e323220c2b5732c204442205765696768743af4202d20526561643a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572f8202d2057726974653a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572302023203c2f7765696768743e4c7365745f76616c696461746f725f636f756e74040c6e657730436f6d706163743c7533323e209420536574732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e5c2042617365205765696768743a20312e37313720c2b5735c2057726974653a2056616c696461746f7220436f756e74302023203c2f7765696768743e60696e6372656173655f76616c696461746f725f636f756e7404286164646974696f6e616c30436f6d706163743c7533323e20ac20496e6372656d656e74732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e5c2042617365205765696768743a20312e37313720c2b5737020526561642f57726974653a2056616c696461746f7220436f756e74302023203c2f7765696768743e547363616c655f76616c696461746f725f636f756e740418666163746f721c50657263656e7420d4205363616c652075702074686520696465616c206e756d626572206f662076616c696461746f7273206279206120666163746f722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e5c2042617365205765696768743a20312e37313720c2b5737020526561642f57726974653a2056616c696461746f7220436f756e74302023203c2f7765696768743e34666f7263655f6e6f5f657261730024b020466f72636520746865726520746f206265206e6f206e6577206572617320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e64202d2042617365205765696768743a20312e38353720c2b57348202d2057726974653a20466f726365457261302023203c2f7765696768743e34666f7263655f6e65775f65726100284d0120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f6620746865206e6578742073657373696f6e2e20416674657220746869732c2069742077696c6c206265a020726573657420746f206e6f726d616c20286e6f6e2d666f7263656429206265686176696f75722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e64202d2042617365205765696768743a20312e39353920c2b57344202d20577269746520466f726365457261302023203c2f7765696768743e447365745f696e76756c6e657261626c6573042876616c696461746f7273445665633c543a3a4163636f756e7449643e24cc20536574207468652076616c696461746f72732077686f2063616e6e6f7420626520736c61736865642028696620616e79292e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e1c202d204f28562990202d2042617365205765696768743a20322e323038202b202e303036202a205620c2b5735c202d2057726974653a20496e76756c6e657261626c6573302023203c2f7765696768743e34666f7263655f756e7374616b650814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c7533322c0d0120466f72636520612063757272656e74207374616b657220746f206265636f6d6520636f6d706c6574656c7920756e7374616b65642c20696d6d6564696174656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743eec204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2062652072656d6f7665648c2042617365205765696768743a2035332e3037202b20322e333635202a205320c2b573b82052656164733a20426f6e6465642c20536c617368696e67205370616e732c204163636f756e742c204c6f636b738501205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c204163636f756e742c204c6f636b736c2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e50666f7263655f6e65775f6572615f616c776179730020050120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f662073657373696f6e7320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e60202d2042617365205765696768743a20322e303520c2b57348202d2057726974653a20466f726365457261302023203c2f7765696768743e5463616e63656c5f64656665727265645f736c617368080c65726120457261496e64657834736c6173685f696e6469636573205665633c7533323e38982043616e63656c20656e6163746d656e74206f66206120646566657272656420736c6173682e00b42043616e2062652063616c6c6564206279207468652060543a3a536c61736843616e63656c4f726967696e602e00050120506172616d65746572733a2065726120616e6420696e6469636573206f662074686520736c617368657320666f7220746861742065726120746f206b696c6c2e002c2023203c7765696768743e5420436f6d706c65786974793a204f2855202b205329b82077697468205520756e6170706c69656420736c6173686573207765696768746564207769746820553d31303030d420616e64205320697320746865206e756d626572206f6620736c61736820696e646963657320746f2062652063616e63656c65642e74202d20426173653a2035383730202b2033342e3631202a205320c2b57368202d20526561643a20556e6170706c69656420536c61736865736c202d2057726974653a20556e6170706c69656420536c6173686573302023203c2f7765696768743e387061796f75745f7374616b657273083c76616c696461746f725f737461736830543a3a4163636f756e7449640c65726120457261496e64657864110120506179206f757420616c6c20746865207374616b65727320626568696e6420612073696e676c652076616c696461746f7220666f7220612073696e676c65206572612e004d01202d206076616c696461746f725f73746173686020697320746865207374617368206163636f756e74206f66207468652076616c696461746f722e205468656972206e6f6d696e61746f72732c20757020746f290120202060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602c2077696c6c20616c736f207265636569766520746865697220726577617264732e3501202d206065726160206d617920626520616e7920657261206265747765656e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e00590120546865206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e20416e79206163636f756e742063616e2063616c6c20746869732066756e6374696f6e2c206576656e20696678206974206973206e6f74206f6e65206f6620746865207374616b6572732e00010120546869732063616e206f6e6c792062652063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e0101202d2054696d6520636f6d706c65786974793a206174206d6f7374204f284d61784e6f6d696e61746f72526577617264656450657256616c696461746f72292ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e30202d2d2d2d2d2d2d2d2d2d2d1d01204e20697320746865204e756d626572206f66207061796f75747320666f72207468652076616c696461746f722028696e636c7564696e67207468652076616c696461746f7229342042617365205765696768743a0101202d205265776172642044657374696e6174696f6e205374616b65643a20313130202b2035342e32202a204e20c2b57320284d656469616e20536c6f706573294101202d205265776172642044657374696e6174696f6e20436f6e74726f6c6c657220284372656174696e67293a20313230202b2034312e3935202a204e20c2b57320284d656469616e20536c6f706573292c204442205765696768743a2901202d20526561643a20457261456c656374696f6e5374617475732c2043757272656e744572612c20486973746f727944657074682c204572617356616c696461746f725265776172642c2d01202020202020202020457261735374616b657273436c69707065642c2045726173526577617264506f696e74732c204572617356616c696461746f725072656673202838206974656d73291101202d205265616420456163683a20426f6e6465642c204c65646765722c2050617965652c204c6f636b732c2053797374656d204163636f756e74202835206974656d7329d8202d20577269746520456163683a2053797374656d204163636f756e742c204c6f636b732c204c6564676572202833206974656d7329302023203c2f7765696768743e187265626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e3ce0205265626f6e64206120706f7274696f6e206f6620746865207374617368207363686564756c656420746f20626520756e6c6f636b65642e00550120546865206469737061746368206f726967696e206d757374206265207369676e65642062792074686520636f6e74726f6c6c65722c20616e642069742063616e206265206f6e6c792063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ed4202d2054696d6520636f6d706c65786974793a204f284c292c207768657265204c20697320756e6c6f636b696e67206368756e6b7394202d20426f756e64656420627920604d41585f554e4c4f434b494e475f4348554e4b53602ef4202d2053746f72616765206368616e6765733a2043616e277420696e6372656173652073746f726167652c206f6e6c792064656372656173652069742e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d98202d2042617365205765696768743a2033342e353120c2b573202a202e303438204c20c2b57334202d204442205765696768743a010120202020202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c204c6f636b732c205b4f726967696e204163636f756e745db820202020202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e447365745f686973746f72795f646570746808446e65775f686973746f72795f646570746844436f6d706163743c457261496e6465783e485f6572615f6974656d735f64656c6574656430436f6d706163743c7533323e543101205365742060486973746f72794465707468602076616c75652e20546869732066756e6374696f6e2077696c6c2064656c65746520616e7920686973746f727920696e666f726d6174696f6e80207768656e2060486973746f727944657074686020697320726564756365642e003020506172616d65746572733a1101202d20606e65775f686973746f72795f6465707468603a20546865206e657720686973746f727920646570746820796f7520776f756c64206c696b6520746f207365742e4901202d20606572615f6974656d735f64656c65746564603a20546865206e756d626572206f66206974656d7320746861742077696c6c2062652064656c6574656420627920746869732064697370617463682e450120202020546869732073686f756c64207265706f727420616c6c207468652073746f72616765206974656d7320746861742077696c6c2062652064656c6574656420627920636c656172696e67206f6c6445012020202065726120686973746f72792e204e656564656420746f207265706f727420616e2061636375726174652077656967687420666f72207468652064697370617463682e2054727573746564206279a02020202060526f6f746020746f207265706f727420616e206163637572617465206e756d6265722e0054204f726967696e206d75737420626520726f6f742e002c2023203c7765696768743ee0202d20453a204e756d626572206f6620686973746f7279206465707468732072656d6f7665642c20692e652e203130202d3e2037203d203374202d2042617365205765696768743a2032392e3133202a204520c2b57334202d204442205765696768743aa020202020202d2052656164733a2043757272656e74204572612c20486973746f72792044657074687020202020202d205772697465733a20486973746f7279204465707468310120202020202d20436c6561722050726566697820456163683a20457261205374616b6572732c204572615374616b657273436c69707065642c204572617356616c696461746f725072656673810120202020202d2057726974657320456163683a204572617356616c696461746f725265776172642c2045726173526577617264506f696e74732c2045726173546f74616c5374616b652c2045726173537461727453657373696f6e496e646578302023203c2f7765696768743e28726561705f73746173680814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c7533324039012052656d6f766520616c6c20646174612073747275637475726520636f6e6365726e696e672061207374616b65722f7374617368206f6e6365206974732062616c616e6365206973207a65726f2e6101205468697320697320657373656e7469616c6c79206571756976616c656e7420746f206077697468647261775f756e626f6e64656460206578636570742069742063616e2062652063616c6c656420627920616e796f6e65c020616e6420746865207461726765742060737461736860206d7573742068617665206e6f2066756e6473206c6566742e009020546869732063616e2062652063616c6c65642066726f6d20616e79206f726967696e2e000101202d20607374617368603a20546865207374617368206163636f756e7420746f20726561702e204974732062616c616e6365206d757374206265207a65726f2e002c2023203c7765696768743e250120436f6d706c65786974793a204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e73206f6e20746865206163636f756e742e8c2042617365205765696768743a2037352e3934202b20322e333936202a205320c2b5732c204442205765696768743ad8202d2052656164733a205374617368204163636f756e742c20426f6e6465642c20536c617368696e67205370616e732c204c6f636b73a501202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c205374617368204163636f756e742c204c6f636b7374202d2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e607375626d69745f656c656374696f6e5f736f6c7574696f6e141c77696e6e6572734c5665633c56616c696461746f72496e6465783e1c636f6d7061637448436f6d7061637441737369676e6d656e74731473636f726534456c656374696f6e53636f72650c65726120457261496e6465781073697a6530456c656374696f6e53697a65bce4205375626d697420616e20656c656374696f6e20726573756c7420746f2074686520636861696e2e2049662074686520736f6c7574696f6e3a003420312e2069732076616c69642e150120322e206861732061206265747465722073636f7265207468616e206120706f74656e7469616c6c79206578697374696e6720736f6c7574696f6e206f6e20636861696e2e0084207468656e2c2069742077696c6c206265205f7075745f206f6e20636861696e2e00ac204120736f6c7574696f6e20636f6e7369737473206f662074776f20706965636573206f6620646174613a00f420312e206077696e6e657273603a206120666c617420766563746f72206f6620616c6c207468652077696e6e657273206f662074686520726f756e642e510120322e206061737369676e6d656e7473603a2074686520636f6d706163742076657273696f6e206f6620616e2061737369676e6d656e7420766563746f72207468617420656e636f6465732074686520656467653020202020776569676874732e00210120426f7468206f66207768696368206d617920626520636f6d7075746564207573696e67205f70687261676d656e5f2c206f7220616e79206f7468657220616c676f726974686d2e00a8204164646974696f6e616c6c792c20746865207375626d6974746572206d7573742070726f766964653a00c8202d20546865206073636f7265602074686174207468657920636c61696d20746865697220736f6c7574696f6e206861732e004d0120426f74682076616c696461746f727320616e64206e6f6d696e61746f72732077696c6c20626520726570726573656e74656420627920696e646963657320696e2074686520736f6c7574696f6e2e205468651d0120696e64696365732073686f756c6420726573706563742074686520636f72726573706f6e64696e6720747970657320285b6056616c696461746f72496e646578605d20616e643101205b604e6f6d696e61746f72496e646578605d292e204d6f72656f7665722c20746865792073686f756c642062652076616c6964207768656e207573656420746f20696e64657820696e746f5101205b60536e617073686f7456616c696461746f7273605d20616e64205b60536e617073686f744e6f6d696e61746f7273605d2e20416e7920696e76616c696420696e6465782077696c6c20636175736520746865610120736f6c7574696f6e20746f2062652072656a65637465642e2054686573652074776f2073746f72616765206974656d73206172652073657420647572696e672074686520656c656374696f6e2077696e646f7720616e6498206d6179206265207573656420746f2064657465726d696e652074686520696e64696365732e0060204120736f6c7574696f6e2069732076616c69642069663a00e420302e204974206973207375626d6974746564207768656e205b60457261456c656374696f6e537461747573605d20697320604f70656e602ef820312e2049747320636c61696d65642073636f726520697320657175616c20746f207468652073636f726520636f6d7075746564206f6e2d636861696e2eac20322e2050726573656e74732074686520636f7272656374206e756d626572206f662077696e6e6572732e550120332e20416c6c20696e6465786573206d7573742062652076616c7565206163636f7264696e6720746f2074686520736e617073686f7420766563746f72732e20416c6c20656467652076616c756573206d7573745d0120202020616c736f20626520636f727265637420616e642073686f756c64206e6f74206f766572666c6f7720746865206772616e756c6172697479206f662074686520726174696f20747970652028692e652e2032353640202020206f722062696c6c696f6e292e0d0120342e20466f72206561636820656467652c20616c6c2074617267657473206172652061637475616c6c79206e6f6d696e617465642062792074686520766f7465722e6c20352e2048617320636f72726563742073656c662d766f7465732e00c0204120736f6c7574696f6e732073636f726520697320636f6e736973746564206f66203320706172616d65746572733a00650120312e20606d696e207b20737570706f72742e746f74616c207d6020666f72206561636820737570706f7274206f6620612077696e6e65722e20546869732076616c75652073686f756c64206265206d6178696d697a65642e650120322e206073756d207b20737570706f72742e746f74616c207d6020666f72206561636820737570706f7274206f6620612077696e6e65722e20546869732076616c75652073686f756c64206265206d696e696d697a65642e410120332e206073756d207b20737570706f72742e746f74616c5e32207d6020666f72206561636820737570706f7274206f6620612077696e6e65722e20546869732076616c75652073686f756c642062659c202020206d696e696d697a65642028746f20656e73757265206c6573732076617269616e636529002c2023203c7765696768743e7020536565206063726174653a3a77656967687460206d6f64756c652e302023203c2f7765696768743e847375626d69745f656c656374696f6e5f736f6c7574696f6e5f756e7369676e6564141c77696e6e6572734c5665633c56616c696461746f72496e6465783e1c636f6d7061637448436f6d7061637441737369676e6d656e74731473636f726534456c656374696f6e53636f72650c65726120457261496e6465781073697a6530456c656374696f6e53697a6524c020556e7369676e65642076657273696f6e206f6620607375626d69745f656c656374696f6e5f736f6c7574696f6e602e005d01204e6f746520746861742074686973206d757374207061737320746865205b6056616c6964617465556e7369676e6564605d20636865636b207768696368206f6e6c7920616c6c6f7773207472616e73616374696f6e7361012066726f6d20746865206c6f63616c206e6f646520746f20626520696e636c756465642e20496e206f7468657220776f7264732c206f6e6c792074686520626c6f636b20617574686f722063616e20696e636c756465206168207472616e73616374696f6e20696e2074686520626c6f636b2e002c2023203c7765696768743e7020536565206063726174653a3a77656967687460206d6f64756c652e302023203c2f7765696768743e0124244572615061796f75740c20457261496e6465781c42616c616e63651c42616c616e63650c59012054686520657261207061796f757420686173206265656e207365743b207468652066697273742062616c616e6365206973207468652076616c696461746f722d7061796f75743b20746865207365636f6e64206973c4207468652072656d61696e6465722066726f6d20746865206d6178696d756d20616d6f756e74206f66207265776172642ea4205b6572615f696e6465782c2076616c696461746f725f7061796f75742c2072656d61696e6465725d1852657761726408244163636f756e7449641c42616c616e636504f420546865207374616b657220686173206265656e207265776172646564206279207468697320616d6f756e742e205b73746173682c20616d6f756e745d14536c61736808244163636f756e7449641c42616c616e6365082501204f6e652076616c696461746f722028616e6420697473206e6f6d696e61746f72732920686173206265656e20736c61736865642062792074686520676976656e20616d6f756e742e50205b76616c696461746f722c20616d6f756e745d684f6c64536c617368696e675265706f7274446973636172646564043053657373696f6e496e646578081d0120416e206f6c6420736c617368696e67207265706f72742066726f6d2061207072696f72206572612077617320646973636172646564206265636175736520697420636f756c6488206e6f742062652070726f6365737365642e205b73657373696f6e5f696e6465785d3c5374616b696e67456c656374696f6e043c456c656374696f6e436f6d7075746504ec2041206e657720736574206f66207374616b6572732077617320656c656374656420776974682074686520676976656e205b636f6d707574655d2e38536f6c7574696f6e53746f726564043c456c656374696f6e436f6d707574650411012041206e657720736f6c7574696f6e20666f7220746865207570636f6d696e6720656c656374696f6e20686173206265656e2073746f7265642e205b636f6d707574655d18426f6e64656408244163636f756e7449641c42616c616e636510cc20416e206163636f756e742068617320626f6e646564207468697320616d6f756e742e205b73746173682c20616d6f756e745d005101204e4f54453a2054686973206576656e74206973206f6e6c7920656d6974746564207768656e2066756e64732061726520626f6e64656420766961206120646973706174636861626c652e204e6f7461626c792c25012069742077696c6c206e6f7420626520656d697474656420666f72207374616b696e672072657761726473207768656e20746865792061726520616464656420746f207374616b652e20556e626f6e64656408244163636f756e7449641c42616c616e636504d420416e206163636f756e742068617320756e626f6e646564207468697320616d6f756e742e205b73746173682c20616d6f756e745d2457697468647261776e08244163636f756e7449641c42616c616e6365085d0120416e206163636f756e74206861732063616c6c6564206077697468647261775f756e626f6e6465646020616e642072656d6f76656420756e626f6e64696e67206368756e6b7320776f727468206042616c616e636560a82066726f6d2074686520756e6c6f636b696e672071756575652e205b73746173682c20616d6f756e745d1c3853657373696f6e735065724572613053657373696f6e496e64657810060000000470204e756d626572206f662073657373696f6e7320706572206572612e3c426f6e64696e674475726174696f6e20457261496e64657810a002000004e4204e756d626572206f6620657261732074686174207374616b65642066756e6473206d7573742072656d61696e20626f6e64656420666f722e48536c61736844656665724475726174696f6e20457261496e64657810a8000000140101204e756d626572206f662065726173207468617420736c6173686573206172652064656665727265642062792c20616674657220636f6d7075746174696f6e2e00bc20546869732073686f756c64206265206c657373207468616e2074686520626f6e64696e67206475726174696f6e2e2d012053657420746f203020696620736c61736865732073686f756c64206265206170706c69656420696d6d6564696174656c792c20776974686f7574206f70706f7274756e69747920666f723820696e74657276656e74696f6e2e44456c656374696f6e4c6f6f6b616865616438543a3a426c6f636b4e756d62657210320000001c710120546865206e756d626572206f6620626c6f636b73206265666f72652074686520656e64206f6620746865206572612066726f6d20776869636820656c656374696f6e207375626d697373696f6e732061726520616c6c6f7765642e006d012053657474696e67207468697320746f207a65726f2077696c6c2064697361626c6520746865206f6666636861696e20636f6d7075746520616e64206f6e6c79206f6e2d636861696e207365712d70687261676d656e2077696c6c2420626520757365642e007501205468697320697320626f756e646564206279206265696e672077697468696e20746865206c6173742073657373696f6e2e2048656e63652c2073657474696e6720697420746f20612076616c7565206d6f7265207468616e207468659c206c656e677468206f6620612073657373696f6e2077696c6c20626520706f696e746c6573732e344d6178497465726174696f6e730c753332100a0000000c2901204d6178696d756d206e756d626572206f662062616c616e63696e6720697465726174696f6e7320746f2072756e20696e20746865206f6666636861696e207375626d697373696f6e2e00ec2049662073657420746f20302c2062616c616e63655f736f6c7574696f6e2077696c6c206e6f7420626520657865637574656420617420616c6c2e504d696e536f6c7574696f6e53636f726542756d701c50657262696c6c1020a1070004610120546865207468726573686f6c64206f6620696d70726f76656d656e7420746861742073686f756c642062652070726f766964656420666f722061206e657720736f6c7574696f6e20746f2062652061636365707465642e804d61784e6f6d696e61746f72526577617264656450657256616c696461746f720c753332104000000010f820546865206d6178696d756d206e756d626572206f66206e6f6d696e61746f727320726577617264656420666f7220656163682076616c696461746f722e00690120466f7220656163682076616c696461746f72206f6e6c79207468652060244d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732063616e20636c61696d2101207468656972207265776172642e2054686973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e7c344e6f74436f6e74726f6c6c65720468204e6f74206120636f6e74726f6c6c6572206163636f756e742e204e6f7453746173680454204e6f742061207374617368206163636f756e742e34416c7265616479426f6e646564046420537461736820697320616c726561647920626f6e6465642e34416c7265616479506169726564047820436f6e74726f6c6c657220697320616c7265616479207061697265642e30456d70747954617267657473046420546172676574732063616e6e6f7420626520656d7074792e384475706c6963617465496e6465780444204475706c696361746520696e6465782e44496e76616c6964536c617368496e646578048820536c617368207265636f726420696e646578206f7574206f6620626f756e64732e44496e73756666696369656e7456616c756504cc2043616e206e6f7420626f6e6420776974682076616c7565206c657373207468616e206d696e696d756d2062616c616e63652e304e6f4d6f72654368756e6b7304942043616e206e6f74207363686564756c65206d6f726520756e6c6f636b206368756e6b732e344e6f556e6c6f636b4368756e6b04a42043616e206e6f74207265626f6e6420776974686f757420756e6c6f636b696e67206368756e6b732e3046756e64656454617267657404cc20417474656d7074696e6720746f2074617267657420612073746173682074686174207374696c6c206861732066756e64732e48496e76616c6964457261546f526577617264045c20496e76616c69642065726120746f207265776172642e68496e76616c69644e756d6265724f664e6f6d696e6174696f6e73047c20496e76616c6964206e756d626572206f66206e6f6d696e6174696f6e732e484e6f74536f72746564416e64556e697175650484204974656d7320617265206e6f7420736f7274656420616e6420756e697175652e38416c7265616479436c61696d6564040d01205265776172647320666f72207468697320657261206861766520616c7265616479206265656e20636c61696d656420666f7220746869732076616c696461746f722e7c4f6666636861696e456c656374696f6e4561726c795375626d697373696f6e04e420546865207375626d697474656420726573756c74206973207265636569766564206f7574206f6620746865206f70656e2077696e646f772e784f6666636861696e456c656374696f6e5765616b5375626d697373696f6e04010120546865207375626d697474656420726573756c74206973206e6f7420617320676f6f6420617320746865206f6e652073746f726564206f6e20636861696e2e4c536e617073686f74556e617661696c61626c6504d02054686520736e617073686f742064617461206f66207468652063757272656e742077696e646f77206973206d697373696e672e804f6666636861696e456c656374696f6e426f67757357696e6e6572436f756e7404b020496e636f7272656374206e756d626572206f662077696e6e65727320776572652070726573656e7465642e6c4f6666636861696e456c656374696f6e426f67757357696e6e6572086101204f6e65206f6620746865207375626d69747465642077696e6e657273206973206e6f7420616e206163746976652063616e646964617465206f6e20636861696e2028696e646578206973206f7574206f662072616e67653820696e20736e617073686f74292e704f6666636861696e456c656374696f6e426f677573436f6d70616374085d01204572726f72207768696c65206275696c64696e67207468652061737369676e6d656e7420747970652066726f6d2074686520636f6d706163742e20546869732063616e2068617070656e20696620616e20696e646578a820697320696e76616c69642c206f72206966207468652077656967687473205f6f766572666c6f775f2e784f6666636861696e456c656374696f6e426f6775734e6f6d696e61746f72041501204f6e65206f6620746865207375626d6974746564206e6f6d696e61746f7273206973206e6f7420616e20616374697665206e6f6d696e61746f72206f6e20636861696e2e7c4f6666636861696e456c656374696f6e426f6775734e6f6d696e6174696f6e044d01204f6e65206f6620746865207375626d6974746564206e6f6d696e61746f72732068617320616e206564676520746f20776869636820746865792068617665206e6f7420766f746564206f6e20636861696e2e844f6666636861696e456c656374696f6e536c61736865644e6f6d696e6174696f6e086101204f6e65206f6620746865207375626d6974746564206e6f6d696e61746f72732068617320616e2065646765207768696368206973207375626d6974746564206265666f726520746865206c617374206e6f6e2d7a65726f5420736c617368206f6620746865207461726765742e744f6666636861696e456c656374696f6e426f67757353656c66566f746504250120412073656c6620766f7465206d757374206f6e6c79206265206f726967696e617465642066726f6d20612076616c696461746f7220746f204f4e4c59207468656d73656c7665732e644f6666636861696e456c656374696f6e426f6775734564676504450120546865207375626d697474656420726573756c742068617320756e6b6e6f776e206564676573207468617420617265206e6f7420616d6f6e67207468652070726573656e7465642077696e6e6572732e684f6666636861696e456c656374696f6e426f67757353636f72650419012054686520636c61696d65642073636f726520646f6573206e6f74206d61746368207769746820746865206f6e6520636f6d70757465642066726f6d2074686520646174612e844f6666636861696e456c656374696f6e426f677573456c656374696f6e53697a6504782054686520656c656374696f6e2073697a6520697320696e76616c69642e3843616c6c4e6f74416c6c6f776564044901205468652063616c6c206973206e6f7420616c6c6f7765642061742074686520676976656e2074696d652064756520746f207265737472696374696f6e73206f6620656c656374696f6e20706572696f642e54496e636f7272656374486973746f7279446570746804c420496e636f72726563742070726576696f757320686973746f727920646570746820696e7075742070726f76696465642e58496e636f7272656374536c617368696e675370616e7304b420496e636f7272656374206e756d626572206f6620736c617368696e67207370616e732070726f76696465642e1c53657373696f6e011c53657373696f6e1c2856616c696461746f727301004c5665633c543a3a56616c696461746f7249643e0400047c205468652063757272656e7420736574206f662076616c696461746f72732e3043757272656e74496e64657801003053657373696f6e496e646578100000000004782043757272656e7420696e646578206f66207468652073657373696f6e2e345175657565644368616e676564010010626f6f6c040008390120547275652069662074686520756e6465726c79696e672065636f6e6f6d6963206964656e746974696573206f7220776569676874696e6720626568696e64207468652076616c696461746f7273a420686173206368616e67656420696e20746865207175657565642076616c696461746f72207365742e285175657565644b6579730100785665633c28543a3a56616c696461746f7249642c20543a3a4b657973293e0400083d012054686520717565756564206b65797320666f7220746865206e6578742073657373696f6e2e205768656e20746865206e6578742073657373696f6e20626567696e732c207468657365206b657973e02077696c6c206265207573656420746f2064657465726d696e65207468652076616c696461746f7227732073657373696f6e206b6579732e4844697361626c656456616c696461746f72730100205665633c7533323e04000c8020496e6469636573206f662064697361626c65642076616c696461746f72732e003501205468652073657420697320636c6561726564207768656e20606f6e5f73657373696f6e5f656e64696e67602072657475726e732061206e657720736574206f66206964656e7469746965732e204e6578744b65797300010538543a3a56616c696461746f7249641c543a3a4b657973000400049c20546865206e6578742073657373696f6e206b65797320666f7220612076616c696461746f722e204b65794f776e657200010550284b65795479706549642c205665633c75383e2938543a3a56616c696461746f72496400040004090120546865206f776e6572206f662061206b65792e20546865206b65792069732074686520604b657954797065496460202b2074686520656e636f646564206b65792e0108207365745f6b65797308106b6579731c543a3a4b6579731470726f6f661c5665633c75383e38e82053657473207468652073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c657220746f20606b657973602e210120416c6c6f777320616e206163636f756e7420746f20736574206974732073657373696f6e206b6579207072696f7220746f206265636f6d696e6720612076616c696461746f722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a20606f726967696e206163636f756e74602c2060543a3a56616c696461746f7249644f66602c20604e6578744b65797360a4202d2044625772697465733a20606f726967696e206163636f756e74602c20604e6578744b6579736084202d204462526561647320706572206b65792069643a20604b65794f776e65726088202d20446257726974657320706572206b65792069643a20604b65794f776e657260302023203c2f7765696768743e2870757267655f6b6579730030cc2052656d6f76657320616e792073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c65722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743eb4202d20436f6d706c65786974793a20604f2831296020696e206e756d626572206f66206b65792074797065732e590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a2060543a3a56616c696461746f7249644f66602c20604e6578744b657973602c20606f726967696e206163636f756e7460a4202d2044625772697465733a20604e6578744b657973602c20606f726967696e206163636f756e74608c202d20446257726974657320706572206b65792069643a20604b65794f776e64657260302023203c2f7765696768743e0104284e657753657373696f6e043053657373696f6e496e646578085d01204e65772073657373696f6e206861732068617070656e65642e204e6f746520746861742074686520617267756d656e7420697320746865205b73657373696f6e5f696e6465785d2c206e6f742074686520626c6f636b88206e756d626572206173207468652074797065206d6967687420737567676573742e001030496e76616c696450726f6f66046420496e76616c6964206f776e6572736869702070726f6f662e5c4e6f4173736f63696174656456616c696461746f72496404a0204e6f206173736f6369617465642076616c696461746f7220494420666f72206163636f756e742e344475706c6963617465644b657904682052656769737465726564206475706c6963617465206b65792e184e6f4b65797304a8204e6f206b65797320617265206173736f63696174656420776974682074686973206163636f756e742e2444656d6f6372616379012444656d6f6372616379383c5075626c696350726f70436f756e7401002450726f70496e646578100000000004f420546865206e756d626572206f6620287075626c6963292070726f706f73616c7320746861742068617665206265656e206d61646520736f206661722e2c5075626c696350726f707301009c5665633c2850726f70496e6465782c20543a3a486173682c20543a3a4163636f756e744964293e040004210120546865207075626c69632070726f706f73616c732e20556e736f727465642e20546865207365636f6e64206974656d206973207468652070726f706f73616c277320686173682e244465706f7369744f660001052450726f70496e64657884285665633c543a3a4163636f756e7449643e2c2042616c616e63654f663c543e290004000c842054686f73652077686f2068617665206c6f636b65642061206465706f7369742e00d82054574f582d4e4f54453a20536166652c20617320696e6372656173696e6720696e7465676572206b6579732061726520736166652e24507265696d616765730001061c543a3a48617368e8507265696d6167655374617475733c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e000400086101204d6170206f662068617368657320746f207468652070726f706f73616c20707265696d6167652c20616c6f6e6720776974682077686f207265676973746572656420697420616e64207468656972206465706f7369742ee42054686520626c6f636b206e756d6265722069732074686520626c6f636b20617420776869636820697420776173206465706f73697465642e3c5265666572656e64756d436f756e7401003c5265666572656e64756d496e646578100000000004310120546865206e6578742066726565207265666572656e64756d20696e6465782c20616b6120746865206e756d626572206f66207265666572656e6461207374617274656420736f206661722e344c6f77657374556e62616b656401003c5265666572656e64756d496e646578100000000008250120546865206c6f77657374207265666572656e64756d20696e64657820726570726573656e74696e6720616e20756e62616b6564207265666572656e64756d2e20457175616c20746fdc20605265666572656e64756d436f756e74602069662074686572652069736e2774206120756e62616b6564207265666572656e64756d2e405265666572656e64756d496e666f4f660001053c5265666572656e64756d496e646578d45265666572656e64756d496e666f3c543a3a426c6f636b4e756d6265722c20543a3a486173682c2042616c616e63654f663c543e3e0004000cb420496e666f726d6174696f6e20636f6e6365726e696e6720616e7920676976656e207265666572656e64756d2e0009012054574f582d4e4f54453a205341464520617320696e646578657320617265206e6f7420756e64657220616e2061747461636b6572e280997320636f6e74726f6c2e20566f74696e674f6601010530543a3a4163636f756e744964c8566f74696e673c42616c616e63654f663c543e2c20543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00d8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000105d0120416c6c20766f74657320666f72206120706172746963756c617220766f7465722e2057652073746f7265207468652062616c616e636520666f7220746865206e756d626572206f6620766f74657320746861742077655d012068617665207265636f726465642e20546865207365636f6e64206974656d2069732074686520746f74616c20616d6f756e74206f662064656c65676174696f6e732c20746861742077696c6c2062652061646465642e00e82054574f582d4e4f54453a205341464520617320604163636f756e7449646073206172652063727970746f2068617368657320616e797761792e144c6f636b7300010530543a3a4163636f756e74496438543a3a426c6f636b4e756d626572000400105d01204163636f756e747320666f7220776869636820746865726520617265206c6f636b7320696e20616374696f6e207768696368206d61792062652072656d6f76656420617420736f6d6520706f696e7420696e207468655101206675747572652e205468652076616c75652069732074686520626c6f636b206e756d62657220617420776869636820746865206c6f636b206578706972657320616e64206d61792062652072656d6f7665642e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e544c6173745461626c656457617345787465726e616c010010626f6f6c0400085901205472756520696620746865206c617374207265666572656e64756d207461626c656420776173207375626d69747465642065787465726e616c6c792e2046616c7365206966206974207761732061207075626c6963282070726f706f73616c2e304e65787445787465726e616c00006028543a3a486173682c20566f74655468726573686f6c6429040010590120546865207265666572656e64756d20746f206265207461626c6564207768656e6576657220697420776f756c642062652076616c696420746f207461626c6520616e2065787465726e616c2070726f706f73616c2e550120546869732068617070656e73207768656e2061207265666572656e64756d206e6565647320746f206265207461626c656420616e64206f6e65206f662074776f20636f6e646974696f6e7320617265206d65743aa4202d20604c6173745461626c656457617345787465726e616c60206973206066616c7365603b206f7268202d20605075626c696350726f70736020697320656d7074792e24426c61636b6c6973740001061c543a3a486173688c28543a3a426c6f636b4e756d6265722c205665633c543a3a4163636f756e7449643e290004000851012041207265636f7264206f662077686f207665746f656420776861742e204d6170732070726f706f73616c206861736820746f206120706f737369626c65206578697374656e7420626c6f636b206e756d626572e82028756e74696c207768656e206974206d6179206e6f742062652072657375626d69747465642920616e642077686f207665746f65642069742e3443616e63656c6c6174696f6e730101061c543a3a4861736810626f6f6c000400042901205265636f7264206f6620616c6c2070726f706f73616c7320746861742068617665206265656e207375626a65637420746f20656d657267656e63792063616e63656c6c6174696f6e2e3853746f7261676556657273696f6e00002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e015c1c70726f706f7365083470726f706f73616c5f686173681c543a3a486173681476616c756554436f6d706163743c42616c616e63654f663c543e3e3ca02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e00190120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573748420686176652066756e647320746f20636f76657220746865206465706f7369742e00d8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20707265696d6167652e1901202d206076616c7565603a2054686520616d6f756e74206f66206465706f73697420286d757374206265206174206c6561737420604d696e696d756d4465706f73697460292e004820456d697473206050726f706f736564602e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960b4202d2044622072656164733a20605075626c696350726f70436f756e74602c20605075626c696350726f707360ec202d204462207772697465733a20605075626c696350726f70436f756e74602c20605075626c696350726f7073602c20604465706f7369744f6660302023203c2f7765696768743e187365636f6e64082070726f706f73616c48436f6d706163743c50726f70496e6465783e4c7365636f6e64735f75707065725f626f756e6430436f6d706163743c7533323e38b8205369676e616c732061677265656d656e742077697468206120706172746963756c61722070726f706f73616c2e00050120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e6465721501206d75737420686176652066756e647320746f20636f76657220746865206465706f7369742c20657175616c20746f20746865206f726967696e616c206465706f7369742e00cc202d206070726f706f73616c603a2054686520696e646578206f66207468652070726f706f73616c20746f207365636f6e642e4501202d20607365636f6e64735f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e207468652063757272656e74206e756d626572206f66207365636f6e6473206f6e2074686973290120202070726f706f73616c2e2045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e002c2023203c7765696768743e3901202d20436f6d706c65786974793a20604f28532960207768657265205320697320746865206e756d626572206f66207365636f6e647320612070726f706f73616c20616c7265616479206861732e60202d2044622072656164733a20604465706f7369744f666064202d204462207772697465733a20604465706f7369744f6660302023203c2f7765696768743e10766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f7465644163636f756e74566f74653c42616c616e63654f663c543e3e38350120566f746520696e2061207265666572656e64756d2e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374207468652070726f706f73616c3bbc206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00e0202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f20766f746520666f722e88202d2060766f7465603a2054686520766f746520636f6e66696775726174696f6e2e002c2023203c7765696768743e4901202d20436f6d706c65786974793a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722068617320766f746564206f6e2ea42020207765696768742069732063686172676564206173206966206d6178696d756d20766f7465732ef4202d2044622072656164733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f66602c206062616c616e636573206c6f636b7360f8202d204462207772697465733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f66602c206062616c616e636573206c6f636b7360302023203c2f7765696768743e40656d657267656e63795f63616e63656c04247265665f696e6465783c5265666572656e64756d496e646578305101205363686564756c6520616e20656d657267656e63792063616e63656c6c6174696f6e206f662061207265666572656e64756d2e2043616e6e6f742068617070656e20747769636520746f207468652073616d6530207265666572656e64756d2e00fc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206043616e63656c6c6174696f6e4f726967696e602e00d4202d607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e002c2023203c7765696768743e58202d20436f6d706c65786974793a20604f283129602ec0202d2044622072656164733a20605265666572656e64756d496e666f4f66602c206043616e63656c6c6174696f6e7360c4202d204462207772697465733a20605265666572656e64756d496e666f4f66602c206043616e63656c6c6174696f6e7360302023203c2f7765696768743e4065787465726e616c5f70726f706f7365043470726f706f73616c5f686173681c543a3a48617368343101205363686564756c652061207265666572656e64756d20746f206265207461626c6564206f6e6365206974206973206c6567616c20746f207363686564756c6520616e2065787465726e616c30207265666572656e64756d2e00ec20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206045787465726e616c4f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e002c2023203c7765696768743e2d01202d20436f6d706c657869747920604f2856296020776974682056206e756d626572206f66207665746f65727320696e2074686520626c61636b6c697374206f662070726f706f73616c2ebc2020204465636f64696e6720766563206f66206c656e67746820562e2043686172676564206173206d6178696d756da0202d2044622072656164733a20604e65787445787465726e616c602c2060426c61636b6c6973746070202d204462207772697465733a20604e65787445787465726e616c60302023203c2f7765696768743e6465787465726e616c5f70726f706f73655f6d616a6f72697479043470726f706f73616c5f686173681c543a3a48617368385901205363686564756c652061206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f207363686564756c656020616e2065787465726e616c207265666572656e64756d2e00f020546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c4d616a6f726974794f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f283129606c202d2044622077726974653a20604e65787445787465726e616c60302023203c2f7765696768743e6065787465726e616c5f70726f706f73655f64656661756c74043470726f706f73616c5f686173681c543a3a48617368384901205363686564756c652061206e656761746976652d7475726e6f75742d62696173207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f84207363686564756c6520616e2065787465726e616c207265666572656e64756d2e00ec20546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c44656661756c744f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f283129606c202d2044622077726974653a20604e65787445787465726e616c60302023203c2f7765696768743e28666173745f747261636b0c3470726f706f73616c5f686173681c543a3a4861736834766f74696e675f706572696f6438543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d626572505101205363686564756c65207468652063757272656e746c792065787465726e616c6c792d70726f706f736564206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564650120696d6d6564696174656c792e204966207468657265206973206e6f2065787465726e616c6c792d70726f706f736564207265666572656e64756d2063757272656e746c792c206f72206966207468657265206973206f6e65ec20627574206974206973206e6f742061206d616a6f726974792d63617272696573207265666572656e64756d207468656e206974206661696c732e00d420546865206469737061746368206f6620746869732063616c6c206d757374206265206046617374547261636b4f726967696e602e00f8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652063757272656e742065787465726e616c2070726f706f73616c2e6101202d2060766f74696e675f706572696f64603a2054686520706572696f64207468617420697320616c6c6f77656420666f7220766f74696e67206f6e20746869732070726f706f73616c2e20496e6372656173656420746f982020206046617374547261636b566f74696e67506572696f646020696620746f6f206c6f772e5501202d206064656c6179603a20546865206e756d626572206f6620626c6f636b20616674657220766f74696e672068617320656e64656420696e20617070726f76616c20616e6420746869732073686f756c64206265bc202020656e61637465642e205468697320646f65736e277420686176652061206d696e696d756d20616d6f756e742e004420456d697473206053746172746564602e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960b8202d2044622072656164733a20604e65787445787465726e616c602c20605265666572656e64756d436f756e74600d01202d204462207772697465733a20604e65787445787465726e616c602c20605265666572656e64756d436f756e74602c20605265666572656e64756d496e666f4f666060202d2042617365205765696768743a2033302e3120c2b573302023203c2f7765696768743e347665746f5f65787465726e616c043470726f706f73616c5f686173681c543a3a4861736838bc205665746f20616e6420626c61636b6c697374207468652065787465726e616c2070726f706f73616c20686173682e00dc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520605665746f4f726967696e602e003101202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c20746f207665746f20616e6420626c61636b6c6973742e004020456d69747320605665746f6564602e002c2023203c7765696768743e1901202d20436f6d706c65786974793a20604f2856202b206c6f6728562929602077686572652056206973206e756d626572206f6620606578697374696e67207665746f657273604501202020506572666f726d7320612062696e61727920736561726368206f6e20606578697374696e675f7665746f657273602077686963682073686f756c64206e6f742062652076657279206c617267652ea0202d2044622072656164733a20604e65787445787465726e616c602c2060426c61636b6c69737460a4202d204462207772697465733a20604e65787445787465726e616c602c2060426c61636b6c69737460302023203c2f7765696768743e4463616e63656c5f7265666572656e64756d04247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e28542052656d6f76652061207265666572656e64756d2e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00d8202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e002c2023203c7765696768743e58202d20436f6d706c65786974793a20604f283129602e80202d204462207772697465733a20605265666572656e64756d496e666f4f6660302023203c2f7765696768743e3463616e63656c5f717565756564041477686963683c5265666572656e64756d496e6465782ca02043616e63656c20612070726f706f73616c2071756575656420666f7220656e6163746d656e742e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00c8202d20607768696368603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e002c2023203c7765696768743e3501202d20604f284429602077686572652060446020697320746865206974656d7320696e207468652064697370617463682071756575652e205765696768746564206173206044203d203130602ec8202d2044622072656164733a20607363686564756c6572206c6f6f6b7570602c207363686564756c6572206167656e646160cc202d204462207772697465733a20607363686564756c6572206c6f6f6b7570602c207363686564756c6572206167656e646160302023203c2f7765696768743e2064656c65676174650c08746f30543a3a4163636f756e74496428636f6e76696374696f6e28436f6e76696374696f6e1c62616c616e63653042616c616e63654f663c543e683d012044656c65676174652074686520766f74696e6720706f77657220287769746820736f6d6520676976656e20636f6e76696374696f6e29206f66207468652073656e64696e67206163636f756e742e005901205468652062616c616e63652064656c656761746564206973206c6f636b656420666f72206173206c6f6e6720617320697427732064656c6567617465642c20616e64207468657265616674657220666f7220746865cc2074696d6520617070726f70726961746520666f722074686520636f6e76696374696f6e2773206c6f636b20706572696f642e00610120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e696e67206163636f756e74206d757374206569746865723a782020202d2062652064656c65676174696e6720616c72656164793b206f725d012020202d2068617665206e6f20766f74696e67206163746976697479202869662074686572652069732c207468656e2069742077696c6c206e65656420746f2062652072656d6f7665642f636f6e736f6c6964617465649820202020207468726f7567682060726561705f766f746560206f722060756e766f746560292e004901202d2060746f603a20546865206163636f756e742077686f736520766f74696e6720746865206074617267657460206163636f756e74277320766f74696e6720706f7765722077696c6c20666f6c6c6f772e5901202d2060636f6e76696374696f6e603a2054686520636f6e76696374696f6e20746861742077696c6c20626520617474616368656420746f207468652064656c65676174656420766f7465732e205768656e2074686545012020206163636f756e7420697320756e64656c6567617465642c207468652066756e64732077696c6c206265206c6f636b656420666f722074686520636f72726573706f6e64696e6720706572696f642e5501202d206062616c616e6365603a2054686520616d6f756e74206f6620746865206163636f756e7427732062616c616e636520746f206265207573656420696e2064656c65676174696e672e2054686973206d757374c82020206e6f74206265206d6f7265207468616e20746865206163636f756e7427732063757272656e742062616c616e63652e004c20456d697473206044656c656761746564602e002c2023203c7765696768743e5901202d20436f6d706c65786974793a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732ec4202d2044622072656164733a20332a60566f74696e674f66602c20606f726967696e206163636f756e74206c6f636b7360c8202d204462207772697465733a20332a60566f74696e674f66602c20606f726967696e206163636f756e74206c6f636b7360a4202d2044622072656164732070657220766f7465733a20605265666572656e64756d496e666f4f6660a8202d204462207772697465732070657220766f7465733a20605265666572656e64756d496e666f4f6660302023203c2f7765696768743e28756e64656c65676174650048d020556e64656c65676174652074686520766f74696e6720706f776572206f66207468652073656e64696e67206163636f756e742e00610120546f6b656e73206d617920626520756e6c6f636b656420666f6c6c6f77696e67206f6e636520616e20616d6f756e74206f662074696d6520636f6e73697374656e74207769746820746865206c6f636b20706572696f64e0206f662074686520636f6e76696374696f6e2077697468207768696368207468652064656c65676174696f6e20776173206973737565642e00490120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265582063757272656e746c792064656c65676174696e672e005420456d6974732060556e64656c656761746564602e002c2023203c7765696768743e5901202d20436f6d706c65786974793a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732e64202d2044622072656164733a20322a60566f74696e674f666068202d204462207772697465733a20322a60566f74696e674f6660a4202d2044622072656164732070657220766f7465733a20605265666572656e64756d496e666f4f6660a8202d204462207772697465732070657220766f7465733a20605265666572656e64756d496e666f4f6660302023203c2f7765696768743e58636c6561725f7075626c69635f70726f706f73616c7300207420436c6561727320616c6c207075626c69632070726f706f73616c732e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e002c2023203c7765696768743e28202d20604f283129602e6c202d204462207772697465733a20605075626c696350726f707360302023203c2f7765696768743e346e6f74655f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e3861012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e205468697320646f65736e27742072657175697265207468652070726f706f73616c20746f206265250120696e207468652064697370617463682071756575652062757420646f657320726571756972652061206465706f7369742c2072657475726e6564206f6e636520656e61637465642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e002c2023203c7765696768743e6901202d20436f6d706c65786974793a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e60202d2044622072656164733a2060507265696d616765736064202d204462207772697465733a2060507265696d6167657360302023203c2f7765696768743e646e6f74655f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e040d012053616d6520617320606e6f74655f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e586e6f74655f696d6d696e656e745f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e4045012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e2054686973207265717569726573207468652070726f706f73616c20746f206265410120696e207468652064697370617463682071756575652e204e6f206465706f736974206973206e65656465642e205768656e20746869732063616c6c206973207375636365737366756c2c20692e652e39012074686520707265696d61676520686173206e6f74206265656e2075706c6f61646564206265666f726520616e64206d61746368657320736f6d6520696d6d696e656e742070726f706f73616c2c40206e6f2066656520697320706169642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e002c2023203c7765696768743e6901202d20436f6d706c65786974793a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e60202d2044622072656164733a2060507265696d616765736064202d204462207772697465733a2060507265696d6167657360302023203c2f7765696768743e886e6f74655f696d6d696e656e745f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e0431012053616d6520617320606e6f74655f696d6d696e656e745f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e34726561705f707265696d616765083470726f706f73616c5f686173681c543a3a486173686070726f706f73616c5f6c656e5f75707065725f626f756e6430436f6d706163743c7533323e4cf42052656d6f766520616e20657870697265642070726f706f73616c20707265696d61676520616e6420636f6c6c65637420746865206465706f7369742e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00d0202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f6620612070726f706f73616c2e2d01202d206070726f706f73616c5f6c656e6774685f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e206c656e677468206f66207468652070726f706f73616c2e010120202045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e00510120546869732077696c6c206f6e6c7920776f726b2061667465722060566f74696e67506572696f646020626c6f636b732066726f6d207468652074696d6520746861742074686520707265696d616765207761735d01206e6f7465642c2069662069742773207468652073616d65206163636f756e7420646f696e672069742e2049662069742773206120646966666572656e74206163636f756e742c207468656e206974276c6c206f6e6c79b020776f726b20616e206164646974696f6e616c2060456e6163746d656e74506572696f6460206c617465722e006020456d6974732060507265696d616765526561706564602e002c2023203c7765696768743ed0202d20436f6d706c65786974793a20604f284429602077686572652044206973206c656e677468206f662070726f706f73616c2ebc202d2044622072656164733a2060507265696d61676573602c2070726f7669646572206163636f756e742064617461bc202d204462207772697465733a2060507265696d61676573602070726f7669646572206163636f756e742064617461302023203c2f7765696768743e18756e6c6f636b041874617267657430543a3a4163636f756e7449642ca420556e6c6f636b20746f6b656e732074686174206861766520616e2065787069726564206c6f636b2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00bc202d2060746172676574603a20546865206163636f756e7420746f2072656d6f766520746865206c6f636b206f6e2e002c2023203c7765696768743ed4202d20436f6d706c657869747920604f2852296020776974682052206e756d626572206f6620766f7465206f66207461726765742eec202d2044622072656164733a2060566f74696e674f66602c206062616c616e636573206c6f636b73602c2060746172676574206163636f756e7460f0202d204462207772697465733a2060566f74696e674f66602c206062616c616e636573206c6f636b73602c2060746172676574206163636f756e7460302023203c2f7765696768743e2c72656d6f76655f766f74650414696e6465783c5265666572656e64756d496e6465787c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e00102049663a8c202d20746865207265666572656e64756d207761732063616e63656c6c65642c206f7280202d20746865207265666572656e64756d206973206f6e676f696e672c206f7294202d20746865207265666572656e64756d2068617320656e6465642073756368207468617401012020202d2074686520766f7465206f6620746865206163636f756e742077617320696e206f70706f736974696f6e20746f2074686520726573756c743b206f72d82020202d20746865726520776173206e6f20636f6e76696374696f6e20746f20746865206163636f756e74277320766f74653b206f72882020202d20746865206163636f756e74206d61646520612073706c697420766f74656101202e2e2e7468656e2074686520766f74652069732072656d6f76656420636c65616e6c7920616e64206120666f6c6c6f77696e672063616c6c20746f2060756e6c6f636b60206d617920726573756c7420696e206d6f72655c2066756e6473206265696e6720617661696c61626c652e00ac2049662c20686f77657665722c20746865207265666572656e64756d2068617320656e64656420616e643af0202d2069742066696e697368656420636f72726573706f6e64696e6720746f2074686520766f7465206f6620746865206163636f756e742c20616e64e0202d20746865206163636f756e74206d6164652061207374616e6461726420766f7465207769746820636f6e76696374696f6e2c20616e64c0202d20746865206c6f636b20706572696f64206f662074686520636f6e76696374696f6e206973206e6f74206f7665725d01202e2e2e7468656e20746865206c6f636b2077696c6c206265206167677265676174656420696e746f20746865206f766572616c6c206163636f756e742773206c6f636b2c207768696368206d617920696e766f6c76655d01202a6f7665726c6f636b696e672a20287768657265207468652074776f206c6f636b732061726520636f6d62696e656420696e746f20612073696e676c65206c6f636b207468617420697320746865206d6178696d756de8206f6620626f74682074686520616d6f756e74206c6f636b656420616e64207468652074696d65206973206974206c6f636b656420666f72292e004d0120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e6572206d7573742068617665206120766f74658c207265676973746572656420666f72207265666572656e64756d2060696e646578602e00f8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e002c2023203c7765696768743e4101202d20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652eac202d2044622072656164733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f6660b0202d204462207772697465733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f6660302023203c2f7765696768743e4472656d6f76655f6f746865725f766f7465081874617267657430543a3a4163636f756e74496414696e6465783c5265666572656e64756d496e6465784c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e0051012049662074686520607461726765746020697320657175616c20746f20746865207369676e65722c207468656e20746869732066756e6374696f6e2069732065786163746c79206571756976616c656e7420746f3101206072656d6f76655f766f7465602e204966206e6f7420657175616c20746f20746865207369676e65722c207468656e2074686520766f7465206d757374206861766520657870697265642c590120656974686572206265636175736520746865207265666572656e64756d207761732063616e63656c6c65642c20626563617573652074686520766f746572206c6f737420746865207265666572656e64756d206f729c20626563617573652074686520636f6e76696374696f6e20706572696f64206973206f7665722e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e005101202d2060746172676574603a20546865206163636f756e74206f662074686520766f746520746f2062652072656d6f7665643b2074686973206163636f756e74206d757374206861766520766f74656420666f72582020207265666572656e64756d2060696e646578602ef8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e002c2023203c7765696768743e4101202d20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652eac202d2044622072656164733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f6660b0202d204462207772697465733a20605265666572656e64756d496e666f4f66602c2060566f74696e674f6660302023203c2f7765696768743e38656e6163745f70726f706f73616c083470726f706f73616c5f686173681c543a3a4861736814696e6465783c5265666572656e64756d496e64657804510120456e61637420612070726f706f73616c2066726f6d2061207265666572656e64756d2e20466f72206e6f77207765206a757374206d616b65207468652077656967687420626520746865206d6178696d756d2e01442050726f706f736564082450726f70496e6465781c42616c616e63650429012041206d6f74696f6e20686173206265656e2070726f706f7365642062792061207075626c6963206163636f756e742e205b70726f706f73616c5f696e6465782c206465706f7369745d185461626c65640c2450726f70496e6465781c42616c616e6365385665633c4163636f756e7449643e0475012041207075626c69632070726f706f73616c20686173206265656e207461626c656420666f72207265666572656e64756d20766f74652e205b70726f706f73616c5f696e6465782c206465706f7369742c206465706f7369746f72735d3845787465726e616c5461626c656400049820416e2065787465726e616c2070726f706f73616c20686173206265656e207461626c65642e1c53746172746564083c5265666572656e64756d496e64657834566f74655468726573686f6c6404bc2041207265666572656e64756d2068617320626567756e2e205b7265665f696e6465782c207468726573686f6c645d18506173736564043c5265666572656e64756d496e64657804e020412070726f706f73616c20686173206265656e20617070726f766564206279207265666572656e64756d2e205b7265665f696e6465785d244e6f74506173736564043c5265666572656e64756d496e64657804e020412070726f706f73616c20686173206265656e2072656a6563746564206279207265666572656e64756d2e205b7265665f696e6465785d2443616e63656c6c6564043c5265666572656e64756d496e64657804b42041207265666572656e64756d20686173206265656e2063616e63656c6c65642e205b7265665f696e6465785d204578656375746564083c5265666572656e64756d496e64657810626f6f6c04c020412070726f706f73616c20686173206265656e20656e61637465642e205b7265665f696e6465782c2069735f6f6b5d2444656c65676174656408244163636f756e744964244163636f756e74496404190120416e206163636f756e74206861732064656c65676174656420746865697220766f746520746f20616e6f74686572206163636f756e742e205b77686f2c207461726765745d2c556e64656c65676174656404244163636f756e74496404f020416e205b6163636f756e745d206861732063616e63656c6c656420612070726576696f75732064656c65676174696f6e206f7065726174696f6e2e185665746f65640c244163636f756e74496410486173682c426c6f636b4e756d62657204090120416e2065787465726e616c2070726f706f73616c20686173206265656e207665746f65642e205b77686f2c2070726f706f73616c5f686173682c20756e74696c5d34507265696d6167654e6f7465640c1048617368244163636f756e7449641c42616c616e636504590120412070726f706f73616c277320707265696d61676520776173206e6f7465642c20616e6420746865206465706f7369742074616b656e2e205b70726f706f73616c5f686173682c2077686f2c206465706f7369745d30507265696d616765557365640c1048617368244163636f756e7449641c42616c616e636508150120412070726f706f73616c20707265696d616765207761732072656d6f76656420616e6420757365642028746865206465706f736974207761732072657475726e6564292e8c205b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369745d3c507265696d616765496e76616c69640810486173683c5265666572656e64756d496e64657804790120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d6167652077617320696e76616c69642e205b70726f706f73616c5f686173682c207265665f696e6465785d3c507265696d6167654d697373696e670810486173683c5265666572656e64756d496e64657804790120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d61676520776173206d697373696e672e205b70726f706f73616c5f686173682c207265665f696e6465785d38507265696d616765526561706564101048617368244163636f756e7449641c42616c616e6365244163636f756e744964082d012041207265676973746572656420707265696d616765207761732072656d6f76656420616e6420746865206465706f73697420636f6c6c656374656420627920746865207265617065722eac205b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369742c207265617065725d20556e6c6f636b656404244163636f756e74496404b420416e205b6163636f756e745d20686173206265656e20756e6c6f636b6564207375636365737366756c6c792e203c456e6163746d656e74506572696f6438543a3a426c6f636b4e756d62657210002f0d0014710120546865206d696e696d756d20706572696f64206f66206c6f636b696e6720616e642074686520706572696f64206265747765656e20612070726f706f73616c206265696e6720617070726f76656420616e6420656e61637465642e0031012049742073686f756c642067656e6572616c6c792062652061206c6974746c65206d6f7265207468616e2074686520756e7374616b6520706572696f6420746f20656e737572652074686174690120766f74696e67207374616b657273206861766520616e206f70706f7274756e69747920746f2072656d6f7665207468656d73656c7665732066726f6d207468652073797374656d20696e2074686520636173652077686572659c207468657920617265206f6e20746865206c6f73696e672073696465206f66206120766f74652e304c61756e6368506572696f6438543a3a426c6f636b4e756d62657210004e0c0004e420486f77206f6674656e2028696e20626c6f636b7329206e6577207075626c6963207265666572656e646120617265206c61756e636865642e30566f74696e67506572696f6438543a3a426c6f636b4e756d62657210004e0c0004b820486f77206f6674656e2028696e20626c6f636b732920746f20636865636b20666f72206e657720766f7465732e384d696e696d756d4465706f7369743042616c616e63654f663c543e400000c16ff2862300000000000000000004350120546865206d696e696d756d20616d6f756e7420746f20626520757365642061732061206465706f73697420666f722061207075626c6963207265666572656e64756d2070726f706f73616c2e5446617374547261636b566f74696e67506572696f6438543a3a426c6f636b4e756d626572108051010004ec204d696e696d756d20766f74696e6720706572696f6420616c6c6f77656420666f7220616e20656d657267656e6379207265666572656e64756d2e34436f6f6c6f6666506572696f6438543a3a426c6f636b4e756d62657210004e0c0004610120506572696f6420696e20626c6f636b7320776865726520616e2065787465726e616c2070726f706f73616c206d6179206e6f742062652072652d7375626d6974746564206166746572206265696e67207665746f65642e4c507265696d616765427974654465706f7369743042616c616e63654f663c543e400010a5d4e800000000000000000000000429012054686520616d6f756e74206f662062616c616e63652074686174206d757374206265206465706f7369746564207065722062797465206f6620707265696d6167652073746f7265642e204d6178566f7465730c753332106400000004b020546865206d6178696d756d206e756d626572206f6620766f74657320666f7220616e206163636f756e742e842056616c75654c6f7704382056616c756520746f6f206c6f773c50726f706f73616c4d697373696e6704602050726f706f73616c20646f6573206e6f7420657869737420426164496e646578043820556e6b6e6f776e20696e6465783c416c726561647943616e63656c656404982043616e6e6f742063616e63656c207468652073616d652070726f706f73616c207477696365444475706c696361746550726f706f73616c04582050726f706f73616c20616c7265616479206d6164654c50726f706f73616c426c61636b6c6973746564046c2050726f706f73616c207374696c6c20626c61636b6c6973746564444e6f7453696d706c654d616a6f7269747904ac204e6578742065787465726e616c2070726f706f73616c206e6f742073696d706c65206d616a6f726974792c496e76616c696448617368043420496e76616c69642068617368284e6f50726f706f73616c0454204e6f2065787465726e616c2070726f706f73616c34416c72656164795665746f6564049c204964656e74697479206d6179206e6f74207665746f20612070726f706f73616c207477696365304e6f7444656c6567617465640438204e6f742064656c656761746564444475706c6963617465507265696d616765045c20507265696d61676520616c7265616479206e6f7465642c4e6f74496d6d696e656e740434204e6f7420696d6d696e656e7420546f6f4561726c79042820546f6f206561726c7920496d6d696e656e74042420496d6d696e656e743c507265696d6167654d697373696e67044c20507265696d616765206e6f7420666f756e64445265666572656e64756d496e76616c6964048820566f746520676976656e20666f7220696e76616c6964207265666572656e64756d3c507265696d616765496e76616c6964044420496e76616c696420707265696d6167652c4e6f6e6557616974696e670454204e6f2070726f706f73616c732077616974696e67244e6f744c6f636b656404a42054686520746172676574206163636f756e7420646f6573206e6f7420686176652061206c6f636b2e284e6f744578706972656404f020546865206c6f636b206f6e20746865206163636f756e7420746f20626520756e6c6f636b656420686173206e6f742079657420657870697265642e204e6f74566f74657204c82054686520676976656e206163636f756e7420646964206e6f7420766f7465206f6e20746865207265666572656e64756d2e304e6f5065726d697373696f6e04cc20546865206163746f7220686173206e6f207065726d697373696f6e20746f20636f6e647563742074686520616374696f6e2e44416c726561647944656c65676174696e67048c20546865206163636f756e7420697320616c72656164792064656c65676174696e672e204f766572666c6f7704a420416e20756e657870656374656420696e7465676572206f766572666c6f77206f636375727265642e24556e646572666c6f7704a820416e20756e657870656374656420696e746567657220756e646572666c6f77206f636375727265642e44496e73756666696369656e7446756e647304010120546f6f206869676820612062616c616e6365207761732070726f7669646564207468617420746865206163636f756e742063616e6e6f74206166666f72642e344e6f7444656c65676174696e6704a420546865206163636f756e74206973206e6f742063757272656e746c792064656c65676174696e672e28566f746573457869737408590120546865206163636f756e742063757272656e746c792068617320766f74657320617474616368656420746f20697420616e6420746865206f7065726174696f6e2063616e6e6f74207375636365656420756e74696cec207468657365206172652072656d6f7665642c20656974686572207468726f7567682060756e766f746560206f722060726561705f766f7465602e44496e7374616e744e6f74416c6c6f77656404dc2054686520696e7374616e74207265666572656e64756d206f726967696e2069732063757272656e746c7920646973616c6c6f7765642e204e6f6e73656e736504982044656c65676174696f6e20746f206f6e6573656c66206d616b6573206e6f2073656e73652e3c57726f6e675570706572426f756e64045420496e76616c696420757070657220626f756e642e3c4d6178566f746573526561636865640484204d6178696d756d206e756d626572206f6620766f74657320726561636865642e1c436f756e63696c014c496e7374616e636531436f6c6c656374697665182450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e7449640400085d0120546865206d656d6265722077686f2070726f7669646573207468652064656661756c7420766f746520666f7220616e79206f74686572206d656d62657273207468617420646f206e6f7420766f7465206265666f7265e4207468652074696d656f75742e204966204e6f6e652c207468656e206e6f206d656d6265722068617320746861742070726976696c6567652e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c30f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e002c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e6c510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed0205b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292ea4205b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e40205b70726f706f73616c5f686173685d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e40205b70726f706f73616c5f686173685d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e60205b70726f706f73616c5f686173682c20726573756c745d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e60205b70726f706f73616c5f686173682c20726573756c745d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e64205b70726f706f73616c5f686173682c207965732c206e6f5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e48546563686e6963616c436f6d6d6974746565014c496e7374616e636532436f6c6c656374697665182450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e7449640400085d0120546865206d656d6265722077686f2070726f7669646573207468652064656661756c7420766f746520666f7220616e79206f74686572206d656d62657273207468617420646f206e6f7420766f7465206265666f7265e4207468652074696d656f75742e204966204e6f6e652c207468656e206e6f206d656d6265722068617320746861742070726976696c6567652e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c30f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e002c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e6c510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed0205b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292ea4205b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e40205b70726f706f73616c5f686173685d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e40205b70726f706f73616c5f686173685d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e60205b70726f706f73616c5f686173682c20726573756c745d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e60205b70726f706f73616c5f686173682c20726573756c745d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e64205b70726f706f73616c5f686173682c207965732c206e6f5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e24456c656374696f6e73014050687261676d656e456c656374696f6e141c4d656d626572730100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e040004f0205468652063757272656e7420656c6563746564206d656d626572736869702e20536f72746564206261736564206f6e206163636f756e742069642e2452756e6e65727355700100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e0400044901205468652063757272656e742072756e6e6572735f75702e20536f72746564206261736564206f6e206c6f7720746f2068696768206d657269742028776f72736520746f20626573742072756e6e6572292e38456c656374696f6e526f756e647301000c75333210000000000441012054686520746f74616c206e756d626572206f6620766f746520726f756e6473207468617420686176652068617070656e65642c206578636c7564696e6720746865207570636f6d696e67206f6e652e18566f74696e6701010530543a3a4163636f756e744964842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e29004400000000000000000000000000000000000cb820566f74657320616e64206c6f636b6564207374616b65206f66206120706172746963756c617220766f7465722e00c02054574f582d4e4f54453a205341464520617320604163636f756e7449646020697320612063727970746f20686173682843616e646964617465730100445665633c543a3a4163636f756e7449643e0400085901205468652070726573656e742063616e646964617465206c6973742e20536f72746564206261736564206f6e206163636f756e742d69642e20412063757272656e74206d656d626572206f722072756e6e65722d757041012063616e206e6576657220656e746572207468697320766563746f7220616e6420697320616c7761797320696d706c696369746c7920617373756d656420746f20626520612063616e6469646174652e011810766f74650814766f746573445665633c543a3a4163636f756e7449643e1476616c756554436f6d706163743c42616c616e63654f663c543e3e645d0120566f746520666f72206120736574206f662063616e6469646174657320666f7220746865207570636f6d696e6720726f756e64206f6620656c656374696f6e2e20546869732063616e2062652063616c6c656420746fe4207365742074686520696e697469616c20766f7465732c206f722075706461746520616c7265616479206578697374696e6720766f7465732e0055012055706f6e20696e697469616c20766f74696e672c206076616c75656020756e697473206f66206077686f6027732062616c616e6365206973206c6f636b656420616e64206120626f6e6420616d6f756e74206973282072657365727665642e0050205468652060766f746573602073686f756c643a482020202d206e6f7420626520656d7074792e59012020202d206265206c657373207468616e20746865206e756d626572206f6620706f737369626c652063616e646964617465732e204e6f7465207468617420616c6c2063757272656e74206d656d6265727320616e641501202020202072756e6e6572732d75702061726520616c736f206175746f6d61746963616c6c792063616e6469646174657320666f7220746865206e65787420726f756e642e005d012049742069732074686520726573706f6e736962696c697479206f66207468652063616c6c657220746f206e6f7420706c61636520616c6c206f662074686569722062616c616e636520696e746f20746865206c6f636ba020616e64206b65657020736f6d6520666f722066757274686572207472616e73616374696f6e732e002c2023203c7765696768743e5c2042617365207765696768743a2034372e393320c2b573342053746174652072656164733ad820092d2043616e646964617465732e6c656e2829202b204d656d626572732e6c656e2829202b2052756e6e65727355702e6c656e28295420092d20566f74696e67202869735f766f74657229d420092d205b4163636f756e7442616c616e63652877686f292028756e72657365727665202b20746f74616c5f62616c616e6365295d38205374617465207772697465733a2820092d20566f74696e672020092d204c6f636b1d0120092d205b4163636f756e7442616c616e63652877686f292028756e72657365727665202d2d206f6e6c79207768656e206372656174696e672061206e657720766f746572295d302023203c2f7765696768743e3072656d6f76655f766f746572003421012052656d6f766520606f726967696e60206173206120766f7465722e20546869732072656d6f76657320746865206c6f636b20616e642072657475726e732074686520626f6e642e002c2023203c7765696768743e582042617365207765696768743a2033362e3820c2b573a820416c6c207374617465206163636573732069732066726f6d20646f5f72656d6f76655f766f7465722e342053746174652072656164733a2820092d20566f74696e675820092d205b4163636f756e74446174612877686f295d38205374617465207772697465733a2820092d20566f74696e672420092d204c6f636b735820092d205b4163636f756e74446174612877686f295d302023203c2f7765696768743e507265706f72745f646566756e63745f766f746572041c646566756e6374c4446566756e6374566f7465723c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e6c5d01205265706f727420607461726765746020666f72206265696e6720616e20646566756e637420766f7465722e20496e2063617365206f6620612076616c6964207265706f72742c20746865207265706f727465722069735d012072657761726465642062792074686520626f6e6420616d6f756e74206f662060746172676574602e204f74686572776973652c20746865207265706f7274657220697473656c662069732072656d6f76656420616e645c20746865697220626f6e6420697320736c61736865642e0088204120646566756e637420766f74657220697320646566696e656420746f2062653a4d012020202d206120766f7465722077686f73652063757272656e74207375626d697474656420766f7465732061726520616c6c20696e76616c69642e20692e652e20616c6c206f66207468656d20617265206e6ff020202020206c6f6e67657220612063616e646964617465206e6f7220616e20616374697665206d656d626572206f7220612072756e6e65722d75702e0000690120546865206f726967696e206d7573742070726f7669646520746865206e756d626572206f662063757272656e742063616e6469646174657320616e6420766f746573206f6620746865207265706f7274656420746172676574c020666f722074686520707572706f7365206f66206163637572617465207765696768742063616c63756c6174696f6e2e002c2023203c7765696768743eb4204e6f204261736520776569676874206261736564206f6e206d696e2073717561726520616e616c797369732ea420436f6d706c6578697479206f662063616e6469646174655f636f756e743a20312e37353520c2b5739020436f6d706c6578697479206f6620766f74655f636f756e743a2031382e353120c2b573342053746174652072656164733a542020092d20566f74696e67287265706f7274657229502020092d2043616e6469646174652e6c656e28294c2020092d20566f74696e672854617267657429d82020092d2043616e646964617465732c204d656d626572732c2052756e6e6572735570202869735f646566756e63745f766f7465722938205374617465207772697465733a7020092d204c6f636b287265706f72746572207c7c2074617267657429dc20092d205b4163636f756e7442616c616e6365287265706f72746572295d202b204163636f756e7442616c616e636528746172676574297820092d20566f74696e67287265706f72746572207c7c20746172676574295901204e6f74653a207468652064622061636365737320697320776f7273652077697468207265737065637420746f2064622c207768696368206973207768656e20746865207265706f727420697320636f72726563742e302023203c2f7765696768743e407375626d69745f63616e646964616379043c63616e6469646174655f636f756e7430436f6d706163743c7533323e5478205375626d6974206f6e6573656c6620666f722063616e6469646163792e006420412063616e6469646174652077696c6c206569746865723aec2020202d204c6f73652061742074686520656e64206f6620746865207465726d20616e6420666f7266656974207468656972206465706f7369742e2d012020202d2057696e20616e64206265636f6d652061206d656d6265722e204d656d626572732077696c6c206576656e7475616c6c7920676574207468656972207374617368206261636b2e55012020202d204265636f6d6520612072756e6e65722d75702e2052756e6e6572732d75707320617265207265736572766564206d656d6265727320696e2063617365206f6e65206765747320666f72636566756c6c7934202020202072656d6f7665642e002c2023203c7765696768743e60204261736520776569676874203d2033332e333320c2b573a420436f6d706c6578697479206f662063616e6469646174655f636f756e743a20302e33373520c2b573342053746174652072656164733a5020092d2043616e646964617465732e6c656e28293820092d2043616e646964617465732c20092d204d656d626572733420092d2052756e6e65727355706420092d205b4163636f756e7442616c616e63652877686f295d38205374617465207772697465733a6420092d205b4163636f756e7442616c616e63652877686f295d3820092d2043616e64696461746573302023203c2f7765696768743e4872656e6f756e63655f63616e646964616379042872656e6f756e63696e672852656e6f756e63696e679851012052656e6f756e6365206f6e65277320696e74656e74696f6e20746f20626520612063616e64696461746520666f7220746865206e65787420656c656374696f6e20726f756e642e203320706f74656e7469616c40206f7574636f6d65732065786973743a4101202d20606f726967696e6020697320612063616e64696461746520616e64206e6f7420656c656374656420696e20616e79207365742e20496e207468697320636173652c2074686520626f6e64206973f4202020756e72657365727665642c2072657475726e656420616e64206f726967696e2069732072656d6f76656420617320612063616e6469646174652e5901202d20606f726967696e6020697320612063757272656e742072756e6e65722d75702e20496e207468697320636173652c2074686520626f6e6420697320756e72657365727665642c2072657475726e656420616e64902020206f726967696e2069732072656d6f76656420617320612072756e6e65722d75702e4d01202d20606f726967696e6020697320612063757272656e74206d656d6265722e20496e207468697320636173652c2074686520626f6e6420697320756e726573657276656420616e64206f726967696e206973590120202072656d6f7665642061732061206d656d6265722c20636f6e73657175656e746c79206e6f74206265696e6720612063616e64696461746520666f7220746865206e65787420726f756e6420616e796d6f72652e650120202053696d696c617220746f205b6072656d6f76655f766f746572605d2c206966207265706c6163656d656e742072756e6e657273206578697374732c20746865792061726520696d6d6564696174656c7920757365642e24203c7765696768743e7820496620612063616e6469646174652069732072656e6f756e63696e673a60200942617365207765696768743a2031372e323820c2b573a82009436f6d706c6578697479206f662063616e6469646174655f636f756e743a20302e32333520c2b57338200953746174652072656164733a3c2009092d2043616e64696461746573982009092d205b4163636f756e7442616c616e63652877686f292028756e72657365727665295d3c20095374617465207772697465733a3c2009092d2043616e64696461746573982009092d205b4163636f756e7442616c616e63652877686f292028756e72657365727665295d64204966206d656d6265722069732072656e6f756e63696e673a60200942617365207765696768743a2034362e323520c2b57338200953746174652072656164733ad02009092d204d656d626572732c2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d626572292c8c2009092d205b4163636f756e74446174612877686f292028756e72657365727665295d3c20095374617465207772697465733ad02009092d204d656d626572732c2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d626572292c8c2009092d205b4163636f756e74446174612877686f292028756e72657365727665295d642049662072756e6e65722069732072656e6f756e63696e673a60200942617365207765696768743a2034362e323520c2b57338200953746174652072656164733aac2009092d2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d626572292c8c2009092d205b4163636f756e74446174612877686f292028756e72657365727665295d3c20095374617465207772697465733aac2009092d2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d626572292c8c2009092d205b4163636f756e74446174612877686f292028756e72657365727665295d000d0120576569676874206e6f74653a205468652063616c6c20696e746f206368616e67654d656d62657273206e65656420746f206265206163636f756e74656420666f722e28203c2f7765696768743e3472656d6f76655f6d656d626572080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653c6861735f7265706c6163656d656e7410626f6f6c485d012052656d6f7665206120706172746963756c6172206d656d6265722066726f6d20746865207365742e20546869732069732065666665637469766520696d6d6564696174656c7920616e642074686520626f6e64206f668020746865206f7574676f696e67206d656d62657220697320736c61736865642e00590120496620612072756e6e65722d757020697320617661696c61626c652c207468656e2074686520626573742072756e6e65722d75702077696c6c2062652072656d6f76656420616e64207265706c61636573207468650101206f7574676f696e67206d656d6265722e204f74686572776973652c2061206e65772070687261676d656e20656c656374696f6e20697320737461727465642e004501204e6f74652074686174207468697320646f6573206e6f7420616666656374207468652064657369676e6174656420626c6f636b206e756d626572206f6620746865206e65787420656c656374696f6e2e002c2023203c7765696768743e6820496620776520686176652061207265706c6163656d656e743a6820092d2042617365207765696768743a2035302e393320c2b5734020092d2053746174652072656164733a502009092d2052756e6e65727355702e6c656e2829cc2009092d204d656d626572732c2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d626572294420092d205374617465207772697465733acc2009092d204d656d626572732c2052756e6e6572735570202872656d6f76655f616e645f7265706c6163655f6d656d62657229650120456c73652c2073696e63652074686973206973206120726f6f742063616c6c20616e642077696c6c20676f20696e746f2070687261676d656e2c20776520617373756d652066756c6c20626c6f636b20666f72206e6f772e302023203c2f7765696768743e01141c4e65775465726d04645665633c284163636f756e7449642c2042616c616e6365293e1061012041206e6577207465726d2077697468205b6e65775f6d656d626572735d2e205468697320696e64696361746573207468617420656e6f7567682063616e64696461746573206578697374656420746f2072756e20746865590120656c656374696f6e2c206e6f74207468617420656e6f756768206861766520686173206265656e20656c65637465642e2054686520696e6e65722076616c7565206d757374206265206578616d696e656420666f726101207468697320707572706f73652e204120604e65775465726d285b5d296020696e64696361746573207468617420736f6d652063616e6469646174657320676f7420746865697220626f6e6420736c617368656420616e645901206e6f6e65207765726520656c65637465642c207768696c73742060456d7074795465726d60206d65616e732074686174206e6f2063616e64696461746573206578697374656420746f20626567696e20776974682e24456d7074795465726d00083501204e6f20286f72206e6f7420656e6f756768292063616e64696461746573206578697374656420666f72207468697320726f756e642e205468697320697320646966666572656e742066726f6dc420604e65775465726d285b5d29602e2053656520746865206465736372697074696f6e206f6620604e65775465726d602e304d656d6265724b69636b656404244163636f756e744964084d012041205b6d656d6265725d20686173206265656e2072656d6f7665642e20546869732073686f756c6420616c7761797320626520666f6c6c6f7765642062792065697468657220604e65775465726d60206f74342060456d7074795465726d602e3c4d656d62657252656e6f756e63656404244163636f756e74496404a82041205b6d656d6265725d206861732072656e6f756e6365642074686569722063616e6469646163792e34566f7465725265706f727465640c244163636f756e744964244163636f756e74496410626f6f6c080901204120766f74657220776173207265706f7274656420776974682074686520746865207265706f7274206265696e67207375636365737366756c206f72206e6f742e6c205b766f7465722c207265706f727465722c20737563636573735d183443616e646964616379426f6e643042616c616e63654f663c543e400080c6a47e8d030000000000000000000028566f74696e67426f6e643042616c616e63654f663c543e4000407a10f35a000000000000000000000038446573697265644d656d626572730c753332100d00000000404465736972656452756e6e65727355700c753332100700000000305465726d4475726174696f6e38543a3a426c6f636b4e756d626572108013030000204d6f64756c654964384c6f636b4964656e74696669657220706872656c656374004430556e61626c65546f566f746504c42043616e6e6f7420766f7465207768656e206e6f2063616e64696461746573206f72206d656d626572732065786973742e1c4e6f566f7465730498204d75737420766f746520666f72206174206c65617374206f6e652063616e6469646174652e30546f6f4d616e79566f74657304882043616e6e6f7420766f7465206d6f7265207468616e2063616e646964617465732e504d6178696d756d566f7465734578636565646564049c2043616e6e6f7420766f7465206d6f7265207468616e206d6178696d756d20616c6c6f7765642e284c6f7742616c616e636504c82043616e6e6f7420766f74652077697468207374616b65206c657373207468616e206d696e696d756d2062616c616e63652e3c556e61626c65546f506179426f6e64047c20566f7465722063616e206e6f742070617920766f74696e6720626f6e642e2c4d7573744265566f7465720444204d757374206265206120766f7465722e285265706f727453656c6604502043616e6e6f74207265706f72742073656c662e4c4475706c69636174656443616e6469646174650484204475706c6963617465642063616e646964617465207375626d697373696f6e2e304d656d6265725375626d6974048c204d656d6265722063616e6e6f742072652d7375626d69742063616e6469646163792e3052756e6e65725375626d6974048c2052756e6e65722063616e6e6f742072652d7375626d69742063616e6469646163792e68496e73756666696369656e7443616e64696461746546756e647304982043616e64696461746520646f6573206e6f74206861766520656e6f7567682066756e64732e244e6f744d656d6265720438204e6f742061206d656d6265722e54496e76616c696443616e646964617465436f756e7404e4205468652070726f766964656420636f756e74206f66206e756d626572206f662063616e6469646174657320697320696e636f72726563742e40496e76616c6964566f7465436f756e7404d0205468652070726f766964656420636f756e74206f66206e756d626572206f6620766f74657320697320696e636f72726563742e44496e76616c696452656e6f756e63696e67040101205468652072656e6f756e63696e67206f726967696e2070726573656e74656420612077726f6e67206052656e6f756e63696e676020706172616d657465722e48496e76616c69645265706c6163656d656e740401012050726564696374696f6e20726567617264696e67207265706c6163656d656e74206166746572206d656d6265722072656d6f76616c2069732077726f6e672e4c546563686e6963616c4d656d62657273686970014c496e7374616e6365314d656d62657273686970081c4d656d626572730100445665633c543a3a4163636f756e7449643e040004c8205468652063757272656e74206d656d626572736869702c2073746f72656420617320616e206f726465726564205665632e145072696d65000030543a3a4163636f756e744964040004a4205468652063757272656e74207072696d65206d656d6265722c206966206f6e65206578697374732e011c286164645f6d656d626572040c77686f30543a3a4163636f756e7449640c7c204164642061206d656d626572206077686f6020746f20746865207365742e00a0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a4164644f726967696e602e3472656d6f76655f6d656d626572040c77686f30543a3a4163636f756e7449640c902052656d6f76652061206d656d626572206077686f602066726f6d20746865207365742e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656d6f76654f726967696e602e2c737761705f6d656d626572081872656d6f766530543a3a4163636f756e7449640c61646430543a3a4163636f756e74496414c02053776170206f7574206f6e65206d656d626572206072656d6f76656020666f7220616e6f746865722060616464602e00a4204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a537761704f726967696e602e001101205072696d65206d656d62657273686970206973202a6e6f742a207061737365642066726f6d206072656d6f76656020746f2060616464602c20696620657874616e742e3472657365745f6d656d62657273041c6d656d62657273445665633c543a3a4163636f756e7449643e105901204368616e676520746865206d656d6265727368697020746f2061206e6577207365742c20646973726567617264696e6720746865206578697374696e67206d656d626572736869702e204265206e69636520616e646c207061737320606d656d6265727360207072652d736f727465642e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52657365744f726967696e602e286368616e67655f6b6579040c6e657730543a3a4163636f756e74496414d82053776170206f7574207468652073656e64696e67206d656d62657220666f7220736f6d65206f74686572206b657920606e6577602e00f4204d6179206f6e6c792062652063616c6c65642066726f6d20605369676e656460206f726967696e206f6620612063757272656e74206d656d6265722e002101205072696d65206d656d62657273686970206973207061737365642066726f6d20746865206f726967696e206163636f756e7420746f20606e6577602c20696620657874616e742e247365745f7072696d65040c77686f30543a3a4163636f756e7449640cc02053657420746865207072696d65206d656d6265722e204d75737420626520612063757272656e74206d656d6265722e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e2c636c6561725f7072696d65000c982052656d6f766520746865207072696d65206d656d626572206966206974206578697374732e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e01182c4d656d62657241646465640004e42054686520676976656e206d656d626572207761732061646465643b2073656520746865207472616e73616374696f6e20666f722077686f2e344d656d62657252656d6f7665640004ec2054686520676976656e206d656d626572207761732072656d6f7665643b2073656520746865207472616e73616374696f6e20666f722077686f2e384d656d62657273537761707065640004dc2054776f206d656d62657273207765726520737761707065643b2073656520746865207472616e73616374696f6e20666f722077686f2e304d656d6265727352657365740004190120546865206d656d62657273686970207761732072657365743b2073656520746865207472616e73616374696f6e20666f722077686f20746865206e6577207365742069732e284b65794368616e676564000488204f6e65206f6620746865206d656d6265727327206b657973206368616e6765642e1444756d6d7904bc73705f7374643a3a6d61726b65723a3a5068616e746f6d446174613c284163636f756e7449642c204576656e74293e0470205068616e746f6d206d656d6265722c206e6576657220757365642e00003c46696e616c697479547261636b65720001042866696e616c5f68696e74041068696e745c436f6d706163743c543a3a426c6f636b4e756d6265723e08f42048696e7420746861742074686520617574686f72206f66207468697320626c6f636b207468696e6b732074686520626573742066696e616c697a65646c20626c6f636b2069732074686520676976656e206e756d6265722e00082857696e646f7753697a6538543a3a426c6f636b4e756d626572106500000004190120546865206e756d626572206f6620726563656e742073616d706c657320746f206b6565702066726f6d207468697320636861696e2e2044656661756c74206973203130312e345265706f72744c6174656e637938543a3a426c6f636b4e756d62657210e8030000041d01205468652064656c617920616674657220776869636820706f696e74207468696e6773206265636f6d6520737573706963696f75732e2044656661756c7420697320313030302e0838416c72656164795570646174656404c82046696e616c2068696e74206d7573742062652075706461746564206f6e6c79206f6e636520696e2074686520626c6f636b1c42616448696e7404902046696e616c697a6564206865696768742061626f766520626c6f636b206e756d6265721c4772616e647061013c4772616e64706146696e616c6974791814537461746501006c53746f72656453746174653c543a3a426c6f636b4e756d6265723e04000490205374617465206f66207468652063757272656e7420617574686f72697479207365742e3450656e64696e674368616e676500008c53746f72656450656e64696e674368616e67653c543a3a426c6f636b4e756d6265723e040004c42050656e64696e67206368616e67653a20287369676e616c65642061742c207363686564756c6564206368616e6765292e284e657874466f72636564000038543a3a426c6f636b4e756d626572040004bc206e65787420626c6f636b206e756d6265722077686572652077652063616e20666f7263652061206368616e67652e1c5374616c6c656400008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d626572290400049020607472756560206966207765206172652063757272656e746c79207374616c6c65642e3043757272656e7453657449640100145365744964200000000000000000085d0120546865206e756d626572206f66206368616e6765732028626f746820696e207465726d73206f66206b65797320616e6420756e6465726c79696e672065636f6e6f6d696320726573706f6e736962696c697469657329c420696e20746865202273657422206f66204772616e6470612076616c696461746f72732066726f6d2067656e657369732e30536574496453657373696f6e0001051453657449643053657373696f6e496e6465780004001059012041206d617070696e672066726f6d206772616e6470612073657420494420746f2074686520696e646578206f6620746865202a6d6f737420726563656e742a2073657373696f6e20666f722077686963682069747368206d656d62657273207765726520726573706f6e7369626c652e00b82054574f582d4e4f54453a2060536574496460206973206e6f7420756e646572207573657220636f6e74726f6c2e010c4c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66240d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e00110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e306e6f74655f7374616c6c6564081464656c617938543a3a426c6f636b4e756d6265726c626573745f66696e616c697a65645f626c6f636b5f6e756d62657238543a3a426c6f636b4e756d6265721c1d01204e6f74652074686174207468652063757272656e7420617574686f7269747920736574206f6620746865204752414e4450412066696e616c69747920676164676574206861732901207374616c6c65642e20546869732077696c6c2074726967676572206120666f7263656420617574686f7269747920736574206368616e67652061742074686520626567696e6e696e672101206f6620746865206e6578742073657373696f6e2c20746f20626520656e6163746564206064656c61796020626c6f636b7320616674657220746861742e205468652064656c617915012073686f756c64206265206869676820656e6f75676820746f20736166656c7920617373756d6520746861742074686520626c6f636b207369676e616c6c696e6720746865290120666f72636564206368616e67652077696c6c206e6f742062652072652d6f726765642028652e672e203130303020626c6f636b73292e20546865204752414e44504120766f7465727329012077696c6c20737461727420746865206e657720617574686f7269747920736574207573696e672074686520676976656e2066696e616c697a656420626c6f636b20617320626173652e5c204f6e6c792063616c6c61626c6520627920726f6f742e010c384e6577417574686f7269746965730434417574686f726974794c69737404d0204e657720617574686f726974792073657420686173206265656e206170706c6965642e205b617574686f726974795f7365745d1850617573656400049c2043757272656e7420617574686f726974792073657420686173206265656e207061757365642e1c526573756d65640004a02043757272656e7420617574686f726974792073657420686173206265656e20726573756d65642e001c2c50617573654661696c656408090120417474656d707420746f207369676e616c204752414e445041207061757365207768656e2074686520617574686f72697479207365742069736e2774206c697665a8202865697468657220706175736564206f7220616c72656164792070656e64696e67207061757365292e30526573756d654661696c656408150120417474656d707420746f207369676e616c204752414e44504120726573756d65207768656e2074686520617574686f72697479207365742069736e277420706175736564a42028656974686572206c697665206f7220616c72656164792070656e64696e6720726573756d65292e344368616e676550656e64696e6704ec20417474656d707420746f207369676e616c204752414e445041206368616e67652077697468206f6e6520616c72656164792070656e64696e672e1c546f6f536f6f6e04c02043616e6e6f74207369676e616c20666f72636564206368616e676520736f20736f6f6e206166746572206c6173742e60496e76616c69644b65794f776e65727368697050726f6f660435012041206b6579206f776e6572736869702070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e60496e76616c696445717569766f636174696f6e50726f6f6604350120416e2065717569766f636174696f6e2070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e584475706c69636174654f6666656e63655265706f7274041901204120676976656e2065717569766f636174696f6e207265706f72742069732076616c69642062757420616c72656164792070726576696f75736c79207265706f727465642e20547265617375727901205472656173757279143450726f706f73616c436f756e7401003450726f706f73616c496e646578100000000004a4204e756d626572206f662070726f706f73616c7320746861742068617665206265656e206d6164652e2450726f706f73616c730001053450726f706f73616c496e6465789050726f706f73616c3c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400047c2050726f706f73616c7320746861742068617665206265656e206d6164652e24417070726f76616c730100485665633c50726f706f73616c496e6465783e040004f82050726f706f73616c20696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f742079657420617761726465642e10546970730001051c543a3a48617368f04f70656e5469703c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265722c20543a3a486173683e0004000c59012054697073207468617420617265206e6f742079657420636f6d706c657465642e204b65796564206279207468652068617368206f66206028726561736f6e2c2077686f29602066726f6d207468652076616c75652e3d012054686973206861732074686520696e73656375726520656e756d657261626c6520686173682066756e6374696f6e2073696e636520746865206b657920697473656c6620697320616c7265616479802067756172616e7465656420746f20626520612073656375726520686173682e1c526561736f6e730001061c543a3a486173681c5665633c75383e0004000849012053696d706c6520707265696d616765206c6f6f6b75702066726f6d2074686520726561736f6e2773206861736820746f20746865206f726967696e616c20646174612e20416761696e2c2068617320616e610120696e73656375726520656e756d657261626c6520686173682073696e636520746865206b65792069732067756172616e7465656420746f2062652074686520726573756c74206f6620612073656375726520686173682e01203470726f706f73655f7370656e64081476616c756554436f6d706163743c42616c616e63654f663c543e3e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365242d012050757420666f727761726420612073756767657374696f6e20666f72207370656e64696e672e2041206465706f7369742070726f706f7274696f6e616c20746f207468652076616c7565350120697320726573657276656420616e6420736c6173686564206966207468652070726f706f73616c2069732072656a65637465642e2049742069732072657475726e6564206f6e636520746865542070726f706f73616c20697320617761726465642e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129b4202d20446252656164733a206050726f706f73616c436f756e74602c20606f726967696e206163636f756e7460ec202d2044625772697465733a206050726f706f73616c436f756e74602c206050726f706f73616c73602c20606f726967696e206163636f756e7460302023203c2f7765696768743e3c72656a6563745f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e24fc2052656a65637420612070726f706f736564207370656e642e20546865206f726967696e616c206465706f7369742077696c6c20626520736c61736865642e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656a6563744f726967696e602e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129d0202d20446252656164733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460d4202d2044625772697465733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460302023203c2f7765696768743e40617070726f76655f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e285d0120417070726f766520612070726f706f73616c2e2041742061206c617465722074696d652c207468652070726f706f73616c2077696c6c20626520616c6c6f636174656420746f207468652062656e6566696369617279ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e50202d20436f6d706c65786974793a204f2831292e90202d20446252656164733a206050726f706f73616c73602c2060417070726f76616c73605c202d20446257726974653a2060417070726f76616c7360302023203c2f7765696768743e387265706f72745f617765736f6d650818726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e7449644c5d01205265706f727420736f6d657468696e672060726561736f6e60207468617420646573657276657320612074697020616e6420636c61696d20616e79206576656e7475616c207468652066696e6465722773206665652e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c206173d420605469705265706f72744465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743ecc202d20436f6d706c65786974793a20604f2852296020776865726520605260206c656e677468206f662060726561736f6e602e942020202d20656e636f64696e6720616e642068617368696e67206f662027726561736f6e27c4202d20446252656164733a2060526561736f6e73602c206054697073602c206077686f206163636f756e742064617461609c202d2044625772697465733a206054697073602c206077686f206163636f756e74206461746160302023203c2f7765696768743e2c726574726163745f7469700410686173681c543a3a486173684c550120526574726163742061207072696f72207469702d7265706f72742066726f6d20607265706f72745f617765736f6d65602c20616e642063616e63656c207468652070726f63657373206f662074697070696e672e00e0204966207375636365737366756c2c20746865206f726967696e616c206465706f7369742077696c6c20626520756e72657365727665642e00510120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642074686520746970206964656e746966696564206279206068617368604501206d7573742068617665206265656e207265706f7274656420627920746865207369676e696e67206163636f756e74207468726f75676820607265706f72745f617765736f6d65602028616e64206e6f7450207468726f75676820607469705f6e657760292e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e009020456d697473206054697052657472616374656460206966207375636365737366756c2e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960dc2020202d20446570656e6473206f6e20746865206c656e677468206f662060543a3a48617368602077686963682069732066697865642e90202d20446252656164733a206054697073602c20606f726967696e206163636f756e7460c0202d2044625772697465733a2060526561736f6e73602c206054697073602c20606f726967696e206163636f756e7460302023203c2f7765696768743e1c7469705f6e65770c18726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e744964247469705f76616c75653042616c616e63654f663c543e58f4204769766520612074697020666f7220736f6d657468696e67206e65773b206e6f2066696e6465722773206665652077696c6c2062652074616b656e2e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743e5501202d20436f6d706c65786974793a20604f2852202b2054296020776865726520605260206c656e677468206f662060726561736f6e602c2060546020697320746865206e756d626572206f6620746970706572732ec02020202d20604f285429603a206465636f64696e6720605469707065726020766563206f66206c656e6774682060546009012020202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e0d0120202020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602ee42020202d20604f285229603a2068617368696e6720616e6420656e636f64696e67206f6620726561736f6e206f66206c656e6774682060526080202d20446252656164733a206054697070657273602c2060526561736f6e736078202d2044625772697465733a2060526561736f6e73602c20605469707360302023203c2f7765696768743e0c7469700810686173681c543a3a48617368247469705f76616c75653042616c616e63654f663c543e64b4204465636c6172652061207469702076616c756520666f7220616e20616c72656164792d6f70656e207469702e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f66207468652068617368206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279382020206163636f756e742049442e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e00650120456d6974732060546970436c6f73696e676020696620746865207468726573686f6c64206f66207469707065727320686173206265656e207265616368656420616e642074686520636f756e74646f776e20706572696f64342068617320737461727465642e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e15012020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602c20696e736572742074697020616e6420636865636b20636c6f73696e672c0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602e00610120202041637475616c6c792077656967687420636f756c64206265206c6f77657220617320697420646570656e6473206f6e20686f77206d616e7920746970732061726520696e20604f70656e5469706020627574206974d4202020697320776569676874656420617320696620616c6d6f73742066756c6c20692e65206f66206c656e6774682060542d31602e74202d20446252656164733a206054697070657273602c206054697073604c202d2044625772697465733a20605469707360302023203c2f7765696768743e24636c6f73655f7469700410686173681c543a3a48617368446020436c6f736520616e64207061796f75742061207469702e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0019012054686520746970206964656e74696669656420627920606861736860206d75737420686176652066696e69736865642069747320636f756e74646f776e20706572696f642e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e9c2020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602e0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602eac202d20446252656164733a206054697073602c206054697070657273602c20607469702066696e64657260dc202d2044625772697465733a2060526561736f6e73602c206054697073602c206054697070657273602c20607469702066696e64657260302023203c2f7765696768743e012c2050726f706f736564043450726f706f73616c496e646578047c204e65772070726f706f73616c2e205b70726f706f73616c5f696e6465785d205370656e64696e67041c42616c616e6365043501205765206861766520656e6465642061207370656e6420706572696f6420616e642077696c6c206e6f7720616c6c6f636174652066756e64732e205b6275646765745f72656d61696e696e675d1c417761726465640c3450726f706f73616c496e6465781c42616c616e6365244163636f756e74496404150120536f6d652066756e64732068617665206265656e20616c6c6f63617465642e205b70726f706f73616c5f696e6465782c2061776172642c2062656e65666963696172795d2052656a6563746564083450726f706f73616c496e6465781c42616c616e6365041d0120412070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e205b70726f706f73616c5f696e6465782c20736c61736865645d144275726e74041c42616c616e636504a820536f6d65206f66206f75722066756e64732068617665206265656e206275726e742e205b6275726e5d20526f6c6c6f766572041c42616c616e6365047d01205370656e64696e67206861732066696e69736865643b20746869732069732074686520616d6f756e74207468617420726f6c6c73206f76657220756e74696c206e657874207370656e642e205b6275646765745f72656d61696e696e675d1c4465706f736974041c42616c616e636504a820536f6d652066756e64732068617665206265656e206465706f73697465642e205b6465706f7369745d184e657754697004104861736804c42041206e6577207469702073756767657374696f6e20686173206265656e206f70656e65642e205b7469705f686173685d28546970436c6f73696e670410486173680409012041207469702073756767657374696f6e206861732072656163686564207468726573686f6c6420616e6420697320636c6f73696e672e205b7469705f686173685d24546970436c6f7365640c1048617368244163636f756e7449641c42616c616e636504e82041207469702073756767657374696f6e20686173206265656e20636c6f7365642e205b7469705f686173682c2077686f2c207061796f75745d3054697052657472616374656404104861736804c02041207469702073756767657374696f6e20686173206265656e207265747261637465642e205b7469705f686173685d243050726f706f73616c426f6e641c5065726d696c6c1050c30000085501204672616374696f6e206f6620612070726f706f73616c27732076616c756520746861742073686f756c6420626520626f6e64656420696e206f7264657220746f20706c616365207468652070726f706f73616c2e110120416e2061636365707465642070726f706f73616c2067657473207468657365206261636b2e20412072656a65637465642070726f706f73616c20646f6573206e6f742e4c50726f706f73616c426f6e644d696e696d756d3042616c616e63654f663c543e4000407a10f35a00000000000000000000044901204d696e696d756d20616d6f756e74206f662066756e647320746861742073686f756c6420626520706c6163656420696e2061206465706f73697420666f72206d616b696e6720612070726f706f73616c2e2c5370656e64506572696f6438543a3a426c6f636b4e756d6265721080700000048820506572696f64206265747765656e2073756363657373697665207370656e64732e104275726e1c5065726d696c6c1020a107000411012050657263656e74616765206f662073706172652066756e64732028696620616e7929207468617420617265206275726e7420706572207370656e6420706572696f642e30546970436f756e74646f776e38543a3a426c6f636b4e756d62657210807000000445012054686520706572696f6420666f722077686963682061207469702072656d61696e73206f70656e20616674657220697320686173206163686965766564207468726573686f6c6420746970706572732e3454697046696e646572734665651c50657263656e7404140431012054686520616d6f756e74206f66207468652066696e616c2074697020776869636820676f657320746f20746865206f726967696e616c207265706f72746572206f6620746865207469702e505469705265706f72744465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004d42054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120746970207265706f72742e5c5469705265706f72744465706f736974506572427974653042616c616e63654f663c543e400010a5d4e800000000000000000000000409012054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e2074686520746970207265706f727420726561736f6e2e204d6f64756c654964204d6f64756c6549642070792f7472737279041901205468652074726561737572792773206d6f64756c652069642c207573656420666f72206465726976696e672069747320736f7665726569676e206163636f756e742049442e2070496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e50496e76616c696450726f706f73616c496e646578046c204e6f2070726f706f73616c206174207468617420696e6465782e30526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e30416c72656164794b6e6f776e048c20546865207469702077617320616c726561647920666f756e642f737461727465642e28556e6b6e6f776e54697004642054686520746970206861736820697320756e6b6e6f776e2e244e6f7446696e64657204210120546865206163636f756e7420617474656d7074696e6720746f20726574726163742074686520746970206973206e6f74207468652066696e646572206f6620746865207469702e245374696c6c4f70656e042d0120546865207469702063616e6e6f7420626520636c61696d65642f636c6f736564206265636175736520746865726520617265206e6f7420656e6f7567682074697070657273207965742e245072656d617475726504350120546865207469702063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e24436f6e7472616374730124436f6e747261637473143c43757272656e745363686564756c650100205363686564756c6535020000000020a107000000000020a107000000000020a107000000000020a107000000000020a107000000000020a107000000000020a1070000000000e0f7050400000000e024370500000000e0f705040000000020a107000000000020a107000000000080f0fa020000000000e1f505000000000400000000000100100000000040000000200000000000080004942043757272656e7420636f7374207363686564756c6520666f7220636f6e7472616374732e305072697374696e65436f64650001062c436f6465486173683c543e1c5665633c75383e0004000465012041206d617070696e672066726f6d20616e206f726967696e616c20636f6465206861736820746f20746865206f726967696e616c20636f64652c20756e746f756368656420627920696e737472756d656e746174696f6e2e2c436f646553746f726167650001062c436f6465486173683c543e587761736d3a3a5072656661625761736d4d6f64756c650004000465012041206d617070696e67206265747765656e20616e206f726967696e616c20636f6465206861736820616e6420696e737472756d656e746564207761736d20636f64652c20726561647920666f7220657865637574696f6e2e384163636f756e74436f756e74657201000c753634200000000000000000045420546865207375627472696520636f756e7465722e38436f6e7472616374496e666f4f6600010530543a3a4163636f756e7449643c436f6e7472616374496e666f3c543e0004000ca82054686520636f6465206173736f6369617465642077697468206120676976656e206163636f756e742e00d02054574f582d4e4f54453a20534146452073696e636520604163636f756e7449646020697320612073656375726520686173682e01143c7570646174655f7363686564756c6504207363686564756c65205363686564756c650cb4205570646174657320746865207363686564756c6520666f72206d65746572696e6720636f6e7472616374732e000d0120546865207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652073746f726564207363686564756c652e207075745f636f64650410636f64651c5665633c75383e085d012053746f7265732074686520676976656e2062696e617279205761736d20636f646520696e746f2074686520636861696e27732073746f7261676520616e642072657475726e73206974732060636f646568617368602ed420596f752063616e20696e7374616e746961746520636f6e747261637473206f6e6c7920776974682073746f72656420636f64652e1063616c6c1010646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e10646174611c5665633c75383e1c0901204d616b657320612063616c6c20746f20616e206163636f756e742c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e002901202a20496620746865206163636f756e74206973206120736d6172742d636f6e7472616374206163636f756e742c20746865206173736f63696174656420636f64652077696c6c206265b020657865637574656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e1901202a20496620746865206163636f756e74206973206120726567756c6172206163636f756e742c20616e792076616c75652077696c6c206265207472616e736665727265642e4901202a204966206e6f206163636f756e742065786973747320616e64207468652063616c6c2076616c7565206973206e6f74206c657373207468616e20606578697374656e7469616c5f6465706f736974602c1501206120726567756c6172206163636f756e742077696c6c206265206372656174656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e2c696e7374616e74696174651024656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e24636f64655f686173682c436f6465486173683c543e10646174611c5665633c75383e28bd0120496e7374616e7469617465732061206e657720636f6e74726163742066726f6d207468652060636f646568617368602067656e65726174656420627920607075745f636f6465602c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e009820496e7374616e74696174696f6e20697320657865637574656420617320666f6c6c6f77733a004101202d205468652064657374696e6174696f6e206164647265737320697320636f6d7075746564206261736564206f6e207468652073656e64657220616e642068617368206f662074686520636f64652e0501202d2054686520736d6172742d636f6e7472616374206163636f756e7420697320637265617465642061742074686520636f6d707574656420616464726573732e6d01202d20546865206063746f725f636f64656020697320657865637574656420696e2074686520636f6e74657874206f6620746865206e65776c792d63726561746564206163636f756e742e204275666665722072657475726e65645d0120202061667465722074686520657865637574696f6e206973207361766564206173207468652060636f646560206f6620746865206163636f756e742e205468617420636f64652077696c6c20626520696e766f6b6564a820202075706f6e20616e792063616c6c2072656365697665642062792074686973206163636f756e742e7c202d2054686520636f6e747261637420697320696e697469616c697a65642e3c636c61696d5f73757263686172676508106465737430543a3a4163636f756e744964286175785f73656e646572504f7074696f6e3c543a3a4163636f756e7449643e14710120416c6c6f777320626c6f636b2070726f64756365727320746f20636c61696d206120736d616c6c2072657761726420666f72206576696374696e67206120636f6e74726163742e204966206120626c6f636b2070726f64756365721501206661696c7320746f20646f20736f2c206120726567756c61722075736572732077696c6c20626520616c6c6f77656420746f20636c61696d20746865207265776172642e00390120496620636f6e7472616374206973206e6f742065766963746564206173206120726573756c74206f6620746869732063616c6c2c206e6f20616374696f6e73206172652074616b656e20616e64ac207468652073656e646572206973206e6f7420656c696769626c6520666f7220746865207265776172642e011830496e7374616e74696174656408244163636f756e744964244163636f756e74496404250120436f6e7472616374206465706c6f7965642062792061646472657373206174207468652073706563696669656420616464726573732e205b6f776e65722c20636f6e74726163745d1c4576696374656408244163636f756e74496410626f6f6c1ce420436f6e747261637420686173206265656e206576696374656420616e64206973206e6f7720696e20746f6d6273746f6e652073746174652e58205b636f6e74726163742c20746f6d6273746f6e655d042024202320506172616d73000d01202d2060636f6e7472616374603a20604163636f756e744964603a20546865206163636f756e74204944206f6620746865206576696374656420636f6e74726163742e3501202d2060746f6d6273746f6e65603a2060626f6f6c603a205472756520696620746865206576696374656420636f6e7472616374206c65667420626568696e64206120746f6d6273746f6e652e20526573746f72656410244163636f756e744964244163636f756e74496410486173681c42616c616e636524c020526573746f726174696f6e20666f72206120636f6e747261637420686173206265656e207375636365737366756c2ea4205b646f6e6f722c20646573742c20636f64655f686173682c2072656e745f616c6c6f77616e63655d042024202320506172616d7300f4202d2060646f6e6f72603a20604163636f756e744964603a204163636f756e74204944206f662074686520726573746f72696e6720636f6e7472616374ec202d206064657374603a20604163636f756e744964603a204163636f756e74204944206f662074686520726573746f72656420636f6e7472616374e8202d2060636f64655f68617368603a206048617368603a20436f64652068617368206f662074686520726573746f72656420636f6e74726163741901202d206072656e745f616c6c6f77616e63653a206042616c616e6365603a2052656e7420616c6c6f77616e6365206f662074686520726573746f72656420636f6e747261637428436f646553746f72656404104861736808b820436f646520776974682074686520737065636966696564206861736820686173206265656e2073746f7265642e30205b636f64655f686173685d3c5363686564756c6555706461746564040c75333204c820547269676765726564207768656e207468652063757272656e74205b7363686564756c655d20697320757064617465642e44436f6e7472616374457865637574696f6e08244163636f756e7449641c5665633c75383e08090120416e206576656e74206465706f73697465642075706f6e20657865637574696f6e206f66206120636f6e74726163742066726f6d20746865206163636f756e742e40205b6163636f756e742c20646174615d204c5369676e6564436c61696d48616e646963617038543a3a426c6f636b4e756d626572100200000010e0204e756d626572206f6620626c6f636b2064656c617920616e2065787472696e73696320636c61696d20737572636861726765206861732e000d01205768656e20636c61696d207375726368617267652069732063616c6c656420627920616e2065787472696e736963207468652072656e7420697320636865636b65646820666f722063757272656e745f626c6f636b202d2064656c617940546f6d6273746f6e654465706f7369743042616c616e63654f663c543e4000a0acb903000000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f2067656e6572617465206120746f6d6273746f6e652e4453746f7261676553697a654f66667365740c753332100800000018710120412073697a65206f666673657420666f7220616e20636f6e74726163742e2041206a7573742063726561746564206163636f756e74207769746820756e746f75636865642073746f726167652077696c6c20686176652074686174e0206d756368206f662073746f726167652066726f6d20746865207065727370656374697665206f66207468652073746174652072656e742e006101205468697320697320612073696d706c652077617920746f20656e73757265207468617420636f6e747261637473207769746820656d7074792073746f72616765206576656e7475616c6c79206765742064656c657465646501206279206d616b696e67207468656d207061792072656e742e2054686973206372656174657320616e20696e63656e7469766520746f2072656d6f7665207468656d206561726c7920696e206f7264657220746f2073617665182072656e742e2c52656e74427974654665653042616c616e63654f663c543e4000286bee000000000000000000000000043501205072696365206f6620612062797465206f662073746f7261676520706572206f6e6520626c6f636b20696e74657276616c2e2053686f756c642062652067726561746572207468616e20302e4452656e744465706f7369744f66667365743042616c616e63654f663c543e400010a5d4e800000000000000000000001c05012054686520616d6f756e74206f662066756e6473206120636f6e74726163742073686f756c64206465706f73697420696e206f7264657220746f206f6666736574582074686520636f7374206f66206f6e6520627974652e006901204c6574277320737570706f736520746865206465706f73697420697320312c303030204255202862616c616e636520756e697473292f6279746520616e64207468652072656e7420697320312042552f627974652f6461792c5901207468656e206120636f6e7472616374207769746820312c3030302c3030302042552074686174207573657320312c303030206279746573206f662073746f7261676520776f756c6420706179206e6f2072656e742e4d0120427574206966207468652062616c616e6365207265647563656420746f203530302c30303020425520616e64207468652073746f7261676520737461796564207468652073616d6520617420312c3030302c78207468656e20697420776f756c6420706179203530302042552f6461792e3c5375726368617267655265776172643042616c616e63654f663c543e40005cb2ec22000000000000000000000008e4205265776172642074686174206973207265636569766564206279207468652070617274792077686f736520746f75636820686173206c65646820746f2072656d6f76616c206f66206120636f6e74726163742e204d617844657074680c753332102000000008310120546865206d6178696d756d206e657374696e67206c6576656c206f6620612063616c6c2f696e7374616e746961746520737461636b2e204120726561736f6e61626c652064656661756c74382076616c7565206973203130302e304d617856616c756553697a650c753332100040000004390120546865206d6178696d756d2073697a65206f6620612073746f726167652076616c756520696e2062797465732e204120726561736f6e61626c652064656661756c74206973203136204b69422e4858496e76616c69645363686564756c6556657273696f6e0405012041206e6577207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652063757272656e74206f6e652e54496e76616c6964537572636861726765436c61696d04550120416e206f726967696e206d757374206265207369676e6564206f7220696e686572656e7420616e6420617578696c696172792073656e646572206f6e6c792070726f7669646564206f6e20696e686572656e742e54496e76616c6964536f75726365436f6e747261637404dc2043616e6e6f7420726573746f72652066726f6d206e6f6e6578697374696e67206f7220746f6d6273746f6e6520636f6e74726163742e68496e76616c696444657374696e6174696f6e436f6e747261637404c42043616e6e6f7420726573746f726520746f206e6f6e6578697374696e67206f7220616c69766520636f6e74726163742e40496e76616c6964546f6d6273746f6e65046020546f6d6273746f6e657320646f6e2774206d617463682e54496e76616c6964436f6e74726163744f726967696e04bc20416e206f726967696e20547269654964207772697474656e20696e207468652063757272656e7420626c6f636b2e204f75744f6647617304bc2054686520657865637574656420636f6e7472616374206578686175737465642069747320676173206c696d69742e504f7574707574427566666572546f6f536d616c6c04050120546865206f75747075742062756666657220737570706c69656420746f206120636f6e7472616374204150492063616c6c2077617320746f6f20736d616c6c2e6442656c6f7753756273697374656e63655468726573686f6c6410210120506572666f726d696e672074686520726571756573746564207472616e7366657220776f756c6420686176652062726f756768742074686520636f6e74726163742062656c6f773d01207468652073756273697374656e6365207468726573686f6c642e204e6f207472616e7366657220697320616c6c6f77656420746f20646f207468697320696e206f7264657220746f20616c6c6f77450120666f72206120746f6d6273746f6e6520746f20626520637265617465642e2055736520607365616c5f7465726d696e6174656020746f2072656d6f7665206120636f6e747261637420776974686f757470206c656176696e67206120746f6d6273746f6e6520626568696e642e504e6577436f6e74726163744e6f7446756e64656408390120546865206e65776c79206372656174656420636f6e74726163742069732062656c6f77207468652073756273697374656e6365207468726573686f6c6420616674657220657865637574696e6721012069747320636f6e74727563746f722e204e6f20636f6e7472616374732061726520616c6c6f77656420746f2065786973742062656c6f772074686174207468726573686f6c642e385472616e736665724661696c65640c250120506572666f726d696e672074686520726571756573746564207472616e73666572206661696c656420666f72206120726561736f6e206f726967696e6174696e6720696e2074686531012063686f73656e2063757272656e637920696d706c656d656e746174696f6e206f66207468652072756e74696d652e204d6f73742070726f6261626c79207468652062616c616e63652069738c20746f6f206c6f77206f72206c6f636b732061726520706c61636564206f6e2069742e4c4d617843616c6c44657074685265616368656408250120506572666f726d696e6720612063616c6c207761732064656e6965642062656361757365207468652063616c6c696e67206465707468207265616368656420746865206c696d697498206f6620776861742069732073706563696669656420696e20746865207363686564756c652e2c4e6f7443616c6c61626c650831012054686520636f6e74726163742074686174207761732063616c6c656420697320656974686572206e6f20636f6e747261637420617420616c6c20286120706c61696e206163636f756e74294c206f72206973206120746f6d6273746f6e652e30436f6465546f6f4c617267650455012054686520636f646520737570706c69656420746f20607075745f636f646560206578636565647320746865206c696d69742073706563696669656420696e207468652063757272656e74207363686564756c652e30436f64654e6f74466f756e6404c8204e6f20636f646520636f756c6420626520666f756e642061742074686520737570706c69656420636f646520686173682e2c4f75744f66426f756e6473042901204120627566666572206f757473696465206f662073616e64626f78206d656d6f7279207761732070617373656420746f206120636f6e7472616374204150492066756e6374696f6e2e384465636f64696e674661696c6564042d0120496e7075742070617373656420746f206120636f6e7472616374204150492066756e6374696f6e206661696c656420746f206465636f646520617320657870656374656420747970652e3c436f6e747261637454726170706564048c20436f6e7472616374207472617070656420647572696e6720657865637574696f6e2e105375646f01105375646f040c4b6579010030543a3a4163636f756e74496480000000000000000000000000000000000000000000000000000000000000000004842054686520604163636f756e74496460206f6620746865207375646f206b65792e0110107375646f041063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e2839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e547375646f5f756e636865636b65645f776569676874081063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e1c5f776569676874185765696768742839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e310120546869732066756e6374696f6e20646f6573206e6f7420636865636b2074686520776569676874206f66207468652063616c6c2c20616e6420696e737465616420616c6c6f777320746865b4205375646f207573657220746f20737065636966792074686520776569676874206f66207468652063616c6c2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292ed0202d2054686520776569676874206f6620746869732063616c6c20697320646566696e6564206279207468652063616c6c65722e302023203c2f7765696768743e1c7365745f6b6579040c6e65778c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652475012041757468656e74696361746573207468652063757272656e74207375646f206b657920616e6420736574732074686520676976656e204163636f756e7449642028606e6577602920617320746865206e6577207375646f206b65792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e1c7375646f5f6173080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e2c51012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c207769746820605369676e656460206f726967696e2066726f6d44206120676976656e206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e010c14537564696404384469737061746368526573756c7404842041207375646f206a75737420746f6f6b20706c6163652e205b726573756c745d284b65794368616e67656404244163636f756e74496404f820546865205b7375646f65725d206a757374207377697463686564206964656e746974793b20746865206f6c64206b657920697320737570706c6965642e285375646f4173446f6e650410626f6f6c04842041207375646f206a75737420746f6f6b20706c6163652e205b726573756c745d00042c526571756972655375646f04802053656e646572206d75737420626520746865205375646f206163636f756e7420496d4f6e6c696e650120496d4f6e6c696e6510384865617274626561744166746572010038543a3a426c6f636b4e756d62657210000000001831012054686520626c6f636b206e756d6265722061667465722077686963682069742773206f6b20746f2073656e64206865617274626561747320696e2063757272656e742073657373696f6e2e0011012041742074686520626567696e6e696e67206f6620656163682073657373696f6e20776520736574207468697320746f20612076616c756520746861742073686f756c64d02066616c6c20726f7567686c7920696e20746865206d6964646c65206f66207468652073657373696f6e206475726174696f6e2e010120546865206964656120697320746f206669727374207761697420666f72207468652076616c696461746f727320746f2070726f64756365206120626c6f636b390120696e207468652063757272656e742073657373696f6e2c20736f20746861742074686520686561727462656174206c61746572206f6e2077696c6c206e6f74206265206e65636573736172792e104b65797301004c5665633c543a3a417574686f7269747949643e040004d0205468652063757272656e7420736574206f66206b6579732074686174206d61792069737375652061206865617274626561742e485265636569766564486561727462656174730002053053657373696f6e496e6465782441757468496e6465781c5665633c75383e05040008f020466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206041757468496e6465786020746f8020606f6666636861696e3a3a4f70617175654e6574776f726b5374617465602e38417574686f726564426c6f636b730102053053657373696f6e496e64657838543a3a56616c696461746f7249640c75333205100000000008150120466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f662060543a3a56616c696461746f7249646020746f20746865c8206e756d626572206f6620626c6f636b7320617574686f7265642062792074686520676976656e20617574686f726974792e0104246865617274626561740824686561727462656174644865617274626561743c543a3a426c6f636b4e756d6265723e285f7369676e6174757265bc3c543a3a417574686f7269747949642061732052756e74696d654170705075626c69633e3a3a5369676e6174757265282c2023203c7765696768743e2101202d20436f6d706c65786974793a20604f284b202b20452960207768657265204b206973206c656e677468206f6620604b6579736020616e642045206973206c656e677468206f66b4202020604865617274626561742e6e6574776f726b5f73746174652e65787465726e616c5f6164647265737360008c2020202d20604f284b29603a206465636f64696e67206f66206c656e67746820604b60b02020202d20604f284529603a206465636f64696e672f656e636f64696e67206f66206c656e677468206045603d01202d20446252656164733a2070616c6c65745f73657373696f6e206056616c696461746f7273602c2070616c6c65745f73657373696f6e206043757272656e74496e646578602c20604b657973602c5c202020605265636569766564486561727462656174736084202d2044625772697465733a206052656365697665644865617274626561747360302023203c2f7765696768743e010c444865617274626561745265636569766564042c417574686f72697479496404fc2041206e657720686561727462656174207761732072656365697665642066726f6d2060417574686f72697479496460205b617574686f726974795f69645d1c416c6c476f6f640004d42041742074686520656e64206f66207468652073657373696f6e2c206e6f206f6666656e63652077617320636f6d6d69747465642e2c536f6d654f66666c696e6504605665633c4964656e74696669636174696f6e5475706c653e0435012041742074686520656e64206f66207468652073657373696f6e2c206174206c65617374206f6e652076616c696461746f722077617320666f756e6420746f206265205b6f66666c696e655d2e000828496e76616c69644b65790464204e6f6e206578697374656e74207075626c6963206b65792e4c4475706c6963617465644865617274626561740458204475706c696361746564206865617274626561742e48417574686f72697479446973636f76657279000100000000204f6666656e63657301204f6666656e636573101c5265706f727473000105345265706f727449644f663c543ed04f6666656e636544657461696c733c543a3a4163636f756e7449642c20543a3a4964656e74696669636174696f6e5475706c653e00040004490120546865207072696d61727920737472756374757265207468617420686f6c647320616c6c206f6666656e6365207265636f726473206b65796564206279207265706f7274206964656e746966696572732e4044656665727265644f6666656e6365730100645665633c44656665727265644f6666656e63654f663c543e3e0400086501204465666572726564207265706f72747320746861742068617665206265656e2072656a656374656420627920746865206f6666656e63652068616e646c657220616e64206e65656420746f206265207375626d6974746564442061742061206c617465722074696d652e58436f6e63757272656e745265706f727473496e646578010205104b696e64384f706171756554696d65536c6f74485665633c5265706f727449644f663c543e3e050400042901204120766563746f72206f66207265706f727473206f66207468652073616d65206b696e6420746861742068617070656e6564206174207468652073616d652074696d6520736c6f742e485265706f72747342794b696e64496e646578010105104b696e641c5665633c75383e00040018110120456e756d65726174657320616c6c207265706f727473206f662061206b696e6420616c6f6e672077697468207468652074696d6520746865792068617070656e65642e00bc20416c6c207265706f7274732061726520736f72746564206279207468652074696d65206f66206f6666656e63652e004901204e6f74652074686174207468652061637475616c2074797065206f662074686973206d617070696e6720697320605665633c75383e602c207468697320697320626563617573652076616c756573206f66690120646966666572656e7420747970657320617265206e6f7420737570706f7274656420617420746865206d6f6d656e7420736f2077652061726520646f696e6720746865206d616e75616c2073657269616c697a6174696f6e2e010001041c4f6666656e63650c104b696e64384f706171756554696d65536c6f7410626f6f6c10550120546865726520697320616e206f6666656e6365207265706f72746564206f662074686520676976656e20606b696e64602068617070656e656420617420746865206073657373696f6e5f696e6465786020616e644d0120286b696e642d7370656369666963292074696d6520736c6f742e2054686973206576656e74206973206e6f74206465706f736974656420666f72206475706c696361746520736c61736865732e206c6173741d0120656c656d656e7420696e64696361746573206f6620746865206f6666656e636520776173206170706c69656420287472756529206f7220717565756564202866616c736529206c205b6b696e642c2074696d65736c6f742c206170706c6965645d2e000028486973746f726963616c00000000006052616e646f6d6e657373436f6c6c656374697665466c6970016052616e646f6d6e657373436f6c6c656374697665466c6970043852616e646f6d4d6174657269616c0100305665633c543a3a486173683e04000c610120536572696573206f6620626c6f636b20686561646572732066726f6d20746865206c61737420383120626c6f636b73207468617420616374732061732072616e646f6d2073656564206d6174657269616c2e2054686973610120697320617272616e67656420617320612072696e672062756666657220776974682060626c6f636b5f6e756d626572202520383160206265696e672074686520696e64657820696e746f20746865206056656360206f664420746865206f6c6465737420686173682e0100000000204964656e7469747901204964656e7469747910284964656e746974794f6600010530543a3a4163636f756e74496468526567697374726174696f6e3c42616c616e63654f663c543e3e0004000c210120496e666f726d6174696f6e20746861742069732070657274696e656e7420746f206964656e746966792074686520656e7469747920626568696e6420616e206163636f756e742e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e1c53757065724f6600010230543a3a4163636f756e7449645028543a3a4163636f756e7449642c204461746129000400086101205468652073757065722d6964656e74697479206f6620616e20616c7465726e6174697665202273756222206964656e7469747920746f676574686572207769746820697473206e616d652c2077697468696e2074686174510120636f6e746578742e20496620746865206163636f756e74206973206e6f7420736f6d65206f74686572206163636f756e742773207375622d6964656e746974792c207468656e206a75737420604e6f6e65602e18537562734f6601010530543a3a4163636f756e744964842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e290044000000000000000000000000000000000014b820416c7465726e6174697665202273756222206964656e746974696573206f662074686973206163636f756e742e001d0120546865206669727374206974656d20697320746865206465706f7369742c20746865207365636f6e64206973206120766563746f72206f6620746865206163636f756e74732e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e28526567697374726172730100d85665633c4f7074696f6e3c526567697374726172496e666f3c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e3e0400104d012054686520736574206f6620726567697374726172732e204e6f7420657870656374656420746f206765742076657279206269672061732063616e206f6e6c79206265206164646564207468726f7567682061a8207370656369616c206f726967696e20286c696b656c79206120636f756e63696c206d6f74696f6e292e0029012054686520696e64657820696e746f20746869732063616e206265206361737420746f2060526567697374726172496e6465786020746f2067657420612076616c69642076616c75652e013c346164645f726567697374726172041c6163636f756e7430543a3a4163636f756e744964347c2041646420612072656769737472617220746f207468652073797374656d2e00010120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060543a3a5265676973747261724f726967696e602e00ac202d20606163636f756e74603a20746865206163636f756e74206f6620746865207265676973747261722e009820456d6974732060526567697374726172416464656460206966207375636365737366756c2e002c2023203c7765696768743e2901202d20604f2852296020776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e64656420616e6420636f64652d626f756e646564292e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e307365745f6964656e746974790410696e666f304964656e74697479496e666f4c2d012053657420616e206163636f756e742773206964656e7469747920696e666f726d6174696f6e20616e6420726573657276652074686520617070726f707269617465206465706f7369742e00590120496620746865206163636f756e7420616c726561647920686173206964656e7469747920696e666f726d6174696f6e2c20746865206465706f7369742069732074616b656e2061732070617274207061796d656e745420666f7220746865206e6577206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0090202d2060696e666f603a20546865206964656e7469747920696e666f726d6174696f6e2e008c20456d69747320604964656e7469747953657460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2858202b205827202b2052296021012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e64656429e42020202d20776865726520605260206a756467656d656e74732d636f756e7420287265676973747261722d636f756e742d626f756e6465642984202d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e2501202d204f6e652073746f72616765206d75746174696f6e2028636f6465632d7265616420604f285827202b205229602c20636f6465632d777269746520604f2858202b20522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e207365745f73756273041073756273645665633c28543a3a4163636f756e7449642c2044617461293e54902053657420746865207375622d6163636f756e7473206f66207468652073656e6465722e005901205061796d656e743a20416e79206167677265676174652062616c616e63652072657365727665642062792070726576696f757320607365745f73756273602063616c6c732077696c6c2062652072657475726e6564310120616e6420616e20616d6f756e7420605375624163636f756e744465706f736974602077696c6c20626520726573657276656420666f722065616368206974656d20696e206073756273602e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e00b4202d206073756273603a20546865206964656e74697479277320286e657729207375622d6163636f756e74732e002c2023203c7765696768743e34202d20604f2850202b20532960e82020202d20776865726520605060206f6c642d737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e88202d204174206d6f7374206f6e652062616c616e6365206f7065726174696f6e732e18202d2044423ae02020202d206050202b2053602073746f72616765206d75746174696f6e732028636f64656320636f6d706c657869747920604f2831296029c02020202d204f6e652073746f7261676520726561642028636f64656320636f6d706c657869747920604f28502960292ec42020202d204f6e652073746f726167652077726974652028636f64656320636f6d706c657869747920604f28532960292ed42020202d204f6e652073746f726167652d6578697374732028604964656e746974794f663a3a636f6e7461696e735f6b657960292e302023203c2f7765696768743e38636c6561725f6964656e7469747900483d0120436c65617220616e206163636f756e742773206964656e7469747920696e666f20616e6420616c6c207375622d6163636f756e747320616e642072657475726e20616c6c206465706f736974732e00f0205061796d656e743a20416c6c2072657365727665642062616c616e636573206f6e20746865206163636f756e74206172652072657475726e65642e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e009c20456d69747320604964656e74697479436c656172656460206966207375636365737366756c2e002c2023203c7765696768743e44202d20604f2852202b2053202b20582960d02020202d20776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e25012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e646564292e8c202d204f6e652062616c616e63652d756e72657365727665206f7065726174696f6e2ecc202d206032602073746f7261676520726561647320616e64206053202b2032602073746f726167652064656c6574696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e44726571756573745f6a756467656d656e7408247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e1c6d61785f66656554436f6d706163743c42616c616e63654f663c543e3e5c9820526571756573742061206a756467656d656e742066726f6d2061207265676973747261722e005901205061796d656e743a204174206d6f737420606d61785f666565602077696c6c20626520726573657276656420666f72207061796d656e7420746f2074686520726567697374726172206966206a756467656d656e741c20676976656e2e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e002101202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973207265717565737465642e5901202d20606d61785f666565603a20546865206d6178696d756d206665652074686174206d617920626520706169642e20546869732073686f756c64206a757374206265206175746f2d706f70756c617465642061733a0034206060606e6f636f6d70696c65bc2053656c663a3a7265676973747261727328292e676574287265675f696e646578292e756e7772617028292e666565102060606000a820456d69747320604a756467656d656e7452657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2858202b205229602e34202d204f6e65206576656e742e302023203c2f7765696768743e3863616e63656c5f7265717565737404247265675f696e64657838526567697374726172496e646578446c2043616e63656c20612070726576696f757320726571756573742e00fc205061796d656e743a20412070726576696f75736c79207265736572766564206465706f7369742069732072657475726e6564206f6e20737563636573732e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e004901202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206e6f206c6f6e676572207265717565737465642e00b020456d69747320604a756467656d656e74556e72657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e8c202d204f6e652073746f72616765206d75746174696f6e20604f2852202b205829602e30202d204f6e65206576656e74302023203c2f7765696768743e1c7365745f6665650814696e6465785c436f6d706163743c526567697374726172496e6465783e0c66656554436f6d706163743c42616c616e63654f663c543e3e341d0120536574207468652066656520726571756972656420666f722061206a756467656d656e7420746f206265207265717565737465642066726f6d2061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e58202d2060666565603a20746865206e6577206665652e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e333135202b2052202a20302e33323920c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e387365745f6163636f756e745f69640814696e6465785c436f6d706163743c526567697374726172496e6465783e0c6e657730543a3a4163636f756e74496434c0204368616e676520746865206163636f756e74206173736f63696174656420776974682061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e74202d20606e6577603a20746865206e6577206163636f756e742049442e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee4202d2042656e63686d61726b3a20382e383233202b2052202a20302e333220c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e287365745f6669656c64730814696e6465785c436f6d706163743c526567697374726172496e6465783e186669656c6473384964656e746974794669656c647334ac2053657420746865206669656c6420696e666f726d6174696f6e20666f722061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e1101202d20606669656c6473603a20746865206669656c64732074686174207468652072656769737472617220636f6e6365726e73207468656d73656c76657320776974682e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e343634202b2052202a20302e33323520c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e4470726f766964655f6a756467656d656e740c247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365246a756467656d656e745c4a756467656d656e743c42616c616e63654f663c543e3e4cbc2050726f766964652061206a756467656d656e7420666f7220616e206163636f756e742773206964656e746974792e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74b4206f6620746865207265676973747261722077686f736520696e64657820697320607265675f696e646578602e002501202d20607265675f696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206265696e67206d6164652e5901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e4d01202d20606a756467656d656e74603a20746865206a756467656d656e74206f662074686520726567697374726172206f6620696e64657820607265675f696e646578602061626f75742060746172676574602e009820456d69747320604a756467656d656e74476976656e60206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e88202d204f6e652062616c616e63652d7472616e73666572206f7065726174696f6e2e98202d20557020746f206f6e65206163636f756e742d6c6f6f6b7570206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2852202b205829602e34202d204f6e65206576656e742e302023203c2f7765696768743e346b696c6c5f6964656e7469747904187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654c45012052656d6f766520616e206163636f756e742773206964656e7469747920616e64207375622d6163636f756e7420696e666f726d6174696f6e20616e6420736c61736820746865206465706f736974732e006501205061796d656e743a2052657365727665642062616c616e6365732066726f6d20607365745f737562736020616e6420607365745f6964656e74697479602061726520736c617368656420616e642068616e646c656420627949012060536c617368602e20566572696669636174696f6e2072657175657374206465706f7369747320617265206e6f742072657475726e65643b20746865792073686f756c642062652063616e63656c6c656484206d616e75616c6c79207573696e67206063616e63656c5f72657175657374602e00fc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206d617463682060543a3a466f7263654f726967696e602e005901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e009820456d69747320604964656e746974794b696c6c656460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2852202b2053202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e74202d206053202b2032602073746f72616765206d75746174696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e1c6164645f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365106461746110446174611cb0204164642074686520676976656e206163636f756e7420746f207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656e616d655f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651064617461104461746110d020416c74657220746865206173736f636961746564206e616d65206f662074686520676976656e207375622d6163636f756e742e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656d6f76655f737562040c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651cc42052656d6f76652074686520676976656e206163636f756e742066726f6d207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e20717569745f7375620028902052656d6f7665207468652073656e6465722061732061207375622d6163636f756e742e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c206265207265706174726961746564b820746f207468652073656e64657220282a6e6f742a20746865206f726967696e616c206465706f7369746f72292e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206861766520612072656769737465726564402073757065722d6964656e746974792e004901204e4f54453a20546869732073686f756c64206e6f74206e6f726d616c6c7920626520757365642c206275742069732070726f766964656420696e207468652063617365207468617420746865206e6f6e2d150120636f6e74726f6c6c6572206f6620616e206163636f756e74206973206d616c6963696f75736c7920726567697374657265642061732061207375622d6163636f756e742e01282c4964656e7469747953657404244163636f756e7449640409012041206e616d652077617320736574206f72207265736574202877686963682077696c6c2072656d6f766520616c6c206a756467656d656e7473292e205b77686f5d3c4964656e74697479436c656172656408244163636f756e7449641c42616c616e6365040d012041206e616d652077617320636c65617265642c20616e642074686520676976656e2062616c616e63652072657475726e65642e205b77686f2c206465706f7369745d384964656e746974794b696c6c656408244163636f756e7449641c42616c616e63650405012041206e616d65207761732072656d6f76656420616e642074686520676976656e2062616c616e636520736c61736865642e205b77686f2c206465706f7369745d484a756467656d656e7452657175657374656408244163636f756e74496438526567697374726172496e64657804fc2041206a756467656d656e74207761732061736b65642066726f6d2061207265676973747261722e205b77686f2c207265676973747261725f696e6465785d504a756467656d656e74556e72657175657374656408244163636f756e74496438526567697374726172496e64657804e82041206a756467656d656e74207265717565737420776173207265747261637465642e205b77686f2c207265676973747261725f696e6465785d384a756467656d656e74476976656e08244163636f756e74496438526567697374726172496e6465780401012041206a756467656d656e742077617320676976656e2062792061207265676973747261722e205b7461726765742c207265676973747261725f696e6465785d3852656769737472617241646465640438526567697374726172496e64657804a4204120726567697374726172207761732061646465642e205b7265676973747261725f696e6465785d405375624964656e7469747941646465640c244163636f756e744964244163636f756e7449641c42616c616e6365044d012041207375622d6964656e746974792077617320616464656420746f20616e206964656e7469747920616e6420746865206465706f73697420706169642e205b7375622c206d61696e2c206465706f7369745d485375624964656e7469747952656d6f7665640c244163636f756e744964244163636f756e7449641c42616c616e6365080d012041207375622d6964656e74697479207761732072656d6f7665642066726f6d20616e206964656e7469747920616e6420746865206465706f7369742066726565642e54205b7375622c206d61696e2c206465706f7369745d485375624964656e746974795265766f6b65640c244163636f756e744964244163636f756e7449641c42616c616e6365081d012041207375622d6964656e746974792077617320636c65617265642c20616e642074686520676976656e206465706f7369742072657061747269617465642066726f6d207468652101206d61696e206964656e74697479206163636f756e7420746f20746865207375622d6964656e74697479206163636f756e742e205b7375622c206d61696e2c206465706f7369745d183042617369634465706f7369743042616c616e63654f663c543e400080c6a47e8d0300000000000000000004d82054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564206964656e746974792e304669656c644465706f7369743042616c616e63654f663c543e4000a031a95fe300000000000000000000042d012054686520616d6f756e742068656c64206f6e206465706f73697420706572206164646974696f6e616c206669656c6420666f7220612072656769737465726564206964656e746974792e445375624163636f756e744465706f7369743042616c616e63654f663c543e400080f420e6b5000000000000000000000c65012054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564207375626163636f756e742e20546869732073686f756c64206163636f756e7420666f7220746865206661637471012074686174206f6e652073746f72616765206974656d27732076616c75652077696c6c20696e637265617365206279207468652073697a65206f6620616e206163636f756e742049442c20616e642074686572652077696c6c206265290120616e6f746865722074726965206974656d2077686f73652076616c7565206973207468652073697a65206f6620616e206163636f756e7420494420706c75732033322062797465732e384d61785375624163636f756e74730c7533321064000000040d0120546865206d6178696d756d206e756d626572206f66207375622d6163636f756e747320616c6c6f77656420706572206964656e746966696564206163636f756e742e4c4d61784164646974696f6e616c4669656c64730c7533321064000000086501204d6178696d756d206e756d626572206f66206164646974696f6e616c206669656c64732074686174206d61792062652073746f72656420696e20616e2049442e204e656564656420746f20626f756e642074686520492f4fe020726571756972656420746f2061636365737320616e206964656e746974792c206275742063616e2062652070726574747920686967682e344d6178526567697374726172730c7533321014000000085101204d61786d696d756d206e756d626572206f66207265676973747261727320616c6c6f77656420696e207468652073797374656d2e204e656564656420746f20626f756e642074686520636f6d706c65786974797c206f662c20652e672e2c207570646174696e67206a756467656d656e74732e4048546f6f4d616e795375624163636f756e7473046020546f6f206d616e7920737562732d6163636f756e74732e204e6f74466f756e640454204163636f756e742069736e277420666f756e642e204e6f744e616d65640454204163636f756e742069736e2774206e616d65642e28456d707479496e646578043420456d70747920696e6465782e284665654368616e676564044020466565206973206368616e6765642e284e6f4964656e74697479044c204e6f206964656e7469747920666f756e642e3c537469636b794a756467656d656e74044820537469636b79206a756467656d656e742e384a756467656d656e74476976656e0444204a756467656d656e7420676976656e2e40496e76616c69644a756467656d656e74044c20496e76616c6964206a756467656d656e742e30496e76616c6964496e64657804582054686520696e64657820697320696e76616c69642e34496e76616c6964546172676574045c205468652074617267657420697320696e76616c69642e34546f6f4d616e794669656c6473047020546f6f206d616e79206164646974696f6e616c206669656c64732e44546f6f4d616e795265676973747261727304ec204d6178696d756d20616d6f756e74206f66207265676973747261727320726561636865642e2043616e6e6f742061646420616e79206d6f72652e38416c7265616479436c61696d65640474204163636f756e7420494420697320616c7265616479206e616d65642e184e6f7453756204742053656e646572206973206e6f742061207375622d6163636f756e742e204e6f744f776e6564048c205375622d6163636f756e742069736e2774206f776e65642062792073656e6465722e1c536f6369657479011c536f6369657479401c466f756e646572000030543a3a4163636f756e7449640400044820546865206669727374206d656d6265722e1452756c657300001c543a3a48617368040008510120412068617368206f66207468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e2043616e206f6e6c7920626520736574206f6e636520616e6454206f6e6c792062792074686520666f756e6465722e2843616e6469646174657301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e0400043901205468652063757272656e7420736574206f662063616e646964617465733b206269646465727320746861742061726520617474656d7074696e6720746f206265636f6d65206d656d626572732e4c53757370656e64656443616e6469646174657300010530543a3a4163636f756e744964e42842616c616e63654f663c542c20493e2c204269644b696e643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e2900040004842054686520736574206f662073757370656e6465642063616e646964617465732e0c506f7401003c42616c616e63654f663c542c20493e400000000000000000000000000000000004410120416d6f756e74206f66206f7572206163636f756e742062616c616e63652074686174206973207370656369666963616c6c7920666f7220746865206e65787420726f756e642773206269642873292e1048656164000030543a3a4163636f756e744964040004e820546865206d6f7374207072696d6172792066726f6d20746865206d6f737420726563656e746c7920617070726f766564206d656d626572732e1c4d656d626572730100445665633c543a3a4163636f756e7449643e04000494205468652063757272656e7420736574206f66206d656d626572732c206f7264657265642e4053757370656e6465644d656d6265727301010530543a3a4163636f756e74496410626f6f6c00040004782054686520736574206f662073757370656e646564206d656d626572732e104269647301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e040004e8205468652063757272656e7420626964732c2073746f726564206f726465726564206279207468652076616c7565206f6620746865206269642e20566f756368696e6700010530543a3a4163636f756e74496438566f756368696e6753746174757300040004e4204d656d626572732063757272656e746c7920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e1c5061796f75747301010530543a3a4163636f756e744964985665633c28543a3a426c6f636b4e756d6265722c2042616c616e63654f663c542c20493e293e000400044d012050656e64696e67207061796f7574733b206f72646572656420627920626c6f636b206e756d6265722c20776974682074686520616d6f756e7420746861742073686f756c642062652070616964206f75742e1c537472696b657301010530543a3a4163636f756e7449642c537472696b65436f756e7400100000000004dc20546865206f6e676f696e67206e756d626572206f66206c6f73696e6720766f746573206361737420627920746865206d656d6265722e14566f74657300020530543a3a4163636f756e74496430543a3a4163636f756e74496410566f746505040004d020446f75626c65206d61702066726f6d2043616e646964617465202d3e20566f746572202d3e20284d617962652920566f74652e20446566656e646572000030543a3a4163636f756e744964040004c42054686520646566656e64696e67206d656d6265722063757272656e746c79206265696e67206368616c6c656e6765642e34446566656e646572566f74657300010530543a3a4163636f756e74496410566f7465000400046020566f74657320666f722074686520646566656e6465722e284d61784d656d6265727301000c753332100000000004dc20546865206d6178206e756d626572206f66206d656d6265727320666f722074686520736f6369657479206174206f6e652074696d652e01300c626964041476616c75653c42616c616e63654f663c542c20493e84e020412075736572206f757473696465206f662074686520736f63696574792063616e206d616b6520612062696420666f7220656e7472792e003901205061796d656e743a206043616e6469646174654465706f736974602077696c6c20626520726573657276656420666f72206d616b696e672061206269642e2049742069732072657475726e6564f0207768656e2074686520626964206265636f6d65732061206d656d6265722c206f7220696620746865206269642063616c6c732060756e626964602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a5901202d206076616c7565603a2041206f6e652074696d65207061796d656e74207468652062696420776f756c64206c696b6520746f2072656365697665207768656e206a6f696e696e672074686520736f63696574792e002c2023203c7765696768743e5501204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520726573657276652944202d2053746f726167652052656164733aec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f284329c820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d2948202d2053746f72616765205772697465733a810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3a2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6820092d204f6e65206576656e7420666f72206e6577206269642efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e14756e626964040c706f730c7533324cd82041206269646465722063616e2072656d6f76652074686569722062696420666f7220656e74727920696e746f20736f63696574792e010120427920646f696e6720736f2c20746865792077696c6c20686176652074686569722063616e646964617465206465706f7369742072657475726e6564206f728420746865792077696c6c20756e766f75636820746865697220766f75636865722e00fc205061796d656e743a2054686520626964206465706f73697420697320756e7265736572766564206966207468652075736572206d6164652061206269642e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206269646465722e003020506172616d65746572733a1901202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2077616e747320746f20756e6269642e002c2023203c7765696768743eb0204b65793a204220286c656e206f662062696473292c2058202862616c616e636520756e72657365727665290d01202d204f6e652073746f72616765207265616420616e6420777269746520746f20726574726965766520616e64207570646174652074686520626964732e204f2842294501202d20456974686572206f6e6520756e726573657276652062616c616e636520616374696f6e204f285829206f72206f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2842202b205829302023203c2f7765696768743e14766f7563680c0c77686f30543a3a4163636f756e7449641476616c75653c42616c616e63654f663c542c20493e0c7469703c42616c616e63654f663c542c20493eb045012041732061206d656d6265722c20766f75636820666f7220736f6d656f6e6520746f206a6f696e20736f636965747920627920706c6163696e67206120626964206f6e20746865697220626568616c662e005501205468657265206973206e6f206465706f73697420726571756972656420746f20766f75636820666f722061206e6577206269642c206275742061206d656d6265722063616e206f6e6c7920766f75636820666f725d01206f6e652062696420617420612074696d652e2049662074686520626964206265636f6d657320612073757370656e6465642063616e64696461746520616e6420756c74696d6174656c792072656a65637465642062794101207468652073757370656e73696f6e206a756467656d656e74206f726967696e2c20746865206d656d6265722077696c6c2062652062616e6e65642066726f6d20766f756368696e6720616761696e2e005901204173206120766f756368696e67206d656d6265722c20796f752063616e20636c61696d206120746970206966207468652063616e6469646174652069732061636365707465642e2054686973207469702077696c6c51012062652070616964206173206120706f7274696f6e206f66207468652072657761726420746865206d656d6265722077696c6c207265636569766520666f72206a6f696e696e672074686520736f63696574792e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733acc202d206077686f603a2054686520757365722077686f20796f7520776f756c64206c696b6520746f20766f75636820666f722e5101202d206076616c7565603a2054686520746f74616c2072657761726420746f2062652070616964206265747765656e20796f7520616e64207468652063616e6469646174652069662074686579206265636f6d65642061206d656d62657220696e2074686520736f63696574792e4901202d2060746970603a20596f757220637574206f662074686520746f74616c206076616c756560207061796f7574207768656e207468652063616e64696461746520697320696e64756374656420696e746f15012074686520736f63696574792e2054697073206c6172676572207468616e206076616c7565602077696c6c206265207361747572617465642075706f6e207061796f75742e002c2023203c7765696768743e0101204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d626572732944202d2053746f726167652052656164733ac820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d29090120092d204f6e652073746f72616765207265616420746f20636865636b206d656d626572206973206e6f7420616c726561647920766f756368696e672e204f283129ec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f28432948202d2053746f72616765205772697465733a0d0120092d204f6e652073746f7261676520777269746520746f20696e7365727420766f756368696e672073746174757320746f20746865206d656d6265722e204f283129810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3ac020092d204f286c6f67204d292073656172636820746f20636865636b2073656e6465722069732061206d656d6265722e2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6020092d204f6e65206576656e7420666f7220766f7563682efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e1c756e766f756368040c706f730c753332442d01204173206120766f756368696e67206d656d6265722c20756e766f7563682061206269642e2054686973206f6e6c7920776f726b73207768696c6520766f7563686564207573657220697394206f6e6c792061206269646465722028616e64206e6f7420612063616e646964617465292e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206120766f756368696e67206d656d6265722e003020506172616d65746572733a2d01202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2073686f756c6420626520756e766f75636865642e002c2023203c7765696768743e54204b65793a204220286c656e206f662062696473290901202d204f6e652073746f726167652072656164204f28312920746f20636865636b20746865207369676e6572206973206120766f756368696e67206d656d6265722eec202d204f6e652073746f72616765206d757461746520746f20726574726965766520616e64207570646174652074686520626964732e204f28422994202d204f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f284229302023203c2f7765696768743e10766f7465082463616e6469646174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c617070726f766510626f6f6c4c882041732061206d656d6265722c20766f7465206f6e20612063616e6469646174652e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733a0d01202d206063616e646964617465603a205468652063616e646964617465207468617420746865206d656d62657220776f756c64206c696b6520746f20626964206f6e2ef4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265d82020202020202020202020202020617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743ebc204b65793a204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722e58202d204f6e65206163636f756e74206c6f6f6b75702e2d01202d204f6e652073746f726167652072656164204f28432920616e64204f2843292073656172636820746f20636865636b2074686174207573657220697320612063616e6469646174652ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204329302023203c2f7765696768743e34646566656e6465725f766f7465041c617070726f766510626f6f6c408c2041732061206d656d6265722c20766f7465206f6e2074686520646566656e6465722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733af4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265a420617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743e68202d204b65793a204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e007820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d29302023203c2f7765696768743e187061796f757400504501205472616e7366657220746865206669727374206d617475726564207061796f757420666f72207468652073656e64657220616e642072656d6f76652069742066726f6d20746865207265636f7264732e006901204e4f54453a20546869732065787472696e736963206e6565647320746f2062652063616c6c6564206d756c7469706c652074696d657320746f20636c61696d206d756c7469706c65206d617475726564207061796f7574732e002101205061796d656e743a20546865206d656d6265722077696c6c20726563656976652061207061796d656e7420657175616c20746f207468656972206669727374206d61747572656478207061796f757420746f20746865697220667265652062616c616e63652e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d62657220776974684c207061796f7574732072656d61696e696e672e002c2023203c7765696768743e1d01204b65793a204d20286c656e206f66206d656d62657273292c205020286e756d626572206f66207061796f75747320666f72206120706172746963756c6172206d656d626572292501202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b207369676e65722069732061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28502920746f2067657420616c6c207061796f75747320666f722061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28312920746f20676574207468652063757272656e7420626c6f636b206e756d6265722e8c202d204f6e652063757272656e6379207472616e736665722063616c6c2e204f2858291101202d204f6e652073746f72616765207772697465206f722072656d6f76616c20746f2075706461746520746865206d656d6265722773207061796f7574732e204f285029009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2050202b205829302023203c2f7765696768743e14666f756e640c1c666f756e64657230543a3a4163636f756e7449642c6d61785f6d656d626572730c7533321472756c65731c5665633c75383e4c4c20466f756e642074686520736f63696574792e00f0205468697320697320646f6e65206173206120646973637265746520616374696f6e20696e206f7264657220746f20616c6c6f7720666f72207468651901206d6f64756c6520746f20626520696e636c7564656420696e746f20612072756e6e696e6720636861696e20616e642063616e206f6e6c7920626520646f6e65206f6e63652e001d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f466f756e6465725365744f726967696e5f2e003020506172616d65746572733a1901202d2060666f756e64657260202d20546865206669727374206d656d62657220616e642068656164206f6620746865206e65776c7920666f756e64656420736f63696574792e1501202d20606d61785f6d656d6265727360202d2054686520696e697469616c206d6178206e756d626572206f66206d656d6265727320666f722074686520736f63696574792ef4202d206072756c657360202d205468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e002c2023203c7765696768743ee0202d2054776f2073746f72616765206d75746174657320746f207365742060486561646020616e642060466f756e646572602e204f283129f4202d204f6e652073746f7261676520777269746520746f2061646420746865206669727374206d656d62657220746f20736f63696574792e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e1c756e666f756e6400348c20416e6e756c2074686520666f756e64696e67206f662074686520736f63696574792e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205369676e65642c20616e6420746865207369676e696e67206163636f756e74206d75737420626520626f74685901207468652060466f756e6465726020616e6420746865206048656164602e205468697320696d706c6965732074686174206974206d6179206f6e6c7920626520646f6e65207768656e207468657265206973206f6e6520206d656d6265722e002c2023203c7765696768743e68202d2054776f2073746f72616765207265616473204f2831292e78202d20466f75722073746f726167652072656d6f76616c73204f2831292e34202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e586a756467655f73757370656e6465645f6d656d626572080c77686f30543a3a4163636f756e7449641c666f726769766510626f6f6c6c2d0120416c6c6f772073757370656e73696f6e206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e646564206d656d6265722e00590120496620612073757370656e646564206d656d62657220697320666f72676976656e2c2077652073696d706c7920616464207468656d206261636b2061732061206d656d6265722c206e6f7420616666656374696e67cc20616e79206f6620746865206578697374696e672073746f72616765206974656d7320666f722074686174206d656d6265722e00490120496620612073757370656e646564206d656d6265722069732072656a65637465642c2072656d6f766520616c6c206173736f6369617465642073746f72616765206974656d732c20696e636c7564696e670101207468656972207061796f7574732c20616e642072656d6f766520616e7920766f7563686564206269647320746865792063757272656e746c7920686176652e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ab4202d206077686f60202d205468652073757370656e646564206d656d62657220746f206265206a75646765642e3501202d2060666f726769766560202d204120626f6f6c65616e20726570726573656e74696e672077686574686572207468652073757370656e73696f6e206a756467656d656e74206f726967696e2501202020202020202020202020202020666f726769766573202860747275656029206f722072656a6563747320286066616c7365602920612073757370656e646564206d656d6265722e002c2023203c7765696768743ea4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d6265727329f8202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e646564206d656d6265722e204f2831297101202d20557020746f206f6e652073746f72616765207772697465204f284d292077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d626572206261636b20746f20736f63696574792ef8202d20557020746f20332073746f726167652072656d6f76616c73204f28312920746f20636c65616e20757020612072656d6f766564206d656d6265722e4501202d20557020746f206f6e652073746f72616765207772697465204f2842292077697468204f2842292073656172636820746f2072656d6f766520766f7563686564206269642066726f6d20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e70202d204f6e652073746f726167652072656d6f76616c2e204f2831297c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204229302023203c2f7765696768743e646a756467655f73757370656e6465645f63616e646964617465080c77686f30543a3a4163636f756e744964246a756467656d656e74244a756467656d656e74a0350120416c6c6f772073757370656e646564206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e6465642063616e6469646174652e005d0120496620746865206a756467656d656e742069732060417070726f7665602c20776520616464207468656d20746f20736f63696574792061732061206d656d62657220776974682074686520617070726f70726961746574207061796d656e7420666f72206a6f696e696e6720736f63696574792e00550120496620746865206a756467656d656e74206973206052656a656374602c2077652065697468657220736c61736820746865206465706f736974206f6620746865206269642c20676976696e67206974206261636b110120746f2074686520736f63696574792074726561737572792c206f722077652062616e2074686520766f75636865722066726f6d20766f756368696e6720616761696e2e005d0120496620746865206a756467656d656e7420697320605265626964602c20776520707574207468652063616e646964617465206261636b20696e207468652062696420706f6f6c20616e64206c6574207468656d20676f94207468726f7567682074686520696e64756374696f6e2070726f6365737320616761696e2e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ac0202d206077686f60202d205468652073757370656e6465642063616e64696461746520746f206265206a75646765642ec4202d20606a756467656d656e7460202d2060417070726f7665602c206052656a656374602c206f7220605265626964602e002c2023203c7765696768743ef4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520616374696f6e29f0202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e6465642063616e6469646174652ec8202d204f6e652073746f726167652072656d6f76616c206f66207468652073757370656e6465642063616e6469646174652e40202d20417070726f7665204c6f676963150120092d204f6e652073746f72616765207265616420746f206765742074686520617661696c61626c6520706f7420746f2070617920757365727320776974682e204f283129dc20092d204f6e652073746f7261676520777269746520746f207570646174652074686520617661696c61626c6520706f742e204f283129e820092d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f283129b420092d204f6e652073746f72616765207265616420746f2067657420616c6c206d656d626572732e204f284d29a020092d20557020746f206f6e6520756e726573657276652063757272656e637920616374696f6e2eb020092d20557020746f2074776f206e65772073746f726167652077726974657320746f207061796f7574732e4d0120092d20557020746f206f6e652073746f726167652077726974652077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d62657220746f20736f63696574792e3c202d2052656a656374204c6f676963dc20092d20557020746f206f6e6520726570617472696174652072657365727665642063757272656e637920616374696f6e2e204f2858292d0120092d20557020746f206f6e652073746f7261676520777269746520746f2062616e2074686520766f756368696e67206d656d6265722066726f6d20766f756368696e6720616761696e2e38202d205265626964204c6f676963410120092d2053746f72616765206d75746174652077697468204f286c6f672042292062696e6172792073656172636820746f20706c616365207468652075736572206261636b20696e746f20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e5c202d204f6e652073746f726167652072656d6f76616c2e7c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2042202b205829302023203c2f7765696768743e3c7365745f6d61785f6d656d62657273040c6d61780c753332381d0120416c6c6f777320726f6f74206f726967696e20746f206368616e676520746865206d6178696d756d206e756d626572206f66206d656d6265727320696e20736f63696574792eb4204d6178206d656d6265727368697020636f756e74206d7573742062652067726561746572207468616e20312e00dc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d205f524f4f545f2e003020506172616d65746572733ae4202d20606d617860202d20546865206d6178696d756d206e756d626572206f66206d656d6265727320666f722074686520736f63696574792e002c2023203c7765696768743eb0202d204f6e652073746f7261676520777269746520746f2075706461746520746865206d61782e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e01401c466f756e64656404244163636f756e74496404e02054686520736f636965747920697320666f756e6465642062792074686520676976656e206964656e746974792e205b666f756e6465725d0c42696408244163636f756e7449641c42616c616e63650861012041206d656d6265727368697020626964206a7573742068617070656e65642e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e64207468656972206f666665729420697320746865207365636f6e642e205b63616e6469646174655f69642c206f666665725d14566f7563680c244163636f756e7449641c42616c616e6365244163636f756e7449640861012041206d656d6265727368697020626964206a7573742068617070656e656420627920766f756368696e672e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e647101207468656972206f6666657220697320746865207365636f6e642e2054686520766f756368696e67207061727479206973207468652074686972642e205b63616e6469646174655f69642c206f666665722c20766f756368696e675d244175746f556e62696404244163636f756e7449640411012041205b63616e6469646174655d207761732064726f70706564202864756520746f20616e20657863657373206f66206269647320696e207468652073797374656d292e14556e62696404244163636f756e74496404b82041205b63616e6469646174655d207761732064726f70706564202862792074686569722072657175657374292e1c556e766f75636804244163636f756e7449640401012041205b63616e6469646174655d207761732064726f70706564202862792072657175657374206f662077686f20766f756368656420666f72207468656d292e20496e64756374656408244163636f756e744964385665633c4163636f756e7449643e08590120412067726f7570206f662063616e646964617465732068617665206265656e20696e6475637465642e205468652062617463682773207072696d617279206973207468652066697273742076616c75652c20746865cc20626174636820696e2066756c6c20697320746865207365636f6e642e205b7072696d6172792c2063616e646964617465735d6053757370656e6465644d656d6265724a756467656d656e7408244163636f756e74496410626f6f6c04c820412073757370656e646564206d656d62657220686173206265656e206a75646765642e205b77686f2c206a75646765645d4843616e64696461746553757370656e64656404244163636f756e74496404842041205b63616e6469646174655d20686173206265656e2073757370656e6465643c4d656d62657253757370656e64656404244163636f756e74496404782041205b6d656d6265725d20686173206265656e2073757370656e646564284368616c6c656e67656404244163636f756e744964047c2041205b6d656d6265725d20686173206265656e206368616c6c656e67656410566f74650c244163636f756e744964244163636f756e74496410626f6f6c04c0204120766f746520686173206265656e20706c61636564205b63616e6469646174652c20766f7465722c20766f74655d30446566656e646572566f746508244163636f756e74496410626f6f6c04f0204120766f746520686173206265656e20706c6163656420666f72206120646566656e64696e67206d656d626572205b766f7465722c20766f74655d344e65774d61784d656d62657273040c75333204982041206e6577205b6d61785d206d656d62657220636f756e7420686173206265656e2073657424556e666f756e64656404244163636f756e744964048020536f636965747920697320756e666f756e6465642e205b666f756e6465725d1c4465706f736974041c42616c616e636504f020536f6d652066756e64732077657265206465706f736974656420696e746f2074686520736f6369657479206163636f756e742e205b76616c75655d1c4043616e6469646174654465706f7369743c42616c616e63654f663c542c20493e400080c6a47e8d0300000000000000000004fc20546865206d696e696d756d20616d6f756e74206f662061206465706f73697420726571756972656420666f7220612062696420746f206265206d6164652e4857726f6e6753696465446564756374696f6e3c42616c616e63654f663c542c20493e400080f420e6b5000000000000000000000855012054686520616d6f756e74206f662074686520756e70616964207265776172642074686174206765747320646564756374656420696e207468652063617365207468617420656974686572206120736b6570746963c020646f65736e277420766f7465206f7220736f6d656f6e6520766f74657320696e207468652077726f6e67207761792e284d6178537472696b65730c753332100a00000008750120546865206e756d626572206f662074696d65732061206d656d626572206d617920766f7465207468652077726f6e672077617920286f72206e6f7420617420616c6c2c207768656e207468657920617265206120736b65707469632978206265666f72652074686579206265636f6d652073757370656e6465642e2c506572696f645370656e643c42616c616e63654f663c542c20493e400000c52ebca2b1000000000000000000042d012054686520616d6f756e74206f6620696e63656e7469766520706169642077697468696e206561636820706572696f642e20446f65736e277420696e636c75646520566f7465725469702e38526f746174696f6e506572696f6438543a3a426c6f636b4e756d626572100077010004110120546865206e756d626572206f6620626c6f636b73206265747765656e2063616e6469646174652f6d656d6265727368697020726f746174696f6e20706572696f64732e3c4368616c6c656e6765506572696f6438543a3a426c6f636b4e756d626572108013030004d020546865206e756d626572206f6620626c6f636b73206265747765656e206d656d62657273686970206368616c6c656e6765732e204d6f64756c654964204d6f64756c6549642070792f736f63696504682054686520736f636965746965732773206d6f64756c65206964482c426164506f736974696f6e049020416e20696e636f727265637420706f736974696f6e207761732070726f76696465642e244e6f744d656d62657204582055736572206973206e6f742061206d656d6265722e34416c72656164794d656d6265720468205573657220697320616c72656164792061206d656d6265722e2453757370656e646564044c20557365722069732073757370656e6465642e304e6f7453757370656e646564045c2055736572206973206e6f742073757370656e6465642e204e6f5061796f7574044c204e6f7468696e6720746f207061796f75742e38416c7265616479466f756e646564046420536f636965747920616c726561647920666f756e6465642e3c496e73756666696369656e74506f74049c204e6f7420656e6f75676820696e20706f7420746f206163636570742063616e6469646174652e3c416c7265616479566f756368696e6704e8204d656d62657220697320616c726561647920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e2e2c4e6f74566f756368696e670460204d656d626572206973206e6f7420766f756368696e672e104865616404942043616e6e6f742072656d6f7665207468652068656164206f662074686520636861696e2e1c466f756e646572046c2043616e6e6f742072656d6f76652074686520666f756e6465722e28416c7265616479426964047420557365722068617320616c7265616479206d6164652061206269642e40416c726561647943616e6469646174650474205573657220697320616c726561647920612063616e6469646174652e304e6f7443616e64696461746504642055736572206973206e6f7420612063616e6469646174652e284d61784d656d62657273048420546f6f206d616e79206d656d6265727320696e2074686520736f63696574792e284e6f74466f756e646572047c205468652063616c6c6572206973206e6f742074686520666f756e6465722e1c4e6f74486561640470205468652063616c6c6572206973206e6f742074686520686561642e205265636f7665727901205265636f766572790c2c5265636f76657261626c6500010530543a3a4163636f756e744964e85265636f76657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e0004000409012054686520736574206f66207265636f76657261626c65206163636f756e747320616e64207468656972207265636f7665727920636f6e66696775726174696f6e2e404163746976655265636f76657269657300020530543a3a4163636f756e74496430543a3a4163636f756e744964e84163746976655265636f766572793c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e050400106820416374697665207265636f7665727920617474656d7074732e001501204669727374206163636f756e7420697320746865206163636f756e7420746f206265207265636f76657265642c20616e6420746865207365636f6e64206163636f756e74ac20697320746865207573657220747279696e6720746f207265636f76657220746865206163636f756e742e1450726f787900010230543a3a4163636f756e74496430543a3a4163636f756e7449640004000c9020546865206c697374206f6620616c6c6f7765642070726f7879206163636f756e74732e00f8204d61702066726f6d2074686520757365722077686f2063616e2061636365737320697420746f20746865207265636f7665726564206163636f756e742e01243061735f7265636f7665726564081c6163636f756e7430543a3a4163636f756e7449641063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e34a42053656e6420612063616c6c207468726f7567682061207265636f7665726564206163636f756e742e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a2501202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f752077616e7420746f206d616b6520612063616c6c206f6e2d626568616c662d6f662e0101202d206063616c6c603a205468652063616c6c20796f752077616e7420746f206d616b65207769746820746865207265636f7665726564206163636f756e742e002c2023203c7765696768743e94202d2054686520776569676874206f6620746865206063616c6c60202b2031302c3030302e0901202d204f6e652073746f72616765206c6f6f6b757020746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e347365745f7265636f766572656408106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e744964341d0120416c6c6f7720524f4f5420746f2062797061737320746865207265636f766572792070726f6365737320616e642073657420616e20612072657363756572206163636f756e747420666f722061206c6f7374206163636f756e74206469726563746c792e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f524f4f545f2e003020506172616d65746572733ab8202d20606c6f7374603a2054686520226c6f7374206163636f756e742220746f206265207265636f76657265642e1d01202d206072657363756572603a20546865202272657363756572206163636f756e74222077686963682063616e2063616c6c20617320746865206c6f7374206163636f756e742e002c2023203c7765696768743e64202d204f6e652073746f72616765207772697465204f28312930202d204f6e65206576656e74302023203c2f7765696768743e3c6372656174655f7265636f766572790c1c667269656e6473445665633c543a3a4163636f756e7449643e247468726573686f6c640c7531363064656c61795f706572696f6438543a3a426c6f636b4e756d6265726c5d01204372656174652061207265636f7665727920636f6e66696775726174696f6e20666f7220796f7572206163636f756e742e2054686973206d616b657320796f7572206163636f756e74207265636f76657261626c652e003101205061796d656e743a2060436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732062616c616e636549012077696c6c20626520726573657276656420666f722073746f72696e6720746865207265636f7665727920636f6e66696775726174696f6e2e2054686973206465706f7369742069732072657475726e6564bc20696e2066756c6c207768656e2074686520757365722063616c6c73206072656d6f76655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2501202d2060667269656e6473603a2041206c697374206f6620667269656e647320796f7520747275737420746f20766f75636820666f72207265636f7665727920617474656d7074732ed420202053686f756c64206265206f72646572656420616e6420636f6e7461696e206e6f206475706c69636174652076616c7565732e3101202d20607468726573686f6c64603a20546865206e756d626572206f6620667269656e64732074686174206d75737420766f75636820666f722061207265636f7665727920617474656d70741d012020206265666f726520746865206163636f756e742063616e206265207265636f76657265642e2053686f756c64206265206c657373207468616e206f7220657175616c20746f94202020746865206c656e677468206f6620746865206c697374206f6620667269656e64732e3d01202d206064656c61795f706572696f64603a20546865206e756d626572206f6620626c6f636b732061667465722061207265636f7665727920617474656d707420697320696e697469616c697a6564e820202074686174206e6565647320746f2070617373206265666f726520746865206163636f756e742063616e206265207265636f76657265642e002c2023203c7765696768743e68202d204b65793a204620286c656e206f6620667269656e6473292d01202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973206e6f7420616c7265616479207265636f76657261626c652e204f2831292eec202d204120636865636b20746861742074686520667269656e6473206c69737420697320736f7274656420616e6420756e697175652e204f2846299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f2858299c202d204f6e652073746f726167652077726974652e204f2831292e20436f646563204f2846292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e44696e6974696174655f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496458ec20496e697469617465207468652070726f6365737320666f72207265636f766572696e672061207265636f76657261626c65206163636f756e742e001d01205061796d656e743a20605265636f766572794465706f736974602062616c616e63652077696c6c20626520726573657276656420666f7220696e6974696174696e67207468652501207265636f766572792070726f636573732e2054686973206465706f7369742077696c6c20616c7761797320626520726570617472696174656420746f20746865206163636f756e74b820747279696e6720746f206265207265636f76657265642e205365652060636c6f73655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e2054686973206163636f756e7401012020206e6565647320746f206265207265636f76657261626c652028692e652e20686176652061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743ef8202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973207265636f76657261626c652e204f2846295101202d204f6e652073746f72616765207265616420746f20636865636b20746861742074686973207265636f766572792070726f63657373206861736e277420616c726561647920737461727465642e204f2831299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f285829e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831296c202d204f6e652073746f726167652077726974652e204f2831292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e38766f7563685f7265636f7665727908106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e74496464290120416c6c6f7720612022667269656e6422206f662061207265636f76657261626c65206163636f756e7420746f20766f75636820666f7220616e20616374697665207265636f76657279682070726f6365737320666f722074686174206163636f756e742e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d75737420626520612022667269656e64227420666f7220746865207265636f76657261626c65206163636f756e742e003020506172616d65746572733ad4202d20606c6f7374603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f2072657363756520746865206c6f7374206163636f756e74207468617420796f755420202077616e7420746f20766f75636820666f722e0025012054686520636f6d62696e6174696f6e206f662074686573652074776f20706172616d6574657273206d75737420706f696e7420746f20616e20616374697665207265636f76657279242070726f636573732e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629ec202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c6572206973206120667269656e642e204f286c6f6746291d01202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c657220686173206e6f7420616c726561647920766f75636865642e204f286c6f6756299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e00a420546f74616c20436f6d706c65786974793a204f2846202b206c6f6746202b2056202b206c6f675629302023203c2f7765696768743e38636c61696d5f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496450f420416c6c6f772061207375636365737366756c207265736375657220746f20636c61696d207468656972207265636f7665726564206163636f756e742e002d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061202272657363756572221d012077686f20686173207375636365737366756c6c7920636f6d706c6574656420746865206163636f756e74207265636f766572792070726f636573733a20636f6c6c6563746564310120607468726573686f6c6460206f72206d6f726520766f75636865732c20776169746564206064656c61795f706572696f646020626c6f636b732073696e636520696e6974696174696f6e2e003020506172616d65746572733a2d01202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f20636c61696d20686173206265656e207375636365737366756c6c79502020207265636f766572656420627920796f752e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205629302023203c2f7765696768743e38636c6f73655f7265636f76657279041c7265736375657230543a3a4163636f756e7449645015012041732074686520636f6e74726f6c6c6572206f662061207265636f76657261626c65206163636f756e742c20636c6f736520616e20616374697665207265636f76657279682070726f6365737320666f7220796f7572206163636f756e742e002101205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e2c20746865207265636f76657261626c65206163636f756e742077696c6c2072656365697665f820746865207265636f76657279206465706f73697420605265636f766572794465706f7369746020706c616365642062792074686520726573637565722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061f0207265636f76657261626c65206163636f756e74207769746820616e20616374697665207265636f766572792070726f6365737320666f722069742e003020506172616d65746572733a1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f207265736375652074686973207265636f76657261626c65206163636f756e742e002c2023203c7765696768743e84204b65793a205620286c656e206f6620766f756368696e6720667269656e6473293d01202d204f6e652073746f7261676520726561642f72656d6f766520746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629c0202d204f6e652062616c616e63652063616c6c20746f20726570617472696174652072657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2856202b205829302023203c2f7765696768743e3c72656d6f76655f7265636f7665727900545d012052656d6f766520746865207265636f766572792070726f6365737320666f7220796f7572206163636f756e742e205265636f7665726564206163636f756e747320617265207374696c6c2061636365737369626c652e001501204e4f54453a205468652075736572206d757374206d616b65207375726520746f2063616c6c2060636c6f73655f7265636f7665727960206f6e20616c6c206163746976650901207265636f7665727920617474656d707473206265666f72652063616c6c696e6720746869732066756e6374696f6e20656c73652069742077696c6c206661696c2e002501205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e20746865207265636f76657261626c65206163636f756e742077696c6c20756e7265736572766598207468656972207265636f7665727920636f6e66696775726174696f6e206465706f7369742ef4202860436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732900050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061e4207265636f76657261626c65206163636f756e742028692e652e206861732061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743e60204b65793a204620286c656e206f6620667269656e6473292901202d204f6e652073746f72616765207265616420746f206765742074686520707265666978206974657261746f7220666f7220616374697665207265636f7665726965732e204f2831293901202d204f6e652073746f7261676520726561642f72656d6f766520746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846299c202d204f6e652062616c616e63652063616c6c20746f20756e72657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e4063616e63656c5f7265636f7665726564041c6163636f756e7430543a3a4163636f756e7449642ce02043616e63656c20746865206162696c69747920746f20757365206061735f7265636f76657265646020666f7220606163636f756e74602e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a1901202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f75206172652061626c6520746f2063616c6c206f6e2d626568616c662d6f662e002c2023203c7765696768743e1101202d204f6e652073746f72616765206d75746174696f6e20746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e01183c5265636f766572794372656174656404244163636f756e74496404d42041207265636f766572792070726f6365737320686173206265656e2073657420757020666f7220616e205b6163636f756e745d2e445265636f76657279496e6974696174656408244163636f756e744964244163636f756e744964082d012041207265636f766572792070726f6365737320686173206265656e20696e6974696174656420666f72206c6f7374206163636f756e742062792072657363756572206163636f756e742e40205b6c6f73742c20726573637565725d3c5265636f76657279566f75636865640c244163636f756e744964244163636f756e744964244163636f756e744964085d012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20766f756368656420666f722062792073656e6465722e60205b6c6f73742c20726573637565722c2073656e6465725d385265636f76657279436c6f73656408244163636f756e744964244163636f756e7449640821012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20636c6f7365642e40205b6c6f73742c20726573637565725d404163636f756e745265636f766572656408244163636f756e744964244163636f756e744964080501204c6f7374206163636f756e7420686173206265656e207375636365737366756c6c79207265636f76657265642062792072657363756572206163636f756e742e40205b6c6f73742c20726573637565725d3c5265636f7665727952656d6f76656404244163636f756e74496404d82041207265636f766572792070726f6365737320686173206265656e2072656d6f76656420666f7220616e205b6163636f756e745d2e1044436f6e6669674465706f736974426173653042616c616e63654f663c543e4000406352bfc60100000000000000000004550120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e4c467269656e644465706f736974466163746f723042616c616e63654f663c543e4000203d88792d000000000000000000000469012054686520616d6f756e74206f662063757272656e6379206e656564656420706572206164646974696f6e616c2075736572207768656e206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e284d6178467269656e64730c753136080900040d0120546865206d6178696d756d20616d6f756e74206f6620667269656e647320616c6c6f77656420696e2061207265636f7665727920636f6e66696775726174696f6e2e3c5265636f766572794465706f7369743042616c616e63654f663c543e4000406352bfc601000000000000000000041d0120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72207374617274696e672061207265636f766572792e40284e6f74416c6c6f77656404f42055736572206973206e6f7420616c6c6f77656420746f206d616b6520612063616c6c206f6e20626568616c66206f662074686973206163636f756e74345a65726f5468726573686f6c640490205468726573686f6c64206d7573742062652067726561746572207468616e207a65726f404e6f74456e6f756768467269656e647304d420467269656e6473206c697374206d7573742062652067726561746572207468616e207a65726f20616e64207468726573686f6c64284d6178467269656e647304ac20467269656e6473206c697374206d757374206265206c657373207468616e206d617820667269656e6473244e6f74536f7274656404cc20467269656e6473206c697374206d75737420626520736f7274656420616e642066726565206f66206475706c696361746573384e6f745265636f76657261626c6504a02054686973206163636f756e74206973206e6f742073657420757020666f72207265636f7665727948416c72656164795265636f76657261626c6504b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f7665727938416c72656164795374617274656404e02041207265636f766572792070726f636573732068617320616c7265616479207374617274656420666f722074686973206163636f756e74284e6f745374617274656404d02041207265636f766572792070726f6365737320686173206e6f74207374617274656420666f7220746869732072657363756572244e6f74467269656e6404ac2054686973206163636f756e74206973206e6f74206120667269656e642077686f2063616e20766f7563682c44656c6179506572696f64041d012054686520667269656e64206d757374207761697420756e74696c207468652064656c617920706572696f6420746f20766f75636820666f722074686973207265636f7665727938416c7265616479566f756368656404c0205468697320757365722068617320616c726561647920766f756368656420666f722074686973207265636f76657279245468726573686f6c6404ec20546865207468726573686f6c6420666f72207265636f766572696e672074686973206163636f756e7420686173206e6f74206265656e206d65742c5374696c6c41637469766504010120546865726520617265207374696c6c20616374697665207265636f7665727920617474656d7074732074686174206e65656420746f20626520636c6f736564204f766572666c6f77049c2054686572652077617320616e206f766572666c6f7720696e20612063616c63756c6174696f6e30416c726561647950726f787904b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f766572791c56657374696e67011c56657374696e67041c56657374696e6700010230543a3a4163636f756e744964a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e00040004d820496e666f726d6174696f6e20726567617264696e67207468652076657374696e67206f66206120676976656e206163636f756e742e011010766573740044bc20556e6c6f636b20616e79207665737465642066756e6473206f66207468652073656e646572206163636f756e742e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652066756e6473207374696c6c68206c6f636b656420756e6465722074686973206d6f64756c652e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20322052656164732c203220577269746573fc20202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d010120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d34202d2042656e63686d61726b3aec20202020202d20556e6c6f636b65643a2034382e3736202b202e303438202a206c20c2b57320286d696e2073717561726520616e616c7973697329e420202020202d204c6f636b65643a2034342e3433202b202e323834202a206c20c2b57320286d696e2073717561726520616e616c7973697329ad01202d205573696e6720353020c2b5732066697865642e20417373756d696e67206c657373207468616e203530206c6f636b73206f6e20616e7920757365722c20656c7365207765206d61792077616e7420666163746f7220696e206e756d626572206f66206c6f636b732e302023203c2f7765696768743e28766573745f6f7468657204187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654cbc20556e6c6f636b20616e79207665737465642066756e6473206f662061206074617267657460206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501202d2060746172676574603a20546865206163636f756e742077686f7365207665737465642066756e64732073686f756c6420626520756e6c6f636b65642e204d75737420686176652066756e6473207374696c6c68206c6f636b656420756e6465722074686973206d6f64756c652e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c203320577269746573f420202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e74f820202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e7434202d2042656e63686d61726b3ae820202020202d20556e6c6f636b65643a2034342e33202b202e323934202a206c20c2b57320286d696e2073717561726520616e616c7973697329e420202020202d204c6f636b65643a2034382e3136202b202e313033202a206c20c2b57320286d696e2073717561726520616e616c7973697329ad01202d205573696e6720353020c2b5732066697865642e20417373756d696e67206c657373207468616e203530206c6f636b73206f6e20616e7920757365722c20656c7365207765206d61792077616e7420666163746f7220696e206e756d626572206f66206c6f636b732e302023203c2f7765696768743e3c7665737465645f7472616e7366657208187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e486820437265617465206120766573746564207472616e736665722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e001501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c2033205772697465733d0120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745d410120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745de0202d2042656e63686d61726b3a203130302e33202b202e333635202a206c20c2b57320286d696e2073717561726520616e616c7973697329b101202d205573696e672031303020c2b5732066697865642e20417373756d696e67206c657373207468616e203530206c6f636b73206f6e20616e7920757365722c20656c7365207765206d61792077616e7420666163746f7220696e206e756d626572206f66206c6f636b732e302023203c2f7765696768743e54666f7263655f7665737465645f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e4c6420466f726365206120766573746564207472616e736665722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00ec202d2060736f75726365603a20546865206163636f756e742077686f73652066756e64732073686f756c64206265207472616e736665727265642e1501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20342052656164732c203420577269746573350120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74390120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74e0202d2042656e63686d61726b3a203130302e33202b202e333635202a206c20c2b57320286d696e2073717561726520616e616c7973697329b101202d205573696e672031303020c2b5732066697865642e20417373756d696e67206c657373207468616e203530206c6f636b73206f6e20616e7920757365722c20656c7365207765206d61792077616e7420666163746f7220696e206e756d626572206f66206c6f636b732e302023203c2f7765696768743e01083856657374696e675570646174656408244163636f756e7449641c42616c616e63650c59012054686520616d6f756e742076657374656420686173206265656e20757064617465642e205468697320636f756c6420696e646963617465206d6f72652066756e64732061726520617661696c61626c652e205468651d012062616c616e636520676976656e2069732074686520616d6f756e74207768696368206973206c65667420756e7665737465642028616e642074687573206c6f636b6564292e2050205b6163636f756e742c20756e7665737465645d4056657374696e67436f6d706c6574656404244163636f756e74496404150120416e205b6163636f756e745d20686173206265636f6d652066756c6c79207665737465642e204e6f20667572746865722076657374696e672063616e2068617070656e2e04444d696e5665737465645472616e736665723042616c616e63654f663c543e400000c16ff28623000000000000000000041d0120546865206d696e696d756d20616d6f756e7420746f206265207472616e7366657272656420746f206372656174652061206e65772076657374696e67207363686564756c652e0c284e6f7456657374696e67048820546865206163636f756e7420676976656e206973206e6f742076657374696e672e5c4578697374696e6756657374696e675363686564756c65045d0120416e206578697374696e672076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e7420746861742063616e6e6f7420626520636c6f6262657265642e24416d6f756e744c6f7704090120416d6f756e74206265696e67207472616e7366657272656420697320746f6f206c6f7720746f2063726561746520612076657374696e67207363686564756c652e245363686564756c657201245363686564756c65720c184167656e646101010538543a3a426c6f636b4e756d6265726d015665633c4f7074696f6e3c5363686564756c65643c3c542061732054726169743e3a3a43616c6c2c20543a3a426c6f636b4e756d6265722c20543a3a0a50616c6c6574734f726967696e2c20543a3a4163636f756e7449643e3e3e000400044d01204974656d7320746f2062652065786563757465642c20696e64657865642062792074686520626c6f636b206e756d626572207468617420746865792073686f756c64206265206578656375746564206f6e2e184c6f6f6b75700001051c5665633c75383e6c5461736b416464726573733c543a3a426c6f636b4e756d6265723e000400040101204c6f6f6b75702066726f6d206964656e7469747920746f2074686520626c6f636b206e756d62657220616e6420696e646578206f6620746865207461736b2e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e0118207363686564756c6510107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e287420416e6f6e796d6f75736c79207363686564756c652061207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7390202d2042617365205765696768743a2032322e3239202b202e313236202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64615020202020202d2057726974653a204167656e64613d01202d2057696c6c20757365206261736520776569676874206f662032352077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e1863616e63656c08107768656e38543a3a426c6f636b4e756d62657214696e6465780c75333228982043616e63656c20616e20616e6f6e796d6f75736c79207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032322e3135202b20322e383639202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64617020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f6e616d6564140869641c5665633c75383e107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e285c205363686564756c652061206e616d6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c738c202d2042617365205765696768743a2032392e36202b202e313539202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704d01202d2057696c6c20757365206261736520776569676874206f662033352077686963682073686f756c6420626520676f6f6420666f72206d6f7265207468616e203330207363686564756c65642063616c6c73302023203c2f7765696768743e3063616e63656c5f6e616d6564040869641c5665633c75383e287c2043616e63656c2061206e616d6564207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032342e3931202b20322e393037202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f61667465721014616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e14ac20416e6f6e796d6f75736c79207363686564756c652061207461736b20616674657220612064656c61792e002c2023203c7765696768743e582053616d65206173205b607363686564756c65605d2e302023203c2f7765696768743e507363686564756c655f6e616d65645f6166746572140869641c5665633c75383e14616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e1494205363686564756c652061206e616d6564207461736b20616674657220612064656c61792e002c2023203c7765696768743e702053616d65206173205b607363686564756c655f6e616d6564605d2e302023203c2f7765696768743e010c245363686564756c6564082c426c6f636b4e756d6265720c753332048c205363686564756c656420736f6d65207461736b2e205b7768656e2c20696e6465785d2043616e63656c6564082c426c6f636b4e756d6265720c75333204882043616e63656c656420736f6d65207461736b2e205b7768656e2c20696e6465785d28446973706174636865640c605461736b416464726573733c426c6f636b4e756d6265723e3c4f7074696f6e3c5665633c75383e3e384469737061746368526573756c7404a4204469737061746368656420736f6d65207461736b2e205b7461736b2c2069642c20726573756c745d000c404661696c6564546f5363686564756c650468204661696c656420746f207363686564756c6520612063616c6c384661696c6564546f43616e63656c0488204661696c656420746f2063616e63656c2061207363686564756c65642063616c6c5c546172676574426c6f636b4e756d626572496e5061737404a820476976656e2074617267657420626c6f636b206e756d62657220697320696e2074686520706173742e1450726f7879011450726f7879081c50726f7869657301010530543a3a4163636f756e7449644501285665633c50726f7879446566696e6974696f6e3c543a3a4163636f756e7449642c20543a3a50726f7879547970652c20543a3a426c6f636b4e756d6265723e3e2c0a2042616c616e63654f663c543e29004400000000000000000000000000000000000845012054686520736574206f66206163636f756e742070726f786965732e204d61707320746865206163636f756e74207768696368206861732064656c65676174656420746f20746865206163636f756e7473210120776869636820617265206265696e672064656c65676174656420746f2c20746f67657468657220776974682074686520616d6f756e742068656c64206f6e206465706f7369742e34416e6e6f756e63656d656e747301010530543a3a4163636f756e7449643d01285665633c416e6e6f756e63656d656e743c543a3a4163636f756e7449642c2043616c6c486173684f663c543e2c20543a3a426c6f636b4e756d6265723e3e2c0a2042616c616e63654f663c543e290044000000000000000000000000000000000004ac2054686520616e6e6f756e63656d656e7473206d616465206279207468652070726f787920286b6579292e01281470726f78790c107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e3c51012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f726973656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e246164645f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d6265722c490120526567697374657220612070726f7879206163636f756e7420666f72207468652073656e64657220746861742069732061626c6520746f206d616b652063616c6c73206f6e2069747320626568616c662e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f206d616b6520612070726f78792e0101202d206070726f78795f74797065603a20546865207065726d697373696f6e7320616c6c6f77656420666f7220746869732070726f7879206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3072656d6f76655f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d6265722cac20556e726567697374657220612070726f7879206163636f756e7420666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2901202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f2072656d6f766520617320612070726f78792e4501202d206070726f78795f74797065603a20546865207065726d697373696f6e732063757272656e746c7920656e61626c656420666f72207468652072656d6f7665642070726f7879206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3872656d6f76655f70726f786965730028b820556e726567697374657220616c6c2070726f7879206163636f756e747320666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901205741524e494e473a2054686973206d61792062652063616c6c6564206f6e206163636f756e747320637265617465642062792060616e6f6e796d6f7573602c20686f776576657220696620646f6e652c207468656e5d012074686520756e726573657276656420666565732077696c6c20626520696e61636365737369626c652e202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e24616e6f6e796d6f75730c2870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d62657214696e6465780c7531365c3d0120537061776e2061206672657368206e6577206163636f756e7420746861742069732067756172616e7465656420746f206265206f746865727769736520696e61636365737369626c652c20616e64010120696e697469616c697a65206974207769746820612070726f7879206f66206070726f78795f747970656020666f7220606f726967696e602073656e6465722e0070205265717569726573206120605369676e656460206f726967696e2e005501202d206070726f78795f74797065603a205468652074797065206f66207468652070726f78792074686174207468652073656e6465722077696c6c2062652072656769737465726564206173206f766572207468655101206e6577206163636f756e742e20546869732077696c6c20616c6d6f737420616c7761797320626520746865206d6f7374207065726d697373697665206050726f7879547970656020706f737369626c6520746f7c20616c6c6f7720666f72206d6178696d756d20666c65786962696c6974792e5501202d2060696e646578603a204120646973616d626967756174696f6e20696e6465782c20696e206361736520746869732069732063616c6c6564206d756c7469706c652074696d657320696e207468652073616d656101207472616e73616374696f6e2028652e672e207769746820607574696c6974793a3a626174636860292e20556e6c65737320796f75277265207573696e67206062617463686020796f752070726f6261626c79206a757374442077616e7420746f20757365206030602e5101202d206064656c6179603a2054686520616e6e6f756e63656d656e7420706572696f64207265717569726564206f662074686520696e697469616c2070726f78792e2057696c6c2067656e6572616c6c7920626518207a65726f2e005501204661696c73207769746820604475706c69636174656020696620746869732068617320616c7265616479206265656e2063616c6c656420696e2074686973207472616e73616374696f6e2c2066726f6d207468659c2073616d652073656e6465722c2077697468207468652073616d6520706172616d65746572732e00e8204661696c732069662074686572652061726520696e73756666696369656e742066756e647320746f2070617920666f72206465706f7369742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e9020544f444f3a204d69676874206265206f76657220636f756e74696e6720312072656164386b696c6c5f616e6f6e796d6f7573141c737061776e657230543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f78795479706514696e6465780c753136186865696768745c436f6d706163743c543a3a426c6f636b4e756d6265723e246578745f696e64657830436f6d706163743c7533323e50b82052656d6f76657320612070726576696f75736c7920737061776e656420616e6f6e796d6f75732070726f78792e004d01205741524e494e473a202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a20416e792066756e64732068656c6420696e2069742077696c6c2062653820696e61636365737369626c652e005d01205265717569726573206120605369676e656460206f726967696e2c20616e64207468652073656e646572206163636f756e74206d7573742068617665206265656e206372656174656420627920612063616c6c20746fac2060616e6f6e796d6f757360207769746820636f72726573706f6e64696e6720706172616d65746572732e005101202d2060737061776e6572603a20546865206163636f756e742074686174206f726967696e616c6c792063616c6c65642060616e6f6e796d6f75736020746f206372656174652074686973206163636f756e742e5101202d2060696e646578603a2054686520646973616d626967756174696f6e20696e646578206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e2050726f6261626c79206030602e0501202d206070726f78795f74797065603a205468652070726f78792074797065206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e4101202d2060686569676874603a2054686520686569676874206f662074686520636861696e207768656e207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e4d01202d20606578745f696e646578603a205468652065787472696e73696320696e64657820696e207768696368207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e004d01204661696c73207769746820604e6f5065726d697373696f6e6020696e2063617365207468652063616c6c6572206973206e6f7420612070726576696f75736c79206372656174656420616e6f6e796d6f7573f4206163636f756e742077686f73652060616e6f6e796d6f7573602063616c6c2068617320636f72726573706f6e64696e6720706172616d65746572732e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e20616e6e6f756e636508107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e540901205075626c697368207468652068617368206f6620612070726f78792d63616c6c20746861742077696c6c206265206d61646520696e20746865206675747572652e0061012054686973206d7573742062652063616c6c656420736f6d65206e756d626572206f6620626c6f636b73206265666f72652074686520636f72726573706f6e64696e67206070726f78796020697320617474656d707465642901206966207468652064656c6179206173736f6369617465642077697468207468652070726f78792072656c6174696f6e736869702069732067726561746572207468616e207a65726f2e001501204e6f206d6f7265207468616e20604d617850656e64696e676020616e6e6f756e63656d656e7473206d6179206265206d61646520617420616e79206f6e652074696d652e000d0120546869732077696c6c2074616b652061206465706f736974206f662060416e6e6f756e63656d656e744465706f736974466163746f72602061732077656c6c2061731d012060416e6e6f756e63656d656e744465706f736974426173656020696620746865726520617265206e6f206f746865722070656e64696e6720616e6e6f756e63656d656e74732e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420612070726f7879206f6620607265616c602e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656d6f76655f616e6e6f756e63656d656e7408107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40742052656d6f7665206120676976656e20616e6e6f756e63656d656e742e005d01204d61792062652063616c6c656420627920612070726f7879206163636f756e7420746f2072656d6f766520612063616c6c20746865792070726576696f75736c7920616e6e6f756e63656420616e642072657475726e3420746865206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656a6563745f616e6e6f756e63656d656e74082064656c656761746530543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40b42052656d6f76652074686520676976656e20616e6e6f756e63656d656e74206f6620612064656c65676174652e006501204d61792062652063616c6c6564206279206120746172676574202870726f7869656429206163636f756e7420746f2072656d6f766520612063616c6c2074686174206f6e65206f662074686569722064656c656761746573290120286064656c656761746560292068617320616e6e6f756e63656420746865792077616e7420746f20657865637574652e20546865206465706f7369742069732072657475726e65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733af8202d206064656c6567617465603a20546865206163636f756e7420746861742070726576696f75736c7920616e6e6f756e636564207468652063616c6c2ec0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e3c70726f78795f616e6e6f756e636564102064656c656761746530543a3a4163636f756e744964107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e4451012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f726973656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e010c3450726f7879457865637574656404384469737061746368526573756c7404e420412070726f78792077617320657865637574656420636f72726563746c792c20776974682074686520676976656e205b726573756c745d2e40416e6f6e796d6f75734372656174656410244163636f756e744964244163636f756e7449642450726f7879547970650c75313608ec20416e6f6e796d6f7573206163636f756e7420686173206265656e2063726561746564206279206e65772070726f7879207769746820676976656e610120646973616d626967756174696f6e20696e64657820616e642070726f787920747970652e205b616e6f6e796d6f75732c2077686f2c2070726f78795f747970652c20646973616d626967756174696f6e5f696e6465785d24416e6e6f756e6365640c244163636f756e744964244163636f756e744964104861736804490120416e20616e6e6f756e63656d656e742077617320706c6163656420746f206d616b6520612063616c6c20696e20746865206675747572652e205b7265616c2c2070726f78792c2063616c6c5f686173685d184050726f78794465706f736974426173653042616c616e63654f663c543e4000f09e544c390000000000000000000004110120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e6720612070726f78792e4850726f78794465706f736974466163746f723042616c616e63654f663c543e400060aa7714b40000000000000000000004bc2054686520616d6f756e74206f662063757272656e6379206e6565646564207065722070726f78792061646465642e284d617850726f786965730c75313608200004f020546865206d6178696d756d20616d6f756e74206f662070726f7869657320616c6c6f77656420666f7220612073696e676c65206163636f756e742e284d617850656e64696e670c7533321020000000047820604d617850656e64696e6760206d6574616461746120736861646f772e5c416e6e6f756e63656d656e744465706f736974426173653042616c616e63654f663c543e4000f09e544c390000000000000000000004ac2060416e6e6f756e63656d656e744465706f7369744261736560206d6574616461746120736861646f772e64416e6e6f756e63656d656e744465706f736974466163746f723042616c616e63654f663c543e4000c054ef28680100000000000000000004b42060416e6e6f756e63656d656e744465706f736974466163746f7260206d6574616461746120736861646f772e1c1c546f6f4d616e790425012054686572652061726520746f6f206d616e792070726f786965732072656769737465726564206f7220746f6f206d616e7920616e6e6f756e63656d656e74732070656e64696e672e204e6f74466f756e6404782050726f787920726567697374726174696f6e206e6f7420666f756e642e204e6f7450726f787904d02053656e646572206973206e6f7420612070726f7879206f6620746865206163636f756e7420746f2062652070726f786965642e2c556e70726f787961626c6504250120412063616c6c20776869636820697320696e636f6d70617469626c652077697468207468652070726f7879207479706527732066696c7465722077617320617474656d707465642e244475706c69636174650470204163636f756e7420697320616c726561647920612070726f78792e304e6f5065726d697373696f6e0419012043616c6c206d6179206e6f74206265206d6164652062792070726f78792062656361757365206974206d617920657363616c617465206974732070726976696c656765732e2c556e616e6e6f756e63656404d420416e6e6f756e63656d656e742c206966206d61646520617420616c6c2c20776173206d61646520746f6f20726563656e746c792e204d756c746973696701204d756c746973696708244d756c74697369677300020530543a3a4163636f756e744964205b75383b2033325dd04d756c74697369673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e02040004942054686520736574206f66206f70656e206d756c7469736967206f7065726174696f6e732e1443616c6c73000106205b75383b2033325da0284f706171756543616c6c2c20543a3a4163636f756e7449642c2042616c616e63654f663c543e290004000001105061735f6d756c74695f7468726573686f6c645f3108446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e1063616c6c5c426f783c3c542061732054726169743e3a3a43616c6c3e44550120496d6d6564696174656c792064697370617463682061206d756c74692d7369676e61747572652063616c6c207573696e6720612073696e676c6520617070726f76616c2066726f6d207468652063616c6c65722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e004101202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f206172652070617274206f66207468650501206d756c74692d7369676e61747572652c2062757420646f206e6f7420706172746963697061746520696e2074686520617070726f76616c2070726f636573732e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e00bc20526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c742e002c2023203c7765696768743e1d01204f285a202b204329207768657265205a20697320746865206c656e677468206f66207468652063616c6c20616e6420432069747320657865637574696f6e207765696768742e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d2042617365205765696768743a2033332e3732202b20302e303032202a205a20c2b57348202d204442205765696768743a204e6f6e654c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e2061735f6d756c746918247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e1063616c6c284f706171756543616c6c2873746f72655f63616c6c10626f6f6c286d61785f77656967687418576569676874cc590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e00b42049662074686572652061726520656e6f7567682c207468656e206469737061746368207468652063616c6c2e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e002101204e4f54453a20556e6c6573732074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2067656e6572616c6c792077616e7420746f207573651d012060617070726f76655f61735f6d756c74696020696e73746561642c2073696e6365206974206f6e6c7920726571756972657320612068617368206f66207468652063616c6c2e005d0120526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c7420696620607468726573686f6c64602069732065786163746c79206031602e204f74686572776973655901206f6e20737563636573732c20726573756c7420697320604f6b6020616e642074686520726573756c742066726f6d2074686520696e746572696f722063616c6c2c206966206974207761732065786563757465642ce0206d617920626520666f756e6420696e20746865206465706f736974656420604d756c7469736967457865637574656460206576656e742e002c2023203c7765696768743e54202d20604f2853202b205a202b2043616c6c29602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2e2501202d204f6e652063616c6c20656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285a296020776865726520605a602069732074782d6c656e2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e70202d2054686520776569676874206f6620746865206063616c6c602e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d3c202d2042617365205765696768743ae020202020202d204372656174653a2020202020202020202034312e3839202b20302e313138202a2053202b202e303032202a205a20c2b573e020202020202d2043726561746520772f2053746f72653a2035332e3537202b20302e313139202a2053202b202e303033202a205a20c2b573e020202020202d20417070726f76653a20202020202020202033312e3339202b20302e313336202a2053202b202e303032202a205a20c2b573e020202020202d20436f6d706c6574653a202020202020202033392e3934202b20302e323620202a2053202b202e303032202a205a20c2b57334202d204442205765696768743a250120202020202d2052656164733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c6029290120202020202d205772697465733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c60294c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e40617070726f76655f61735f6d756c746914247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e2463616c6c5f68617368205b75383b2033325d286d61785f776569676874185765696768749c590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e003901204e4f54453a2049662074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2077616e7420746f20757365206061735f6d756c74696020696e73746561642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d3c202d2042617365205765696768743a8020202020202d204372656174653a2034342e3731202b20302e303838202a20538420202020202d20417070726f76653a2033312e3438202b20302e313136202a205334202d204442205765696768743abc20202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745dc020202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d302023203c2f7765696768743e3c63616e63656c5f61735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e2474696d65706f696e746454696d65706f696e743c543a3a426c6f636b4e756d6265723e2463616c6c5f68617368205b75383b2033325d6c59012043616e63656c2061207072652d6578697374696e672c206f6e2d676f696e67206d756c7469736967207472616e73616374696f6e2e20416e79206465706f7369742072657365727665642070726576696f75736c79c820666f722074686973206f7065726174696f6e2077696c6c20626520756e7265736572766564206f6e20737563636573732e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e6101202d206074696d65706f696e74603a205468652074696d65706f696e742028626c6f636b206e756d62657220616e64207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c7c207472616e73616374696f6e20666f7220746869732064697370617463682ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602e34202d204f6e65206576656e742e88202d20492f4f3a2031207265616420604f285329602c206f6e652072656d6f76652e74202d2053746f726167653a2072656d6f766573206f6e65206974656d2e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d84202d2042617365205765696768743a2033362e3037202b20302e313234202a205334202d204442205765696768743a190120202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c731d0120202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c73302023203c2f7765696768743e01102c4e65774d756c74697369670c244163636f756e744964244163636f756e7449642043616c6c486173680415012041206e6577206d756c7469736967206f7065726174696f6e2068617320626567756e2e205b617070726f76696e672c206d756c74697369672c2063616c6c5f686173685d404d756c7469736967417070726f76616c10244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c48617368047d012041206d756c7469736967206f7065726174696f6e20686173206265656e20617070726f76656420627920736f6d656f6e652e205b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685d404d756c7469736967457865637574656414244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c48617368384469737061746368526573756c740451012041206d756c7469736967206f7065726174696f6e20686173206265656e2065786563757465642e205b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685d444d756c746973696743616e63656c6c656410244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c486173680459012041206d756c7469736967206f7065726174696f6e20686173206265656e2063616e63656c6c65642e205b63616e63656c6c696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685d0038404d696e696d756d5468726573686f6c640480205468726573686f6c64206d7573742062652032206f7220677265617465722e3c416c7265616479417070726f76656404b02043616c6c20697320616c726561647920617070726f7665642062792074686973207369676e61746f72792e444e6f417070726f76616c734e656564656404a02043616c6c20646f65736e2774206e65656420616e7920286d6f72652920617070726f76616c732e44546f6f4665775369676e61746f7269657304ac2054686572652061726520746f6f20666577207369676e61746f7269657320696e20746865206c6973742e48546f6f4d616e795369676e61746f7269657304b02054686572652061726520746f6f206d616e79207369676e61746f7269657320696e20746865206c6973742e545369676e61746f726965734f75744f664f7264657204110120546865207369676e61746f7269657320776572652070726f7669646564206f7574206f66206f726465723b20746865792073686f756c64206265206f7264657265642e4c53656e646572496e5369676e61746f72696573041101205468652073656e6465722077617320636f6e7461696e656420696e20746865206f74686572207369676e61746f726965733b2069742073686f756c646e27742062652e204e6f74466f756e6404e0204d756c7469736967206f7065726174696f6e206e6f7420666f756e64207768656e20617474656d7074696e6720746f2063616e63656c2e204e6f744f776e6572043101204f6e6c7920746865206163636f756e742074686174206f726967696e616c6c79206372656174656420746865206d756c74697369672069732061626c6520746f2063616e63656c2069742e2c4e6f54696d65706f696e74042101204e6f2074696d65706f696e742077617320676976656e2c2079657420746865206d756c7469736967206f7065726174696f6e20697320616c726561647920756e6465727761792e3857726f6e6754696d65706f696e74043101204120646966666572656e742074696d65706f696e742077617320676976656e20746f20746865206d756c7469736967206f7065726174696f6e207468617420697320756e6465727761792e4c556e657870656374656454696d65706f696e7404f820412074696d65706f696e742077617320676976656e2c20796574206e6f206d756c7469736967206f7065726174696f6e20697320756e6465727761792e30576569676874546f6f4c6f7704d420546865206d6178696d756d2077656967687420696e666f726d6174696f6e2070726f76696465642077617320746f6f206c6f772e34416c726561647953746f72656404a420546865206461746120746f2062652073746f72656420697320616c72656164792073746f7265642e041c40436865636b5370656356657273696f6e38436865636b547856657273696f6e30436865636b47656e6573697338436865636b4d6f7274616c69747928436865636b4e6f6e63652c436865636b576569676874604368617267655472616e73616374696f6e5061796d656e74 \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v11.json b/packages/polkadot/tests/meta/v11.json new file mode 100644 index 00000000..22ce8ddb --- /dev/null +++ b/packages/polkadot/tests/meta/v11.json @@ -0,0 +1,11686 @@ +{ + "magicNumber": 1635018093, + "metadata": { + "v11": { + "modules": [ + { + "name": "System", + "storage": { + "prefix": "System", + "items": [ + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountInfo", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The full account information for a particular account ID." + ] + }, + { + "name": "ExtrinsicCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total extrinsics count for the current block." + ] + }, + { + "name": "BlockWeight", + "modifier": "Default", + "type": { + "plain": "ExtrinsicsWeight" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The current weight for the block." + ] + }, + { + "name": "AllExtrinsicsLen", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total length (in bytes) for all extrinsics put together, for the current block." + ] + }, + { + "name": "BlockHash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Map of block numbers to block hashes." + ] + }, + { + "name": "ExtrinsicData", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Extrinsics data for the current block (maps an extrinsic's index to its data)." + ] + }, + { + "name": "Number", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The current block number being processed. Set by `execute_block`." + ] + }, + { + "name": "ParentHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Hash of the previous block." + ] + }, + { + "name": "ExtrinsicsRoot", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Extrinsics root of the current block, also part of the block header." + ] + }, + { + "name": "Digest", + "modifier": "Default", + "type": { + "plain": "DigestOf" + }, + "fallback": "0x00", + "docs": [ + " Digest of the current block, also part of the block header." + ] + }, + { + "name": "Events", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Events deposited for the current block." + ] + }, + { + "name": "EventCount", + "modifier": "Default", + "type": { + "plain": "EventIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of events in the `Events` list." + ] + }, + { + "name": "EventTopics", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "Hash", + "value": "Vec<(BlockNumber,EventIndex)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Mapping between a topic (represented by T::Hash) and a vector of indexes", + " of events in the `>` list.", + "", + " All topic vectors have deterministic storage locations depending on the topic. This", + " allows light-clients to leverage the changes trie storage tracking mechanism and", + " in case of changes fetch the list of events of interest.", + "", + " The value has the type `(T::BlockNumber, EventIndex)` because if we used only just", + " the `EventIndex` then in case if the topic has the same contents on the next block", + " no notification will be triggered thus the event might be lost." + ] + }, + { + "name": "LastRuntimeUpgrade", + "modifier": "Optional", + "type": { + "plain": "LastRuntimeUpgradeInfo" + }, + "fallback": "0x00", + "docs": [ + " Stores the `spec_version` and `spec_name` of when the last runtime upgrade happened." + ] + }, + { + "name": "ExecutionPhase", + "modifier": "Optional", + "type": { + "plain": "Phase" + }, + "fallback": "0x00", + "docs": [ + " The execution phase of the block." + ] + } + ] + }, + "calls": [ + { + "name": "fill_block", + "args": [ + { + "name": "_ratio", + "type": "Perbill" + } + ], + "docs": [ + " A dispatch that will fill the block weight up to the given ratio." + ] + }, + { + "name": "remark", + "args": [ + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark.", + "", + " # ", + " - `O(1)`", + " - Base Weight: 0.665 µs, independent of remark length.", + " - No DB operations.", + " # " + ] + }, + { + "name": "set_heap_pages", + "args": [ + { + "name": "pages", + "type": "u64" + } + ], + "docs": [ + " Set the number of pages in the WebAssembly environment's heap.", + "", + " # ", + " - `O(1)`", + " - 1 storage write.", + " - Base Weight: 1.405 µs", + " - 1 write to HEAP_PAGES", + " # " + ] + }, + { + "name": "set_code", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code.", + "", + " # ", + " - `O(C + S)` where `C` length of `code` and `S` complexity of `can_set_code`", + " - 1 storage write (codec `O(C)`).", + " - 1 call to `can_set_code`: `O(S)` (calls `sp_io::misc::runtime_version` which is expensive).", + " - 1 event.", + " The weight of this function is dependent on the runtime, but generally this is very expensive.", + " We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_code_without_checks", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code without doing any checks of the given `code`.", + "", + " # ", + " - `O(C)` where `C` length of `code`", + " - 1 storage write (codec `O(C)`).", + " - 1 event.", + " The weight of this function is dependent on the runtime. We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_changes_trie_config", + "args": [ + { + "name": "changes_trie_config", + "type": "Option" + } + ], + "docs": [ + " Set the new changes trie configuration.", + "", + " # ", + " - `O(1)`", + " - 1 storage write or delete (codec `O(1)`).", + " - 1 call to `deposit_log`: Uses `append` API, so O(1)", + " - Base Weight: 7.218 µs", + " - DB Weight:", + " - Writes: Changes Trie, System Digest", + " # " + ] + }, + { + "name": "set_storage", + "args": [ + { + "name": "items", + "type": "Vec" + } + ], + "docs": [ + " Set some items of storage.", + "", + " # ", + " - `O(I)` where `I` length of `items`", + " - `I` storage writes (`O(1)`).", + " - Base Weight: 0.568 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_storage", + "args": [ + { + "name": "keys", + "type": "Vec" + } + ], + "docs": [ + " Kill some items from storage.", + "", + " # ", + " - `O(IK)` where `I` length of `keys` and `K` length of one key", + " - `I` storage deletions.", + " - Base Weight: .378 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_prefix", + "args": [ + { + "name": "prefix", + "type": "Key" + }, + { + "name": "_subkeys", + "type": "u32" + } + ], + "docs": [ + " Kill all storage items with a key that starts with the given prefix.", + "", + " **NOTE:** We rely on the Root origin to provide us the number of subkeys under", + " the prefix we are removing to accurately calculate the weight of this function.", + "", + " # ", + " - `O(P)` where `P` amount of keys with prefix `prefix`", + " - `P` storage deletions.", + " - Base Weight: 0.834 * P µs", + " - Writes: Number of subkeys + 1", + " # " + ] + }, + { + "name": "suicide", + "args": [], + "docs": [ + " Kill the sending account, assuming there are no references outstanding and the composite", + " data is equal to its default value.", + "", + " # ", + " - `O(1)`", + " - 1 storage read and deletion.", + " --------------------", + " Base Weight: 8.626 µs", + " No DB Read or Write operations because caller is already in overlay", + " # " + ] + } + ], + "events": [ + { + "name": "ExtrinsicSuccess", + "args": [ + "DispatchInfo" + ], + "docs": [ + " An extrinsic completed successfully. [info]" + ] + }, + { + "name": "ExtrinsicFailed", + "args": [ + "DispatchError", + "DispatchInfo" + ], + "docs": [ + " An extrinsic failed. [error, info]" + ] + }, + { + "name": "CodeUpdated", + "args": [], + "docs": [ + " `:code` was updated." + ] + }, + { + "name": "NewAccount", + "args": [ + "AccountId" + ], + "docs": [ + " A new [account] was created." + ] + }, + { + "name": "KilledAccount", + "args": [ + "AccountId" + ], + "docs": [ + " An [account] was reaped." + ] + } + ], + "constants": [ + { + "name": "BlockHashCount", + "type": "BlockNumber", + "value": "0x60090000", + "docs": [ + " The maximum number of blocks to allow in mortal eras." + ] + }, + { + "name": "MaximumBlockWeight", + "type": "Weight", + "value": "0x00204aa9d1010000", + "docs": [ + " The maximum weight of a block." + ] + }, + { + "name": "DbWeight", + "type": "RuntimeDbWeight", + "value": "0x40787d010000000000e1f50500000000", + "docs": [ + " The weight of runtime database operations the runtime can invoke." + ] + }, + { + "name": "BlockExecutionWeight", + "type": "Weight", + "value": "0x00f2052a01000000", + "docs": [ + " The base weight of executing a block, independent of the transactions in the block." + ] + }, + { + "name": "ExtrinsicBaseWeight", + "type": "Weight", + "value": "0x4059730700000000", + "docs": [ + " The base weight of an Extrinsic in the block, independent of the of extrinsic being executed." + ] + }, + { + "name": "MaximumBlockLength", + "type": "u32", + "value": "0x00005000", + "docs": [ + " The maximum length of a block (in bytes)." + ] + } + ], + "errors": [ + { + "name": "InvalidSpecName", + "docs": [ + " The name of specification does not match between the current runtime", + " and the new runtime." + ] + }, + { + "name": "SpecVersionNeedsToIncrease", + "docs": [ + " The specification version is not allowed to decrease between the current runtime", + " and the new runtime." + ] + }, + { + "name": "FailedToExtractRuntimeVersion", + "docs": [ + " Failed to extract the runtime version from the new runtime.", + "", + " Either calling `Core_version` or decoding `RuntimeVersion` failed." + ] + }, + { + "name": "NonDefaultComposite", + "docs": [ + " Suicide called when the account has non-default composite data." + ] + }, + { + "name": "NonZeroRefCount", + "docs": [ + " There is a non-zero reference count preventing the account from being purged." + ] + } + ] + }, + { + "name": "Utility", + "storage": null, + "calls": [ + { + "name": "batch", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " If origin is root then call are dispatch without checking origin filter. (This includes", + " bypassing `frame_system::Trait::BaseCallFilter`).", + "", + " # ", + " - Base weight: 14.39 + .987 * c µs", + " - Plus the sum of the weights of the `calls`.", + " - Plus one additional event. (repeat read/write)", + " # ", + "", + " This will return `Ok` in all circumstances. To determine the success of the batch, an", + " event is deposited. If a call failed and the batch was interrupted, then the", + " `BatchInterrupted` event is deposited, along with the number of successful calls made", + " and the error of the failed call. If all were successful, then the `BatchCompleted`", + " event is deposited." + ] + }, + { + "name": "as_derivative", + "args": [ + { + "name": "index", + "type": "u16" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through an indexed pseudonym of the sender.", + "", + " Filter from origin are passed along. The call will be dispatched with an origin which", + " use the same filter as the origin of this call.", + "", + " NOTE: If you need to ensure that any account-based filtering is not honored (i.e.", + " because you expect `proxy` to have been used prior in the call stack and you do not want", + " the call restrictions to apply to any sub-accounts), then use `as_multi_threshold_1`", + " in the Multisig pallet instead.", + "", + " NOTE: Prior to version *12, this was called `as_limited_sub`.", + "", + " The dispatch origin for this call must be _Signed_." + ] + } + ], + "events": [ + { + "name": "BatchInterrupted", + "args": [ + "u32", + "DispatchError" + ], + "docs": [ + " Batch of dispatches did not complete fully. Index of first failing dispatch given, as", + " well as the error. [index, error]" + ] + }, + { + "name": "BatchCompleted", + "args": [], + "docs": [ + " Batch of dispatches completed fully with no error." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Babe", + "storage": { + "prefix": "Babe", + "items": [ + { + "name": "EpochIndex", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current epoch index." + ] + }, + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Current epoch authorities." + ] + }, + { + "name": "GenesisSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The slot at which the first epoch actually started. This is 0", + " until the first block of the chain." + ] + }, + { + "name": "CurrentSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current slot number." + ] + }, + { + "name": "Randomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The epoch randomness for the *current* epoch.", + "", + " # Security", + "", + " This MUST NOT be used for gambling, as it can be influenced by a", + " malicious validator in the short term. It MAY be used in many", + " cryptographic protocols, however, so long as one remembers that this", + " (like everything else on-chain) it is public. For example, it can be", + " used where a number is needed that cannot have been chosen by an", + " adversary, for purposes such as public-coin zero-knowledge proofs." + ] + }, + { + "name": "NextEpochConfig", + "modifier": "Optional", + "type": { + "plain": "NextConfigDescriptor" + }, + "fallback": "0x00", + "docs": [ + " Next epoch configuration, if changed." + ] + }, + { + "name": "NextRandomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Next epoch randomness." + ] + }, + { + "name": "SegmentIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Randomness under construction.", + "", + " We make a tradeoff between storage accesses and list length.", + " We store the under-construction randomness in segments of up to", + " `UNDER_CONSTRUCTION_SEGMENT_LENGTH`.", + "", + " Once a segment reaches this length, we begin the next one.", + " We reset all segments and return to `0` at the beginning of every", + " epoch." + ] + }, + { + "name": "UnderConstruction", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " TWOX-NOTE: `SegmentIndex` is an increasing integer, so this is okay." + ] + }, + { + "name": "Initialized", + "modifier": "Optional", + "type": { + "plain": "MaybeRandomness" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) which is `Some`", + " if per-block initialization has already been called for current block." + ] + }, + { + "name": "Lateness", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " How late the current block is compared to its parent.", + "", + " This entry is populated as part of block execution and is cleaned up", + " on block finalization. Querying this storage entry outside of block", + " execution context should always yield zero." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported.", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + } + ], + "events": null, + "constants": [ + { + "name": "EpochDuration", + "type": "u64", + "value": "0xc800000000000000", + "docs": [ + " The number of **slots** that an epoch takes. We couple sessions to", + " epochs, i.e. we start a new session once the new epoch begins." + ] + }, + { + "name": "ExpectedBlockTime", + "type": "Moment", + "value": "0xb80b000000000000", + "docs": [ + " The expected average block time at which BABE should be creating", + " blocks. Since BABE is probabilistic it is not trivial to figure out", + " what the expected average block time should be based on the slot", + " duration and the security parameter `c` (where `1 - c` represents", + " the probability of a slot being empty)." + ] + } + ], + "errors": [] + }, + { + "name": "Timestamp", + "storage": { + "prefix": "Timestamp", + "items": [ + { + "name": "Now", + "modifier": "Default", + "type": { + "plain": "Moment" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current time for the current block." + ] + }, + { + "name": "DidUpdate", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Did the timestamp get updated in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "set", + "args": [ + { + "name": "now", + "type": "Compact" + } + ], + "docs": [ + " Set the current time.", + "", + " This call should be invoked exactly once per block. It will panic at the finalization", + " phase, if this call hasn't been invoked by that time.", + "", + " The timestamp should be greater than the previous one by the amount specified by", + " `MinimumPeriod`.", + "", + " The dispatch origin for this call must be `Inherent`.", + "", + " # ", + " - `O(T)` where `T` complexity of `on_timestamp_set`", + " - 1 storage read and 1 storage mutation (codec `O(1)`). (because of `DidUpdate::take` in `on_finalize`)", + " - 1 event handler `on_timestamp_set` `O(T)`.", + " # " + ] + } + ], + "events": null, + "constants": [ + { + "name": "MinimumPeriod", + "type": "Moment", + "value": "0xdc05000000000000", + "docs": [ + " The minimum period between blocks. Beware that this is different to the *expected* period", + " that the block production apparatus provides. Your chosen consensus system will generally", + " work with this to determine a sensible block time. e.g. For Aura, it will be double this", + " period on default settings." + ] + } + ], + "errors": [] + }, + { + "name": "Authorship", + "storage": { + "prefix": "Authorship", + "items": [ + { + "name": "Uncles", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Uncles" + ] + }, + { + "name": "Author", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " Author of current block." + ] + }, + { + "name": "DidSetUncles", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Whether uncles were already set in this block." + ] + } + ] + }, + "calls": [ + { + "name": "set_uncles", + "args": [ + { + "name": "new_uncles", + "type": "Vec
" + } + ], + "docs": [ + " Provide a set of uncles." + ] + } + ], + "events": null, + "constants": [], + "errors": [ + { + "name": "InvalidUncleParent", + "docs": [ + " The uncle parent not in the chain." + ] + }, + { + "name": "UnclesAlreadySet", + "docs": [ + " Uncles already set in the block." + ] + }, + { + "name": "TooManyUncles", + "docs": [ + " Too many uncles." + ] + }, + { + "name": "GenesisUncle", + "docs": [ + " The uncle is genesis." + ] + }, + { + "name": "TooHighUncle", + "docs": [ + " The uncle is too high in chain." + ] + }, + { + "name": "UncleAlreadyIncluded", + "docs": [ + " The uncle is already included." + ] + }, + { + "name": "OldUncle", + "docs": [ + " The uncle isn't recent enough to be included." + ] + } + ] + }, + { + "name": "Indices", + "storage": { + "prefix": "Indices", + "items": [ + { + "name": "Accounts", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountIndex", + "value": "(AccountId,BalanceOf,bool)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The lookup from index to account." + ] + } + ] + }, + "calls": [ + { + "name": "claim", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an previously unassigned index.", + "", + " Payment: `Deposit` is reserved from the sender account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be claimed. This must not be in use.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - Base Weight: 28.69 µs", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an index already owned by the sender to another account. The balance reservation", + " is effectively transferred to the new account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be re-assigned. This must be owned by the sender.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One transfer operation.", + " - One event.", + " -------------------", + " - Base Weight: 33.74 µs", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (recipient)", + " - Writes: Indices Accounts, System Account (recipient)", + " # " + ] + }, + { + "name": "free", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Free up an index owned by the sender.", + "", + " Payment: Any previous deposit placed for the index is unreserved in the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must own the index.", + "", + " - `index`: the index to be freed. This must be owned by the sender.", + "", + " Emits `IndexFreed` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - Base Weight: 25.53 µs", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + }, + { + "name": "freeze", + "type": "bool" + } + ], + "docs": [ + " Force an index to an account. This doesn't require a deposit. If the index is already", + " held, then any deposit is reimbursed to its current owner.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `index`: the index to be (re-)assigned.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + " - `freeze`: if set to `true`, will freeze the index so it cannot be transferred.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one reserve operation.", + " - One event.", + " -------------------", + " - Base Weight: 26.83 µs", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (original owner)", + " - Writes: Indices Accounts, System Account (original owner)", + " # " + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Freeze an index so it will always point to the sender account. This consumes the deposit.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must have a", + " non-frozen account `index`.", + "", + " - `index`: the index to be frozen in place.", + "", + " Emits `IndexFrozen` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one slash operation.", + " - One event.", + " -------------------", + " - Base Weight: 30.86 µs", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + } + ], + "events": [ + { + "name": "IndexAssigned", + "args": [ + "AccountId", + "AccountIndex" + ], + "docs": [ + " A account index was assigned. [who, index]" + ] + }, + { + "name": "IndexFreed", + "args": [ + "AccountIndex" + ], + "docs": [ + " A account index has been freed up (unassigned). [index]" + ] + }, + { + "name": "IndexFrozen", + "args": [ + "AccountIndex", + "AccountId" + ], + "docs": [ + " A account index has been frozen to its current account ID. [who, index]" + ] + } + ], + "constants": [ + { + "name": "Deposit", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The deposit needed for reserving an index." + ] + } + ], + "errors": [] + }, + { + "name": "Balances", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "TotalIssuance", + "modifier": "Default", + "type": { + "plain": "Balance" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total units issued in the system." + ] + }, + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountData", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The balance of an account.", + "", + " NOTE: This is only used in the case that this module is used to store balances." + ] + }, + { + "name": "Locks", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Any liquidity locks on some account balances.", + " NOTE: Should only be accessed when setting, changing and freeing a lock." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " This is set to v2.0.0 for new networks." + ] + } + ] + }, + "calls": [ + { + "name": "transfer", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Transfer some liquid free balance to another account.", + "", + " `transfer` will set the `FreeBalance` of the sender and receiver.", + " It will decrease the total issuance of the system by the `TransferFee`.", + " If the sender's account is below the existential deposit as a result", + " of the transfer, the account will be reaped.", + "", + " The dispatch origin for this call must be `Signed` by the transactor.", + "", + " # ", + " - Dependent on arguments but not critical, given proper implementations for", + " input config types. See related functions below.", + " - It contains a limited number of reads and writes internally and no complex computation.", + "", + " Related functions:", + "", + " - `ensure_can_withdraw` is always called internally but has a bounded complexity.", + " - Transferring balances to accounts that did not exist before will cause", + " `T::OnNewAccount::on_new_account` to be called.", + " - Removing enough funds from an account will trigger `T::DustRemoval::on_unbalanced`.", + " - `transfer_keep_alive` works the same way as `transfer`, but has an additional", + " check that the transfer will not kill the origin account.", + " ---------------------------------", + " - Base Weight: 73.64 µs, worst case scenario (account created, account removed)", + " - DB Weight: 1 Read and 1 Write to destination account", + " - Origin account is already in memory, so no DB operations for them.", + " # " + ] + }, + { + "name": "set_balance", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "new_free", + "type": "Compact" + }, + { + "name": "new_reserved", + "type": "Compact" + } + ], + "docs": [ + " Set the balances of a given account.", + "", + " This will alter `FreeBalance` and `ReservedBalance` in storage. it will", + " also decrease the total issuance of the system (`TotalIssuance`).", + " If the new free or reserved balance is below the existential deposit,", + " it will reset the account nonce (`frame_system::AccountNonce`).", + "", + " The dispatch origin for this call is `root`.", + "", + " # ", + " - Independent of the arguments.", + " - Contains a limited number of reads and writes.", + " ---------------------", + " - Base Weight:", + " - Creating: 27.56 µs", + " - Killing: 35.11 µs", + " - DB Weight: 1 Read, 1 Write to `who`", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Exactly as `transfer`, except the origin must be root and the source account may be", + " specified.", + " # ", + " - Same as transfer, but additional read and write because the source account is", + " not assumed to be in the overlay.", + " # " + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Same as the [`transfer`] call, but with a check that the transfer will not kill the", + " origin account.", + "", + " 99% of the time you want [`transfer`] instead.", + "", + " [`transfer`]: struct.Module.html#method.transfer", + " # ", + " - Cheaper than transfer because account cannot be killed.", + " - Base Weight: 51.4 µs", + " - DB Weight: 1 Read and 1 Write to dest (sender is in overlay already)", + " #" + ] + } + ], + "events": [ + { + "name": "Endowed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was created with some free balance. [account, free_balance]" + ] + }, + { + "name": "DustLost", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was removed whose balance was non-zero but below ExistentialDeposit,", + " resulting in an outright loss. [account, balance]" + ] + }, + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " Transfer succeeded. [from, to, value]" + ] + }, + { + "name": "BalanceSet", + "args": [ + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " A balance was set by root. [who, free, reserved]" + ] + }, + { + "name": "Deposit", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some amount was deposited (e.g. for transaction fees). [who, deposit]" + ] + }, + { + "name": "Reserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was reserved (moved from free to reserved). [who, value]" + ] + }, + { + "name": "Unreserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was unreserved (moved from reserved to free). [who, value]" + ] + }, + { + "name": "ReserveRepatriated", + "args": [ + "AccountId", + "AccountId", + "Balance", + "BalanceStatus" + ], + "docs": [ + " Some balance was moved from the reserve of the first account to the second account.", + " Final argument indicates the destination balance type.", + " [from, to, balance, destination_status]" + ] + } + ], + "constants": [ + { + "name": "ExistentialDeposit", + "type": "Balance", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to keep an account open." + ] + } + ], + "errors": [ + { + "name": "VestingBalance", + "docs": [ + " Vesting balance too high to send value" + ] + }, + { + "name": "LiquidityRestrictions", + "docs": [ + " Account liquidity restrictions prevent withdrawal" + ] + }, + { + "name": "Overflow", + "docs": [ + " Got an overflow after adding" + ] + }, + { + "name": "InsufficientBalance", + "docs": [ + " Balance too low to send value" + ] + }, + { + "name": "ExistentialDeposit", + "docs": [ + " Value too low to create account due to existential deposit" + ] + }, + { + "name": "KeepAlive", + "docs": [ + " Transfer/payment would kill account" + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " A vesting schedule already exists for this account" + ] + }, + { + "name": "DeadAccount", + "docs": [ + " Beneficiary account must pre-exist" + ] + } + ] + }, + { + "name": "TransactionPayment", + "storage": { + "prefix": "TransactionPayment", + "items": [ + { + "name": "NextFeeMultiplier", + "modifier": "Default", + "type": { + "plain": "Multiplier" + }, + "fallback": "0x000064a7b3b6e00d0000000000000000", + "docs": [] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": null, + "events": null, + "constants": [ + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + }, + { + "name": "WeightToFee", + "type": "Vec", + "value": "0x0401000000000000000000000000000000000000000001", + "docs": [ + " The polynomial that is applied in order to derive fee from weight." + ] + } + ], + "errors": [] + }, + { + "name": "Staking", + "storage": { + "prefix": "Staking", + "items": [ + { + "name": "HistoryDepth", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x54000000", + "docs": [ + " Number of eras to keep in history.", + "", + " Information is kept for eras in `[current_era - history_depth; current_era]`.", + "", + " Must be more than the number of eras delayed by session otherwise. I.e. active era must", + " always be in history. I.e. `active_era > current_era - history_depth` must be", + " guaranteed." + ] + }, + { + "name": "ValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The ideal number of staking participants." + ] + }, + { + "name": "MinimumValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Minimum number of staking participants before emergency conditions are imposed." + ] + }, + { + "name": "Invulnerables", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Any validators that may never be slashed or forcibly kicked. It's a Vec since they're", + " easy to initialize and the performance hit is minimal (we expect no more than four", + " invulnerables) and restricted to testnets." + ] + }, + { + "name": "Bonded", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all locked \"stash\" accounts to the controller account." + ] + }, + { + "name": "Ledger", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "StakingLedger", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all (unlocked) \"controller\" accounts to the info regarding the staking." + ] + }, + { + "name": "Payee", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RewardDestination", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Where the reward payment should be made. Keyed by stash." + ] + }, + { + "name": "Validators", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ValidatorPrefs", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The map from (wannabe) validator stash key to the preferences of that validator." + ] + }, + { + "name": "Nominators", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Nominations", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The map from nominator stash key to the set of stash keys of all validators to nominate." + ] + }, + { + "name": "CurrentEra", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The current era index.", + "", + " This is the latest planned era, depending on how the Session pallet queues the validator", + " set, it might be active or not." + ] + }, + { + "name": "ActiveEra", + "modifier": "Optional", + "type": { + "plain": "ActiveEraInfo" + }, + "fallback": "0x00", + "docs": [ + " The active era information, it holds index and start.", + "", + " The active era is the era currently rewarded.", + " Validator set of this era must be equal to `SessionInterface::validators`." + ] + }, + { + "name": "ErasStartSessionIndex", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The session index at which the era start for the last `HISTORY_DEPTH` eras." + ] + }, + { + "name": "ErasStakers", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Exposure of validator at era.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasStakersClipped", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Clipped Exposure of validator at era.", + "", + " This is similar to [`ErasStakers`] but number of nominators exposed is reduced to the", + " `T::MaxNominatorRewardedPerValidator` biggest stakers.", + " (Note: the field `total` and `own` of the exposure remains unchanged).", + " This is used to limit the i/o cost for the nominator payout.", + "", + " This is keyed fist by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasValidatorPrefs", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "ValidatorPrefs", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Similar to `ErasStakers`, this holds the preferences of validators.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras." + ] + }, + { + "name": "ErasValidatorReward", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The total validator era payout for the last `HISTORY_DEPTH` eras.", + "", + " Eras that haven't finished yet or has been removed doesn't have reward." + ] + }, + { + "name": "ErasRewardPoints", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "EraRewardPoints", + "linked": false + } + }, + "fallback": "0x0000000000", + "docs": [ + " Rewards for the last `HISTORY_DEPTH` eras.", + " If reward hasn't been set or has been removed then 0 reward is returned." + ] + }, + { + "name": "ErasTotalStake", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total amount staked for the last `HISTORY_DEPTH` eras.", + " If total hasn't been set or has been removed then 0 stake is returned." + ] + }, + { + "name": "ForceEra", + "modifier": "Default", + "type": { + "plain": "Forcing" + }, + "fallback": "0x00", + "docs": [ + " Mode of era forcing." + ] + }, + { + "name": "SlashRewardFraction", + "modifier": "Default", + "type": { + "plain": "Perbill" + }, + "fallback": "0x00000000", + "docs": [ + " The percentage of the slash that is distributed to reporters.", + "", + " The rest of the slashed value is handled by the `Slash`." + ] + }, + { + "name": "CanceledSlashPayout", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of currency given to reporters of a slash event which was", + " canceled by extraordinary circumstances (e.g. governance)." + ] + }, + { + "name": "UnappliedSlashes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " All unapplied slashes that are queued for later." + ] + }, + { + "name": "BondedEras", + "modifier": "Default", + "type": { + "plain": "Vec<(EraIndex,SessionIndex)>" + }, + "fallback": "0x00", + "docs": [ + " A mapping from still-bonded eras to the first session index of that era.", + "", + " Must contains information for eras for the range:", + " `[active_era - bounding_duration; active_era]`" + ] + }, + { + "name": "ValidatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "(Perbill,BalanceOf)", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on validators, mapped by era to the highest slash proportion", + " and slash value of the era." + ] + }, + { + "name": "NominatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "BalanceOf", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on nominators, mapped by era to the highest slash value of the era." + ] + }, + { + "name": "SlashingSpans", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SlashingSpans", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Slashing spans for stash accounts." + ] + }, + { + "name": "SpanSlash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(AccountId,SpanIndex)", + "value": "SpanRecord", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Records information about the maximum slash of a stash within a slashing span,", + " as well as how much reward has been paid out." + ] + }, + { + "name": "EarliestUnappliedSlash", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The earliest era for which we have a pending, unapplied slash." + ] + }, + { + "name": "SnapshotValidators", + "modifier": "Optional", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Snapshot of validators at the beginning of the current election window. This should only", + " have a value when [`EraElectionStatus`] == `ElectionStatus::Open(_)`." + ] + }, + { + "name": "SnapshotNominators", + "modifier": "Optional", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Snapshot of nominators at the beginning of the current election window. This should only", + " have a value when [`EraElectionStatus`] == `ElectionStatus::Open(_)`." + ] + }, + { + "name": "QueuedElected", + "modifier": "Optional", + "type": { + "plain": "ElectionResult" + }, + "fallback": "0x00", + "docs": [ + " The next validator set. At the end of an era, if this is available (potentially from the", + " result of an offchain worker), it is immediately used. Otherwise, the on-chain election", + " is executed." + ] + }, + { + "name": "QueuedScore", + "modifier": "Optional", + "type": { + "plain": "ElectionScore" + }, + "fallback": "0x00", + "docs": [ + " The score of the current [`QueuedElected`]." + ] + }, + { + "name": "EraElectionStatus", + "modifier": "Default", + "type": { + "plain": "ElectionStatus" + }, + "fallback": "0x00", + "docs": [ + " Flag to control the execution of the offchain election. When `Open(_)`, we accept", + " solutions to be submitted." + ] + }, + { + "name": "IsCurrentSessionFinal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the current **planned** session is final. Note that this does not take era", + " forcing into account." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x03", + "docs": [ + " True if network has been upgraded to this version.", + " Storage version of the pallet.", + "", + " This is set to v3.0.0 for new networks." + ] + } + ] + }, + "calls": [ + { + "name": "bond", + "args": [ + { + "name": "controller", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " Take the origin account as a stash and lock up `value` of its balance. `controller` will", + " be the account that controls it.", + "", + " `value` must be more than the `minimum_balance` specified by `T::Currency`.", + "", + " The dispatch origin for this call must be _Signed_ by the stash account.", + "", + " Emits `Bonded`.", + "", + " # ", + " - Independent of the arguments. Moderate complexity.", + " - O(1).", + " - Three extra DB entries.", + "", + " NOTE: Two of the storage writes (`Self::bonded`, `Self::payee`) are _never_ cleaned", + " unless the `origin` falls below _existential deposit_ and gets removed as dust.", + " ------------------", + " Base Weight: 67.87 µs", + " DB Weight:", + " - Read: Bonded, Ledger, [Origin Account], Current Era, History Depth, Locks", + " - Write: Bonded, Payee, [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "bond_extra", + "args": [ + { + "name": "max_additional", + "type": "Compact" + } + ], + "docs": [ + " Add some extra amount that have appeared in the stash `free_balance` into the balance up", + " for staking.", + "", + " Use this if there are additional funds in your stash account that you wish to bond.", + " Unlike [`bond`] or [`unbond`] this function does not impose any limitation on the amount", + " that can be added.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller and", + " it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Bonded`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - O(1).", + " - One DB entry.", + " ------------", + " Base Weight: 54.88 µs", + " DB Weight:", + " - Read: Era Election Status, Bonded, Ledger, [Origin Account], Locks", + " - Write: [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "unbond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Schedule a portion of the stash to be unlocked ready for transfer out after the bond", + " period ends. If this leaves an amount actively bonded less than", + " T::Currency::minimum_balance(), then it is increased to the full amount.", + "", + " Once the unlock period is done, you can call `withdraw_unbonded` to actually move", + " the funds out of management ready for transfer.", + "", + " No more than a limited number of unlocking chunks (see `MAX_UNLOCKING_CHUNKS`)", + " can co-exists at the same time. In that case, [`Call::withdraw_unbonded`] need", + " to be called first to remove some of the chunks (if possible).", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Unbonded`.", + "", + " See also [`Call::withdraw_unbonded`].", + "", + " # ", + " - Independent of the arguments. Limited but potentially exploitable complexity.", + " - Contains a limited number of reads.", + " - Each call (requires the remainder of the bonded balance to be above `minimum_balance`)", + " will cause a new entry to be inserted into a vector (`Ledger.unlocking`) kept in storage.", + " The only way to clean the aforementioned storage item is also user-controlled via", + " `withdraw_unbonded`.", + " - One DB entry.", + " ----------", + " Base Weight: 50.34 µs", + " DB Weight:", + " - Read: Era Election Status, Ledger, Current Era, Locks, [Origin Account]", + " - Write: [Origin Account], Locks, Ledger", + " " + ] + }, + { + "name": "withdraw_unbonded", + "args": [ + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove any unlocked chunks from the `unlocking` queue from our management.", + "", + " This essentially frees up that balance to be used by the stash account to do", + " whatever it wants.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Withdrawn`.", + "", + " See also [`Call::unbond`].", + "", + " # ", + " - Could be dependent on the `origin` argument and how much `unlocking` chunks exist.", + " It implies `consolidate_unlocked` which loops over `Ledger.unlocking`, which is", + " indirectly user-controlled. See [`unbond`] for more detail.", + " - Contains a limited number of reads, yet the size of which could be large based on `ledger`.", + " - Writes are limited to the `origin` account key.", + " ---------------", + " Complexity O(S) where S is the number of slashing spans to remove", + " Base Weight:", + " Update: 50.52 + .028 * S µs", + " - Reads: EraElectionStatus, Ledger, Current Era, Locks, [Origin Account]", + " - Writes: [Origin Account], Locks, Ledger", + " Kill: 79.41 + 2.366 * S µs", + " - Reads: EraElectionStatus, Ledger, Current Era, Bonded, Slashing Spans, [Origin Account], Locks", + " - Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, [Origin Account], Locks", + " - Writes Each: SpanSlash * S", + " NOTE: Weight annotation is the kill scenario, we refund otherwise.", + " # " + ] + }, + { + "name": "validate", + "args": [ + { + "name": "prefs", + "type": "ValidatorPrefs" + } + ], + "docs": [ + " Declare the desire to validate for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " -----------", + " Base Weight: 17.13 µs", + " DB Weight:", + " - Read: Era Election Status, Ledger", + " - Write: Nominators, Validators", + " # " + ] + }, + { + "name": "nominate", + "args": [ + { + "name": "targets", + "type": "Vec" + } + ], + "docs": [ + " Declare the desire to nominate `targets` for the origin controller.", + "", + " Effects will be felt at the beginning of the next era. This can only be called when", + " [`EraElectionStatus`] is `Closed`.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - The transaction's complexity is proportional to the size of `targets` (N)", + " which is capped at CompactAssignments::LIMIT (MAX_NOMINATIONS).", + " - Both the reads and writes follow a similar pattern.", + " ---------", + " Base Weight: 22.34 + .36 * N µs", + " where N is the number of targets", + " DB Weight:", + " - Reads: Era Election Status, Ledger, Current Era", + " - Writes: Validators, Nominators", + " # " + ] + }, + { + "name": "chill", + "args": [], + "docs": [ + " Declare no desire to either validate or nominate.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains one read.", + " - Writes are limited to the `origin` account key.", + " --------", + " Base Weight: 16.53 µs", + " DB Weight:", + " - Read: EraElectionStatus, Ledger", + " - Write: Validators, Nominators", + " # " + ] + }, + { + "name": "set_payee", + "args": [ + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " (Re-)set the payment target for a controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ---------", + " - Base Weight: 11.33 µs", + " - DB Weight:", + " - Read: Ledger", + " - Write: Payee", + " # " + ] + }, + { + "name": "set_controller", + "args": [ + { + "name": "controller", + "type": "LookupSource" + } + ], + "docs": [ + " (Re-)set the controller of a stash.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ----------", + " Base Weight: 25.22 µs", + " DB Weight:", + " - Read: Bonded, Ledger New Controller, Ledger Old Controller", + " - Write: Bonded, Ledger New Controller, Ledger Old Controller", + " # " + ] + }, + { + "name": "set_validator_count", + "args": [ + { + "name": "new", + "type": "Compact" + } + ], + "docs": [ + " Sets the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Base Weight: 1.717 µs", + " Write: Validator Count", + " # " + ] + }, + { + "name": "increase_validator_count", + "args": [ + { + "name": "additional", + "type": "Compact" + } + ], + "docs": [ + " Increments the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Base Weight: 1.717 µs", + " Read/Write: Validator Count", + " # " + ] + }, + { + "name": "scale_validator_count", + "args": [ + { + "name": "factor", + "type": "Percent" + } + ], + "docs": [ + " Scale up the ideal number of validators by a factor.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Base Weight: 1.717 µs", + " Read/Write: Validator Count", + " # " + ] + }, + { + "name": "force_no_eras", + "args": [], + "docs": [ + " Force there to be no new eras indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - No arguments.", + " - Base Weight: 1.857 µs", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "force_new_era", + "args": [], + "docs": [ + " Force there to be a new era at the end of the next session. After this, it will be", + " reset to normal (non-forced) behaviour.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - No arguments.", + " - Base Weight: 1.959 µs", + " - Write ForceEra", + " # " + ] + }, + { + "name": "set_invulnerables", + "args": [ + { + "name": "validators", + "type": "Vec" + } + ], + "docs": [ + " Set the validators who cannot be slashed (if any).", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - O(V)", + " - Base Weight: 2.208 + .006 * V µs", + " - Write: Invulnerables", + " # " + ] + }, + { + "name": "force_unstake", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Force a current staker to become completely unstaked, immediately.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " O(S) where S is the number of slashing spans to be removed", + " Base Weight: 53.07 + 2.365 * S µs", + " Reads: Bonded, Slashing Spans, Account, Locks", + " Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Account, Locks", + " Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "force_new_era_always", + "args": [], + "docs": [ + " Force there to be a new era at the end of sessions indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - Base Weight: 2.05 µs", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "cancel_deferred_slash", + "args": [ + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "slash_indices", + "type": "Vec" + } + ], + "docs": [ + " Cancel enactment of a deferred slash.", + "", + " Can be called by the `T::SlashCancelOrigin`.", + "", + " Parameters: era and indices of the slashes for that era to kill.", + "", + " # ", + " Complexity: O(U + S)", + " with U unapplied slashes weighted with U=1000", + " and S is the number of slash indices to be canceled.", + " - Base: 5870 + 34.61 * S µs", + " - Read: Unapplied Slashes", + " - Write: Unapplied Slashes", + " # " + ] + }, + { + "name": "payout_stakers", + "args": [ + { + "name": "validator_stash", + "type": "AccountId" + }, + { + "name": "era", + "type": "EraIndex" + } + ], + "docs": [ + " Pay out all the stakers behind a single validator for a single era.", + "", + " - `validator_stash` is the stash account of the validator. Their nominators, up to", + " `T::MaxNominatorRewardedPerValidator`, will also receive their rewards.", + " - `era` may be any era between `[current_era - history_depth; current_era]`.", + "", + " The origin of this call must be _Signed_. Any account can call this function, even if", + " it is not one of the stakers.", + "", + " This can only be called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Time complexity: at most O(MaxNominatorRewardedPerValidator).", + " - Contains a limited number of reads and writes.", + " -----------", + " N is the Number of payouts for the validator (including the validator)", + " Base Weight:", + " - Reward Destination Staked: 110 + 54.2 * N µs (Median Slopes)", + " - Reward Destination Controller (Creating): 120 + 41.95 * N µs (Median Slopes)", + " DB Weight:", + " - Read: EraElectionStatus, CurrentEra, HistoryDepth, ErasValidatorReward,", + " ErasStakersClipped, ErasRewardPoints, ErasValidatorPrefs (8 items)", + " - Read Each: Bonded, Ledger, Payee, Locks, System Account (5 items)", + " - Write Each: System Account, Locks, Ledger (3 items)", + " # " + ] + }, + { + "name": "rebond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Rebond a portion of the stash scheduled to be unlocked.", + "", + " The dispatch origin must be signed by the controller, and it can be only called when", + " [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Time complexity: O(L), where L is unlocking chunks", + " - Bounded by `MAX_UNLOCKING_CHUNKS`.", + " - Storage changes: Can't increase storage, only decrease it.", + " ---------------", + " - Base Weight: 34.51 µs * .048 L µs", + " - DB Weight:", + " - Reads: EraElectionStatus, Ledger, Locks, [Origin Account]", + " - Writes: [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "set_history_depth", + "args": [ + { + "name": "new_history_depth", + "type": "Compact" + }, + { + "name": "_era_items_deleted", + "type": "Compact" + } + ], + "docs": [ + " Set `HistoryDepth` value. This function will delete any history information", + " when `HistoryDepth` is reduced.", + "", + " Parameters:", + " - `new_history_depth`: The new history depth you would like to set.", + " - `era_items_deleted`: The number of items that will be deleted by this dispatch.", + " This should report all the storage items that will be deleted by clearing old", + " era history. Needed to report an accurate weight for the dispatch. Trusted by", + " `Root` to report an accurate number.", + "", + " Origin must be root.", + "", + " # ", + " - E: Number of history depths removed, i.e. 10 -> 7 = 3", + " - Base Weight: 29.13 * E µs", + " - DB Weight:", + " - Reads: Current Era, History Depth", + " - Writes: History Depth", + " - Clear Prefix Each: Era Stakers, EraStakersClipped, ErasValidatorPrefs", + " - Writes Each: ErasValidatorReward, ErasRewardPoints, ErasTotalStake, ErasStartSessionIndex", + " # " + ] + }, + { + "name": "reap_stash", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove all data structure concerning a staker/stash once its balance is zero.", + " This is essentially equivalent to `withdraw_unbonded` except it can be called by anyone", + " and the target `stash` must have no funds left.", + "", + " This can be called from any origin.", + "", + " - `stash`: The stash account to reap. Its balance must be zero.", + "", + " # ", + " Complexity: O(S) where S is the number of slashing spans on the account.", + " Base Weight: 75.94 + 2.396 * S µs", + " DB Weight:", + " - Reads: Stash Account, Bonded, Slashing Spans, Locks", + " - Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Stash Account, Locks", + " - Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "submit_election_solution", + "args": [ + { + "name": "winners", + "type": "Vec" + }, + { + "name": "compact", + "type": "CompactAssignments" + }, + { + "name": "score", + "type": "ElectionScore" + }, + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "size", + "type": "ElectionSize" + } + ], + "docs": [ + " Submit an election result to the chain. If the solution:", + "", + " 1. is valid.", + " 2. has a better score than a potentially existing solution on chain.", + "", + " then, it will be _put_ on chain.", + "", + " A solution consists of two pieces of data:", + "", + " 1. `winners`: a flat vector of all the winners of the round.", + " 2. `assignments`: the compact version of an assignment vector that encodes the edge", + " weights.", + "", + " Both of which may be computed using _phragmen_, or any other algorithm.", + "", + " Additionally, the submitter must provide:", + "", + " - The `score` that they claim their solution has.", + "", + " Both validators and nominators will be represented by indices in the solution. The", + " indices should respect the corresponding types ([`ValidatorIndex`] and", + " [`NominatorIndex`]). Moreover, they should be valid when used to index into", + " [`SnapshotValidators`] and [`SnapshotNominators`]. Any invalid index will cause the", + " solution to be rejected. These two storage items are set during the election window and", + " may be used to determine the indices.", + "", + " A solution is valid if:", + "", + " 0. It is submitted when [`EraElectionStatus`] is `Open`.", + " 1. Its claimed score is equal to the score computed on-chain.", + " 2. Presents the correct number of winners.", + " 3. All indexes must be value according to the snapshot vectors. All edge values must", + " also be correct and should not overflow the granularity of the ratio type (i.e. 256", + " or billion).", + " 4. For each edge, all targets are actually nominated by the voter.", + " 5. Has correct self-votes.", + "", + " A solutions score is consisted of 3 parameters:", + "", + " 1. `min { support.total }` for each support of a winner. This value should be maximized.", + " 2. `sum { support.total }` for each support of a winner. This value should be minimized.", + " 3. `sum { support.total^2 }` for each support of a winner. This value should be", + " minimized (to ensure less variance)", + "", + " # ", + " See `crate::weight` module.", + " # " + ] + }, + { + "name": "submit_election_solution_unsigned", + "args": [ + { + "name": "winners", + "type": "Vec" + }, + { + "name": "compact", + "type": "CompactAssignments" + }, + { + "name": "score", + "type": "ElectionScore" + }, + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "size", + "type": "ElectionSize" + } + ], + "docs": [ + " Unsigned version of `submit_election_solution`.", + "", + " Note that this must pass the [`ValidateUnsigned`] check which only allows transactions", + " from the local node to be included. In other words, only the block author can include a", + " transaction in the block.", + "", + " # ", + " See `crate::weight` module.", + " # " + ] + } + ], + "events": [ + { + "name": "EraPayout", + "args": [ + "EraIndex", + "Balance", + "Balance" + ], + "docs": [ + " The era payout has been set; the first balance is the validator-payout; the second is", + " the remainder from the maximum amount of reward.", + " [era_index, validator_payout, remainder]" + ] + }, + { + "name": "Reward", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The staker has been rewarded by this amount. [stash, amount]" + ] + }, + { + "name": "Slash", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " One validator (and its nominators) has been slashed by the given amount.", + " [validator, amount]" + ] + }, + { + "name": "OldSlashingReportDiscarded", + "args": [ + "SessionIndex" + ], + "docs": [ + " An old slashing report from a prior era was discarded because it could", + " not be processed. [session_index]" + ] + }, + { + "name": "StakingElection", + "args": [ + "ElectionCompute" + ], + "docs": [ + " A new set of stakers was elected with the given [compute]." + ] + }, + { + "name": "SolutionStored", + "args": [ + "ElectionCompute" + ], + "docs": [ + " A new solution for the upcoming election has been stored. [compute]" + ] + }, + { + "name": "Bonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has bonded this amount. [stash, amount]", + "", + " NOTE: This event is only emitted when funds are bonded via a dispatchable. Notably,", + " it will not be emitted for staking rewards when they are added to stake." + ] + }, + { + "name": "Unbonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has unbonded this amount. [stash, amount]" + ] + }, + { + "name": "Withdrawn", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has called `withdraw_unbonded` and removed unbonding chunks worth `Balance`", + " from the unlocking queue. [stash, amount]" + ] + } + ], + "constants": [ + { + "name": "SessionsPerEra", + "type": "SessionIndex", + "value": "0x06000000", + "docs": [ + " Number of sessions per era." + ] + }, + { + "name": "BondingDuration", + "type": "EraIndex", + "value": "0xa0020000", + "docs": [ + " Number of eras that staked funds must remain bonded for." + ] + }, + { + "name": "SlashDeferDuration", + "type": "EraIndex", + "value": "0xa8000000", + "docs": [ + " Number of eras that slashes are deferred by, after computation.", + "", + " This should be less than the bonding duration.", + " Set to 0 if slashes should be applied immediately, without opportunity for", + " intervention." + ] + }, + { + "name": "ElectionLookahead", + "type": "BlockNumber", + "value": "0x32000000", + "docs": [ + " The number of blocks before the end of the era from which election submissions are allowed.", + "", + " Setting this to zero will disable the offchain compute and only on-chain seq-phragmen will", + " be used.", + "", + " This is bounded by being within the last session. Hence, setting it to a value more than the", + " length of a session will be pointless." + ] + }, + { + "name": "MaxIterations", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Maximum number of balancing iterations to run in the offchain submission.", + "", + " If set to 0, balance_solution will not be executed at all." + ] + }, + { + "name": "MinSolutionScoreBump", + "type": "Perbill", + "value": "0x20a10700", + "docs": [ + " The threshold of improvement that should be provided for a new solution to be accepted." + ] + }, + { + "name": "MaxNominatorRewardedPerValidator", + "type": "u32", + "value": "0x40000000", + "docs": [ + " The maximum number of nominators rewarded for each validator.", + "", + " For each validator only the `$MaxNominatorRewardedPerValidator` biggest stakers can claim", + " their reward. This used to limit the i/o cost for the nominator payout." + ] + } + ], + "errors": [ + { + "name": "NotController", + "docs": [ + " Not a controller account." + ] + }, + { + "name": "NotStash", + "docs": [ + " Not a stash account." + ] + }, + { + "name": "AlreadyBonded", + "docs": [ + " Stash is already bonded." + ] + }, + { + "name": "AlreadyPaired", + "docs": [ + " Controller is already paired." + ] + }, + { + "name": "EmptyTargets", + "docs": [ + " Targets cannot be empty." + ] + }, + { + "name": "DuplicateIndex", + "docs": [ + " Duplicate index." + ] + }, + { + "name": "InvalidSlashIndex", + "docs": [ + " Slash record index out of bounds." + ] + }, + { + "name": "InsufficientValue", + "docs": [ + " Can not bond with value less than minimum balance." + ] + }, + { + "name": "NoMoreChunks", + "docs": [ + " Can not schedule more unlock chunks." + ] + }, + { + "name": "NoUnlockChunk", + "docs": [ + " Can not rebond without unlocking chunks." + ] + }, + { + "name": "FundedTarget", + "docs": [ + " Attempting to target a stash that still has funds." + ] + }, + { + "name": "InvalidEraToReward", + "docs": [ + " Invalid era to reward." + ] + }, + { + "name": "InvalidNumberOfNominations", + "docs": [ + " Invalid number of nominations." + ] + }, + { + "name": "NotSortedAndUnique", + "docs": [ + " Items are not sorted and unique." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Rewards for this era have already been claimed for this validator." + ] + }, + { + "name": "OffchainElectionEarlySubmission", + "docs": [ + " The submitted result is received out of the open window." + ] + }, + { + "name": "OffchainElectionWeakSubmission", + "docs": [ + " The submitted result is not as good as the one stored on chain." + ] + }, + { + "name": "SnapshotUnavailable", + "docs": [ + " The snapshot data of the current window is missing." + ] + }, + { + "name": "OffchainElectionBogusWinnerCount", + "docs": [ + " Incorrect number of winners were presented." + ] + }, + { + "name": "OffchainElectionBogusWinner", + "docs": [ + " One of the submitted winners is not an active candidate on chain (index is out of range", + " in snapshot)." + ] + }, + { + "name": "OffchainElectionBogusCompact", + "docs": [ + " Error while building the assignment type from the compact. This can happen if an index", + " is invalid, or if the weights _overflow_." + ] + }, + { + "name": "OffchainElectionBogusNominator", + "docs": [ + " One of the submitted nominators is not an active nominator on chain." + ] + }, + { + "name": "OffchainElectionBogusNomination", + "docs": [ + " One of the submitted nominators has an edge to which they have not voted on chain." + ] + }, + { + "name": "OffchainElectionSlashedNomination", + "docs": [ + " One of the submitted nominators has an edge which is submitted before the last non-zero", + " slash of the target." + ] + }, + { + "name": "OffchainElectionBogusSelfVote", + "docs": [ + " A self vote must only be originated from a validator to ONLY themselves." + ] + }, + { + "name": "OffchainElectionBogusEdge", + "docs": [ + " The submitted result has unknown edges that are not among the presented winners." + ] + }, + { + "name": "OffchainElectionBogusScore", + "docs": [ + " The claimed score does not match with the one computed from the data." + ] + }, + { + "name": "OffchainElectionBogusElectionSize", + "docs": [ + " The election size is invalid." + ] + }, + { + "name": "CallNotAllowed", + "docs": [ + " The call is not allowed at the given time due to restrictions of election period." + ] + }, + { + "name": "IncorrectHistoryDepth", + "docs": [ + " Incorrect previous history depth input provided." + ] + }, + { + "name": "IncorrectSlashingSpans", + "docs": [ + " Incorrect number of slashing spans provided." + ] + } + ] + }, + { + "name": "Session", + "storage": { + "prefix": "Session", + "items": [ + { + "name": "Validators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of validators." + ] + }, + { + "name": "CurrentIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Current index of the session." + ] + }, + { + "name": "QueuedChanged", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the underlying economic identities or weighting behind the validators", + " has changed in the queued validator set." + ] + }, + { + "name": "QueuedKeys", + "modifier": "Default", + "type": { + "plain": "Vec<(ValidatorId,Keys)>" + }, + "fallback": "0x00", + "docs": [ + " The queued keys for the next session. When the next session begins, these keys", + " will be used to determine the validator's session keys." + ] + }, + { + "name": "DisabledValidators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Indices of disabled validators.", + "", + " The set is cleared when `on_session_ending` returns a new set of identities." + ] + }, + { + "name": "NextKeys", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ValidatorId", + "value": "Keys", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The next session keys for a validator." + ] + }, + { + "name": "KeyOwner", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(KeyTypeId,Bytes)", + "value": "ValidatorId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The owner of a key. The key is the `KeyTypeId` + the encoded key." + ] + } + ] + }, + "calls": [ + { + "name": "set_keys", + "args": [ + { + "name": "keys", + "type": "Keys" + }, + { + "name": "proof", + "type": "Bytes" + } + ], + "docs": [ + " Sets the session key(s) of the function caller to `keys`.", + " Allows an account to set its session key prior to becoming a validator.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)`", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `origin account`, `T::ValidatorIdOf`, `NextKeys`", + " - DbWrites: `origin account`, `NextKeys`", + " - DbReads per key id: `KeyOwner`", + " - DbWrites per key id: `KeyOwner`", + " # " + ] + }, + { + "name": "purge_keys", + "args": [], + "docs": [ + " Removes any session key(s) of the function caller.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)` in number of key types.", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `T::ValidatorIdOf`, `NextKeys`, `origin account`", + " - DbWrites: `NextKeys`, `origin account`", + " - DbWrites per key id: `KeyOwnder`", + " # " + ] + } + ], + "events": [ + { + "name": "NewSession", + "args": [ + "SessionIndex" + ], + "docs": [ + " New session has happened. Note that the argument is the [session_index], not the block", + " number as the type might suggest." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidProof", + "docs": [ + " Invalid ownership proof." + ] + }, + { + "name": "NoAssociatedValidatorId", + "docs": [ + " No associated validator ID for account." + ] + }, + { + "name": "DuplicatedKey", + "docs": [ + " Registered duplicate key." + ] + }, + { + "name": "NoKeys", + "docs": [ + " No keys are associated with this account." + ] + } + ] + }, + { + "name": "Democracy", + "storage": { + "prefix": "Democracy", + "items": [ + { + "name": "PublicPropCount", + "modifier": "Default", + "type": { + "plain": "PropIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of (public) proposals that have been made so far." + ] + }, + { + "name": "PublicProps", + "modifier": "Default", + "type": { + "plain": "Vec<(PropIndex,Hash,AccountId)>" + }, + "fallback": "0x00", + "docs": [ + " The public proposals. Unsorted. The second item is the proposal's hash." + ] + }, + { + "name": "DepositOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "PropIndex", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Those who have locked a deposit.", + "", + " TWOX-NOTE: Safe, as increasing integer keys are safe." + ] + }, + { + "name": "Preimages", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "PreimageStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map of hashes to the proposal preimage, along with who registered it and their deposit.", + " The block number is the block at which it was deposited." + ] + }, + { + "name": "ReferendumCount", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free referendum index, aka the number of referenda started so far." + ] + }, + { + "name": "LowestUnbaked", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The lowest referendum index representing an unbaked referendum. Equal to", + " `ReferendumCount` if there isn't a unbaked referendum." + ] + }, + { + "name": "ReferendumInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReferendumIndex", + "value": "ReferendumInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information concerning any given referendum.", + "", + " TWOX-NOTE: SAFE as indexes are not under an attacker’s control." + ] + }, + { + "name": "VotingOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Voting", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " All votes for a particular voter. We store the balance for the number of votes that we", + " have recorded. The second item is the total amount of delegations, that will be added.", + "", + " TWOX-NOTE: SAFE as `AccountId`s are crypto hashes anyway." + ] + }, + { + "name": "Locks", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "BlockNumber", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Accounts for which there are locks in action which may be removed at some point in the", + " future. The value is the block number at which the lock expires and may be removed.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "LastTabledWasExternal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the last referendum tabled was submitted externally. False if it was a public", + " proposal." + ] + }, + { + "name": "NextExternal", + "modifier": "Optional", + "type": { + "plain": "(Hash,VoteThreshold)" + }, + "fallback": "0x00", + "docs": [ + " The referendum to be tabled whenever it would be valid to table an external proposal.", + " This happens when a referendum needs to be tabled and one of two conditions are met:", + " - `LastTabledWasExternal` is `false`; or", + " - `PublicProps` is empty." + ] + }, + { + "name": "Blacklist", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "(BlockNumber,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A record of who vetoed what. Maps proposal hash to a possible existent block number", + " (until when it may not be resubmitted) and who vetoed it." + ] + }, + { + "name": "Cancellations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Record of all proposals that have been subject to emergency cancellation." + ] + }, + { + "name": "StorageVersion", + "modifier": "Optional", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " The dispatch origin of this call must be _Signed_ and the sender must", + " have funds to cover the deposit.", + "", + " - `proposal_hash`: The hash of the proposal preimage.", + " - `value`: The amount of deposit (must be at least `MinimumDeposit`).", + "", + " Emits `Proposed`.", + "", + " # ", + " - Complexity: `O(1)`", + " - Db reads: `PublicPropCount`, `PublicProps`", + " - Db writes: `PublicPropCount`, `PublicProps`, `DepositOf`", + " # " + ] + }, + { + "name": "second", + "args": [ + { + "name": "proposal", + "type": "Compact" + }, + { + "name": "seconds_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Signals agreement with a particular proposal.", + "", + " The dispatch origin of this call must be _Signed_ and the sender", + " must have funds to cover the deposit, equal to the original deposit.", + "", + " - `proposal`: The index of the proposal to second.", + " - `seconds_upper_bound`: an upper bound on the current number of seconds on this", + " proposal. Extrinsic is weighted according to this value with no refund.", + "", + " # ", + " - Complexity: `O(S)` where S is the number of seconds a proposal already has.", + " - Db reads: `DepositOf`", + " - Db writes: `DepositOf`", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "AccountVote" + } + ], + "docs": [ + " Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;", + " otherwise it is a vote to keep the status quo.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `ref_index`: The index of the referendum to vote for.", + " - `vote`: The vote configuration.", + "", + " # ", + " - Complexity: `O(R)` where R is the number of referendums the voter has voted on.", + " weight is charged as if maximum votes.", + " - Db reads: `ReferendumInfoOf`, `VotingOf`, `balances locks`", + " - Db writes: `ReferendumInfoOf`, `VotingOf`, `balances locks`", + " # " + ] + }, + { + "name": "emergency_cancel", + "args": [ + { + "name": "ref_index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Schedule an emergency cancellation of a referendum. Cannot happen twice to the same", + " referendum.", + "", + " The dispatch origin of this call must be `CancellationOrigin`.", + "", + " -`ref_index`: The index of the referendum to cancel.", + "", + " # ", + " - Complexity: `O(1)`.", + " - Db reads: `ReferendumInfoOf`, `Cancellations`", + " - Db writes: `ReferendumInfoOf`, `Cancellations`", + " # " + ] + }, + { + "name": "external_propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a referendum to be tabled once it is legal to schedule an external", + " referendum.", + "", + " The dispatch origin of this call must be `ExternalOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " # ", + " - Complexity `O(V)` with V number of vetoers in the blacklist of proposal.", + " Decoding vec of length V. Charged as maximum", + " - Db reads: `NextExternal`, `Blacklist`", + " - Db writes: `NextExternal`", + " # " + ] + }, + { + "name": "external_propose_majority", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a majority-carries referendum to be tabled next once it is legal to schedule", + " an external referendum.", + "", + " The dispatch of this call must be `ExternalMajorityOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " # ", + " - Complexity: `O(1)`", + " - Db write: `NextExternal`", + " # " + ] + }, + { + "name": "external_propose_default", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a negative-turnout-bias referendum to be tabled next once it is legal to", + " schedule an external referendum.", + "", + " The dispatch of this call must be `ExternalDefaultOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " # ", + " - Complexity: `O(1)`", + " - Db write: `NextExternal`", + " # " + ] + }, + { + "name": "fast_track", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "voting_period", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Schedule the currently externally-proposed majority-carries referendum to be tabled", + " immediately. If there is no externally-proposed referendum currently, or if there is one", + " but it is not a majority-carries referendum then it fails.", + "", + " The dispatch of this call must be `FastTrackOrigin`.", + "", + " - `proposal_hash`: The hash of the current external proposal.", + " - `voting_period`: The period that is allowed for voting on this proposal. Increased to", + " `FastTrackVotingPeriod` if too low.", + " - `delay`: The number of block after voting has ended in approval and this should be", + " enacted. This doesn't have a minimum amount.", + "", + " Emits `Started`.", + "", + " # ", + " - Complexity: `O(1)`", + " - Db reads: `NextExternal`, `ReferendumCount`", + " - Db writes: `NextExternal`, `ReferendumCount`, `ReferendumInfoOf`", + " - Base Weight: 30.1 µs", + " # " + ] + }, + { + "name": "veto_external", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Veto and blacklist the external proposal hash.", + "", + " The dispatch origin of this call must be `VetoOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal to veto and blacklist.", + "", + " Emits `Vetoed`.", + "", + " # ", + " - Complexity: `O(V + log(V))` where V is number of `existing vetoers`", + " Performs a binary search on `existing_vetoers` which should not be very large.", + " - Db reads: `NextExternal`, `Blacklist`", + " - Db writes: `NextExternal`, `Blacklist`", + " # " + ] + }, + { + "name": "cancel_referendum", + "args": [ + { + "name": "ref_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a referendum.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `ref_index`: The index of the referendum to cancel.", + "", + " # ", + " - Complexity: `O(1)`.", + " - Db writes: `ReferendumInfoOf`", + " # " + ] + }, + { + "name": "cancel_queued", + "args": [ + { + "name": "which", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Cancel a proposal queued for enactment.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `which`: The index of the referendum to cancel.", + "", + " # ", + " - `O(D)` where `D` is the items in the dispatch queue. Weighted as `D = 10`.", + " - Db reads: `scheduler lookup`, scheduler agenda`", + " - Db writes: `scheduler lookup`, scheduler agenda`", + " # " + ] + }, + { + "name": "delegate", + "args": [ + { + "name": "to", + "type": "AccountId" + }, + { + "name": "conviction", + "type": "Conviction" + }, + { + "name": "balance", + "type": "BalanceOf" + } + ], + "docs": [ + " Delegate the voting power (with some given conviction) of the sending account.", + "", + " The balance delegated is locked for as long as it's delegated, and thereafter for the", + " time appropriate for the conviction's lock period.", + "", + " The dispatch origin of this call must be _Signed_, and the signing account must either:", + " - be delegating already; or", + " - have no voting activity (if there is, then it will need to be removed/consolidated", + " through `reap_vote` or `unvote`).", + "", + " - `to`: The account whose voting the `target` account's voting power will follow.", + " - `conviction`: The conviction that will be attached to the delegated votes. When the", + " account is undelegated, the funds will be locked for the corresponding period.", + " - `balance`: The amount of the account's balance to be used in delegating. This must", + " not be more than the account's current balance.", + "", + " Emits `Delegated`.", + "", + " # ", + " - Complexity: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes.", + " - Db reads: 3*`VotingOf`, `origin account locks`", + " - Db writes: 3*`VotingOf`, `origin account locks`", + " - Db reads per votes: `ReferendumInfoOf`", + " - Db writes per votes: `ReferendumInfoOf`", + " # " + ] + }, + { + "name": "undelegate", + "args": [], + "docs": [ + " Undelegate the voting power of the sending account.", + "", + " Tokens may be unlocked following once an amount of time consistent with the lock period", + " of the conviction with which the delegation was issued.", + "", + " The dispatch origin of this call must be _Signed_ and the signing account must be", + " currently delegating.", + "", + " Emits `Undelegated`.", + "", + " # ", + " - Complexity: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes.", + " - Db reads: 2*`VotingOf`", + " - Db writes: 2*`VotingOf`", + " - Db reads per votes: `ReferendumInfoOf`", + " - Db writes per votes: `ReferendumInfoOf`", + " # " + ] + }, + { + "name": "clear_public_proposals", + "args": [], + "docs": [ + " Clears all public proposals.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " # ", + " - `O(1)`.", + " - Db writes: `PublicProps`", + " # " + ] + }, + { + "name": "note_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This doesn't require the proposal to be", + " in the dispatch queue but does require a deposit, returned once enacted.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " # ", + " - Complexity: `O(E)` with E size of `encoded_proposal` (protected by a required deposit).", + " - Db reads: `Preimages`", + " - Db writes: `Preimages`", + " # " + ] + }, + { + "name": "note_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "note_imminent_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This requires the proposal to be", + " in the dispatch queue. No deposit is needed. When this call is successful, i.e.", + " the preimage has not been uploaded before and matches some imminent proposal,", + " no fee is paid.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " # ", + " - Complexity: `O(E)` with E size of `encoded_proposal` (protected by a required deposit).", + " - Db reads: `Preimages`", + " - Db writes: `Preimages`", + " # " + ] + }, + { + "name": "note_imminent_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_imminent_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "reap_preimage", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "proposal_len_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Remove an expired proposal preimage and collect the deposit.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `proposal_hash`: The preimage hash of a proposal.", + " - `proposal_length_upper_bound`: an upper bound on length of the proposal.", + " Extrinsic is weighted according to this value with no refund.", + "", + " This will only work after `VotingPeriod` blocks from the time that the preimage was", + " noted, if it's the same account doing it. If it's a different account, then it'll only", + " work an additional `EnactmentPeriod` later.", + "", + " Emits `PreimageReaped`.", + "", + " # ", + " - Complexity: `O(D)` where D is length of proposal.", + " - Db reads: `Preimages`, provider account data", + " - Db writes: `Preimages` provider account data", + " # " + ] + }, + { + "name": "unlock", + "args": [ + { + "name": "target", + "type": "AccountId" + } + ], + "docs": [ + " Unlock tokens that have an expired lock.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account to remove the lock on.", + "", + " # ", + " - Complexity `O(R)` with R number of vote of target.", + " - Db reads: `VotingOf`, `balances locks`, `target account`", + " - Db writes: `VotingOf`, `balances locks`, `target account`", + " # " + ] + }, + { + "name": "remove_vote", + "args": [ + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If:", + " - the referendum was cancelled, or", + " - the referendum is ongoing, or", + " - the referendum has ended such that", + " - the vote of the account was in opposition to the result; or", + " - there was no conviction to the account's vote; or", + " - the account made a split vote", + " ...then the vote is removed cleanly and a following call to `unlock` may result in more", + " funds being available.", + "", + " If, however, the referendum has ended and:", + " - it finished corresponding to the vote of the account, and", + " - the account made a standard vote with conviction, and", + " - the lock period of the conviction is not over", + " ...then the lock will be aggregated into the overall account's lock, which may involve", + " *overlocking* (where the two locks are combined into a single lock that is the maximum", + " of both the amount locked and the time is it locked for).", + "", + " The dispatch origin of this call must be _Signed_, and the signer must have a vote", + " registered for referendum `index`.", + "", + " - `index`: The index of referendum of the vote to be removed.", + "", + " # ", + " - `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote.", + " - Db reads: `ReferendumInfoOf`, `VotingOf`", + " - Db writes: `ReferendumInfoOf`, `VotingOf`", + " # " + ] + }, + { + "name": "remove_other_vote", + "args": [ + { + "name": "target", + "type": "AccountId" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If the `target` is equal to the signer, then this function is exactly equivalent to", + " `remove_vote`. If not equal to the signer, then the vote must have expired,", + " either because the referendum was cancelled, because the voter lost the referendum or", + " because the conviction period is over.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account of the vote to be removed; this account must have voted for", + " referendum `index`.", + " - `index`: The index of referendum of the vote to be removed.", + "", + " # ", + " - `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote.", + " - Db reads: `ReferendumInfoOf`, `VotingOf`", + " - Db writes: `ReferendumInfoOf`, `VotingOf`", + " # " + ] + }, + { + "name": "enact_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Enact a proposal from a referendum. For now we just make the weight be the maximum." + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "PropIndex", + "Balance" + ], + "docs": [ + " A motion has been proposed by a public account. [proposal_index, deposit]" + ] + }, + { + "name": "Tabled", + "args": [ + "PropIndex", + "Balance", + "Vec" + ], + "docs": [ + " A public proposal has been tabled for referendum vote. [proposal_index, deposit, depositors]" + ] + }, + { + "name": "ExternalTabled", + "args": [], + "docs": [ + " An external proposal has been tabled." + ] + }, + { + "name": "Started", + "args": [ + "ReferendumIndex", + "VoteThreshold" + ], + "docs": [ + " A referendum has begun. [ref_index, threshold]" + ] + }, + { + "name": "Passed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been approved by referendum. [ref_index]" + ] + }, + { + "name": "NotPassed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been rejected by referendum. [ref_index]" + ] + }, + { + "name": "Cancelled", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A referendum has been cancelled. [ref_index]" + ] + }, + { + "name": "Executed", + "args": [ + "ReferendumIndex", + "bool" + ], + "docs": [ + " A proposal has been enacted. [ref_index, is_ok]" + ] + }, + { + "name": "Delegated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " An account has delegated their vote to another account. [who, target]" + ] + }, + { + "name": "Undelegated", + "args": [ + "AccountId" + ], + "docs": [ + " An [account] has cancelled a previous delegation operation." + ] + }, + { + "name": "Vetoed", + "args": [ + "AccountId", + "Hash", + "BlockNumber" + ], + "docs": [ + " An external proposal has been vetoed. [who, proposal_hash, until]" + ] + }, + { + "name": "PreimageNoted", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal's preimage was noted, and the deposit taken. [proposal_hash, who, deposit]" + ] + }, + { + "name": "PreimageUsed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal preimage was removed and used (the deposit was returned).", + " [proposal_hash, provider, deposit]" + ] + }, + { + "name": "PreimageInvalid", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was invalid. [proposal_hash, ref_index]" + ] + }, + { + "name": "PreimageMissing", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was missing. [proposal_hash, ref_index]" + ] + }, + { + "name": "PreimageReaped", + "args": [ + "Hash", + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A registered preimage was removed and the deposit collected by the reaper.", + " [proposal_hash, provider, deposit, reaper]" + ] + }, + { + "name": "Unlocked", + "args": [ + "AccountId" + ], + "docs": [ + " An [account] has been unlocked successfully." + ] + } + ], + "constants": [ + { + "name": "EnactmentPeriod", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The minimum period of locking and the period between a proposal being approved and enacted.", + "", + " It should generally be a little more than the unstake period to ensure that", + " voting stakers have an opportunity to remove themselves from the system in the case where", + " they are on the losing side of a vote." + ] + }, + { + "name": "LaunchPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) new public referenda are launched." + ] + }, + { + "name": "VotingPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) to check for new votes." + ] + }, + { + "name": "MinimumDeposit", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be used as a deposit for a public referendum proposal." + ] + }, + { + "name": "FastTrackVotingPeriod", + "type": "BlockNumber", + "value": "0x80510100", + "docs": [ + " Minimum voting period allowed for an emergency referendum." + ] + }, + { + "name": "CooloffPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " Period in blocks where an external proposal may not be re-submitted after being vetoed." + ] + }, + { + "name": "PreimageByteDeposit", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of balance that must be deposited per byte of preimage stored." + ] + }, + { + "name": "MaxVotes", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of votes for an account." + ] + } + ], + "errors": [ + { + "name": "ValueLow", + "docs": [ + " Value too low" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal does not exist" + ] + }, + { + "name": "BadIndex", + "docs": [ + " Unknown index" + ] + }, + { + "name": "AlreadyCanceled", + "docs": [ + " Cannot cancel the same proposal twice" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Proposal already made" + ] + }, + { + "name": "ProposalBlacklisted", + "docs": [ + " Proposal still blacklisted" + ] + }, + { + "name": "NotSimpleMajority", + "docs": [ + " Next external proposal not simple majority" + ] + }, + { + "name": "InvalidHash", + "docs": [ + " Invalid hash" + ] + }, + { + "name": "NoProposal", + "docs": [ + " No external proposal" + ] + }, + { + "name": "AlreadyVetoed", + "docs": [ + " Identity may not veto a proposal twice" + ] + }, + { + "name": "NotDelegated", + "docs": [ + " Not delegated" + ] + }, + { + "name": "DuplicatePreimage", + "docs": [ + " Preimage already noted" + ] + }, + { + "name": "NotImminent", + "docs": [ + " Not imminent" + ] + }, + { + "name": "TooEarly", + "docs": [ + " Too early" + ] + }, + { + "name": "Imminent", + "docs": [ + " Imminent" + ] + }, + { + "name": "PreimageMissing", + "docs": [ + " Preimage not found" + ] + }, + { + "name": "ReferendumInvalid", + "docs": [ + " Vote given for invalid referendum" + ] + }, + { + "name": "PreimageInvalid", + "docs": [ + " Invalid preimage" + ] + }, + { + "name": "NoneWaiting", + "docs": [ + " No proposals waiting" + ] + }, + { + "name": "NotLocked", + "docs": [ + " The target account does not have a lock." + ] + }, + { + "name": "NotExpired", + "docs": [ + " The lock on the account to be unlocked has not yet expired." + ] + }, + { + "name": "NotVoter", + "docs": [ + " The given account did not vote on the referendum." + ] + }, + { + "name": "NoPermission", + "docs": [ + " The actor has no permission to conduct the action." + ] + }, + { + "name": "AlreadyDelegating", + "docs": [ + " The account is already delegating." + ] + }, + { + "name": "Overflow", + "docs": [ + " An unexpected integer overflow occurred." + ] + }, + { + "name": "Underflow", + "docs": [ + " An unexpected integer underflow occurred." + ] + }, + { + "name": "InsufficientFunds", + "docs": [ + " Too high a balance was provided that the account cannot afford." + ] + }, + { + "name": "NotDelegating", + "docs": [ + " The account is not currently delegating." + ] + }, + { + "name": "VotesExist", + "docs": [ + " The account currently has votes attached to it and the operation cannot succeed until", + " these are removed, either through `unvote` or `reap_vote`." + ] + }, + { + "name": "InstantNotAllowed", + "docs": [ + " The instant referendum origin is currently disallowed." + ] + }, + { + "name": "Nonsense", + "docs": [ + " Delegation to oneself makes no sense." + ] + }, + { + "name": "WrongUpperBound", + "docs": [ + " Invalid upper bound." + ] + }, + { + "name": "MaxVotesReached", + "docs": [ + " Maximum number of votes reached." + ] + } + ] + }, + { + "name": "Council", + "storage": { + "prefix": "Instance1Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The member who provides the default vote for any other members that do not vote before", + " the timeout. If None, then no member has that privilege." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " [account, proposal_index, proposal_hash, threshold]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " [account, proposal_hash, voted, yes, no]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " [proposal_hash]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " [proposal_hash]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " [proposal_hash, result]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " [proposal_hash, result]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " [proposal_hash, yes, no]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ] + }, + { + "name": "TechnicalCommittee", + "storage": { + "prefix": "Instance2Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The member who provides the default vote for any other members that do not vote before", + " the timeout. If None, then no member has that privilege." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " [account, proposal_index, proposal_hash, threshold]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " [account, proposal_hash, voted, yes, no]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " [proposal_hash]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " [proposal_hash]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " [proposal_hash, result]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " [proposal_hash, result]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " [proposal_hash, yes, no]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ] + }, + { + "name": "Elections", + "storage": { + "prefix": "PhragmenElection", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current elected membership. Sorted based on account id." + ] + }, + { + "name": "RunnersUp", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current runners_up. Sorted based on low to high merit (worse to best runner)." + ] + }, + { + "name": "ElectionRounds", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The total number of vote rounds that have happened, excluding the upcoming one." + ] + }, + { + "name": "Voting", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " Votes and locked stake of a particular voter.", + "", + " TWOX-NOTE: SAFE as `AccountId` is a crypto hash" + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The present candidate list. Sorted based on account-id. A current member or runner-up", + " can never enter this vector and is always implicitly assumed to be a candidate." + ] + } + ] + }, + "calls": [ + { + "name": "vote", + "args": [ + { + "name": "votes", + "type": "Vec" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Vote for a set of candidates for the upcoming round of election. This can be called to", + " set the initial votes, or update already existing votes.", + "", + " Upon initial voting, `value` units of `who`'s balance is locked and a bond amount is", + " reserved.", + "", + " The `votes` should:", + " - not be empty.", + " - be less than the number of possible candidates. Note that all current members and", + " runners-up are also automatically candidates for the next round.", + "", + " It is the responsibility of the caller to not place all of their balance into the lock", + " and keep some for further transactions.", + "", + " # ", + " Base weight: 47.93 µs", + " State reads:", + " \t- Candidates.len() + Members.len() + RunnersUp.len()", + " \t- Voting (is_voter)", + " \t- [AccountBalance(who) (unreserve + total_balance)]", + " State writes:", + " \t- Voting", + " \t- Lock", + " \t- [AccountBalance(who) (unreserve -- only when creating a new voter)]", + " # " + ] + }, + { + "name": "remove_voter", + "args": [], + "docs": [ + " Remove `origin` as a voter. This removes the lock and returns the bond.", + "", + " # ", + " Base weight: 36.8 µs", + " All state access is from do_remove_voter.", + " State reads:", + " \t- Voting", + " \t- [AccountData(who)]", + " State writes:", + " \t- Voting", + " \t- Locks", + " \t- [AccountData(who)]", + " # " + ] + }, + { + "name": "report_defunct_voter", + "args": [ + { + "name": "defunct", + "type": "DefunctVoter" + } + ], + "docs": [ + " Report `target` for being an defunct voter. In case of a valid report, the reporter is", + " rewarded by the bond amount of `target`. Otherwise, the reporter itself is removed and", + " their bond is slashed.", + "", + " A defunct voter is defined to be:", + " - a voter whose current submitted votes are all invalid. i.e. all of them are no", + " longer a candidate nor an active member or a runner-up.", + "", + "", + " The origin must provide the number of current candidates and votes of the reported target", + " for the purpose of accurate weight calculation.", + "", + " # ", + " No Base weight based on min square analysis.", + " Complexity of candidate_count: 1.755 µs", + " Complexity of vote_count: 18.51 µs", + " State reads:", + " \t- Voting(reporter)", + " \t- Candidate.len()", + " \t- Voting(Target)", + " \t- Candidates, Members, RunnersUp (is_defunct_voter)", + " State writes:", + " \t- Lock(reporter || target)", + " \t- [AccountBalance(reporter)] + AccountBalance(target)", + " \t- Voting(reporter || target)", + " Note: the db access is worse with respect to db, which is when the report is correct.", + " # " + ] + }, + { + "name": "submit_candidacy", + "args": [ + { + "name": "candidate_count", + "type": "Compact" + } + ], + "docs": [ + " Submit oneself for candidacy.", + "", + " A candidate will either:", + " - Lose at the end of the term and forfeit their deposit.", + " - Win and become a member. Members will eventually get their stash back.", + " - Become a runner-up. Runners-ups are reserved members in case one gets forcefully", + " removed.", + "", + " # ", + " Base weight = 33.33 µs", + " Complexity of candidate_count: 0.375 µs", + " State reads:", + " \t- Candidates.len()", + " \t- Candidates", + " \t- Members", + " \t- RunnersUp", + " \t- [AccountBalance(who)]", + " State writes:", + " \t- [AccountBalance(who)]", + " \t- Candidates", + " # " + ] + }, + { + "name": "renounce_candidacy", + "args": [ + { + "name": "renouncing", + "type": "Renouncing" + } + ], + "docs": [ + " Renounce one's intention to be a candidate for the next election round. 3 potential", + " outcomes exist:", + " - `origin` is a candidate and not elected in any set. In this case, the bond is", + " unreserved, returned and origin is removed as a candidate.", + " - `origin` is a current runner-up. In this case, the bond is unreserved, returned and", + " origin is removed as a runner-up.", + " - `origin` is a current member. In this case, the bond is unreserved and origin is", + " removed as a member, consequently not being a candidate for the next round anymore.", + " Similar to [`remove_voter`], if replacement runners exists, they are immediately used.", + " ", + " If a candidate is renouncing:", + " \tBase weight: 17.28 µs", + " \tComplexity of candidate_count: 0.235 µs", + " \tState reads:", + " \t\t- Candidates", + " \t\t- [AccountBalance(who) (unreserve)]", + " \tState writes:", + " \t\t- Candidates", + " \t\t- [AccountBalance(who) (unreserve)]", + " If member is renouncing:", + " \tBase weight: 46.25 µs", + " \tState reads:", + " \t\t- Members, RunnersUp (remove_and_replace_member),", + " \t\t- [AccountData(who) (unreserve)]", + " \tState writes:", + " \t\t- Members, RunnersUp (remove_and_replace_member),", + " \t\t- [AccountData(who) (unreserve)]", + " If runner is renouncing:", + " \tBase weight: 46.25 µs", + " \tState reads:", + " \t\t- RunnersUp (remove_and_replace_member),", + " \t\t- [AccountData(who) (unreserve)]", + " \tState writes:", + " \t\t- RunnersUp (remove_and_replace_member),", + " \t\t- [AccountData(who) (unreserve)]", + "", + " Weight note: The call into changeMembers need to be accounted for.", + " " + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "has_replacement", + "type": "bool" + } + ], + "docs": [ + " Remove a particular member from the set. This is effective immediately and the bond of", + " the outgoing member is slashed.", + "", + " If a runner-up is available, then the best runner-up will be removed and replaces the", + " outgoing member. Otherwise, a new phragmen election is started.", + "", + " Note that this does not affect the designated block number of the next election.", + "", + " # ", + " If we have a replacement:", + " \t- Base weight: 50.93 µs", + " \t- State reads:", + " \t\t- RunnersUp.len()", + " \t\t- Members, RunnersUp (remove_and_replace_member)", + " \t- State writes:", + " \t\t- Members, RunnersUp (remove_and_replace_member)", + " Else, since this is a root call and will go into phragmen, we assume full block for now.", + " # " + ] + } + ], + "events": [ + { + "name": "NewTerm", + "args": [ + "Vec<(AccountId,Balance)>" + ], + "docs": [ + " A new term with [new_members]. This indicates that enough candidates existed to run the", + " election, not that enough have has been elected. The inner value must be examined for", + " this purpose. A `NewTerm([])` indicates that some candidates got their bond slashed and", + " none were elected, whilst `EmptyTerm` means that no candidates existed to begin with." + ] + }, + { + "name": "EmptyTerm", + "args": [], + "docs": [ + " No (or not enough) candidates existed for this round. This is different from", + " `NewTerm([])`. See the description of `NewTerm`." + ] + }, + { + "name": "MemberKicked", + "args": [ + "AccountId" + ], + "docs": [ + " A [member] has been removed. This should always be followed by either `NewTerm` ot", + " `EmptyTerm`." + ] + }, + { + "name": "MemberRenounced", + "args": [ + "AccountId" + ], + "docs": [ + " A [member] has renounced their candidacy." + ] + }, + { + "name": "VoterReported", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A voter was reported with the the report being successful or not.", + " [voter, reporter, success]" + ] + } + ], + "constants": [ + { + "name": "CandidacyBond", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [] + }, + { + "name": "VotingBond", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [] + }, + { + "name": "DesiredMembers", + "type": "u32", + "value": "0x0d000000", + "docs": [] + }, + { + "name": "DesiredRunnersUp", + "type": "u32", + "value": "0x07000000", + "docs": [] + }, + { + "name": "TermDuration", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [] + }, + { + "name": "ModuleId", + "type": "LockIdentifier", + "value": "0x706872656c656374", + "docs": [] + } + ], + "errors": [ + { + "name": "UnableToVote", + "docs": [ + " Cannot vote when no candidates or members exist." + ] + }, + { + "name": "NoVotes", + "docs": [ + " Must vote for at least one candidate." + ] + }, + { + "name": "TooManyVotes", + "docs": [ + " Cannot vote more than candidates." + ] + }, + { + "name": "MaximumVotesExceeded", + "docs": [ + " Cannot vote more than maximum allowed." + ] + }, + { + "name": "LowBalance", + "docs": [ + " Cannot vote with stake less than minimum balance." + ] + }, + { + "name": "UnableToPayBond", + "docs": [ + " Voter can not pay voting bond." + ] + }, + { + "name": "MustBeVoter", + "docs": [ + " Must be a voter." + ] + }, + { + "name": "ReportSelf", + "docs": [ + " Cannot report self." + ] + }, + { + "name": "DuplicatedCandidate", + "docs": [ + " Duplicated candidate submission." + ] + }, + { + "name": "MemberSubmit", + "docs": [ + " Member cannot re-submit candidacy." + ] + }, + { + "name": "RunnerSubmit", + "docs": [ + " Runner cannot re-submit candidacy." + ] + }, + { + "name": "InsufficientCandidateFunds", + "docs": [ + " Candidate does not have enough funds." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + }, + { + "name": "InvalidCandidateCount", + "docs": [ + " The provided count of number of candidates is incorrect." + ] + }, + { + "name": "InvalidVoteCount", + "docs": [ + " The provided count of number of votes is incorrect." + ] + }, + { + "name": "InvalidRenouncing", + "docs": [ + " The renouncing origin presented a wrong `Renouncing` parameter." + ] + }, + { + "name": "InvalidReplacement", + "docs": [ + " Prediction regarding replacement after member removal is wrong." + ] + } + ] + }, + { + "name": "TechnicalMembership", + "storage": { + "prefix": "Instance1Membership", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current membership, stored as an ordered Vec." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The current prime member, if one exists." + ] + } + ] + }, + "calls": [ + { + "name": "add_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Add a member `who` to the set.", + "", + " May only be called from `T::AddOrigin`." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Remove a member `who` from the set.", + "", + " May only be called from `T::RemoveOrigin`." + ] + }, + { + "name": "swap_member", + "args": [ + { + "name": "remove", + "type": "AccountId" + }, + { + "name": "add", + "type": "AccountId" + } + ], + "docs": [ + " Swap out one member `remove` for another `add`.", + "", + " May only be called from `T::SwapOrigin`.", + "", + " Prime membership is *not* passed from `remove` to `add`, if extant." + ] + }, + { + "name": "reset_members", + "args": [ + { + "name": "members", + "type": "Vec" + } + ], + "docs": [ + " Change the membership to a new set, disregarding the existing membership. Be nice and", + " pass `members` pre-sorted.", + "", + " May only be called from `T::ResetOrigin`." + ] + }, + { + "name": "change_key", + "args": [ + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Swap out the sending member for some other key `new`.", + "", + " May only be called from `Signed` origin of a current member.", + "", + " Prime membership is passed from the origin account to `new`, if extant." + ] + }, + { + "name": "set_prime", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Set the prime member. Must be a current member.", + "", + " May only be called from `T::PrimeOrigin`." + ] + }, + { + "name": "clear_prime", + "args": [], + "docs": [ + " Remove the prime member if it exists.", + "", + " May only be called from `T::PrimeOrigin`." + ] + } + ], + "events": [ + { + "name": "MemberAdded", + "args": [], + "docs": [ + " The given member was added; see the transaction for who." + ] + }, + { + "name": "MemberRemoved", + "args": [], + "docs": [ + " The given member was removed; see the transaction for who." + ] + }, + { + "name": "MembersSwapped", + "args": [], + "docs": [ + " Two members were swapped; see the transaction for who." + ] + }, + { + "name": "MembersReset", + "args": [], + "docs": [ + " The membership was reset; see the transaction for who the new set is." + ] + }, + { + "name": "KeyChanged", + "args": [], + "docs": [ + " One of the members' keys changed." + ] + }, + { + "name": "Dummy", + "args": [ + "PhantomData" + ], + "docs": [ + " Phantom member, never used." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "FinalityTracker", + "storage": null, + "calls": [ + { + "name": "final_hint", + "args": [ + { + "name": "hint", + "type": "Compact" + } + ], + "docs": [ + " Hint that the author of this block thinks the best finalized", + " block is the given number." + ] + } + ], + "events": null, + "constants": [ + { + "name": "WindowSize", + "type": "BlockNumber", + "value": "0x65000000", + "docs": [ + " The number of recent samples to keep from this chain. Default is 101." + ] + }, + { + "name": "ReportLatency", + "type": "BlockNumber", + "value": "0xe8030000", + "docs": [ + " The delay after which point things become suspicious. Default is 1000." + ] + } + ], + "errors": [ + { + "name": "AlreadyUpdated", + "docs": [ + " Final hint must be updated only once in the block" + ] + }, + { + "name": "BadHint", + "docs": [ + " Finalized height above block number" + ] + } + ] + }, + { + "name": "Grandpa", + "storage": { + "prefix": "GrandpaFinality", + "items": [ + { + "name": "State", + "modifier": "Default", + "type": { + "plain": "StoredState" + }, + "fallback": "0x00", + "docs": [ + " State of the current authority set." + ] + }, + { + "name": "PendingChange", + "modifier": "Optional", + "type": { + "plain": "StoredPendingChange" + }, + "fallback": "0x00", + "docs": [ + " Pending change: (signaled at, scheduled change)." + ] + }, + { + "name": "NextForced", + "modifier": "Optional", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00", + "docs": [ + " next block number where we can force a change." + ] + }, + { + "name": "Stalled", + "modifier": "Optional", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x00", + "docs": [ + " `true` if we are currently stalled." + ] + }, + { + "name": "CurrentSetId", + "modifier": "Default", + "type": { + "plain": "SetId" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The number of changes (both in terms of keys and underlying economic responsibilities)", + " in the \"set\" of Grandpa validators from genesis." + ] + }, + { + "name": "SetIdSession", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "SetId", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from grandpa set ID to the index of the *most recent* session for which its", + " members were responsible.", + "", + " TWOX-NOTE: `SetId` is not under user control." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported.", + "", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + }, + { + "name": "note_stalled", + "args": [ + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "best_finalized_block_number", + "type": "BlockNumber" + } + ], + "docs": [ + " Note that the current authority set of the GRANDPA finality gadget has", + " stalled. This will trigger a forced authority set change at the beginning", + " of the next session, to be enacted `delay` blocks after that. The delay", + " should be high enough to safely assume that the block signalling the", + " forced change will not be re-orged (e.g. 1000 blocks). The GRANDPA voters", + " will start the new authority set using the given finalized block as base.", + " Only callable by root." + ] + } + ], + "events": [ + { + "name": "NewAuthorities", + "args": [ + "AuthorityList" + ], + "docs": [ + " New authority set has been applied. [authority_set]" + ] + }, + { + "name": "Paused", + "args": [], + "docs": [ + " Current authority set has been paused." + ] + }, + { + "name": "Resumed", + "args": [], + "docs": [ + " Current authority set has been resumed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "PauseFailed", + "docs": [ + " Attempt to signal GRANDPA pause when the authority set isn't live", + " (either paused or already pending pause)." + ] + }, + { + "name": "ResumeFailed", + "docs": [ + " Attempt to signal GRANDPA resume when the authority set isn't paused", + " (either live or already pending resume)." + ] + }, + { + "name": "ChangePending", + "docs": [ + " Attempt to signal GRANDPA change with one already pending." + ] + }, + { + "name": "TooSoon", + "docs": [ + " Cannot signal forced change so soon after last." + ] + }, + { + "name": "InvalidKeyOwnershipProof", + "docs": [ + " A key ownership proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "InvalidEquivocationProof", + "docs": [ + " An equivocation proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "DuplicateOffenceReport", + "docs": [ + " A given equivocation report is valid but already previously reported." + ] + } + ] + }, + { + "name": "Treasury", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "ProposalIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of proposals that have been made." + ] + }, + { + "name": "Proposals", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ProposalIndex", + "value": "TreasuryProposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Proposals that have been made." + ] + }, + { + "name": "Approvals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Proposal indices that have been approved but not yet awarded." + ] + }, + { + "name": "Tips", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Hash", + "value": "OpenTip", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Tips that are not yet completed. Keyed by the hash of `(reason, who)` from the value.", + " This has the insecure enumerable hash function since the key itself is already", + " guaranteed to be a secure hash." + ] + }, + { + "name": "Reasons", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Simple preimage lookup from the reason's hash to the original data. Again, has an", + " insecure enumerable hash since the key is guaranteed to be the result of a secure hash." + ] + } + ] + }, + "calls": [ + { + "name": "propose_spend", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Put forward a suggestion for spending. A deposit proportional to the value", + " is reserved and slashed if the proposal is rejected. It is returned once the", + " proposal is awarded.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `ProposalCount`, `origin account`", + " - DbWrites: `ProposalCount`, `Proposals`, `origin account`", + " # " + ] + }, + { + "name": "reject_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Reject a proposed spend. The original deposit will be slashed.", + "", + " May only be called from `T::RejectOrigin`.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `Proposals`, `rejected proposer account`", + " - DbWrites: `Proposals`, `rejected proposer account`", + " # " + ] + }, + { + "name": "approve_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a proposal. At a later time, the proposal will be allocated to the beneficiary", + " and the original deposit will be returned.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - Complexity: O(1).", + " - DbReads: `Proposals`, `Approvals`", + " - DbWrite: `Approvals`", + " # " + ] + }, + { + "name": "report_awesome", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Report something `reason` that deserves a tip and claim any eventual the finder's fee.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `TipReportDepositPerByte` for each byte in `reason`.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R)` where `R` length of `reason`.", + " - encoding and hashing of 'reason'", + " - DbReads: `Reasons`, `Tips`, `who account data`", + " - DbWrites: `Tips`, `who account data`", + " # " + ] + }, + { + "name": "retract_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Retract a prior tip-report from `report_awesome`, and cancel the process of tipping.", + "", + " If successful, the original deposit will be unreserved.", + "", + " The dispatch origin for this call must be _Signed_ and the tip identified by `hash`", + " must have been reported by the signing account through `report_awesome` (and not", + " through `tip_new`).", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " Emits `TipRetracted` if successful.", + "", + " # ", + " - Complexity: `O(1)`", + " - Depends on the length of `T::Hash` which is fixed.", + " - DbReads: `Tips`, `origin account`", + " - DbWrites: `Reasons`, `Tips`, `origin account`", + " # " + ] + }, + { + "name": "tip_new", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + }, + { + "name": "tip_value", + "type": "BalanceOf" + } + ], + "docs": [ + " Give a tip for something new; no finder's fee will be taken.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R + T)` where `R` length of `reason`, `T` is the number of tippers.", + " - `O(T)`: decoding `Tipper` vec of length `T`", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - `O(R)`: hashing and encoding of reason of length `R`", + " - DbReads: `Tippers`, `Reasons`", + " - DbWrites: `Reasons`, `Tips`", + " # " + ] + }, + { + "name": "tip", + "args": [ + { + "name": "hash", + "type": "Hash" + }, + { + "name": "tip_value", + "type": "BalanceOf" + } + ], + "docs": [ + " Declare a tip value for an already-open tip.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the hash of the original tip `reason` and the beneficiary", + " account ID.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `TipClosing` if the threshold of tippers has been reached and the countdown period", + " has started.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`, insert tip and check closing,", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + "", + " Actually weight could be lower as it depends on how many tips are in `OpenTip` but it", + " is weighted as if almost full i.e of length `T-1`.", + " - DbReads: `Tippers`, `Tips`", + " - DbWrites: `Tips`", + " # " + ] + }, + { + "name": "close_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Close and payout a tip.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " The tip identified by `hash` must have finished its countdown period.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`.", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - DbReads: `Tips`, `Tippers`, `tip finder`", + " - DbWrites: `Reasons`, `Tips`, `Tippers`, `tip finder`", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "ProposalIndex" + ], + "docs": [ + " New proposal. [proposal_index]" + ] + }, + { + "name": "Spending", + "args": [ + "Balance" + ], + "docs": [ + " We have ended a spend period and will now allocate funds. [budget_remaining]" + ] + }, + { + "name": "Awarded", + "args": [ + "ProposalIndex", + "Balance", + "AccountId" + ], + "docs": [ + " Some funds have been allocated. [proposal_index, award, beneficiary]" + ] + }, + { + "name": "Rejected", + "args": [ + "ProposalIndex", + "Balance" + ], + "docs": [ + " A proposal was rejected; funds were slashed. [proposal_index, slashed]" + ] + }, + { + "name": "Burnt", + "args": [ + "Balance" + ], + "docs": [ + " Some of our funds have been burnt. [burn]" + ] + }, + { + "name": "Rollover", + "args": [ + "Balance" + ], + "docs": [ + " Spending has finished; this is the amount that rolls over until next spend. [budget_remaining]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds have been deposited. [deposit]" + ] + }, + { + "name": "NewTip", + "args": [ + "Hash" + ], + "docs": [ + " A new tip suggestion has been opened. [tip_hash]" + ] + }, + { + "name": "TipClosing", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has reached threshold and is closing. [tip_hash]" + ] + }, + { + "name": "TipClosed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been closed. [tip_hash, who, payout]" + ] + }, + { + "name": "TipRetracted", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has been retracted. [tip_hash]" + ] + } + ], + "constants": [ + { + "name": "ProposalBond", + "type": "Permill", + "value": "0x50c30000", + "docs": [ + " Fraction of a proposal's value that should be bonded in order to place the proposal.", + " An accepted proposal gets these back. A rejected proposal does not." + ] + }, + { + "name": "ProposalBondMinimum", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Minimum amount of funds that should be placed in a deposit for making a proposal." + ] + }, + { + "name": "SpendPeriod", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " Period between successive spends." + ] + }, + { + "name": "Burn", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of spare funds (if any) that are burnt per spend period." + ] + }, + { + "name": "TipCountdown", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The period for which a tip remains open after is has achieved threshold tippers." + ] + }, + { + "name": "TipFindersFee", + "type": "Percent", + "value": "0x14", + "docs": [ + " The amount of the final tip which goes to the original reporter of the tip." + ] + }, + { + "name": "TipReportDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a tip report." + ] + }, + { + "name": "TipReportDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within the tip report reason." + ] + }, + { + "name": "ModuleId", + "type": "ModuleId", + "value": "0x70792f7472737279", + "docs": [ + " The treasury's module id, used for deriving its sovereign account ID." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidProposalIndex", + "docs": [ + " No proposal at that index." + ] + }, + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "AlreadyKnown", + "docs": [ + " The tip was already found/started." + ] + }, + { + "name": "UnknownTip", + "docs": [ + " The tip hash is unknown." + ] + }, + { + "name": "NotFinder", + "docs": [ + " The account attempting to retract the tip is not the finder of the tip." + ] + }, + { + "name": "StillOpen", + "docs": [ + " The tip cannot be claimed/closed because there are not enough tippers yet." + ] + }, + { + "name": "Premature", + "docs": [ + " The tip cannot be claimed/closed because it's still in the countdown period." + ] + } + ] + }, + { + "name": "Contracts", + "storage": { + "prefix": "Contracts", + "items": [ + { + "name": "CurrentSchedule", + "modifier": "Default", + "type": { + "plain": "Schedule" + }, + "fallback": "0x0000000020a107000000000020a107000000000020a107000000000020a107000000000020a107000000000020a107000000000020a1070000000000e0f7050400000000e024370500000000e0f705040000000020a107000000000020a107000000000080f0fa020000000000e1f5050000000004000000000001001000000000400000002000000000000800", + "docs": [ + " Current cost schedule for contracts." + ] + }, + { + "name": "PristineCode", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from an original code hash to the original code, untouched by instrumentation." + ] + }, + { + "name": "CodeStorage", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "PrefabWasmModule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping between an original code hash and instrumented wasm code, ready for execution." + ] + }, + { + "name": "AccountCounter", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The subtrie counter." + ] + }, + { + "name": "ContractInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ContractInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The code associated with a given account.", + "", + " TWOX-NOTE: SAFE since `AccountId` is a secure hash." + ] + } + ] + }, + "calls": [ + { + "name": "update_schedule", + "args": [ + { + "name": "schedule", + "type": "Schedule" + } + ], + "docs": [ + " Updates the schedule for metering contracts.", + "", + " The schedule must have a greater version than the stored schedule." + ] + }, + { + "name": "put_code", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Stores the given binary Wasm code into the chain's storage and returns its `codehash`.", + " You can instantiate contracts only with stored code." + ] + }, + { + "name": "call", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Makes a call to an account, optionally transferring some balance.", + "", + " * If the account is a smart-contract account, the associated code will be", + " executed and any value will be transferred.", + " * If the account is a regular account, any value will be transferred.", + " * If no account exists and the call value is not less than `existential_deposit`,", + " a regular account will be created and any value will be transferred." + ] + }, + { + "name": "instantiate", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code_hash", + "type": "CodeHash" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a new contract from the `codehash` generated by `put_code`, optionally transferring some balance.", + "", + " Instantiation is executed as follows:", + "", + " - The destination address is computed based on the sender and hash of the code.", + " - The smart-contract account is created at the computed address.", + " - The `ctor_code` is executed in the context of the newly-created account. Buffer returned", + " after the execution is saved as the `code` of the account. That code will be invoked", + " upon any call received by this account.", + " - The contract is initialized." + ] + }, + { + "name": "claim_surcharge", + "args": [ + { + "name": "dest", + "type": "AccountId" + }, + { + "name": "aux_sender", + "type": "Option" + } + ], + "docs": [ + " Allows block producers to claim a small reward for evicting a contract. If a block producer", + " fails to do so, a regular users will be allowed to claim the reward.", + "", + " If contract is not evicted as a result of this call, no actions are taken and", + " the sender is not eligible for the reward." + ] + } + ], + "events": [ + { + "name": "Instantiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract deployed by address at the specified address. [owner, contract]" + ] + }, + { + "name": "Evicted", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " Contract has been evicted and is now in tombstone state.", + " [contract, tombstone]", + " ", + " # Params", + "", + " - `contract`: `AccountId`: The account ID of the evicted contract.", + " - `tombstone`: `bool`: True if the evicted contract left behind a tombstone." + ] + }, + { + "name": "Restored", + "args": [ + "AccountId", + "AccountId", + "Hash", + "Balance" + ], + "docs": [ + " Restoration for a contract has been successful.", + " [donor, dest, code_hash, rent_allowance]", + " ", + " # Params", + "", + " - `donor`: `AccountId`: Account ID of the restoring contract", + " - `dest`: `AccountId`: Account ID of the restored contract", + " - `code_hash`: `Hash`: Code hash of the restored contract", + " - `rent_allowance: `Balance`: Rent allowance of the restored contract" + ] + }, + { + "name": "CodeStored", + "args": [ + "Hash" + ], + "docs": [ + " Code with the specified hash has been stored.", + " [code_hash]" + ] + }, + { + "name": "ScheduleUpdated", + "args": [ + "u32" + ], + "docs": [ + " Triggered when the current [schedule] is updated." + ] + }, + { + "name": "ContractExecution", + "args": [ + "AccountId", + "Bytes" + ], + "docs": [ + " An event deposited upon execution of a contract from the account.", + " [account, data]" + ] + } + ], + "constants": [ + { + "name": "SignedClaimHandicap", + "type": "BlockNumber", + "value": "0x02000000", + "docs": [ + " Number of block delay an extrinsic claim surcharge has.", + "", + " When claim surcharge is called by an extrinsic the rent is checked", + " for current_block - delay" + ] + }, + { + "name": "TombstoneDeposit", + "type": "BalanceOf", + "value": "0x00a0acb9030000000000000000000000", + "docs": [ + " The minimum amount required to generate a tombstone." + ] + }, + { + "name": "StorageSizeOffset", + "type": "u32", + "value": "0x08000000", + "docs": [ + " A size offset for an contract. A just created account with untouched storage will have that", + " much of storage from the perspective of the state rent.", + "", + " This is a simple way to ensure that contracts with empty storage eventually get deleted", + " by making them pay rent. This creates an incentive to remove them early in order to save", + " rent." + ] + }, + { + "name": "RentByteFee", + "type": "BalanceOf", + "value": "0x00286bee000000000000000000000000", + "docs": [ + " Price of a byte of storage per one block interval. Should be greater than 0." + ] + }, + { + "name": "RentDepositOffset", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of funds a contract should deposit in order to offset", + " the cost of one byte.", + "", + " Let's suppose the deposit is 1,000 BU (balance units)/byte and the rent is 1 BU/byte/day,", + " then a contract with 1,000,000 BU that uses 1,000 bytes of storage would pay no rent.", + " But if the balance reduced to 500,000 BU and the storage stayed the same at 1,000,", + " then it would pay 500 BU/day." + ] + }, + { + "name": "SurchargeReward", + "type": "BalanceOf", + "value": "0x005cb2ec220000000000000000000000", + "docs": [ + " Reward that is received by the party whose touch has led", + " to removal of a contract." + ] + }, + { + "name": "MaxDepth", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum nesting level of a call/instantiate stack. A reasonable default", + " value is 100." + ] + }, + { + "name": "MaxValueSize", + "type": "u32", + "value": "0x00400000", + "docs": [ + " The maximum size of a storage value in bytes. A reasonable default is 16 KiB." + ] + } + ], + "errors": [ + { + "name": "InvalidScheduleVersion", + "docs": [ + " A new schedule must have a greater version than the current one." + ] + }, + { + "name": "InvalidSurchargeClaim", + "docs": [ + " An origin must be signed or inherent and auxiliary sender only provided on inherent." + ] + }, + { + "name": "InvalidSourceContract", + "docs": [ + " Cannot restore from nonexisting or tombstone contract." + ] + }, + { + "name": "InvalidDestinationContract", + "docs": [ + " Cannot restore to nonexisting or alive contract." + ] + }, + { + "name": "InvalidTombstone", + "docs": [ + " Tombstones don't match." + ] + }, + { + "name": "InvalidContractOrigin", + "docs": [ + " An origin TrieId written in the current block." + ] + }, + { + "name": "OutOfGas", + "docs": [ + " The executed contract exhausted its gas limit." + ] + }, + { + "name": "OutputBufferTooSmall", + "docs": [ + " The output buffer supplied to a contract API call was too small." + ] + }, + { + "name": "BelowSubsistenceThreshold", + "docs": [ + " Performing the requested transfer would have brought the contract below", + " the subsistence threshold. No transfer is allowed to do this in order to allow", + " for a tombstone to be created. Use `seal_terminate` to remove a contract without", + " leaving a tombstone behind." + ] + }, + { + "name": "NewContractNotFunded", + "docs": [ + " The newly created contract is below the subsistence threshold after executing", + " its contructor. No contracts are allowed to exist below that threshold." + ] + }, + { + "name": "TransferFailed", + "docs": [ + " Performing the requested transfer failed for a reason originating in the", + " chosen currency implementation of the runtime. Most probably the balance is", + " too low or locks are placed on it." + ] + }, + { + "name": "MaxCallDepthReached", + "docs": [ + " Performing a call was denied because the calling depth reached the limit", + " of what is specified in the schedule." + ] + }, + { + "name": "NotCallable", + "docs": [ + " The contract that was called is either no contract at all (a plain account)", + " or is a tombstone." + ] + }, + { + "name": "CodeTooLarge", + "docs": [ + " The code supplied to `put_code` exceeds the limit specified in the current schedule." + ] + }, + { + "name": "CodeNotFound", + "docs": [ + " No code could be found at the supplied code hash." + ] + }, + { + "name": "OutOfBounds", + "docs": [ + " A buffer outside of sandbox memory was passed to a contract API function." + ] + }, + { + "name": "DecodingFailed", + "docs": [ + " Input passed to a contract API function failed to decode as expected type." + ] + }, + { + "name": "ContractTrapped", + "docs": [ + " Contract trapped during execution." + ] + } + ] + }, + { + "name": "Sudo", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "Key", + "modifier": "Default", + "type": { + "plain": "AccountId" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The `AccountId` of the sudo key." + ] + } + ] + }, + "calls": [ + { + "name": "sudo", + "args": [ + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + }, + { + "name": "sudo_unchecked_weight", + "args": [ + { + "name": "call", + "type": "Call" + }, + { + "name": "_weight", + "type": "Weight" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + " This function does not check the weight of the call, and instead allows the", + " Sudo user to specify the weight of the call.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - The weight of this call is defined by the caller.", + " # " + ] + }, + { + "name": "set_key", + "args": [ + { + "name": "new", + "type": "LookupSource" + } + ], + "docs": [ + " Authenticates the current sudo key and sets the given AccountId (`new`) as the new sudo key.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "sudo_as", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Signed` origin from", + " a given account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + } + ], + "events": [ + { + "name": "Sudid", + "args": [ + "DispatchResult" + ], + "docs": [ + " A sudo just took place. [result]" + ] + }, + { + "name": "KeyChanged", + "args": [ + "AccountId" + ], + "docs": [ + " The [sudoer] just switched identity; the old key is supplied." + ] + }, + { + "name": "SudoAsDone", + "args": [ + "bool" + ], + "docs": [ + " A sudo just took place. [result]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "RequireSudo", + "docs": [ + " Sender must be the Sudo account" + ] + } + ] + }, + { + "name": "ImOnline", + "storage": { + "prefix": "ImOnline", + "items": [ + { + "name": "HeartbeatAfter", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The block number after which it's ok to send heartbeats in current session.", + "", + " At the beginning of each session we set this to a value that should", + " fall roughly in the middle of the session duration.", + " The idea is to first wait for the validators to produce a block", + " in the current session, so that the heartbeat later on will not be necessary." + ] + }, + { + "name": "Keys", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of keys that may issue a heartbeat." + ] + }, + { + "name": "ReceivedHeartbeats", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "AuthIndex", + "value": "Bytes", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " For each session index, we keep a mapping of `AuthIndex` to", + " `offchain::OpaqueNetworkState`." + ] + }, + { + "name": "AuthoredBlocks", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "ValidatorId", + "value": "u32", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00000000", + "docs": [ + " For each session index, we keep a mapping of `T::ValidatorId` to the", + " number of blocks authored by the given authority." + ] + } + ] + }, + "calls": [ + { + "name": "heartbeat", + "args": [ + { + "name": "heartbeat", + "type": "Heartbeat" + }, + { + "name": "_signature", + "type": "Signature" + } + ], + "docs": [ + " # ", + " - Complexity: `O(K + E)` where K is length of `Keys` and E is length of", + " `Heartbeat.network_state.external_address`", + "", + " - `O(K)`: decoding of length `K`", + " - `O(E)`: decoding/encoding of length `E`", + " - DbReads: pallet_session `Validators`, pallet_session `CurrentIndex`, `Keys`,", + " `ReceivedHeartbeats`", + " - DbWrites: `ReceivedHeartbeats`", + " # " + ] + } + ], + "events": [ + { + "name": "HeartbeatReceived", + "args": [ + "AuthorityId" + ], + "docs": [ + " A new heartbeat was received from `AuthorityId` [authority_id]" + ] + }, + { + "name": "AllGood", + "args": [], + "docs": [ + " At the end of the session, no offence was committed." + ] + }, + { + "name": "SomeOffline", + "args": [ + "Vec" + ], + "docs": [ + " At the end of the session, at least one validator was found to be [offline]." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidKey", + "docs": [ + " Non existent public key." + ] + }, + { + "name": "DuplicatedHeartbeat", + "docs": [ + " Duplicated heartbeat." + ] + } + ] + }, + { + "name": "AuthorityDiscovery", + "storage": null, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Offences", + "storage": { + "prefix": "Offences", + "items": [ + { + "name": "Reports", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReportIdOf", + "value": "OffenceDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The primary structure that holds all offence records keyed by report identifiers." + ] + }, + { + "name": "DeferredOffences", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Deferred reports that have been rejected by the offence handler and need to be submitted", + " at a later time." + ] + }, + { + "name": "ConcurrentReportsIndex", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Kind", + "key2": "OpaqueTimeSlot", + "value": "Vec", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " A vector of reports of the same kind that happened at the same time slot." + ] + }, + { + "name": "ReportsByKindIndex", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Kind", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Enumerates all reports of a kind along with the time they happened.", + "", + " All reports are sorted by the time of offence.", + "", + " Note that the actual type of this mapping is `Vec`, this is because values of", + " different types are not supported at the moment so we are doing the manual serialization." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "Offence", + "args": [ + "Kind", + "OpaqueTimeSlot", + "bool" + ], + "docs": [ + " There is an offence reported of the given `kind` happened at the `session_index` and", + " (kind-specific) time slot. This event is not deposited for duplicate slashes. last", + " element indicates of the offence was applied (true) or queued (false) ", + " [kind, timeslot, applied]." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Historical", + "storage": null, + "calls": null, + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "RandomnessCollectiveFlip", + "storage": { + "prefix": "RandomnessCollectiveFlip", + "items": [ + { + "name": "RandomMaterial", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Series of block headers from the last 81 blocks that acts as random seed material. This", + " is arranged as a ring buffer with `block_number % 81` being the index into the `Vec` of", + " the oldest hash." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Identity", + "storage": { + "prefix": "Identity", + "items": [ + { + "name": "IdentityOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Registration", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information that is pertinent to identify the entity behind an account.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "SuperOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "(AccountId,Data)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The super-identity of an alternative \"sub\" identity together with its name, within that", + " context. If the account is not some other account's sub-identity, then just `None`." + ] + }, + { + "name": "SubsOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " Alternative \"sub\" identities of this account.", + "", + " The first item is the deposit, the second is a vector of the accounts.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "Registrars", + "modifier": "Default", + "type": { + "plain": "Vec>" + }, + "fallback": "0x00", + "docs": [ + " The set of registrars. Not expected to get very big as can only be added through a", + " special origin (likely a council motion).", + "", + " The index into this can be cast to `RegistrarIndex` to get a valid value." + ] + } + ] + }, + "calls": [ + { + "name": "add_registrar", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Add a registrar to the system.", + "", + " The dispatch origin for this call must be `T::RegistrarOrigin`.", + "", + " - `account`: the account of the registrar.", + "", + " Emits `RegistrarAdded` if successful.", + "", + " # ", + " - `O(R)` where `R` registrar-count (governance-bounded and code-bounded).", + " - One storage mutation (codec `O(R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_identity", + "args": [ + { + "name": "info", + "type": "IdentityInfo" + } + ], + "docs": [ + " Set an account's identity information and reserve the appropriate deposit.", + "", + " If the account already has identity information, the deposit is taken as part payment", + " for the new deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `info`: The identity information.", + "", + " Emits `IdentitySet` if successful.", + "", + " # ", + " - `O(X + X' + R)`", + " - where `X` additional-field-count (deposit-bounded and code-bounded)", + " - where `R` judgements-count (registrar-count-bounded)", + " - One balance reserve operation.", + " - One storage mutation (codec-read `O(X' + R)`, codec-write `O(X + R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_subs", + "args": [ + { + "name": "subs", + "type": "Vec<(AccountId,Data)>" + } + ], + "docs": [ + " Set the sub-accounts of the sender.", + "", + " Payment: Any aggregate balance reserved by previous `set_subs` calls will be returned", + " and an amount `SubAccountDeposit` will be reserved for each item in `subs`.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " - `subs`: The identity's (new) sub-accounts.", + "", + " # ", + " - `O(P + S)`", + " - where `P` old-subs-count (hard- and deposit-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - At most one balance operations.", + " - DB:", + " - `P + S` storage mutations (codec complexity `O(1)`)", + " - One storage read (codec complexity `O(P)`).", + " - One storage write (codec complexity `O(S)`).", + " - One storage-exists (`IdentityOf::contains_key`).", + " # " + ] + }, + { + "name": "clear_identity", + "args": [], + "docs": [ + " Clear an account's identity info and all sub-accounts and return all deposits.", + "", + " Payment: All reserved balances on the account are returned.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " Emits `IdentityCleared` if successful.", + "", + " # ", + " - `O(R + S + X)`", + " - where `R` registrar-count (governance-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - where `X` additional-field-count (deposit-bounded and code-bounded).", + " - One balance-unreserve operation.", + " - `2` storage reads and `S + 2` storage deletions.", + " - One event.", + " # " + ] + }, + { + "name": "request_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "max_fee", + "type": "Compact" + } + ], + "docs": [ + " Request a judgement from a registrar.", + "", + " Payment: At most `max_fee` will be reserved for payment to the registrar if judgement", + " given.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is requested.", + " - `max_fee`: The maximum fee that may be paid. This should just be auto-populated as:", + "", + " ```nocompile", + " Self::registrars().get(reg_index).unwrap().fee", + " ```", + "", + " Emits `JudgementRequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(X + R)`.", + " - One event.", + " # " + ] + }, + { + "name": "cancel_request", + "args": [ + { + "name": "reg_index", + "type": "RegistrarIndex" + } + ], + "docs": [ + " Cancel a previous request.", + "", + " Payment: A previously reserved deposit is returned on success.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is no longer requested.", + "", + " Emits `JudgementUnrequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - One storage mutation `O(R + X)`.", + " - One event", + " # " + ] + }, + { + "name": "set_fee", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Set the fee required for a judgement to be requested from a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fee`: the new fee.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.315 + R * 0.329 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_account_id", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Change the account associated with a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `new`: the new account ID.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 8.823 + R * 0.32 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_fields", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fields", + "type": "IdentityFields" + } + ], + "docs": [ + " Set the field information for a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fields`: the fields that the registrar concerns themselves with.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.464 + R * 0.325 µs (min squares analysis)", + " # " + ] + }, + { + "name": "provide_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "judgement", + "type": "IdentityJudgement" + } + ], + "docs": [ + " Provide a judgement for an account's identity.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `reg_index`.", + "", + " - `reg_index`: the index of the registrar whose judgement is being made.", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + " - `judgement`: the judgement of the registrar of index `reg_index` about `target`.", + "", + " Emits `JudgementGiven` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-transfer operation.", + " - Up to one account-lookup operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(R + X)`.", + " - One event.", + " # " + ] + }, + { + "name": "kill_identity", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Remove an account's identity and sub-account information and slash the deposits.", + "", + " Payment: Reserved balances from `set_subs` and `set_identity` are slashed and handled by", + " `Slash`. Verification request deposits are not returned; they should be cancelled", + " manually using `cancel_request`.", + "", + " The dispatch origin for this call must match `T::ForceOrigin`.", + "", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + "", + " Emits `IdentityKilled` if successful.", + "", + " # ", + " - `O(R + S + X)`.", + " - One balance-reserve operation.", + " - `S + 2` storage mutations.", + " - One event.", + " # " + ] + }, + { + "name": "add_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Add the given account to the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "rename_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Alter the associated name of the given sub-account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "remove_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + } + ], + "docs": [ + " Remove the given account from the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "quit_sub", + "args": [], + "docs": [ + " Remove the sender as a sub-account.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender (*not* the original depositor).", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " super-identity.", + "", + " NOTE: This should not normally be used, but is provided in the case that the non-", + " controller of an account is maliciously registered as a sub-account." + ] + } + ], + "events": [ + { + "name": "IdentitySet", + "args": [ + "AccountId" + ], + "docs": [ + " A name was set or reset (which will remove all judgements). [who]" + ] + }, + { + "name": "IdentityCleared", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was cleared, and the given balance returned. [who, deposit]" + ] + }, + { + "name": "IdentityKilled", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was removed and the given balance slashed. [who, deposit]" + ] + }, + { + "name": "JudgementRequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was asked from a registrar. [who, registrar_index]" + ] + }, + { + "name": "JudgementUnrequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement request was retracted. [who, registrar_index]" + ] + }, + { + "name": "JudgementGiven", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was given by a registrar. [target, registrar_index]" + ] + }, + { + "name": "RegistrarAdded", + "args": [ + "RegistrarIndex" + ], + "docs": [ + " A registrar was added. [registrar_index]" + ] + }, + { + "name": "SubIdentityAdded", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was added to an identity and the deposit paid. [sub, main, deposit]" + ] + }, + { + "name": "SubIdentityRemoved", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was removed from an identity and the deposit freed.", + " [sub, main, deposit]" + ] + }, + { + "name": "SubIdentityRevoked", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was cleared, and the given deposit repatriated from the", + " main identity account to the sub-identity account. [sub, main, deposit]" + ] + } + ], + "constants": [ + { + "name": "BasicDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The amount held on deposit for a registered identity." + ] + }, + { + "name": "FieldDeposit", + "type": "BalanceOf", + "value": "0x00a031a95fe300000000000000000000", + "docs": [ + " The amount held on deposit per additional field for a registered identity." + ] + }, + { + "name": "SubAccountDeposit", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount held on deposit for a registered subaccount. This should account for the fact", + " that one storage item's value will increase by the size of an account ID, and there will be", + " another trie item whose value is the size of an account ID plus 32 bytes." + ] + }, + { + "name": "MaxSubAccounts", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of sub-accounts allowed per identified account." + ] + }, + { + "name": "MaxAdditionalFields", + "type": "u32", + "value": "0x64000000", + "docs": [ + " Maximum number of additional fields that may be stored in an ID. Needed to bound the I/O", + " required to access an identity, but can be pretty high." + ] + }, + { + "name": "MaxRegistrars", + "type": "u32", + "value": "0x14000000", + "docs": [ + " Maxmimum number of registrars allowed in the system. Needed to bound the complexity", + " of, e.g., updating judgements." + ] + } + ], + "errors": [ + { + "name": "TooManySubAccounts", + "docs": [ + " Too many subs-accounts." + ] + }, + { + "name": "NotFound", + "docs": [ + " Account isn't found." + ] + }, + { + "name": "NotNamed", + "docs": [ + " Account isn't named." + ] + }, + { + "name": "EmptyIndex", + "docs": [ + " Empty index." + ] + }, + { + "name": "FeeChanged", + "docs": [ + " Fee is changed." + ] + }, + { + "name": "NoIdentity", + "docs": [ + " No identity found." + ] + }, + { + "name": "StickyJudgement", + "docs": [ + " Sticky judgement." + ] + }, + { + "name": "JudgementGiven", + "docs": [ + " Judgement given." + ] + }, + { + "name": "InvalidJudgement", + "docs": [ + " Invalid judgement." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " The index is invalid." + ] + }, + { + "name": "InvalidTarget", + "docs": [ + " The target is invalid." + ] + }, + { + "name": "TooManyFields", + "docs": [ + " Too many additional fields." + ] + }, + { + "name": "TooManyRegistrars", + "docs": [ + " Maximum amount of registrars reached. Cannot add any more." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Account ID is already named." + ] + }, + { + "name": "NotSub", + "docs": [ + " Sender is not a sub-account." + ] + }, + { + "name": "NotOwned", + "docs": [ + " Sub-account isn't owned by sender." + ] + } + ] + }, + { + "name": "Society", + "storage": { + "prefix": "Society", + "items": [ + { + "name": "Founder", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The first member." + ] + }, + { + "name": "Rules", + "modifier": "Optional", + "type": { + "plain": "Hash" + }, + "fallback": "0x00", + "docs": [ + " A hash of the rules of this society concerning membership. Can only be set once and", + " only by the founder." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of candidates; bidders that are attempting to become members." + ] + }, + { + "name": "SuspendedCandidates", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,BidKind)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended candidates." + ] + }, + { + "name": "Pot", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Amount of our account balance that is specifically for the next round's bid(s)." + ] + }, + { + "name": "Head", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The most primary from the most recently approved members." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of members, ordered." + ] + }, + { + "name": "SuspendedMembers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended members." + ] + }, + { + "name": "Bids", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current bids, stored ordered by the value of the bid." + ] + }, + { + "name": "Vouching", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "VouchingStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Members currently vouching or banned from vouching again" + ] + }, + { + "name": "Payouts", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Vec<(BlockNumber,BalanceOf)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Pending payouts; ordered by block number, with the amount that should be paid out." + ] + }, + { + "name": "Strikes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "StrikeCount", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " The ongoing number of losing votes cast by the member." + ] + }, + { + "name": "Votes", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "SocietyVote", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Double map from Candidate -> Voter -> (Maybe) Vote." + ] + }, + { + "name": "Defender", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The defending member currently being challenged." + ] + }, + { + "name": "DefenderVotes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SocietyVote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes for the defender." + ] + }, + { + "name": "MaxMembers", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The max number of members for the society at one time." + ] + } + ] + }, + "calls": [ + { + "name": "bid", + "args": [ + { + "name": "value", + "type": "BalanceOf" + } + ], + "docs": [ + " A user outside of the society can make a bid for entry.", + "", + " Payment: `CandidateDeposit` will be reserved for making a bid. It is returned", + " when the bid becomes a member, or if the bid calls `unbid`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `value`: A one time payment the bid would like to receive when joining the society.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members), X (balance reserve)", + " - Storage Reads:", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " \t- One storage read to retrieve all members. O(M)", + " - Storage Writes:", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for new bid.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unbid", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " A bidder can remove their bid for entry into society.", + " By doing so, they will have their candidate deposit returned or", + " they will unvouch their voucher.", + "", + " Payment: The bid deposit is unreserved if the user made a bid.", + "", + " The dispatch origin for this call must be _Signed_ and a bidder.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who wants to unbid.", + "", + " # ", + " Key: B (len of bids), X (balance unreserve)", + " - One storage read and write to retrieve and update the bids. O(B)", + " - Either one unreserve balance action O(X) or one vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B + X)", + " # " + ] + }, + { + "name": "vouch", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "value", + "type": "BalanceOf" + }, + { + "name": "tip", + "type": "BalanceOf" + } + ], + "docs": [ + " As a member, vouch for someone to join society by placing a bid on their behalf.", + "", + " There is no deposit required to vouch for a new bid, but a member can only vouch for", + " one bid at a time. If the bid becomes a suspended candidate and ultimately rejected by", + " the suspension judgement origin, the member will be banned from vouching again.", + "", + " As a vouching member, you can claim a tip if the candidate is accepted. This tip will", + " be paid as a portion of the reward the member will receive for joining the society.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `who`: The user who you would like to vouch for.", + " - `value`: The total reward to be paid between you and the candidate if they become", + " a member in the society.", + " - `tip`: Your cut of the total `value` payout when the candidate is inducted into", + " the society. Tips larger than `value` will be saturated upon payout.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members)", + " - Storage Reads:", + " \t- One storage read to retrieve all members. O(M)", + " \t- One storage read to check member is not already vouching. O(1)", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " - Storage Writes:", + " \t- One storage write to insert vouching status to the member. O(1)", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(log M) search to check sender is a member.", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for vouch.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unvouch", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " As a vouching member, unvouch a bid. This only works while vouched user is", + " only a bidder (and not a candidate).", + "", + " The dispatch origin for this call must be _Signed_ and a vouching member.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who should be unvouched.", + "", + " # ", + " Key: B (len of bids)", + " - One storage read O(1) to check the signer is a vouching member.", + " - One storage mutate to retrieve and update the bids. O(B)", + " - One vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B)", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "candidate", + "type": "LookupSource" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on a candidate.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `candidate`: The candidate that the member would like to bid on.", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " Key: C (len of candidates), M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One account lookup.", + " - One storage read O(C) and O(C) search to check that user is a candidate.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM + C)", + " # " + ] + }, + { + "name": "defender_vote", + "args": [ + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on the defender.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " - Key: M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM)", + " # " + ] + }, + { + "name": "payout", + "args": [], + "docs": [ + " Transfer the first matured payout for the sender and remove it from the records.", + "", + " NOTE: This extrinsic needs to be called multiple times to claim multiple matured payouts.", + "", + " Payment: The member will receive a payment equal to their first matured", + " payout to their free balance.", + "", + " The dispatch origin for this call must be _Signed_ and a member with", + " payouts remaining.", + "", + " # ", + " Key: M (len of members), P (number of payouts for a particular member)", + " - One storage read O(M) and O(log M) search to check signer is a member.", + " - One storage read O(P) to get all payouts for a member.", + " - One storage read O(1) to get the current block number.", + " - One currency transfer call. O(X)", + " - One storage write or removal to update the member's payouts. O(P)", + "", + " Total Complexity: O(M + logM + P + X)", + " # " + ] + }, + { + "name": "found", + "args": [ + { + "name": "founder", + "type": "AccountId" + }, + { + "name": "max_members", + "type": "u32" + }, + { + "name": "rules", + "type": "Bytes" + } + ], + "docs": [ + " Found the society.", + "", + " This is done as a discrete action in order to allow for the", + " module to be included into a running chain and can only be done once.", + "", + " The dispatch origin for this call must be from the _FounderSetOrigin_.", + "", + " Parameters:", + " - `founder` - The first member and head of the newly founded society.", + " - `max_members` - The initial max number of members for the society.", + " - `rules` - The rules of this society concerning membership.", + "", + " # ", + " - Two storage mutates to set `Head` and `Founder`. O(1)", + " - One storage write to add the first member to society. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "unfound", + "args": [], + "docs": [ + " Annul the founding of the society.", + "", + " The dispatch origin for this call must be Signed, and the signing account must be both", + " the `Founder` and the `Head`. This implies that it may only be done when there is one", + " member.", + "", + " # ", + " - Two storage reads O(1).", + " - Four storage removals O(1).", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "judge_suspended_member", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "forgive", + "type": "bool" + } + ], + "docs": [ + " Allow suspension judgement origin to make judgement on a suspended member.", + "", + " If a suspended member is forgiven, we simply add them back as a member, not affecting", + " any of the existing storage items for that member.", + "", + " If a suspended member is rejected, remove all associated storage items, including", + " their payouts, and remove any vouched bids they currently have.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended member to be judged.", + " - `forgive` - A boolean representing whether the suspension judgement origin", + " forgives (`true`) or rejects (`false`) a suspended member.", + "", + " # ", + " Key: B (len of bids), M (len of members)", + " - One storage read to check `who` is a suspended member. O(1)", + " - Up to one storage write O(M) with O(log M) binary search to add a member back to society.", + " - Up to 3 storage removals O(1) to clean up a removed member.", + " - Up to one storage write O(B) with O(B) search to remove vouched bid from bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal. O(1)", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B)", + " # " + ] + }, + { + "name": "judge_suspended_candidate", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "judgement", + "type": "SocietyJudgement" + } + ], + "docs": [ + " Allow suspended judgement origin to make judgement on a suspended candidate.", + "", + " If the judgement is `Approve`, we add them to society as a member with the appropriate", + " payment for joining society.", + "", + " If the judgement is `Reject`, we either slash the deposit of the bid, giving it back", + " to the society treasury, or we ban the voucher from vouching again.", + "", + " If the judgement is `Rebid`, we put the candidate back in the bid pool and let them go", + " through the induction process again.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended candidate to be judged.", + " - `judgement` - `Approve`, `Reject`, or `Rebid`.", + "", + " # ", + " Key: B (len of bids), M (len of members), X (balance action)", + " - One storage read to check `who` is a suspended candidate.", + " - One storage removal of the suspended candidate.", + " - Approve Logic", + " \t- One storage read to get the available pot to pay users with. O(1)", + " \t- One storage write to update the available pot. O(1)", + " \t- One storage read to get the current block number. O(1)", + " \t- One storage read to get all members. O(M)", + " \t- Up to one unreserve currency action.", + " \t- Up to two new storage writes to payouts.", + " \t- Up to one storage write with O(log M) binary search to add a member to society.", + " - Reject Logic", + " \t- Up to one repatriate reserved currency action. O(X)", + " \t- Up to one storage write to ban the vouching member from vouching again.", + " - Rebid Logic", + " \t- Storage mutate with O(log B) binary search to place the user back into bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal.", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B + X)", + " # " + ] + }, + { + "name": "set_max_members", + "args": [ + { + "name": "max", + "type": "u32" + } + ], + "docs": [ + " Allows root origin to change the maximum number of members in society.", + " Max membership count must be greater than 1.", + "", + " The dispatch origin for this call must be from _ROOT_.", + "", + " Parameters:", + " - `max` - The maximum number of members for the society.", + "", + " # ", + " - One storage write to update the max. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "Founded", + "args": [ + "AccountId" + ], + "docs": [ + " The society is founded by the given identity. [founder]" + ] + }, + { + "name": "Bid", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A membership bid just happened. The given account is the candidate's ID and their offer", + " is the second. [candidate_id, offer]" + ] + }, + { + "name": "Vouch", + "args": [ + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A membership bid just happened by vouching. The given account is the candidate's ID and", + " their offer is the second. The vouching party is the third. [candidate_id, offer, vouching]" + ] + }, + { + "name": "AutoUnbid", + "args": [ + "AccountId" + ], + "docs": [ + " A [candidate] was dropped (due to an excess of bids in the system)." + ] + }, + { + "name": "Unbid", + "args": [ + "AccountId" + ], + "docs": [ + " A [candidate] was dropped (by their request)." + ] + }, + { + "name": "Unvouch", + "args": [ + "AccountId" + ], + "docs": [ + " A [candidate] was dropped (by request of who vouched for them)." + ] + }, + { + "name": "Inducted", + "args": [ + "AccountId", + "Vec" + ], + "docs": [ + " A group of candidates have been inducted. The batch's primary is the first value, the", + " batch in full is the second. [primary, candidates]" + ] + }, + { + "name": "SuspendedMemberJudgement", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A suspended member has been judged. [who, judged]" + ] + }, + { + "name": "CandidateSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A [candidate] has been suspended" + ] + }, + { + "name": "MemberSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A [member] has been suspended" + ] + }, + { + "name": "Challenged", + "args": [ + "AccountId" + ], + "docs": [ + " A [member] has been challenged" + ] + }, + { + "name": "Vote", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed [candidate, voter, vote]" + ] + }, + { + "name": "DefenderVote", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed for a defending member [voter, vote]" + ] + }, + { + "name": "NewMaxMembers", + "args": [ + "u32" + ], + "docs": [ + " A new [max] member count has been set" + ] + }, + { + "name": "Unfounded", + "args": [ + "AccountId" + ], + "docs": [ + " Society is unfounded. [founder]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds were deposited into the society account. [value]" + ] + } + ], + "constants": [ + { + "name": "CandidateDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The minimum amount of a deposit required for a bid to be made." + ] + }, + { + "name": "WrongSideDeduction", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount of the unpaid reward that gets deducted in the case that either a skeptic", + " doesn't vote or someone votes in the wrong way." + ] + }, + { + "name": "MaxStrikes", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The number of times a member may vote the wrong way (or not at all, when they are a skeptic)", + " before they become suspended." + ] + }, + { + "name": "PeriodSpend", + "type": "BalanceOf", + "value": "0x0000c52ebca2b1000000000000000000", + "docs": [ + " The amount of incentive paid within each period. Doesn't include VoterTip." + ] + }, + { + "name": "RotationPeriod", + "type": "BlockNumber", + "value": "0x00770100", + "docs": [ + " The number of blocks between candidate/membership rotation periods." + ] + }, + { + "name": "ChallengePeriod", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " The number of blocks between membership challenges." + ] + }, + { + "name": "ModuleId", + "type": "ModuleId", + "value": "0x70792f736f636965", + "docs": [ + " The societies's module id" + ] + } + ], + "errors": [ + { + "name": "BadPosition", + "docs": [ + " An incorrect position was provided." + ] + }, + { + "name": "NotMember", + "docs": [ + " User is not a member." + ] + }, + { + "name": "AlreadyMember", + "docs": [ + " User is already a member." + ] + }, + { + "name": "Suspended", + "docs": [ + " User is suspended." + ] + }, + { + "name": "NotSuspended", + "docs": [ + " User is not suspended." + ] + }, + { + "name": "NoPayout", + "docs": [ + " Nothing to payout." + ] + }, + { + "name": "AlreadyFounded", + "docs": [ + " Society already founded." + ] + }, + { + "name": "InsufficientPot", + "docs": [ + " Not enough in pot to accept candidate." + ] + }, + { + "name": "AlreadyVouching", + "docs": [ + " Member is already vouching or banned from vouching again." + ] + }, + { + "name": "NotVouching", + "docs": [ + " Member is not vouching." + ] + }, + { + "name": "Head", + "docs": [ + " Cannot remove the head of the chain." + ] + }, + { + "name": "Founder", + "docs": [ + " Cannot remove the founder." + ] + }, + { + "name": "AlreadyBid", + "docs": [ + " User has already made a bid." + ] + }, + { + "name": "AlreadyCandidate", + "docs": [ + " User is already a candidate." + ] + }, + { + "name": "NotCandidate", + "docs": [ + " User is not a candidate." + ] + }, + { + "name": "MaxMembers", + "docs": [ + " Too many members in the society." + ] + }, + { + "name": "NotFounder", + "docs": [ + " The caller is not the founder." + ] + }, + { + "name": "NotHead", + "docs": [ + " The caller is not the head." + ] + } + ] + }, + { + "name": "Recovery", + "storage": { + "prefix": "Recovery", + "items": [ + { + "name": "Recoverable", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RecoveryConfig", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of recoverable accounts and their recovery configuration." + ] + }, + { + "name": "ActiveRecoveries", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "ActiveRecovery", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Active recovery attempts.", + "", + " First account is the account to be recovered, and the second account", + " is the user trying to recover the account." + ] + }, + { + "name": "Proxy", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The list of allowed proxy accounts.", + "", + " Map from the user who can access it to the recovered account." + ] + } + ] + }, + "calls": [ + { + "name": "as_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through a recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you want to make a call on-behalf-of.", + " - `call`: The call you want to make with the recovered account.", + "", + " # ", + " - The weight of the `call` + 10,000.", + " - One storage lookup to check account is recovered by `who`. O(1)", + " # " + ] + }, + { + "name": "set_recovered", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow ROOT to bypass the recovery process and set an a rescuer account", + " for a lost account directly.", + "", + " The dispatch origin for this call must be _ROOT_.", + "", + " Parameters:", + " - `lost`: The \"lost account\" to be recovered.", + " - `rescuer`: The \"rescuer account\" which can call as the lost account.", + "", + " # ", + " - One storage write O(1)", + " - One event", + " # " + ] + }, + { + "name": "create_recovery", + "args": [ + { + "name": "friends", + "type": "Vec" + }, + { + "name": "threshold", + "type": "u16" + }, + { + "name": "delay_period", + "type": "BlockNumber" + } + ], + "docs": [ + " Create a recovery configuration for your account. This makes your account recoverable.", + "", + " Payment: `ConfigDepositBase` + `FriendDepositFactor` * #_of_friends balance", + " will be reserved for storing the recovery configuration. This deposit is returned", + " in full when the user calls `remove_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `friends`: A list of friends you trust to vouch for recovery attempts.", + " Should be ordered and contain no duplicate values.", + " - `threshold`: The number of friends that must vouch for a recovery attempt", + " before the account can be recovered. Should be less than or equal to", + " the length of the list of friends.", + " - `delay_period`: The number of blocks after a recovery attempt is initialized", + " that needs to pass before the account can be recovered.", + "", + " # ", + " - Key: F (len of friends)", + " - One storage read to check that account is not already recoverable. O(1).", + " - A check that the friends list is sorted and unique. O(F)", + " - One currency reserve operation. O(X)", + " - One storage write. O(1). Codec O(F).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "initiate_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Initiate the process for recovering a recoverable account.", + "", + " Payment: `RecoveryDeposit` balance will be reserved for initiating the", + " recovery process. This deposit will always be repatriated to the account", + " trying to be recovered. See `close_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `account`: The lost account that you want to recover. This account", + " needs to be recoverable (i.e. have a recovery configuration).", + "", + " # ", + " - One storage read to check that account is recoverable. O(F)", + " - One storage read to check that this recovery process hasn't already started. O(1)", + " - One currency reserve operation. O(X)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "vouch_recovery", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow a \"friend\" of a recoverable account to vouch for an active recovery", + " process for that account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"friend\"", + " for the recoverable account.", + "", + " Parameters:", + " - `lost`: The lost account that you want to recover.", + " - `rescuer`: The account trying to rescue the lost account that you", + " want to vouch for.", + "", + " The combination of these two parameters must point to an active recovery", + " process.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One binary search to confirm caller is a friend. O(logF)", + " - One binary search to confirm caller has not already vouched. O(logV)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + logF + V + logV)", + " # " + ] + }, + { + "name": "claim_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Allow a successful rescuer to claim their recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"rescuer\"", + " who has successfully completed the account recovery process: collected", + " `threshold` or more vouches, waited `delay_period` blocks since initiation.", + "", + " Parameters:", + " - `account`: The lost account that you want to claim has been successfully", + " recovered by you.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + V)", + " # " + ] + }, + { + "name": "close_recovery", + "args": [ + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " As the controller of a recoverable account, close an active recovery", + " process for your account.", + "", + " Payment: By calling this function, the recoverable account will receive", + " the recovery deposit `RecoveryDeposit` placed by the rescuer.", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account with an active recovery process for it.", + "", + " Parameters:", + " - `rescuer`: The account trying to rescue this recoverable account.", + "", + " # ", + " Key: V (len of vouching friends)", + " - One storage read/remove to get the active recovery process. O(1), Codec O(V)", + " - One balance call to repatriate reserved. O(X)", + " - One event.", + "", + " Total Complexity: O(V + X)", + " # " + ] + }, + { + "name": "remove_recovery", + "args": [], + "docs": [ + " Remove the recovery process for your account. Recovered accounts are still accessible.", + "", + " NOTE: The user must make sure to call `close_recovery` on all active", + " recovery attempts before calling this function else it will fail.", + "", + " Payment: By calling this function the recoverable account will unreserve", + " their recovery configuration deposit.", + " (`ConfigDepositBase` + `FriendDepositFactor` * #_of_friends)", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account (i.e. has a recovery configuration).", + "", + " # ", + " Key: F (len of friends)", + " - One storage read to get the prefix iterator for active recoveries. O(1)", + " - One storage read/remove to get the recovery configuration. O(1), Codec O(F)", + " - One balance call to unreserved. O(X)", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "cancel_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Cancel the ability to use `as_recovered` for `account`.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you are able to call on-behalf-of.", + "", + " # ", + " - One storage mutation to check account is recovered by `who`. O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "RecoveryCreated", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been set up for an [account]." + ] + }, + { + "name": "RecoveryInitiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process has been initiated for lost account by rescuer account.", + " [lost, rescuer]" + ] + }, + { + "name": "RecoveryVouched", + "args": [ + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been vouched for by sender.", + " [lost, rescuer, sender]" + ] + }, + { + "name": "RecoveryClosed", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been closed.", + " [lost, rescuer]" + ] + }, + { + "name": "AccountRecovered", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Lost account has been successfully recovered by rescuer account.", + " [lost, rescuer]" + ] + }, + { + "name": "RecoveryRemoved", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been removed for an [account]." + ] + } + ], + "constants": [ + { + "name": "ConfigDepositBase", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a recovery configuration." + ] + }, + { + "name": "FriendDepositFactor", + "type": "BalanceOf", + "value": "0x00203d88792d00000000000000000000", + "docs": [ + " The amount of currency needed per additional user when creating a recovery configuration." + ] + }, + { + "name": "MaxFriends", + "type": "u16", + "value": "0x0900", + "docs": [ + " The maximum amount of friends allowed in a recovery configuration." + ] + }, + { + "name": "RecoveryDeposit", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for starting a recovery." + ] + } + ], + "errors": [ + { + "name": "NotAllowed", + "docs": [ + " User is not allowed to make a call on behalf of this account" + ] + }, + { + "name": "ZeroThreshold", + "docs": [ + " Threshold must be greater than zero" + ] + }, + { + "name": "NotEnoughFriends", + "docs": [ + " Friends list must be greater than zero and threshold" + ] + }, + { + "name": "MaxFriends", + "docs": [ + " Friends list must be less than max friends" + ] + }, + { + "name": "NotSorted", + "docs": [ + " Friends list must be sorted and free of duplicates" + ] + }, + { + "name": "NotRecoverable", + "docs": [ + " This account is not set up for recovery" + ] + }, + { + "name": "AlreadyRecoverable", + "docs": [ + " This account is already set up for recovery" + ] + }, + { + "name": "AlreadyStarted", + "docs": [ + " A recovery process has already started for this account" + ] + }, + { + "name": "NotStarted", + "docs": [ + " A recovery process has not started for this rescuer" + ] + }, + { + "name": "NotFriend", + "docs": [ + " This account is not a friend who can vouch" + ] + }, + { + "name": "DelayPeriod", + "docs": [ + " The friend must wait until the delay period to vouch for this recovery" + ] + }, + { + "name": "AlreadyVouched", + "docs": [ + " This user has already vouched for this recovery" + ] + }, + { + "name": "Threshold", + "docs": [ + " The threshold for recovering this account has not been met" + ] + }, + { + "name": "StillActive", + "docs": [ + " There are still active recovery attempts that need to be closed" + ] + }, + { + "name": "Overflow", + "docs": [ + " There was an overflow in a calculation" + ] + }, + { + "name": "AlreadyProxy", + "docs": [ + " This account is already set up for recovery" + ] + } + ] + }, + { + "name": "Vesting", + "storage": { + "prefix": "Vesting", + "items": [ + { + "name": "Vesting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "VestingInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information regarding the vesting of a given account." + ] + } + ] + }, + "calls": [ + { + "name": "vest", + "args": [], + "docs": [ + " Unlock any vested funds of the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have funds still", + " locked under this module.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 2 Reads, 2 Writes", + " - Reads: Vesting Storage, Balances Locks, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, [Sender Account]", + " - Benchmark:", + " - Unlocked: 48.76 + .048 * l µs (min square analysis)", + " - Locked: 44.43 + .284 * l µs (min square analysis)", + " - Using 50 µs fixed. Assuming less than 50 locks on any user, else we may want factor in number of locks.", + " # " + ] + }, + { + "name": "vest_other", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Unlock any vested funds of a `target` account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account whose vested funds should be unlocked. Must have funds still", + " locked under this module.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account", + " - Writes: Vesting Storage, Balances Locks, Target Account", + " - Benchmark:", + " - Unlocked: 44.3 + .294 * l µs (min square analysis)", + " - Locked: 48.16 + .103 * l µs (min square analysis)", + " - Using 50 µs fixed. Assuming less than 50 locks on any user, else we may want factor in number of locks.", + " # " + ] + }, + { + "name": "vested_transfer", + "args": [ + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Create a vested transfer.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " - Benchmark: 100.3 + .365 * l µs (min square analysis)", + " - Using 100 µs fixed. Assuming less than 50 locks on any user, else we may want factor in number of locks.", + " # " + ] + }, + { + "name": "force_vested_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Force a vested transfer.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `source`: The account whose funds should be transferred.", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 4 Reads, 4 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, Source Account", + " - Writes: Vesting Storage, Balances Locks, Target Account, Source Account", + " - Benchmark: 100.3 + .365 * l µs (min square analysis)", + " - Using 100 µs fixed. Assuming less than 50 locks on any user, else we may want factor in number of locks.", + " # " + ] + } + ], + "events": [ + { + "name": "VestingUpdated", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The amount vested has been updated. This could indicate more funds are available. The", + " balance given is the amount which is left unvested (and thus locked). ", + " [account, unvested]" + ] + }, + { + "name": "VestingCompleted", + "args": [ + "AccountId" + ], + "docs": [ + " An [account] has become fully vested. No further vesting can happen." + ] + } + ], + "constants": [ + { + "name": "MinVestedTransfer", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be transferred to create a new vesting schedule." + ] + } + ], + "errors": [ + { + "name": "NotVesting", + "docs": [ + " The account given is not vesting." + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " An existing vesting schedule already exists for this account that cannot be clobbered." + ] + }, + { + "name": "AmountLow", + "docs": [ + " Amount being transferred is too low to create a vesting schedule." + ] + } + ] + }, + { + "name": "Scheduler", + "storage": { + "prefix": "Scheduler", + "items": [ + { + "name": "Agenda", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Vec>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Items to be executed, indexed by the block number that they should be executed on." + ] + }, + { + "name": "Lookup", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Bytes", + "value": "TaskAddress", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Lookup from identity to the block number and index of the task." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "schedule", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.29 + .126 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda", + " - Will use base weight of 25 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u32" + } + ], + "docs": [ + " Cancel an anonymously scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.15 + 2.869 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_named", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 29.6 + .159 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 35 which should be good for more than 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel_named", + "args": [ + { + "name": "id", + "type": "Bytes" + } + ], + "docs": [ + " Cancel a named scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 24.91 + 2.907 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_after", + "args": [ + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task after a delay.", + "", + " # ", + " Same as [`schedule`].", + " # " + ] + }, + { + "name": "schedule_named_after", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task after a delay.", + "", + " # ", + " Same as [`schedule_named`].", + " # " + ] + } + ], + "events": [ + { + "name": "Scheduled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Scheduled some task. [when, index]" + ] + }, + { + "name": "Canceled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Canceled some task. [when, index]" + ] + }, + { + "name": "Dispatched", + "args": [ + "TaskAddress", + "Option", + "DispatchResult" + ], + "docs": [ + " Dispatched some task. [task, id, result]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "FailedToSchedule", + "docs": [ + " Failed to schedule a call" + ] + }, + { + "name": "FailedToCancel", + "docs": [ + " Failed to cancel a scheduled call" + ] + }, + { + "name": "TargetBlockNumberInPast", + "docs": [ + " Given target block number is in the past." + ] + } + ] + }, + { + "name": "Proxy", + "storage": { + "prefix": "Proxy", + "items": [ + { + "name": "Proxies", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The set of account proxies. Maps the account which has delegated to the accounts", + " which are being delegated to, together with the amount held on deposit." + ] + }, + { + "name": "Announcements", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The announcements made by the proxy (key)." + ] + } + ] + }, + "calls": [ + { + "name": "proxy", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorised for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "add_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Register a proxy account for the sender that is able to make calls on its behalf.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to make a proxy.", + " - `proxy_type`: The permissions allowed for this proxy account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Unregister a proxy account for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to remove as a proxy.", + " - `proxy_type`: The permissions currently enabled for the removed proxy account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxies", + "args": [], + "docs": [ + " Unregister all proxy accounts for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " WARNING: This may be called on accounts created by `anonymous`, however if done, then", + " the unreserved fees will be inaccessible. **All access to this account will be lost.**", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "anonymous", + "args": [ + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u16" + } + ], + "docs": [ + " Spawn a fresh new account that is guaranteed to be otherwise inaccessible, and", + " initialize it with a proxy of `proxy_type` for `origin` sender.", + "", + " Requires a `Signed` origin.", + "", + " - `proxy_type`: The type of the proxy that the sender will be registered as over the", + " new account. This will almost always be the most permissive `ProxyType` possible to", + " allow for maximum flexibility.", + " - `index`: A disambiguation index, in case this is called multiple times in the same", + " transaction (e.g. with `utility::batch`). Unless you're using `batch` you probably just", + " want to use `0`.", + " - `delay`: The announcement period required of the initial proxy. Will generally be", + " zero.", + "", + " Fails with `Duplicate` if this has already been called in this transaction, from the", + " same sender, with the same parameters.", + "", + " Fails if there are insufficient funds to pay for deposit.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # ", + " TODO: Might be over counting 1 read" + ] + }, + { + "name": "kill_anonymous", + "args": [ + { + "name": "spawner", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "index", + "type": "u16" + }, + { + "name": "height", + "type": "Compact" + }, + { + "name": "ext_index", + "type": "Compact" + } + ], + "docs": [ + " Removes a previously spawned anonymous proxy.", + "", + " WARNING: **All access to this account will be lost.** Any funds held in it will be", + " inaccessible.", + "", + " Requires a `Signed` origin, and the sender account must have been created by a call to", + " `anonymous` with corresponding parameters.", + "", + " - `spawner`: The account that originally called `anonymous` to create this account.", + " - `index`: The disambiguation index originally passed to `anonymous`. Probably `0`.", + " - `proxy_type`: The proxy type originally passed to `anonymous`.", + " - `height`: The height of the chain when the call to `anonymous` was processed.", + " - `ext_index`: The extrinsic index in which the call to `anonymous` was processed.", + "", + " Fails with `NoPermission` in case the caller is not a previously created anonymous", + " account whose `anonymous` call has corresponding parameters.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "announce", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Publish the hash of a proxy-call that will be made in the future.", + "", + " This must be called some number of blocks before the corresponding `proxy` is attempted", + " if the delay associated with the proxy relationship is greater than zero.", + "", + " No more than `MaxPending` announcements may be made at any one time.", + "", + " This will take a deposit of `AnnouncementDepositFactor` as well as", + " `AnnouncementDepositBase` if there are no other pending announcements.", + "", + " The dispatch origin for this call must be _Signed_ and a proxy of `real`.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "remove_announcement", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove a given announcement.", + "", + " May be called by a proxy account to remove a call they previously announced and return", + " the deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "reject_announcement", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove the given announcement of a delegate.", + "", + " May be called by a target (proxied) account to remove a call that one of their delegates", + " (`delegate`) has announced they want to execute. The deposit is returned.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `delegate`: The account that previously announced the call.", + " - `call_hash`: The hash of the call to be made.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "proxy_announced", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorised for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + } + ], + "events": [ + { + "name": "ProxyExecuted", + "args": [ + "DispatchResult" + ], + "docs": [ + " A proxy was executed correctly, with the given [result]." + ] + }, + { + "name": "AnonymousCreated", + "args": [ + "AccountId", + "AccountId", + "ProxyType", + "u16" + ], + "docs": [ + " Anonymous account has been created by new proxy with given", + " disambiguation index and proxy type. [anonymous, who, proxy_type, disambiguation_index]" + ] + }, + { + "name": "Announced", + "args": [ + "AccountId", + "AccountId", + "Hash" + ], + "docs": [ + " An announcement was placed to make a call in the future. [real, proxy, call_hash]" + ] + } + ], + "constants": [ + { + "name": "ProxyDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a proxy." + ] + }, + { + "name": "ProxyDepositFactor", + "type": "BalanceOf", + "value": "0x0060aa7714b400000000000000000000", + "docs": [ + " The amount of currency needed per proxy added." + ] + }, + { + "name": "MaxProxies", + "type": "u16", + "value": "0x2000", + "docs": [ + " The maximum amount of proxies allowed for a single account." + ] + }, + { + "name": "MaxPending", + "type": "u32", + "value": "0x20000000", + "docs": [ + " `MaxPending` metadata shadow." + ] + }, + { + "name": "AnnouncementDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " `AnnouncementDepositBase` metadata shadow." + ] + }, + { + "name": "AnnouncementDepositFactor", + "type": "BalanceOf", + "value": "0x00c054ef286801000000000000000000", + "docs": [ + " `AnnouncementDepositFactor` metadata shadow." + ] + } + ], + "errors": [ + { + "name": "TooMany", + "docs": [ + " There are too many proxies registered or too many announcements pending." + ] + }, + { + "name": "NotFound", + "docs": [ + " Proxy registration not found." + ] + }, + { + "name": "NotProxy", + "docs": [ + " Sender is not a proxy of the account to be proxied." + ] + }, + { + "name": "Unproxyable", + "docs": [ + " A call which is incompatible with the proxy type's filter was attempted." + ] + }, + { + "name": "Duplicate", + "docs": [ + " Account is already a proxy." + ] + }, + { + "name": "NoPermission", + "docs": [ + " Call may not be made by proxy because it may escalate its privileges." + ] + }, + { + "name": "Unannounced", + "docs": [ + " Announcement, if made at all, was made too recently." + ] + } + ] + }, + { + "name": "Multisig", + "storage": { + "prefix": "Multisig", + "items": [ + { + "name": "Multisigs", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "[u8;32]", + "value": "Multisig", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " The set of open multisig operations." + ] + }, + { + "name": "Calls", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "[u8;32]", + "value": "(OpaqueCall,AccountId,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": [ + { + "name": "as_multi_threshold_1", + "args": [ + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Immediately dispatch a multi-signature call using a single approval from the caller.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `other_signatories`: The accounts (other than the sender) who are part of the", + " multi-signature, but do not participate in the approval process.", + " - `call`: The call to be executed.", + "", + " Result is equivalent to the dispatched result.", + "", + " # ", + " O(Z + C) where Z is the length of the call and C its execution weight.", + " -------------------------------", + " - Base Weight: 33.72 + 0.002 * Z µs", + " - DB Weight: None", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call", + "type": "OpaqueCall" + }, + { + "name": "store_call", + "type": "bool" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " If there are enough, then dispatch the call.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call`: The call to be executed.", + "", + " NOTE: Unless this is the final approval, you will generally want to use", + " `approve_as_multi` instead, since it only requires a hash of the call.", + "", + " Result is equivalent to the dispatched result if `threshold` is exactly `1`. Otherwise", + " on success, result is `Ok` and the result from the interior call, if it was executed,", + " may be found in the deposited `MultisigExecuted` event.", + "", + " # ", + " - `O(S + Z + Call)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One call encode & hash, both of complexity `O(Z)` where `Z` is tx-len.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - The weight of the `call`.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " -------------------------------", + " - Base Weight:", + " - Create: 41.89 + 0.118 * S + .002 * Z µs", + " - Create w/ Store: 53.57 + 0.119 * S + .003 * Z µs", + " - Approve: 31.39 + 0.136 * S + .002 * Z µs", + " - Complete: 39.94 + 0.26 * S + .002 * Z µs", + " - DB Weight:", + " - Reads: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Writes: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "approve_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call_hash", + "type": "[u8;32]" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call_hash`: The hash of the call to be executed.", + "", + " NOTE: If this is the final approval, you will want to use `as_multi` instead.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " ----------------------------------", + " - Base Weight:", + " - Create: 44.71 + 0.088 * S", + " - Approve: 31.48 + 0.116 * S", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account]", + " - Write: Multisig Storage, [Caller Account]", + " # " + ] + }, + { + "name": "cancel_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "timepoint", + "type": "Timepoint" + }, + { + "name": "call_hash", + "type": "[u8;32]" + } + ], + "docs": [ + " Cancel a pre-existing, on-going multisig transaction. Any deposit reserved previously", + " for this operation will be unreserved on success.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `timepoint`: The timepoint (block number and transaction index) of the first approval", + " transaction for this dispatch.", + " - `call_hash`: The hash of the call to be executed.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - One event.", + " - I/O: 1 read `O(S)`, one remove.", + " - Storage: removes one item.", + " ----------------------------------", + " - Base Weight: 36.07 + 0.124 * S", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account], Refund Account, Calls", + " - Write: Multisig Storage, [Caller Account], Refund Account, Calls", + " # " + ] + } + ], + "events": [ + { + "name": "NewMultisig", + "args": [ + "AccountId", + "AccountId", + "CallHash" + ], + "docs": [ + " A new multisig operation has begun. [approving, multisig, call_hash]" + ] + }, + { + "name": "MultisigApproval", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been approved by someone. [approving, timepoint, multisig, call_hash]" + ] + }, + { + "name": "MultisigExecuted", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash", + "DispatchResult" + ], + "docs": [ + " A multisig operation has been executed. [approving, timepoint, multisig, call_hash]" + ] + }, + { + "name": "MultisigCancelled", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been cancelled. [cancelling, timepoint, multisig, call_hash]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "MinimumThreshold", + "docs": [ + " Threshold must be 2 or greater." + ] + }, + { + "name": "AlreadyApproved", + "docs": [ + " Call is already approved by this signatory." + ] + }, + { + "name": "NoApprovalsNeeded", + "docs": [ + " Call doesn't need any (more) approvals." + ] + }, + { + "name": "TooFewSignatories", + "docs": [ + " There are too few signatories in the list." + ] + }, + { + "name": "TooManySignatories", + "docs": [ + " There are too many signatories in the list." + ] + }, + { + "name": "SignatoriesOutOfOrder", + "docs": [ + " The signatories were provided out of order; they should be ordered." + ] + }, + { + "name": "SenderInSignatories", + "docs": [ + " The sender was contained in the other signatories; it shouldn't be." + ] + }, + { + "name": "NotFound", + "docs": [ + " Multisig operation not found when attempting to cancel." + ] + }, + { + "name": "NotOwner", + "docs": [ + " Only the account that originally created the multisig is able to cancel it." + ] + }, + { + "name": "NoTimepoint", + "docs": [ + " No timepoint was given, yet the multisig operation is already underway." + ] + }, + { + "name": "WrongTimepoint", + "docs": [ + " A different timepoint was given to the multisig operation that is underway." + ] + }, + { + "name": "UnexpectedTimepoint", + "docs": [ + " A timepoint was given, yet no multisig operation is underway." + ] + }, + { + "name": "WeightTooLow", + "docs": [ + " The maximum weight information provided was too low." + ] + }, + { + "name": "AlreadyStored", + "docs": [ + " The data to be stored is already stored." + ] + } + ] + } + ], + "extrinsic": { + "version": 4, + "signedExtensions": [ + "CheckSpecVersion", + "CheckTxVersion", + "CheckGenesis", + "CheckMortality", + "CheckNonce", + "CheckWeight", + "ChargeTransactionPayment" + ] + } + } + } +} diff --git a/packages/polkadot/tests/meta/v12.hex b/packages/polkadot/tests/meta/v12.hex new file mode 100644 index 00000000..6ede6938 --- /dev/null +++ b/packages/polkadot/tests/meta/v12.hex @@ -0,0 +1 @@ +0x6d6574610c981853797374656d011853797374656d401c4163636f756e7401010230543a3a4163636f756e744964944163636f756e74496e666f3c543a3a496e6465782c20543a3a4163636f756e74446174613e004101000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004e8205468652066756c6c206163636f756e7420696e666f726d6174696f6e20666f72206120706172746963756c6172206163636f756e742049442e3845787472696e736963436f756e7400000c753332040004b820546f74616c2065787472696e7369637320636f756e7420666f72207468652063757272656e7420626c6f636b2e2c426c6f636b576569676874010038436f6e73756d6564576569676874600000000000000000000000000000000000000000000000000488205468652063757272656e742077656967687420666f722074686520626c6f636b2e40416c6c45787472696e736963734c656e00000c753332040004410120546f74616c206c656e6774682028696e2062797465732920666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e24426c6f636b4861736801010538543a3a426c6f636b4e756d6265721c543a3a48617368008000000000000000000000000000000000000000000000000000000000000000000498204d6170206f6620626c6f636b206e756d6265727320746f20626c6f636b206861736865732e3445787472696e736963446174610101050c7533321c5665633c75383e000400043d012045787472696e73696373206461746120666f72207468652063757272656e7420626c6f636b20286d61707320616e2065787472696e736963277320696e64657820746f206974732064617461292e184e756d626572010038543a3a426c6f636b4e756d6265721000000000040901205468652063757272656e7420626c6f636b206e756d626572206265696e672070726f6365737365642e205365742062792060657865637574655f626c6f636b602e28506172656e744861736801001c543a3a4861736880000000000000000000000000000000000000000000000000000000000000000004702048617368206f66207468652070726576696f757320626c6f636b2e1844696765737401002c4469676573744f663c543e040004f020446967657374206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e184576656e747301008c5665633c4576656e745265636f72643c543a3a4576656e742c20543a3a486173683e3e040004a0204576656e7473206465706f736974656420666f72207468652063757272656e7420626c6f636b2e284576656e74436f756e740100284576656e74496e646578100000000004b820546865206e756d626572206f66206576656e747320696e2074686520604576656e74733c543e60206c6973742e2c4576656e74546f706963730101021c543a3a48617368845665633c28543a3a426c6f636b4e756d6265722c204576656e74496e646578293e000400282501204d617070696e67206265747765656e206120746f7069632028726570726573656e74656420627920543a3a486173682920616e64206120766563746f72206f6620696e646578657394206f66206576656e747320696e2074686520603c4576656e74733c543e3e60206c6973742e00510120416c6c20746f70696320766563746f727320686176652064657465726d696e69737469632073746f72616765206c6f636174696f6e7320646570656e64696e67206f6e2074686520746f7069632e2054686973450120616c6c6f7773206c696768742d636c69656e747320746f206c6576657261676520746865206368616e67657320747269652073746f7261676520747261636b696e67206d656368616e69736d20616e64e420696e2063617365206f66206368616e67657320666574636820746865206c697374206f66206576656e7473206f6620696e7465726573742e004d01205468652076616c756520686173207468652074797065206028543a3a426c6f636b4e756d6265722c204576656e74496e646578296020626563617573652069662077652075736564206f6e6c79206a7573744d012074686520604576656e74496e64657860207468656e20696e20636173652069662074686520746f70696320686173207468652073616d6520636f6e74656e7473206f6e20746865206e65787420626c6f636b0101206e6f206e6f74696669636174696f6e2077696c6c20626520747269676765726564207468757320746865206576656e74206d69676874206265206c6f73742e484c61737452756e74696d65557067726164650000584c61737452756e74696d6555706772616465496e666f04000455012053746f726573207468652060737065635f76657273696f6e6020616e642060737065635f6e616d6560206f66207768656e20746865206c6173742072756e74696d6520757067726164652068617070656e65642e545570677261646564546f553332526566436f756e74010010626f6f6c0400044d012054727565206966207765206861766520757067726164656420736f207468617420607479706520526566436f756e74602069732060753332602e2046616c7365202864656661756c7429206966206e6f742e605570677261646564546f547269706c65526566436f756e74010010626f6f6c0400085d012054727565206966207765206861766520757067726164656420736f2074686174204163636f756e74496e666f20636f6e7461696e73207468726565207479706573206f662060526566436f756e74602e2046616c736548202864656661756c7429206966206e6f742e38457865637574696f6e50686173650000145068617365040004882054686520657865637574696f6e207068617365206f662074686520626c6f636b2e01282866696c6c5f626c6f636b04185f726174696f1c50657262696c6c040901204120646973706174636820746861742077696c6c2066696c6c2074686520626c6f636b2077656967687420757020746f2074686520676976656e20726174696f2e1872656d61726b041c5f72656d61726b1c5665633c75383e146c204d616b6520736f6d65206f6e2d636861696e2072656d61726b2e002c2023203c7765696768743e24202d20604f28312960302023203c2f7765696768743e387365745f686561705f7061676573041470616765730c75363420fc2053657420746865206e756d626572206f6620706167657320696e2074686520576562417373656d626c7920656e7669726f6e6d656e74277320686561702e002c2023203c7765696768743e24202d20604f283129604c202d20312073746f726167652077726974652e64202d2042617365205765696768743a20312e34303520c2b57360202d203120777269746520746f20484541505f5041474553302023203c2f7765696768743e207365745f636f64650410636f64651c5665633c75383e28682053657420746865206e65772072756e74696d6520636f64652e002c2023203c7765696768743e3501202d20604f2843202b2053296020776865726520604360206c656e677468206f662060636f64656020616e642060536020636f6d706c6578697479206f66206063616e5f7365745f636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e7901202d20312063616c6c20746f206063616e5f7365745f636f6465603a20604f28532960202863616c6c73206073705f696f3a3a6d6973633a3a72756e74696d655f76657273696f6e6020776869636820697320657870656e73697665292e2c202d2031206576656e742e7d012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652c206275742067656e6572616c6c792074686973206973207665727920657870656e736976652e902057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f636f64655f776974686f75745f636865636b730410636f64651c5665633c75383e201d012053657420746865206e65772072756e74696d6520636f646520776974686f757420646f696e6720616e7920636865636b73206f662074686520676976656e2060636f6465602e002c2023203c7765696768743e90202d20604f2843296020776865726520604360206c656e677468206f662060636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e2c202d2031206576656e742e75012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652e2057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f6368616e6765735f747269655f636f6e666967044c6368616e6765735f747269655f636f6e666967804f7074696f6e3c4368616e67657354726965436f6e66696775726174696f6e3e28a02053657420746865206e6577206368616e676573207472696520636f6e66696775726174696f6e2e002c2023203c7765696768743e24202d20604f28312960b0202d20312073746f72616765207772697465206f722064656c6574652028636f64656320604f28312960292ed8202d20312063616c6c20746f20606465706f7369745f6c6f67603a20557365732060617070656e6460204150492c20736f204f28312964202d2042617365205765696768743a20372e32313820c2b57334202d204442205765696768743aa820202020202d205772697465733a204368616e67657320547269652c2053797374656d20446967657374302023203c2f7765696768743e2c7365745f73746f7261676504146974656d73345665633c4b657956616c75653e206c2053657420736f6d65206974656d73206f662073746f726167652e002c2023203c7765696768743e94202d20604f2849296020776865726520604960206c656e677468206f6620606974656d73607c202d206049602073746f72616765207772697465732028604f28312960292e74202d2042617365205765696768743a20302e353638202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e306b696c6c5f73746f7261676504106b657973205665633c4b65793e2078204b696c6c20736f6d65206974656d732066726f6d2073746f726167652e002c2023203c7765696768743efc202d20604f28494b296020776865726520604960206c656e677468206f6620606b6579736020616e6420604b60206c656e677468206f66206f6e65206b657964202d206049602073746f726167652064656c6574696f6e732e70202d2042617365205765696768743a202e333738202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e2c6b696c6c5f70726566697808187072656669780c4b6579205f7375626b6579730c7533322c1501204b696c6c20616c6c2073746f72616765206974656d7320776974682061206b657920746861742073746172747320776974682074686520676976656e207072656669782e003d01202a2a4e4f54453a2a2a2057652072656c79206f6e2074686520526f6f74206f726967696e20746f2070726f7669646520757320746865206e756d626572206f66207375626b65797320756e64657241012074686520707265666978207765206172652072656d6f76696e6720746f2061636375726174656c792063616c63756c6174652074686520776569676874206f6620746869732066756e6374696f6e2e002c2023203c7765696768743edc202d20604f285029602077686572652060506020616d6f756e74206f66206b65797320776974682070726566697820607072656669786064202d206050602073746f726167652064656c6574696f6e732e74202d2042617365205765696768743a20302e383334202a205020c2b57380202d205772697465733a204e756d626572206f66207375626b657973202b2031302023203c2f7765696768743e4472656d61726b5f776974685f6576656e74041872656d61726b1c5665633c75383e18a8204d616b6520736f6d65206f6e2d636861696e2072656d61726b20616e6420656d6974206576656e742e002c2023203c7765696768743eb8202d20604f28622960207768657265206220697320746865206c656e677468206f66207468652072656d61726b2e2c202d2031206576656e742e302023203c2f7765696768743e01184045787472696e7369635375636365737304304469737061746368496e666f04b820416e2065787472696e73696320636f6d706c65746564207375636365737366756c6c792e205c5b696e666f5c5d3c45787472696e7369634661696c6564083444697370617463684572726f72304469737061746368496e666f049420416e2065787472696e736963206661696c65642e205c5b6572726f722c20696e666f5c5d2c436f64655570646174656400045420603a636f6465602077617320757064617465642e284e65774163636f756e7404244163636f756e744964047c2041206e6577205c5b6163636f756e745c5d2077617320637265617465642e344b696c6c65644163636f756e7404244163636f756e744964046c20416e205c5b6163636f756e745c5d20776173207265617065642e2052656d61726b656408244163636f756e744964104861736804d4204f6e206f6e2d636861696e2072656d61726b2068617070656e65642e205c5b6f726967696e2c2072656d61726b5f686173685c5d1830426c6f636b57656967687473506c696d6974733a3a426c6f636b57656967687473850100f2052a0100000000204aa9d1010000405973070000000001c06e96a62e010000010098f73e5d010000010000000000000000405973070000000001c0f6e810a30100000100204aa9d1010000010088526a74000000405973070000000000000004d020426c6f636b20262065787472696e7369637320776569676874733a20626173652076616c75657320616e64206c696d6974732e2c426c6f636b4c656e6774684c6c696d6974733a3a426c6f636b4c656e6774683000003c00000050000000500004a820546865206d6178696d756d206c656e677468206f66206120626c6f636b2028696e206279746573292e38426c6f636b48617368436f756e7438543a3a426c6f636b4e756d6265721060090000045501204d6178696d756d206e756d626572206f6620626c6f636b206e756d62657220746f20626c6f636b2068617368206d617070696e677320746f206b65657020286f6c64657374207072756e6564206669727374292e2044625765696768743c52756e74696d6544625765696768744040787d010000000000e1f505000000000409012054686520776569676874206f662072756e74696d65206461746162617365206f7065726174696f6e73207468652072756e74696d652063616e20696e766f6b652e1c56657273696f6e3852756e74696d6556657273696f6e0503106e6f6465387375627374726174652d6e6f64650a000000090100000100000034df6acb689907609b0300000037e397fc7c91f5e40100000040fe3ad401f8959a04000000d2bc9897eed08f1502000000f78b278be53f454c02000000ed99c5acb25eedf502000000cbca25e39f14238702000000687ad44ad37f03c201000000bc9d89904f5b923f0100000068b66ba122c93fa70100000037c8bb1350a9a2a80100000091d5df18b0d2cf5801000000ab3c0572291feb8b01000000020000000484204765742074686520636861696e27732063757272656e742076657273696f6e2e2853533538507265666978087538042a14a8205468652064657369676e61746564205353383520707265666978206f66207468697320636861696e2e0039012054686973207265706c6163657320746865202273733538466f726d6174222070726f7065727479206465636c6172656420696e2074686520636861696e20737065632e20526561736f6e20697331012074686174207468652072756e74696d652073686f756c64206b6e6f772061626f7574207468652070726566697820696e206f7264657220746f206d616b6520757365206f662069742061737020616e206964656e746966696572206f662074686520636861696e2e143c496e76616c6964537065634e616d6508150120546865206e616d65206f662073706563696669636174696f6e20646f6573206e6f74206d61746368206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e685370656356657273696f6e4e65656473546f496e637265617365084501205468652073706563696669636174696f6e2076657273696f6e206973206e6f7420616c6c6f77656420746f206465637265617365206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e744661696c6564546f4578747261637452756e74696d6556657273696f6e0cf0204661696c656420746f2065787472616374207468652072756e74696d652076657273696f6e2066726f6d20746865206e65772072756e74696d652e000d01204569746865722063616c6c696e672060436f72655f76657273696f6e60206f72206465636f64696e67206052756e74696d6556657273696f6e60206661696c65642e4c4e6f6e44656661756c74436f6d706f7369746504010120537569636964652063616c6c6564207768656e20746865206163636f756e7420686173206e6f6e2d64656661756c7420636f6d706f7369746520646174612e3c4e6f6e5a65726f526566436f756e740439012054686572652069732061206e6f6e2d7a65726f207265666572656e636520636f756e742070726576656e74696e6720746865206163636f756e742066726f6d206265696e67207075726765642e001c5574696c69747900010c146261746368041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e48802053656e642061206261746368206f662064697370617463682063616c6c732e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e006101204966206f726967696e20697320726f6f74207468656e2063616c6c2061726520646973706174636820776974686f757420636865636b696e67206f726967696e2066696c7465722e20285468697320696e636c75646573cc20627970617373696e6720606672616d655f73797374656d3a3a436f6e6669673a3a4261736543616c6c46696c74657260292e002c2023203c7765696768743e0501202d20436f6d706c65786974793a204f284329207768657265204320697320746865206e756d626572206f662063616c6c7320746f20626520626174636865642e302023203c2f7765696768743e00590120546869732077696c6c2072657475726e20604f6b6020696e20616c6c2063697263756d7374616e6365732e20546f2064657465726d696e65207468652073756363657373206f66207468652062617463682c20616e3501206576656e74206973206465706f73697465642e20496620612063616c6c206661696c656420616e64207468652062617463682077617320696e7465727275707465642c207468656e20746865590120604261746368496e74657272757074656460206576656e74206973206465706f73697465642c20616c6f6e67207769746820746865206e756d626572206f66207375636365737366756c2063616c6c73206d616465510120616e6420746865206572726f72206f6620746865206661696c65642063616c6c2e20496620616c6c2077657265207375636365737366756c2c207468656e2074686520604261746368436f6d706c657465646050206576656e74206973206465706f73697465642e3461735f646572697661746976650814696e6465780c7531361063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e34e02053656e6420612063616c6c207468726f75676820616e20696e64657865642070736575646f6e796d206f66207468652073656e6465722e0059012046696c7465722066726f6d206f726967696e206172652070617373656420616c6f6e672e205468652063616c6c2077696c6c2062652064697370617463686564207769746820616e206f726967696e207768696368c020757365207468652073616d652066696c74657220617320746865206f726967696e206f6620746869732063616c6c2e004901204e4f54453a20496620796f75206e65656420746f20656e73757265207468617420616e79206163636f756e742d62617365642066696c746572696e67206973206e6f7420686f6e6f7265642028692e652e6501206265636175736520796f7520657870656374206070726f78796020746f2068617665206265656e2075736564207072696f7220696e207468652063616c6c20737461636b20616e6420796f7520646f206e6f742077616e745501207468652063616c6c207265737472696374696f6e7320746f206170706c7920746f20616e79207375622d6163636f756e7473292c207468656e20757365206061735f6d756c74695f7468726573686f6c645f31608020696e20746865204d756c74697369672070616c6c657420696e73746561642e00f8204e4f54453a205072696f7220746f2076657273696f6e202a31322c2074686973207761732063616c6c6564206061735f6c696d697465645f737562602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e2462617463685f616c6c041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e34f02053656e642061206261746368206f662064697370617463682063616c6c7320616e642061746f6d6963616c6c792065786563757465207468656d2e2501205468652077686f6c65207472616e73616374696f6e2077696c6c20726f6c6c6261636b20616e64206661696c20696620616e79206f66207468652063616c6c73206661696c65642e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e006101204966206f726967696e20697320726f6f74207468656e2063616c6c2061726520646973706174636820776974686f757420636865636b696e67206f726967696e2066696c7465722e20285468697320696e636c75646573cc20627970617373696e6720606672616d655f73797374656d3a3a436f6e6669673a3a4261736543616c6c46696c74657260292e002c2023203c7765696768743e0501202d20436f6d706c65786974793a204f284329207768657265204320697320746865206e756d626572206f662063616c6c7320746f20626520626174636865642e302023203c2f7765696768743e0108404261746368496e746572727570746564080c7533323444697370617463684572726f72085901204261746368206f66206469737061746368657320646964206e6f7420636f6d706c6574652066756c6c792e20496e646578206f66206669727374206661696c696e6720646973706174636820676976656e2c206173902077656c6c20617320746865206572726f722e205c5b696e6465782c206572726f725c5d384261746368436f6d706c657465640004cc204261746368206f66206469737061746368657320636f6d706c657465642066756c6c792077697468206e6f206572726f722e0000011042616265011042616265402845706f6368496e64657801000c75363420000000000000000004542043757272656e742065706f636820696e6465782e2c417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e0400046c2043757272656e742065706f636820617574686f7269746965732e2c47656e65736973536c6f74010010536c6f7420000000000000000008f82054686520736c6f74206174207768696368207468652066697273742065706f63682061637475616c6c7920737461727465642e205468697320697320309020756e74696c2074686520666972737420626c6f636b206f662074686520636861696e2e2c43757272656e74536c6f74010010536c6f7420000000000000000004542043757272656e7420736c6f74206e756d6265722e2852616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e65737380000000000000000000000000000000000000000000000000000000000000000028b8205468652065706f63682072616e646f6d6e65737320666f7220746865202a63757272656e742a2065706f63682e002c20232053656375726974790005012054686973204d555354204e4f54206265207573656420666f722067616d626c696e672c2061732069742063616e20626520696e666c75656e6365642062792061f8206d616c6963696f75732076616c696461746f7220696e207468652073686f7274207465726d2e204974204d4159206265207573656420696e206d616e7915012063727970746f677261706869632070726f746f636f6c732c20686f77657665722c20736f206c6f6e67206173206f6e652072656d656d6265727320746861742074686973150120286c696b652065766572797468696e6720656c7365206f6e2d636861696e29206974206973207075626c69632e20466f72206578616d706c652c2069742063616e206265050120757365642077686572652061206e756d626572206973206e656564656420746861742063616e6e6f742068617665206265656e2063686f73656e20627920616e0d01206164766572736172792c20666f7220707572706f7365732073756368206173207075626c69632d636f696e207a65726f2d6b6e6f776c656467652070726f6f66732e6050656e64696e6745706f6368436f6e6669674368616e67650000504e657874436f6e66696744657363726970746f7204000461012050656e64696e672065706f636820636f6e66696775726174696f6e206368616e676520746861742077696c6c206265206170706c696564207768656e20746865206e6578742065706f636820697320656e61637465642e384e65787452616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e657373800000000000000000000000000000000000000000000000000000000000000000045c204e6578742065706f63682072616e646f6d6e6573732e3c4e657874417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e04000460204e6578742065706f636820617574686f7269746965732e305365676d656e74496e64657801000c7533321000000000247c2052616e646f6d6e65737320756e64657220636f6e737472756374696f6e2e00f4205765206d616b6520612074726164656f6666206265747765656e2073746f7261676520616363657373657320616e64206c697374206c656e6774682e01012057652073746f72652074686520756e6465722d636f6e737472756374696f6e2072616e646f6d6e65737320696e207365676d656e7473206f6620757020746f942060554e4445525f434f4e535452554354494f4e5f5345474d454e545f4c454e475448602e00ec204f6e63652061207365676d656e7420726561636865732074686973206c656e6774682c20776520626567696e20746865206e657874206f6e652e090120576520726573657420616c6c207365676d656e747320616e642072657475726e20746f206030602061742074686520626567696e6e696e67206f662065766572791c2065706f63682e44556e646572436f6e737472756374696f6e0101050c7533326c5665633c7363686e6f72726b656c3a3a52616e646f6d6e6573733e0004000415012054574f582d4e4f54453a20605365676d656e74496e6465786020697320616e20696e6372656173696e6720696e74656765722c20736f2074686973206973206f6b61792e2c496e697469616c697a656400003c4d6179626552616e646f6d6e65737304000801012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e292077686963682069732060536f6d65601d01206966207065722d626c6f636b20696e697469616c697a6174696f6e2068617320616c7265616479206265656e2063616c6c656420666f722063757272656e7420626c6f636b2e4c417574686f7256726652616e646f6d6e65737301003c4d6179626552616e646f6d6e65737304000c5d012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e29207468617420696e636c756465732074686520565246206f75747075742067656e6572617465645101206174207468697320626c6f636b2e2054686973206669656c642073686f756c6420616c7761797320626520706f70756c6174656420647572696e6720626c6f636b2070726f63657373696e6720756e6c6573731901207365636f6e6461727920706c61696e20736c6f74732061726520656e61626c65642028776869636820646f6e277420636f6e7461696e206120565246206f7574707574292e2845706f6368537461727401008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d62657229200000000000000000145d012054686520626c6f636b206e756d62657273207768656e20746865206c61737420616e642063757272656e742065706f6368206861766520737461727465642c20726573706563746976656c7920604e2d316020616e641420604e602e4901204e4f54453a20576520747261636b207468697320697320696e206f7264657220746f20616e6e6f746174652074686520626c6f636b206e756d626572207768656e206120676976656e20706f6f6c206f66590120656e74726f7079207761732066697865642028692e652e20697420776173206b6e6f776e20746f20636861696e206f6273657276657273292e2053696e63652065706f6368732061726520646566696e656420696e590120736c6f74732c207768696368206d617920626520736b69707065642c2074686520626c6f636b206e756d62657273206d6179206e6f74206c696e6520757020776974682074686520736c6f74206e756d626572732e204c6174656e657373010038543a3a426c6f636b4e756d626572100000000014d820486f77206c617465207468652063757272656e7420626c6f636b20697320636f6d706172656420746f2069747320706172656e742e001501205468697320656e74727920697320706f70756c617465642061732070617274206f6620626c6f636b20657865637574696f6e20616e6420697320636c65616e65642075701101206f6e20626c6f636b2066696e616c697a6174696f6e2e205175657279696e6720746869732073746f7261676520656e747279206f757473696465206f6620626c6f636bb020657865637574696f6e20636f6e746578742073686f756c6420616c77617973207969656c64207a65726f2e2c45706f6368436f6e6669670000584261626545706f6368436f6e66696775726174696f6e04000485012054686520636f6e66696775726174696f6e20666f72207468652063757272656e742065706f63682e2053686f756c64206e6576657220626520604e6f6e656020617320697420697320696e697469616c697a656420696e2067656e657369732e3c4e65787445706f6368436f6e6669670000584261626545706f6368436f6e66696775726174696f6e0400082d012054686520636f6e66696775726174696f6e20666f7220746865206e6578742065706f63682c20604e6f6e65602069662074686520636f6e6669672077696c6c206e6f74206368616e6765e82028796f752063616e2066616c6c6261636b20746f206045706f6368436f6e6669676020696e737465616420696e20746861742063617365292e010c4c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66200d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e48706c616e5f636f6e6669675f6368616e67650418636f6e666967504e657874436f6e66696744657363726970746f7210610120506c616e20616e2065706f636820636f6e666967206368616e67652e205468652065706f636820636f6e666967206368616e6765206973207265636f7264656420616e642077696c6c20626520656e6163746564206f6e550120746865206e6578742063616c6c20746f2060656e6163745f65706f63685f6368616e6765602e2054686520636f6e6669672077696c6c20626520616374697661746564206f6e652065706f63682061667465722e5d01204d756c7469706c652063616c6c7320746f2074686973206d6574686f642077696c6c207265706c61636520616e79206578697374696e6720706c616e6e656420636f6e666967206368616e676520746861742068616458206e6f74206265656e20656e6163746564207965742e00083445706f63684475726174696f6e0c75363420c8000000000000000cec2054686520616d6f756e74206f662074696d652c20696e20736c6f74732c207468617420656163682065706f63682073686f756c64206c6173742e1901204e4f54453a2043757272656e746c79206974206973206e6f7420706f737369626c6520746f206368616e6765207468652065706f6368206475726174696f6e20616674657221012074686520636861696e2068617320737461727465642e20417474656d7074696e6720746f20646f20736f2077696c6c20627269636b20626c6f636b2070726f64756374696f6e2e444578706563746564426c6f636b54696d6524543a3a4d6f6d656e7420b80b00000000000014050120546865206578706563746564206176657261676520626c6f636b2074696d6520617420776869636820424142452073686f756c64206265206372656174696e67110120626c6f636b732e2053696e636520424142452069732070726f626162696c6973746963206974206973206e6f74207472697669616c20746f20666967757265206f75740501207768617420746865206578706563746564206176657261676520626c6f636b2074696d652073686f756c64206265206261736564206f6e2074686520736c6f740901206475726174696f6e20616e642074686520736563757269747920706172616d657465722060636020287768657265206031202d20636020726570726573656e7473a0207468652070726f626162696c697479206f66206120736c6f74206265696e6720656d707479292e0c60496e76616c696445717569766f636174696f6e50726f6f6604350120416e2065717569766f636174696f6e2070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e60496e76616c69644b65794f776e65727368697050726f6f660435012041206b6579206f776e6572736869702070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e584475706c69636174654f6666656e63655265706f7274041901204120676976656e2065717569766f636174696f6e207265706f72742069732076616c69642062757420616c72656164792070726576696f75736c79207265706f727465642e022454696d657374616d70012454696d657374616d70080c4e6f77010024543a3a4d6f6d656e7420000000000000000004902043757272656e742074696d6520666f72207468652063757272656e7420626c6f636b2e24446964557064617465010010626f6f6c040004b420446964207468652074696d657374616d7020676574207570646174656420696e207468697320626c6f636b3f01040c736574040c6e6f7748436f6d706163743c543a3a4d6f6d656e743e3c5820536574207468652063757272656e742074696d652e00590120546869732063616c6c2073686f756c6420626520696e766f6b65642065786163746c79206f6e63652070657220626c6f636b2e2049742077696c6c2070616e6963206174207468652066696e616c697a6174696f6ed82070686173652c20696620746869732063616c6c206861736e2774206265656e20696e766f6b656420627920746861742074696d652e004501205468652074696d657374616d702073686f756c642062652067726561746572207468616e207468652070726576696f7573206f6e652062792074686520616d6f756e74207370656369666965642062794420604d696e696d756d506572696f64602e00d820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060496e686572656e74602e002c2023203c7765696768743e3501202d20604f2831296020284e6f7465207468617420696d706c656d656e746174696f6e73206f6620604f6e54696d657374616d7053657460206d75737420616c736f20626520604f2831296029a101202d20312073746f72616765207265616420616e6420312073746f72616765206d75746174696f6e2028636f64656320604f28312960292e202862656361757365206f6620604469645570646174653a3a74616b656020696e20606f6e5f66696e616c697a656029d8202d2031206576656e742068616e646c657220606f6e5f74696d657374616d705f736574602e204d75737420626520604f283129602e302023203c2f7765696768743e0004344d696e696d756d506572696f6424543a3a4d6f6d656e7420dc0500000000000010690120546865206d696e696d756d20706572696f64206265747765656e20626c6f636b732e204265776172652074686174207468697320697320646966666572656e7420746f20746865202a65787065637465642a20706572696f64690120746861742074686520626c6f636b2070726f64756374696f6e206170706172617475732070726f76696465732e20596f75722063686f73656e20636f6e73656e7375732073797374656d2077696c6c2067656e6572616c6c79650120776f726b2077697468207468697320746f2064657465726d696e6520612073656e7369626c6520626c6f636b2074696d652e20652e672e20466f7220417572612c2069742077696c6c20626520646f75626c6520746869737020706572696f64206f6e2064656661756c742073657474696e67732e000328417574686f72736869700128417574686f72736869700c18556e636c65730100e85665633c556e636c65456e7472794974656d3c543a3a426c6f636b4e756d6265722c20543a3a486173682c20543a3a4163636f756e7449643e3e0400041c20556e636c657318417574686f72000030543a3a4163636f756e7449640400046420417574686f72206f662063757272656e7420626c6f636b2e30446964536574556e636c6573010010626f6f6c040004bc205768657468657220756e636c6573207765726520616c72656164792073657420696e207468697320626c6f636b2e0104287365745f756e636c657304286e65775f756e636c6573385665633c543a3a4865616465723e04642050726f76696465206120736574206f6620756e636c65732e00001c48496e76616c6964556e636c65506172656e74048c2054686520756e636c6520706172656e74206e6f7420696e2074686520636861696e2e40556e636c6573416c7265616479536574048420556e636c657320616c72656164792073657420696e2074686520626c6f636b2e34546f6f4d616e79556e636c6573044420546f6f206d616e7920756e636c65732e3047656e65736973556e636c6504582054686520756e636c652069732067656e657369732e30546f6f48696768556e636c6504802054686520756e636c6520697320746f6f206869676820696e20636861696e2e50556e636c65416c7265616479496e636c75646564047c2054686520756e636c6520697320616c726561647920696e636c756465642e204f6c64556e636c6504b82054686520756e636c652069736e277420726563656e7420656e6f75676820746f20626520696e636c756465642e041c496e6469636573011c496e646963657304204163636f756e74730001023c543a3a4163636f756e74496e6465788828543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20626f6f6c29000400048820546865206c6f6f6b75702066726f6d20696e64657820746f206163636f756e742e011414636c61696d0414696e6465783c543a3a4163636f756e74496e646578489c2041737369676e20616e2070726576696f75736c7920756e61737369676e656420696e6465782e00e0205061796d656e743a20604465706f736974602069732072657365727665642066726f6d207468652073656e646572206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e00f4202d2060696e646578603a2074686520696e64657820746f20626520636c61696d65642e2054686973206d757374206e6f7420626520696e207573652e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e207472616e73666572080c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e6465785061012041737369676e20616e20696e64657820616c7265616479206f776e6564206279207468652073656e64657220746f20616e6f74686572206163636f756e742e205468652062616c616e6365207265736572766174696f6ebc206973206566666563746976656c79207472616e7366657272656420746f20746865206e6577206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002901202d2060696e646578603a2074686520696e64657820746f2062652072652d61737369676e65642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e68202d204f6e65207472616e73666572206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743ae4202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429e8202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429302023203c2f7765696768743e10667265650414696e6465783c543a3a4163636f756e74496e6465784898204672656520757020616e20696e646578206f776e6564206279207468652073656e6465722e006101205061796d656e743a20416e792070726576696f7573206465706f73697420706c6163656420666f722074686520696e64657820697320756e726573657276656420696e207468652073656e646572206163636f756e742e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206f776e2074686520696e6465782e001101202d2060696e646578603a2074686520696e64657820746f2062652066726565642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e008820456d6974732060496e646578467265656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e38666f7263655f7472616e736665720c0c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e64657818667265657a6510626f6f6c54590120466f72636520616e20696e64657820746f20616e206163636f756e742e205468697320646f65736e277420726571756972652061206465706f7369742e2049662074686520696e64657820697320616c7265616479ec2068656c642c207468656e20616e79206465706f736974206973207265696d62757273656420746f206974732063757272656e74206f776e65722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00a8202d2060696e646578603a2074686520696e64657820746f206265202872652d2961737369676e65642e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e4501202d2060667265657a65603a2069662073657420746f206074727565602c2077696c6c20667265657a652074686520696e64657820736f2069742063616e6e6f74206265207472616e736665727265642e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e7c202d20557020746f206f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743af8202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229fc202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229302023203c2f7765696768743e18667265657a650414696e6465783c543a3a4163636f756e74496e64657844690120467265657a6520616e20696e64657820736f2069742077696c6c20616c7761797320706f696e7420746f207468652073656e646572206163636f756e742e205468697320636f6e73756d657320746865206465706f7369742e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d7573742068617665206170206e6f6e2d66726f7a656e206163636f756e742060696e646578602e00b0202d2060696e646578603a2074686520696e64657820746f2062652066726f7a656e20696e20706c6163652e008c20456d6974732060496e64657846726f7a656e60206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e74202d20557020746f206f6e6520736c617368206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e010c34496e64657841737369676e656408244163636f756e744964304163636f756e74496e64657804b42041206163636f756e7420696e646578207761732061737369676e65642e205c5b696e6465782c2077686f5c5d28496e646578467265656404304163636f756e74496e64657804e82041206163636f756e7420696e64657820686173206265656e2066726565642075702028756e61737369676e6564292e205c5b696e6465785c5d2c496e64657846726f7a656e08304163636f756e74496e646578244163636f756e7449640429012041206163636f756e7420696e64657820686173206265656e2066726f7a656e20746f206974732063757272656e74206163636f756e742049442e205c5b696e6465782c2077686f5c5d041c4465706f7369743042616c616e63654f663c543e4000407a10f35a0000000000000000000004ac20546865206465706f736974206e656564656420666f7220726573657276696e6720616e20696e6465782e142c4e6f7441737369676e656404902054686520696e64657820776173206e6f7420616c72656164792061737369676e65642e204e6f744f776e657204a82054686520696e6465782069732061737369676e656420746f20616e6f74686572206163636f756e742e14496e55736504742054686520696e64657820776173206e6f7420617661696c61626c652e2c4e6f745472616e7366657204cc2054686520736f7572636520616e642064657374696e6174696f6e206163636f756e747320617265206964656e746963616c2e245065726d616e656e7404d42054686520696e646578206973207065726d616e656e7420616e64206d6179206e6f742062652066726565642f6368616e6765642e052042616c616e636573012042616c616e6365731034546f74616c49737375616e6365010028543a3a42616c616e6365400000000000000000000000000000000004982054686520746f74616c20756e6974732069737375656420696e207468652073797374656d2e1c4163636f756e7401010230543a3a4163636f756e7449645c4163636f756e74446174613c543a3a42616c616e63653e000101000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c6c205468652062616c616e6365206f6620616e206163636f756e742e004101204e4f54453a2054686973206973206f6e6c79207573656420696e207468652063617365207468617420746869732070616c6c6574206973207573656420746f2073746f72652062616c616e6365732e144c6f636b7301010230543a3a4163636f756e744964705665633c42616c616e63654c6f636b3c543a3a42616c616e63653e3e00040008b820416e79206c6971756964697479206c6f636b73206f6e20736f6d65206163636f756e742062616c616e6365732e2501204e4f54453a2053686f756c64206f6e6c79206265206163636573736564207768656e2073657474696e672c206368616e67696e6720616e642066726565696e672061206c6f636b2e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076322e302e3020666f72206e6577206e6574776f726b732e0110207472616e736665720810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e6cd8205472616e7366657220736f6d65206c697175696420667265652062616c616e636520746f20616e6f74686572206163636f756e742e00090120607472616e73666572602077696c6c207365742074686520604672656542616c616e636560206f66207468652073656e64657220616e642072656365697665722e21012049742077696c6c2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d2062792074686520605472616e73666572466565602e1501204966207468652073656e6465722773206163636f756e742069732062656c6f7720746865206578697374656e7469616c206465706f736974206173206120726573756c74b4206f6620746865207472616e736665722c20746865206163636f756e742077696c6c206265207265617065642e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605369676e65646020627920746865207472616e736163746f722e002c2023203c7765696768743e3101202d20446570656e64656e74206f6e20617267756d656e747320627574206e6f7420637269746963616c2c20676976656e2070726f70657220696d706c656d656e746174696f6e7320666f72cc202020696e70757420636f6e6669672074797065732e205365652072656c617465642066756e6374696f6e732062656c6f772e6901202d20497420636f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e642077726974657320696e7465726e616c6c7920616e64206e6f20636f6d706c657820636f6d7075746174696f6e2e004c2052656c617465642066756e6374696f6e733a0051012020202d2060656e737572655f63616e5f77697468647261776020697320616c776179732063616c6c656420696e7465726e616c6c792062757420686173206120626f756e64656420636f6d706c65786974792e2d012020202d205472616e7366657272696e672062616c616e63657320746f206163636f756e7473207468617420646964206e6f74206578697374206265666f72652077696c6c206361757365d420202020202060543a3a4f6e4e65774163636f756e743a3a6f6e5f6e65775f6163636f756e746020746f2062652063616c6c65642e61012020202d2052656d6f76696e6720656e6f7567682066756e64732066726f6d20616e206163636f756e742077696c6c20747269676765722060543a3a4475737452656d6f76616c3a3a6f6e5f756e62616c616e636564602e49012020202d20607472616e736665725f6b6565705f616c6976656020776f726b73207468652073616d652077617920617320607472616e73666572602c206275742068617320616e206164646974696f6e616cf82020202020636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c20746865206f726967696e206163636f756e742e88202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d4501202d2042617365205765696768743a2037332e363420c2b5732c20776f7273742063617365207363656e6172696f20286163636f756e7420637265617465642c206163636f756e742072656d6f76656429dc202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374696e6174696f6e206163636f756e741501202d204f726967696e206163636f756e7420697320616c726561647920696e206d656d6f72792c20736f206e6f204442206f7065726174696f6e7320666f72207468656d2e302023203c2f7765696768743e2c7365745f62616c616e63650c0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365206e65775f667265654c436f6d706163743c543a3a42616c616e63653e306e65775f72657365727665644c436f6d706163743c543a3a42616c616e63653e489420536574207468652062616c616e636573206f66206120676976656e206163636f756e742e00210120546869732077696c6c20616c74657220604672656542616c616e63656020616e642060526573657276656442616c616e63656020696e2073746f726167652e2069742077696c6c090120616c736f2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d202860546f74616c49737375616e636560292e190120496620746865206e65772066726565206f722072657365727665642062616c616e63652069732062656c6f7720746865206578697374656e7469616c206465706f7369742c01012069742077696c6c20726573657420746865206163636f756e74206e6f6e63652028606672616d655f73797374656d3a3a4163636f756e744e6f6e636560292e00b420546865206469737061746368206f726967696e20666f7220746869732063616c6c2069732060726f6f74602e002c2023203c7765696768743e80202d20496e646570656e64656e74206f662074686520617267756d656e74732ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e58202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d3c202d2042617365205765696768743a6820202020202d204372656174696e673a2032372e353620c2b5736420202020202d204b696c6c696e673a2033352e313120c2b57398202d204442205765696768743a203120526561642c203120577269746520746f206077686f60302023203c2f7765696768743e38666f7263655f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e1851012045786163746c7920617320607472616e73666572602c2065786365707420746865206f726967696e206d75737420626520726f6f7420616e642074686520736f75726365206163636f756e74206d61792062652c207370656369666965642e2c2023203c7765696768743e4101202d2053616d65206173207472616e736665722c20627574206164646974696f6e616c207265616420616e6420777269746520626563617573652074686520736f75726365206163636f756e74206973902020206e6f7420617373756d656420746f20626520696e20746865206f7665726c61792e302023203c2f7765696768743e4c7472616e736665725f6b6565705f616c6976650810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e2c51012053616d6520617320746865205b607472616e73666572605d2063616c6c2c206275742077697468206120636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c2074686540206f726967696e206163636f756e742e00bc20393925206f66207468652074696d6520796f752077616e74205b607472616e73666572605d20696e73746561642e00c4205b607472616e73666572605d3a207374727563742e50616c6c65742e68746d6c236d6574686f642e7472616e736665722c2023203c7765696768743ee8202d2043686561706572207468616e207472616e736665722062656361757365206163636f756e742063616e6e6f74206265206b696c6c65642e60202d2042617365205765696768743a2035312e3420c2b5731d01202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374202873656e64657220697320696e206f7665726c617920616c7265616479292c20233c2f7765696768743e01201c456e646f77656408244163636f756e7449641c42616c616e636504250120416e206163636f756e74207761732063726561746564207769746820736f6d6520667265652062616c616e63652e205c5b6163636f756e742c20667265655f62616c616e63655c5d20447573744c6f737408244163636f756e7449641c42616c616e636508410120416e206163636f756e74207761732072656d6f7665642077686f73652062616c616e636520776173206e6f6e2d7a65726f206275742062656c6f77204578697374656e7469616c4465706f7369742cd020726573756c74696e6720696e20616e206f75747269676874206c6f73732e205c5b6163636f756e742c2062616c616e63655c5d205472616e736665720c244163636f756e744964244163636f756e7449641c42616c616e636504a0205472616e73666572207375636365656465642e205c5b66726f6d2c20746f2c2076616c75655c5d2842616c616e63655365740c244163636f756e7449641c42616c616e63651c42616c616e636504cc20412062616c616e6365207761732073657420627920726f6f742e205c5b77686f2c20667265652c2072657365727665645c5d1c4465706f73697408244163636f756e7449641c42616c616e636504210120536f6d6520616d6f756e7420776173206465706f73697465642028652e672e20666f72207472616e73616374696f6e2066656573292e205c5b77686f2c206465706f7369745c5d20526573657276656408244163636f756e7449641c42616c616e636504210120536f6d652062616c616e63652077617320726573657276656420286d6f7665642066726f6d206672656520746f207265736572766564292e205c5b77686f2c2076616c75655c5d28556e726573657276656408244163636f756e7449641c42616c616e636504290120536f6d652062616c616e63652077617320756e726573657276656420286d6f7665642066726f6d20726573657276656420746f2066726565292e205c5b77686f2c2076616c75655c5d4852657365727665526570617472696174656410244163636f756e744964244163636f756e7449641c42616c616e6365185374617475730c510120536f6d652062616c616e636520776173206d6f7665642066726f6d207468652072657365727665206f6620746865206669727374206163636f756e7420746f20746865207365636f6e64206163636f756e742edc2046696e616c20617267756d656e7420696e64696361746573207468652064657374696e6174696f6e2062616c616e636520747970652ea8205c5b66726f6d2c20746f2c2062616c616e63652c2064657374696e6174696f6e5f7374617475735c5d04484578697374656e7469616c4465706f73697428543a3a42616c616e63654000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f206b65657020616e206163636f756e74206f70656e2e203856657374696e6742616c616e6365049c2056657374696e672062616c616e636520746f6f206869676820746f2073656e642076616c7565544c69717569646974795265737472696374696f6e7304c8204163636f756e74206c6971756964697479207265737472696374696f6e732070726576656e74207769746864726177616c204f766572666c6f77047420476f7420616e206f766572666c6f7720616674657220616464696e674c496e73756666696369656e7442616c616e636504782042616c616e636520746f6f206c6f7720746f2073656e642076616c7565484578697374656e7469616c4465706f73697404ec2056616c756520746f6f206c6f7720746f20637265617465206163636f756e742064756520746f206578697374656e7469616c206465706f736974244b656570416c6976650490205472616e736665722f7061796d656e7420776f756c64206b696c6c206163636f756e745c4578697374696e6756657374696e675363686564756c6504cc20412076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e742c446561644163636f756e74048c2042656e6566696369617279206163636f756e74206d757374207072652d657869737406485472616e73616374696f6e5061796d656e7401485472616e73616374696f6e5061796d656e7408444e6578744665654d756c7469706c6965720100284d756c7469706c69657240000064a7b3b6e00d0000000000000000003853746f7261676556657273696f6e01002052656c6561736573040000000008485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e2c576569676874546f466565a45665633c576569676874546f466565436f656666696369656e743c42616c616e63654f663c543e3e3e5c0401000000000000000000000000000000000000000001040d012054686520706f6c796e6f6d69616c2074686174206973206170706c69656420696e206f7264657220746f20646572697665206665652066726f6d207765696768742e000768456c656374696f6e50726f76696465724d756c746950686173650168456c656374696f6e50726f76696465724d756c746950686173651814526f756e6401000c753332100100000018ac20496e7465726e616c20636f756e74657220666f7220746865206e756d626572206f6620726f756e64732e00550120546869732069732075736566756c20666f722064652d6475706c69636174696f6e206f66207472616e73616374696f6e73207375626d697474656420746f2074686520706f6f6c2c20616e642067656e6572616c6c20646961676e6f7374696373206f66207468652070616c6c65742e004d012054686973206973206d6572656c7920696e6372656d656e746564206f6e6365207065722065766572792074696d65207468617420616e20757073747265616d2060656c656374602069732063616c6c65642e3043757272656e74506861736501005450686173653c543a3a426c6f636b4e756d6265723e0400043c2043757272656e742070686173652e38517565756564536f6c7574696f6e00006c5265616479536f6c7574696f6e3c543a3a4163636f756e7449643e0400043d012043757272656e74206265737420736f6c7574696f6e2c207369676e6564206f7220756e7369676e65642c2071756575656420746f2062652072657475726e65642075706f6e2060656c656374602e20536e617073686f7400006c526f756e64536e617073686f743c543a3a4163636f756e7449643e04000c7020536e617073686f742064617461206f662074686520726f756e642e005d01205468697320697320637265617465642061742074686520626567696e6e696e67206f6620746865207369676e656420706861736520616e6420636c65617265642075706f6e2063616c6c696e672060656c656374602e38446573697265645461726765747300000c75333204000ccc2044657369726564206e756d626572206f66207461726765747320746f20656c65637420666f72207468697320726f756e642e00a8204f6e6c7920657869737473207768656e205b60536e617073686f74605d2069732070726573656e742e40536e617073686f744d65746164617461000058536f6c7574696f6e4f72536e617073686f7453697a6504000c9820546865206d65746164617461206f6620746865205b60526f756e64536e617073686f74605d00a8204f6e6c7920657869737473207768656e205b60536e617073686f74605d2069732070726573656e742e01043c7375626d69745f756e7369676e65640820736f6c7574696f6e64526177536f6c7574696f6e3c436f6d706163744f663c543e3e1c7769746e65737358536f6c7574696f6e4f72536e617073686f7453697a6538a8205375626d6974206120736f6c7574696f6e20666f722074686520756e7369676e65642070686173652e00cc20546865206469737061746368206f726967696e20666f20746869732063616c6c206d757374206265205f5f6e6f6e655f5f2e0041012054686973207375626d697373696f6e20697320636865636b6564206f6e2074686520666c792e204d6f72656f7665722c207468697320756e7369676e656420736f6c7574696f6e206973206f6e6c7959012076616c696461746564207768656e207375626d697474656420746f2074686520706f6f6c2066726f6d20746865202a2a6c6f63616c2a2a206e6f64652e204566666563746976656c792c2074686973206d65616e7361012074686174206f6e6c79206163746976652076616c696461746f72732063616e207375626d69742074686973207472616e73616374696f6e207768656e20617574686f72696e67206120626c6f636b202873696d696c61724420746f20616e20696e686572656e74292e005d0120546f2070726576656e7420616e7920696e636f727265637420736f6c7574696f6e2028616e642074687573207761737465642074696d652f776569676874292c2074686973207472616e73616374696f6e2077696c6c51012070616e69632069662074686520736f6c7574696f6e207375626d6974746564206279207468652076616c696461746f7220697320696e76616c696420696e20616e79207761792c206566666563746976656c79a02070757474696e6720746865697220617574686f72696e6720726577617264206174207269736b2e00e4204e6f206465706f736974206f7220726577617264206973206173736f63696174656420776974682074686973207375626d697373696f6e2e011838536f6c7574696f6e53746f726564043c456c656374696f6e436f6d7075746510b8204120736f6c7574696f6e207761732073746f72656420776974682074686520676976656e20636f6d707574652e0041012049662074686520736f6c7574696f6e206973207369676e65642c2074686973206d65616e732074686174206974206861736e277420796574206265656e2070726f6365737365642e20496620746865090120736f6c7574696f6e20697320756e7369676e65642c2074686973206d65616e7320746861742069742068617320616c736f206265656e2070726f6365737365642e44456c656374696f6e46696e616c697a6564045c4f7074696f6e3c456c656374696f6e436f6d707574653e0859012054686520656c656374696f6e20686173206265656e2066696e616c697a65642c20776974682060536f6d6560206f662074686520676976656e20636f6d7075746174696f6e2c206f7220656c7365206966207468656420656c656374696f6e206661696c65642c20604e6f6e65602e20526577617264656404244163636f756e74496404290120416e206163636f756e7420686173206265656e20726577617264656420666f72207468656972207369676e6564207375626d697373696f6e206265696e672066696e616c697a65642e1c536c617368656404244163636f756e74496404250120416e206163636f756e7420686173206265656e20736c617368656420666f72207375626d697474696e6720616e20696e76616c6964207369676e6564207375626d697373696f6e2e485369676e6564506861736553746172746564040c75333204c420546865207369676e6564207068617365206f662074686520676976656e20726f756e642068617320737461727465642e50556e7369676e6564506861736553746172746564040c75333204cc2054686520756e7369676e6564207068617365206f662074686520676976656e20726f756e642068617320737461727465642e0c34556e7369676e6564506861736538543a3a426c6f636b4e756d62657210320000000480204475726174696f6e206f662074686520756e7369676e65642070686173652e2c5369676e6564506861736538543a3a426c6f636b4e756d62657210320000000478204475726174696f6e206f6620746865207369676e65642070686173652e70536f6c7574696f6e496d70726f76656d656e745468726573686f6c641c50657262696c6c10a0860100084d0120546865206d696e696d756d20616d6f756e74206f6620696d70726f76656d656e7420746f2074686520736f6c7574696f6e2073636f7265207468617420646566696e6573206120736f6c7574696f6e206173642022626574746572222028696e20616e79207068617365292e0c6850726544697370617463684561726c795375626d697373696f6e0468205375626d697373696f6e2077617320746f6f206561726c792e6c507265446973706174636857726f6e6757696e6e6572436f756e74048c2057726f6e67206e756d626572206f662077696e6e6572732070726573656e7465642e6450726544697370617463685765616b5375626d697373696f6e0494205375626d697373696f6e2077617320746f6f207765616b2c2073636f72652d776973652e081c5374616b696e67011c5374616b696e677830486973746f7279446570746801000c75333210540000001c8c204e756d626572206f66206572617320746f206b65657020696e20686973746f72792e00390120496e666f726d6174696f6e206973206b65707420666f72206572617320696e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e006101204d757374206265206d6f7265207468616e20746865206e756d626572206f6620657261732064656c617965642062792073657373696f6e206f74686572776973652e20492e652e2061637469766520657261206d757374390120616c7761797320626520696e20686973746f72792e20492e652e20606163746976655f657261203e2063757272656e745f657261202d20686973746f72795f646570746860206d757374206265302067756172616e746565642e3856616c696461746f72436f756e7401000c753332100000000004a82054686520696465616c206e756d626572206f66207374616b696e67207061727469636970616e74732e544d696e696d756d56616c696461746f72436f756e7401000c7533321000000000044101204d696e696d756d206e756d626572206f66207374616b696e67207061727469636970616e7473206265666f726520656d657267656e637920636f6e646974696f6e732061726520696d706f7365642e34496e76756c6e657261626c65730100445665633c543a3a4163636f756e7449643e04000c590120416e792076616c696461746f72732074686174206d6179206e6576657220626520736c6173686564206f7220666f726369626c79206b69636b65642e20497427732061205665632073696e636520746865792772654d01206561737920746f20696e697469616c697a6520616e642074686520706572666f726d616e636520686974206973206d696e696d616c2028776520657870656374206e6f206d6f7265207468616e20666f7572ac20696e76756c6e657261626c65732920616e64207265737472696374656420746f20746573746e6574732e18426f6e64656400010530543a3a4163636f756e74496430543a3a4163636f756e744964000400040101204d61702066726f6d20616c6c206c6f636b65642022737461736822206163636f756e747320746f2074686520636f6e74726f6c6c6572206163636f756e742e184c656467657200010230543a3a4163636f756e744964a45374616b696e674c65646765723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400044501204d61702066726f6d20616c6c2028756e6c6f636b6564292022636f6e74726f6c6c657222206163636f756e747320746f2074686520696e666f20726567617264696e6720746865207374616b696e672e14506179656501010530543a3a4163636f756e7449647c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e00040004e42057686572652074686520726577617264207061796d656e742073686f756c64206265206d6164652e204b657965642062792073746173682e2856616c696461746f727301010530543a3a4163636f756e7449643856616c696461746f7250726566730008000004450120546865206d61702066726f6d202877616e6e616265292076616c696461746f72207374617368206b657920746f2074686520707265666572656e636573206f6620746861742076616c696461746f722e284e6f6d696e61746f727300010530543a3a4163636f756e744964644e6f6d696e6174696f6e733c543a3a4163636f756e7449643e00040004650120546865206d61702066726f6d206e6f6d696e61746f72207374617368206b657920746f2074686520736574206f66207374617368206b657973206f6620616c6c2076616c696461746f727320746f206e6f6d696e6174652e2843757272656e74457261000020457261496e6465780400105c205468652063757272656e742065726120696e6465782e006501205468697320697320746865206c617465737420706c616e6e6564206572612c20646570656e64696e67206f6e20686f77207468652053657373696f6e2070616c6c657420717565756573207468652076616c696461746f7280207365742c206974206d6967687420626520616374697665206f72206e6f742e24416374697665457261000034416374697665457261496e666f040010d820546865206163746976652065726120696e666f726d6174696f6e2c20697420686f6c647320696e64657820616e642073746172742e0059012054686520616374697665206572612069732074686520657261206265696e672063757272656e746c792072657761726465642e2056616c696461746f7220736574206f66207468697320657261206d757374206265ac20657175616c20746f205b6053657373696f6e496e746572666163653a3a76616c696461746f7273605d2e5445726173537461727453657373696f6e496e64657800010520457261496e6465783053657373696f6e496e646578000400103101205468652073657373696f6e20696e646578206174207768696368207468652065726120737461727420666f7220746865206c6173742060484953544f52595f44455054486020657261732e006101204e6f74653a205468697320747261636b7320746865207374617274696e672073657373696f6e2028692e652e2073657373696f6e20696e646578207768656e20657261207374617274206265696e672061637469766529f020666f7220746865206572617320696e20605b43757272656e74457261202d20484953544f52595f44455054482c2043757272656e744572615d602e2c457261735374616b65727301020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000001878204578706f73757265206f662076616c696461746f72206174206572612e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e48457261735374616b657273436c697070656401020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000002c9820436c6970706564204578706f73757265206f662076616c696461746f72206174206572612e00590120546869732069732073696d696c617220746f205b60457261735374616b657273605d20627574206e756d626572206f66206e6f6d696e61746f7273206578706f736564206973207265647563656420746f20746865dc2060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732e1d0120284e6f74653a20746865206669656c642060746f74616c6020616e6420606f776e60206f6620746865206578706f737572652072656d61696e7320756e6368616e676564292ef42054686973206973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e005d012054686973206973206b657965642066697374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e484572617356616c696461746f72507265667301020520457261496e64657830543a3a4163636f756e7449643856616c696461746f725072656673050800001411012053696d696c617220746f2060457261735374616b657273602c207468697320686f6c64732074686520707265666572656e636573206f662076616c696461746f72732e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4c4572617356616c696461746f7252657761726400010520457261496e6465783042616c616e63654f663c543e0004000c09012054686520746f74616c2076616c696461746f7220657261207061796f757420666f7220746865206c6173742060484953544f52595f44455054486020657261732e0021012045726173207468617420686176656e27742066696e697368656420796574206f7220686173206265656e2072656d6f76656420646f65736e27742068617665207265776172642e4045726173526577617264506f696e747301010520457261496e64657874457261526577617264506f696e74733c543a3a4163636f756e7449643e0014000000000008ac205265776172647320666f7220746865206c6173742060484953544f52595f44455054486020657261732e250120496620726577617264206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207265776172642069732072657475726e65642e3845726173546f74616c5374616b6501010520457261496e6465783042616c616e63654f663c543e00400000000000000000000000000000000008ec2054686520746f74616c20616d6f756e74207374616b656420666f7220746865206c6173742060484953544f52595f44455054486020657261732e1d0120496620746f74616c206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207374616b652069732072657475726e65642e20466f72636545726101001c466f7263696e6704000454204d6f6465206f662065726120666f7263696e672e4c536c6173685265776172644672616374696f6e01001c50657262696c6c10000000000cf8205468652070657263656e74616765206f662074686520736c617368207468617420697320646973747269627574656420746f207265706f72746572732e00e4205468652072657374206f662074686520736c61736865642076616c75652069732068616e646c6564206279207468652060536c617368602e4c43616e63656c6564536c6173685061796f757401003042616c616e63654f663c543e40000000000000000000000000000000000815012054686520616d6f756e74206f662063757272656e637920676976656e20746f207265706f7274657273206f66206120736c617368206576656e7420776869636820776173ec2063616e63656c65642062792065787472616f7264696e6172792063697263756d7374616e6365732028652e672e20676f7665726e616e6365292e40556e6170706c696564536c617368657301010520457261496e646578bc5665633c556e6170706c696564536c6173683c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e00040004c420416c6c20756e6170706c69656420736c61736865732074686174206172652071756575656420666f72206c617465722e28426f6e646564457261730100745665633c28457261496e6465782c2053657373696f6e496e646578293e04001025012041206d617070696e672066726f6d207374696c6c2d626f6e646564206572617320746f207468652066697273742073657373696f6e20696e646578206f662074686174206572612e00c8204d75737420636f6e7461696e7320696e666f726d6174696f6e20666f72206572617320666f72207468652072616e67653abc20605b6163746976655f657261202d20626f756e64696e675f6475726174696f6e3b206163746976655f6572615d604c56616c696461746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449645c2850657262696c6c2c2042616c616e63654f663c543e2905040008450120416c6c20736c617368696e67206576656e7473206f6e2076616c696461746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682070726f706f7274696f6e7020616e6420736c6173682076616c7565206f6620746865206572612e4c4e6f6d696e61746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449643042616c616e63654f663c543e05040004610120416c6c20736c617368696e67206576656e7473206f6e206e6f6d696e61746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682076616c7565206f6620746865206572612e34536c617368696e675370616e7300010530543a3a4163636f756e7449645c736c617368696e673a3a536c617368696e675370616e73000400048c20536c617368696e67207370616e7320666f72207374617368206163636f756e74732e245370616e536c6173680101058c28543a3a4163636f756e7449642c20736c617368696e673a3a5370616e496e6465782988736c617368696e673a3a5370616e5265636f72643c42616c616e63654f663c543e3e00800000000000000000000000000000000000000000000000000000000000000000083d01205265636f72647320696e666f726d6174696f6e2061626f757420746865206d6178696d756d20736c617368206f6620612073746173682077697468696e206120736c617368696e67207370616e2cb82061732077656c6c20617320686f77206d7563682072657761726420686173206265656e2070616964206f75742e584561726c69657374556e6170706c696564536c617368000020457261496e646578040004fc20546865206561726c696573742065726120666f72207768696368207765206861766520612070656e64696e672c20756e6170706c69656420736c6173682e5443757272656e74506c616e6e656453657373696f6e01003053657373696f6e496e64657810000000000ce820546865206c61737420706c616e6e65642073657373696f6e207363686564756c6564206279207468652073657373696f6e2070616c6c65742e0031012054686973206973206261736963616c6c7920696e2073796e632077697468207468652063616c6c20746f205b6053657373696f6e4d616e616765723a3a6e65775f73657373696f6e605d2e3853746f7261676556657273696f6e01002052656c6561736573040510cc2054727565206966206e6574776f726b20686173206265656e20757067726164656420746f20746869732076657273696f6e2e7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076362e302e3020666f72206e6577206e6574776f726b732e015c10626f6e640c28636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e1470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e5865012054616b6520746865206f726967696e206163636f756e74206173206120737461736820616e64206c6f636b207570206076616c756560206f66206974732062616c616e63652e2060636f6e74726f6c6c6572602077696c6c8420626520746865206163636f756e74207468617420636f6e74726f6c732069742e003101206076616c756560206d757374206265206d6f7265207468616e2074686520606d696e696d756d5f62616c616e636560207370656369666965642062792060543a3a43757272656e6379602e00250120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20627920746865207374617368206163636f756e742e004020456d6974732060426f6e646564602e002c2023203c7765696768743ed4202d20496e646570656e64656e74206f662074686520617267756d656e74732e204d6f64657261746520636f6d706c65786974792e20202d204f2831292e68202d20546872656520657874726120444220656e74726965732e005101204e4f54453a2054776f206f66207468652073746f726167652077726974657320286053656c663a3a626f6e646564602c206053656c663a3a7061796565602920617265205f6e657665725f20636c65616e6564410120756e6c6573732074686520606f726967696e602066616c6c732062656c6f77205f6578697374656e7469616c206465706f7369745f20616e6420676574732072656d6f76656420617320647573742e4c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a3101202d20526561643a20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c2043757272656e74204572612c20486973746f72792044657074682c204c6f636b73e0202d2057726974653a20426f6e6465642c2050617965652c205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e28626f6e645f657874726104386d61785f6164646974696f6e616c54436f6d706163743c42616c616e63654f663c543e3e5465012041646420736f6d6520657874726120616d6f756e742074686174206861766520617070656172656420696e207468652073746173682060667265655f62616c616e63656020696e746f207468652062616c616e63652075703420666f72207374616b696e672e00510120557365207468697320696620746865726520617265206164646974696f6e616c2066756e647320696e20796f7572207374617368206163636f756e74207468617420796f75207769736820746f20626f6e642e650120556e6c696b65205b60626f6e64605d206f72205b60756e626f6e64605d20746869732066756e6374696f6e20646f6573206e6f7420696d706f736520616e79206c696d69746174696f6e206f6e2074686520616d6f756e744c20746861742063616e2062652061646465642e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c657220616e64f82069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004020456d6974732060426f6e646564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e20202d204f2831292e40202d204f6e6520444220656e7472792e34202d2d2d2d2d2d2d2d2d2d2d2d2c204442205765696768743a1501202d20526561643a2045726120456c656374696f6e205374617475732c20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c204c6f636b73a4202d2057726974653a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e18756e626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e805501205363686564756c65206120706f7274696f6e206f662074686520737461736820746f20626520756e6c6f636b656420726561647920666f72207472616e73666572206f75742061667465722074686520626f6e64010120706572696f6420656e64732e2049662074686973206c656176657320616e20616d6f756e74206163746976656c7920626f6e646564206c657373207468616e250120543a3a43757272656e63793a3a6d696e696d756d5f62616c616e636528292c207468656e20697420697320696e6372656173656420746f207468652066756c6c20616d6f756e742e004901204f6e63652074686520756e6c6f636b20706572696f6420697320646f6e652c20796f752063616e2063616c6c206077697468647261775f756e626f6e6465646020746f2061637475616c6c79206d6f7665c0207468652066756e6473206f7574206f66206d616e6167656d656e7420726561647920666f72207472616e736665722e003d01204e6f206d6f7265207468616e2061206c696d69746564206e756d626572206f6620756e6c6f636b696e67206368756e6b73202873656520604d41585f554e4c4f434b494e475f4348554e4b5360293d012063616e20636f2d657869737473206174207468652073616d652074696d652e20496e207468617420636173652c205b6043616c6c3a3a77697468647261775f756e626f6e646564605d206e656564fc20746f2062652063616c6c656420666972737420746f2072656d6f766520736f6d65206f6620746865206368756e6b732028696620706f737369626c65292e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004820456d6974732060556e626f6e646564602e00982053656520616c736f205b6043616c6c3a3a77697468647261775f756e626f6e646564605d2e002c2023203c7765696768743e4101202d20496e646570656e64656e74206f662074686520617267756d656e74732e204c696d697465642062757420706f74656e7469616c6c79206578706c6f697461626c6520636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732e6501202d20456163682063616c6c20287265717569726573207468652072656d61696e646572206f662074686520626f6e6465642062616c616e636520746f2062652061626f766520606d696e696d756d5f62616c616e63656029710120202077696c6c2063617573652061206e657720656e74727920746f20626520696e73657274656420696e746f206120766563746f722028604c65646765722e756e6c6f636b696e676029206b65707420696e2073746f726167652e5101202020546865206f6e6c792077617920746f20636c65616e207468652061666f72656d656e74696f6e65642073746f72616765206974656d20697320616c736f20757365722d636f6e74726f6c6c6564207669615c2020206077697468647261775f756e626f6e646564602e40202d204f6e6520444220656e7472792e2c202d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a1d01202d20526561643a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e744572612c204c6f636b732c2042616c616e63654f662053746173682ca4202d2057726974653a204c6f636b732c204c65646765722c2042616c616e63654f662053746173682c28203c2f7765696768743e4477697468647261775f756e626f6e64656404486e756d5f736c617368696e675f7370616e730c7533327c2d012052656d6f766520616e7920756e6c6f636b6564206368756e6b732066726f6d207468652060756e6c6f636b696e67602071756575652066726f6d206f7572206d616e6167656d656e742e003501205468697320657373656e7469616c6c7920667265657320757020746861742062616c616e636520746f206265207573656420627920746865207374617368206163636f756e7420746f20646f4c2077686174657665722069742077616e74732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004c20456d697473206057697468647261776e602e006c2053656520616c736f205b6043616c6c3a3a756e626f6e64605d2e002c2023203c7765696768743e5501202d20436f756c6420626520646570656e64656e74206f6e2074686520606f726967696e6020617267756d656e7420616e6420686f77206d7563682060756e6c6f636b696e6760206368756e6b732065786973742e45012020497420696d706c6965732060636f6e736f6c69646174655f756e6c6f636b656460207768696368206c6f6f7073206f76657220604c65646765722e756e6c6f636b696e67602c207768696368206973f42020696e6469726563746c7920757365722d636f6e74726f6c6c65642e20536565205b60756e626f6e64605d20666f72206d6f72652064657461696c2e7901202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732c20796574207468652073697a65206f6620776869636820636f756c64206265206c61726765206261736564206f6e20606c6564676572602ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d090120436f6d706c6578697479204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2072656d6f766520205570646174653a2501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c204c6f636b732c205b4f726967696e204163636f756e745da8202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c656467657218204b696c6c3a4501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c20426f6e6465642c20536c617368696e67205370616e732c205b4f726967696e8c2020204163636f756e745d2c204c6f636b732c2042616c616e63654f662073746173685101202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732cb02020205b4f726967696e204163636f756e745d2c204c6f636b732c2042616c616e63654f662073746173682e74202d2057726974657320456163683a205370616e536c617368202a20530d01204e4f54453a2057656967687420616e6e6f746174696f6e20697320746865206b696c6c207363656e6172696f2c20776520726566756e64206f74686572776973652e302023203c2f7765696768743e2076616c6964617465041470726566733856616c696461746f72507265667344e8204465636c617265207468652064657369726520746f2076616c696461746520666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e30202d2d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a90202d20526561643a2045726120456c656374696f6e205374617475732c204c656467657280202d2057726974653a204e6f6d696e61746f72732c2056616c696461746f7273302023203c2f7765696768743e206e6f6d696e617465041c74617267657473a05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e4c1101204465636c617265207468652064657369726520746f206e6f6d696e6174652060746172676574736020666f7220746865206f726967696e20636f6e74726f6c6c65722e00510120456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e20546869732063616e206f6e6c792062652063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e3101202d20546865207472616e73616374696f6e277320636f6d706c65786974792069732070726f706f7274696f6e616c20746f207468652073697a65206f662060746172676574736020284e2901012077686963682069732063617070656420617420436f6d7061637441737369676e6d656e74733a3a4c494d495420284d41585f4e4f4d494e4154494f4e53292ed8202d20426f74682074686520726561647320616e642077726974657320666f6c6c6f7720612073696d696c6172207061747465726e2e28202d2d2d2d2d2d2d2d2d34205765696768743a204f284e2984207768657265204e20697320746865206e756d626572206f6620746172676574732c204442205765696768743ac8202d2052656164733a2045726120456c656374696f6e205374617475732c204c65646765722c2043757272656e742045726184202d205772697465733a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e146368696c6c0044c8204465636c617265206e6f2064657369726520746f206569746865722076616c6964617465206f72206e6f6d696e6174652e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e54202d20436f6e7461696e73206f6e6520726561642ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e24202d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a88202d20526561643a20457261456c656374696f6e5374617475732c204c656467657280202d2057726974653a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e247365745f7061796565041470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e40b8202852652d2973657420746865207061796d656e742074617267657420666f72206120636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e28202d2d2d2d2d2d2d2d2d3c202d205765696768743a204f28312934202d204442205765696768743a4c20202020202d20526561643a204c65646765724c20202020202d2057726974653a205061796565302023203c2f7765696768743e387365745f636f6e74726f6c6c65720428636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654090202852652d297365742074686520636f6e74726f6c6c6572206f6620612073746173682e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e2c202d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743af4202d20526561643a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572f8202d2057726974653a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572302023203c2f7765696768743e4c7365745f76616c696461746f725f636f756e74040c6e657730436f6d706163743c7533323e209420536574732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e34205765696768743a204f2831295c2057726974653a2056616c696461746f7220436f756e74302023203c2f7765696768743e60696e6372656173655f76616c696461746f725f636f756e7404286164646974696f6e616c30436f6d706163743c7533323e1cac20496e6372656d656e74732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e842053616d65206173205b607365745f76616c696461746f725f636f756e74605d2e302023203c2f7765696768743e547363616c655f76616c696461746f725f636f756e740418666163746f721c50657263656e741cd4205363616c652075702074686520696465616c206e756d626572206f662076616c696461746f7273206279206120666163746f722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e842053616d65206173205b607365745f76616c696461746f725f636f756e74605d2e302023203c2f7765696768743e34666f7263655f6e6f5f657261730024b020466f72636520746865726520746f206265206e6f206e6577206572617320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e3c202d205765696768743a204f28312948202d2057726974653a20466f726365457261302023203c2f7765696768743e34666f7263655f6e65775f65726100284d0120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f6620746865206e6578742073657373696f6e2e20416674657220746869732c2069742077696c6c206265a020726573657420746f206e6f726d616c20286e6f6e2d666f7263656429206265686176696f75722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e3c202d205765696768743a204f28312944202d20577269746520466f726365457261302023203c2f7765696768743e447365745f696e76756c6e657261626c65730434696e76756c6e657261626c6573445665633c543a3a4163636f756e7449643e20cc20536574207468652076616c696461746f72732077686f2063616e6e6f7420626520736c61736865642028696620616e79292e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e1c202d204f2856295c202d2057726974653a20496e76756c6e657261626c6573302023203c2f7765696768743e34666f7263655f756e7374616b650814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c753332280d0120466f72636520612063757272656e74207374616b657220746f206265636f6d6520636f6d706c6574656c7920756e7374616b65642c20696d6d6564696174656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743eec204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2062652072656d6f766564b82052656164733a20426f6e6465642c20536c617368696e67205370616e732c204163636f756e742c204c6f636b738501205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c204163636f756e742c204c6f636b736c2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e50666f7263655f6e65775f6572615f616c776179730020050120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f662073657373696f6e7320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e3c202d205765696768743a204f28312948202d2057726974653a20466f726365457261302023203c2f7765696768743e5463616e63656c5f64656665727265645f736c617368080c65726120457261496e64657834736c6173685f696e6469636573205665633c7533323e34982043616e63656c20656e6163746d656e74206f66206120646566657272656420736c6173682e00b42043616e2062652063616c6c6564206279207468652060543a3a536c61736843616e63656c4f726967696e602e00050120506172616d65746572733a2065726120616e6420696e6469636573206f662074686520736c617368657320666f7220746861742065726120746f206b696c6c2e002c2023203c7765696768743e5420436f6d706c65786974793a204f2855202b205329b82077697468205520756e6170706c69656420736c6173686573207765696768746564207769746820553d31303030d420616e64205320697320746865206e756d626572206f6620736c61736820696e646963657320746f2062652063616e63656c65642e68202d20526561643a20556e6170706c69656420536c61736865736c202d2057726974653a20556e6170706c69656420536c6173686573302023203c2f7765696768743e387061796f75745f7374616b657273083c76616c696461746f725f737461736830543a3a4163636f756e7449640c65726120457261496e64657870110120506179206f757420616c6c20746865207374616b65727320626568696e6420612073696e676c652076616c696461746f7220666f7220612073696e676c65206572612e004d01202d206076616c696461746f725f73746173686020697320746865207374617368206163636f756e74206f66207468652076616c696461746f722e205468656972206e6f6d696e61746f72732c20757020746f290120202060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602c2077696c6c20616c736f207265636569766520746865697220726577617264732e3501202d206065726160206d617920626520616e7920657261206265747765656e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e00590120546865206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e20416e79206163636f756e742063616e2063616c6c20746869732066756e6374696f6e2c206576656e20696678206974206973206e6f74206f6e65206f6620746865207374616b6572732e00010120546869732063616e206f6e6c792062652063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e0101202d2054696d6520636f6d706c65786974793a206174206d6f7374204f284d61784e6f6d696e61746f72526577617264656450657256616c696461746f72292ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e30202d2d2d2d2d2d2d2d2d2d2d1d01204e20697320746865204e756d626572206f66207061796f75747320666f72207468652076616c696461746f722028696e636c7564696e67207468652076616c696461746f722920205765696768743a88202d205265776172642044657374696e6174696f6e205374616b65643a204f284e29c4202d205265776172642044657374696e6174696f6e20436f6e74726f6c6c657220284372656174696e67293a204f284e292c204442205765696768743a2901202d20526561643a20457261456c656374696f6e5374617475732c2043757272656e744572612c20486973746f727944657074682c204572617356616c696461746f725265776172642c2d01202020202020202020457261735374616b657273436c69707065642c2045726173526577617264506f696e74732c204572617356616c696461746f725072656673202838206974656d73291101202d205265616420456163683a20426f6e6465642c204c65646765722c2050617965652c204c6f636b732c2053797374656d204163636f756e74202835206974656d7329d8202d20577269746520456163683a2053797374656d204163636f756e742c204c6f636b732c204c6564676572202833206974656d73290051012020204e4f54453a20776569676874732061726520617373756d696e672074686174207061796f75747320617265206d61646520746f20616c697665207374617368206163636f756e7420285374616b6564292e5901202020506179696e67206576656e2061206465616420636f6e74726f6c6c65722069732063686561706572207765696768742d776973652e20576520646f6e277420646f20616e7920726566756e647320686572652e302023203c2f7765696768743e187265626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e38e0205265626f6e64206120706f7274696f6e206f6620746865207374617368207363686564756c656420746f20626520756e6c6f636b65642e00550120546865206469737061746368206f726967696e206d757374206265207369676e65642062792074686520636f6e74726f6c6c65722c20616e642069742063616e206265206f6e6c792063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ed4202d2054696d6520636f6d706c65786974793a204f284c292c207768657265204c20697320756e6c6f636b696e67206368756e6b7394202d20426f756e64656420627920604d41585f554e4c4f434b494e475f4348554e4b53602ef4202d2053746f72616765206368616e6765733a2043616e277420696e6372656173652073746f726167652c206f6e6c792064656372656173652069742e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a010120202020202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c204c6f636b732c205b4f726967696e204163636f756e745db820202020202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e447365745f686973746f72795f646570746808446e65775f686973746f72795f646570746844436f6d706163743c457261496e6465783e485f6572615f6974656d735f64656c6574656430436f6d706163743c7533323e543101205365742060486973746f72794465707468602076616c75652e20546869732066756e6374696f6e2077696c6c2064656c65746520616e7920686973746f727920696e666f726d6174696f6e80207768656e2060486973746f727944657074686020697320726564756365642e003020506172616d65746572733a1101202d20606e65775f686973746f72795f6465707468603a20546865206e657720686973746f727920646570746820796f7520776f756c64206c696b6520746f207365742e4901202d20606572615f6974656d735f64656c65746564603a20546865206e756d626572206f66206974656d7320746861742077696c6c2062652064656c6574656420627920746869732064697370617463682e450120202020546869732073686f756c64207265706f727420616c6c207468652073746f72616765206974656d7320746861742077696c6c2062652064656c6574656420627920636c656172696e67206f6c6445012020202065726120686973746f72792e204e656564656420746f207265706f727420616e2061636375726174652077656967687420666f72207468652064697370617463682e2054727573746564206279a02020202060526f6f746020746f207265706f727420616e206163637572617465206e756d6265722e0054204f726967696e206d75737420626520726f6f742e002c2023203c7765696768743ee0202d20453a204e756d626572206f6620686973746f7279206465707468732072656d6f7665642c20692e652e203130202d3e2037203d20333c202d205765696768743a204f28452934202d204442205765696768743aa020202020202d2052656164733a2043757272656e74204572612c20486973746f72792044657074687020202020202d205772697465733a20486973746f7279204465707468310120202020202d20436c6561722050726566697820456163683a20457261205374616b6572732c204572615374616b657273436c69707065642c204572617356616c696461746f725072656673810120202020202d2057726974657320456163683a204572617356616c696461746f725265776172642c2045726173526577617264506f696e74732c2045726173546f74616c5374616b652c2045726173537461727453657373696f6e496e646578302023203c2f7765696768743e28726561705f73746173680814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c7533323c61012052656d6f766520616c6c20646174612073747275637475726520636f6e6365726e696e672061207374616b65722f7374617368206f6e6365206974732062616c616e636520697320617420746865206d696e696d756d2e6101205468697320697320657373656e7469616c6c79206571756976616c656e7420746f206077697468647261775f756e626f6e64656460206578636570742069742063616e2062652063616c6c656420627920616e796f6e65f820616e6420746865207461726765742060737461736860206d7573742068617665206e6f2066756e6473206c656674206265796f6e64207468652045442e009020546869732063616e2062652063616c6c65642066726f6d20616e79206f726967696e2e000101202d20607374617368603a20546865207374617368206163636f756e7420746f20726561702e204974732062616c616e6365206d757374206265207a65726f2e002c2023203c7765696768743e250120436f6d706c65786974793a204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e73206f6e20746865206163636f756e742e2c204442205765696768743ad8202d2052656164733a205374617368204163636f756e742c20426f6e6465642c20536c617368696e67205370616e732c204c6f636b73a501202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c205374617368204163636f756e742c204c6f636b7374202d2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e106b69636b040c77686fa05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e34e42052656d6f76652074686520676976656e206e6f6d696e6174696f6e732066726f6d207468652063616c6c696e672076616c696461746f722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e490120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e2054686520636f6e74726f6c6c657298206163636f756e742073686f756c6420726570726573656e7420612076616c696461746f722e005101202d206077686f603a2041206c697374206f66206e6f6d696e61746f72207374617368206163636f756e74732077686f20617265206e6f6d696e6174696e6720746869732076616c696461746f72207768696368c420202073686f756c64206e6f206c6f6e676572206265206e6f6d696e6174696e6720746869732076616c696461746f722e005901204e6f74653a204d616b696e6720746869732063616c6c206f6e6c79206d616b65732073656e736520696620796f7520666972737420736574207468652076616c696461746f7220707265666572656e63657320746f7c20626c6f636b20616e792066757274686572206e6f6d696e6174696f6e732e0124244572615061796f75740c20457261496e6465781c42616c616e63651c42616c616e63650c59012054686520657261207061796f757420686173206265656e207365743b207468652066697273742062616c616e6365206973207468652076616c696461746f722d7061796f75743b20746865207365636f6e64206973c4207468652072656d61696e6465722066726f6d20746865206d6178696d756d20616d6f756e74206f66207265776172642eac205c5b6572615f696e6465782c2076616c696461746f725f7061796f75742c2072656d61696e6465725c5d1852657761726408244163636f756e7449641c42616c616e636504fc20546865207374616b657220686173206265656e207265776172646564206279207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d14536c61736808244163636f756e7449641c42616c616e6365082501204f6e652076616c696461746f722028616e6420697473206e6f6d696e61746f72732920686173206265656e20736c61736865642062792074686520676976656e20616d6f756e742e58205c5b76616c696461746f722c20616d6f756e745c5d684f6c64536c617368696e675265706f7274446973636172646564043053657373696f6e496e646578081d0120416e206f6c6420736c617368696e67207265706f72742066726f6d2061207072696f72206572612077617320646973636172646564206265636175736520697420636f756c6490206e6f742062652070726f6365737365642e205c5b73657373696f6e5f696e6465785c5d3c5374616b696e67456c656374696f6e0004882041206e657720736574206f66207374616b6572732077617320656c65637465642e18426f6e64656408244163636f756e7449641c42616c616e636510d420416e206163636f756e742068617320626f6e646564207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d005101204e4f54453a2054686973206576656e74206973206f6e6c7920656d6974746564207768656e2066756e64732061726520626f6e64656420766961206120646973706174636861626c652e204e6f7461626c792c25012069742077696c6c206e6f7420626520656d697474656420666f72207374616b696e672072657761726473207768656e20746865792061726520616464656420746f207374616b652e20556e626f6e64656408244163636f756e7449641c42616c616e636504dc20416e206163636f756e742068617320756e626f6e646564207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d2457697468647261776e08244163636f756e7449641c42616c616e6365085d0120416e206163636f756e74206861732063616c6c6564206077697468647261775f756e626f6e6465646020616e642072656d6f76656420756e626f6e64696e67206368756e6b7320776f727468206042616c616e636560b02066726f6d2074686520756e6c6f636b696e672071756575652e205c5b73746173682c20616d6f756e745c5d184b69636b656408244163636f756e744964244163636f756e744964040d012041206e6f6d696e61746f7220686173206265656e206b69636b65642066726f6d20612076616c696461746f722e205c5b6e6f6d696e61746f722c2073746173685c5d143853657373696f6e735065724572613053657373696f6e496e64657810060000000470204e756d626572206f662073657373696f6e7320706572206572612e3c426f6e64696e674475726174696f6e20457261496e64657810a002000004e4204e756d626572206f6620657261732074686174207374616b65642066756e6473206d7573742072656d61696e20626f6e64656420666f722e48536c61736844656665724475726174696f6e20457261496e64657810a8000000140101204e756d626572206f662065726173207468617420736c6173686573206172652064656665727265642062792c20616674657220636f6d7075746174696f6e2e00bc20546869732073686f756c64206265206c657373207468616e2074686520626f6e64696e67206475726174696f6e2e2d012053657420746f203020696620736c61736865732073686f756c64206265206170706c69656420696d6d6564696174656c792c20776974686f7574206f70706f7274756e69747920666f723820696e74657276656e74696f6e2e804d61784e6f6d696e61746f72526577617264656450657256616c696461746f720c753332100001000010f820546865206d6178696d756d206e756d626572206f66206e6f6d696e61746f727320726577617264656420666f7220656163682076616c696461746f722e00690120466f7220656163682076616c696461746f72206f6e6c79207468652060244d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732063616e20636c61696d2101207468656972207265776172642e2054686973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e384d61784e6f6d696e6174696f6e730c753332101000000004b4204d6178696d756d206e756d626572206f66206e6f6d696e6174696f6e7320706572206e6f6d696e61746f722e50344e6f74436f6e74726f6c6c65720468204e6f74206120636f6e74726f6c6c6572206163636f756e742e204e6f7453746173680454204e6f742061207374617368206163636f756e742e34416c7265616479426f6e646564046420537461736820697320616c726561647920626f6e6465642e34416c7265616479506169726564047820436f6e74726f6c6c657220697320616c7265616479207061697265642e30456d70747954617267657473046420546172676574732063616e6e6f7420626520656d7074792e384475706c6963617465496e6465780444204475706c696361746520696e6465782e44496e76616c6964536c617368496e646578048820536c617368207265636f726420696e646578206f7574206f6620626f756e64732e44496e73756666696369656e7456616c756504cc2043616e206e6f7420626f6e6420776974682076616c7565206c657373207468616e206d696e696d756d2062616c616e63652e304e6f4d6f72654368756e6b7304942043616e206e6f74207363686564756c65206d6f726520756e6c6f636b206368756e6b732e344e6f556e6c6f636b4368756e6b04a42043616e206e6f74207265626f6e6420776974686f757420756e6c6f636b696e67206368756e6b732e3046756e64656454617267657404cc20417474656d7074696e6720746f2074617267657420612073746173682074686174207374696c6c206861732066756e64732e48496e76616c6964457261546f526577617264045c20496e76616c69642065726120746f207265776172642e68496e76616c69644e756d6265724f664e6f6d696e6174696f6e73047c20496e76616c6964206e756d626572206f66206e6f6d696e6174696f6e732e484e6f74536f72746564416e64556e697175650484204974656d7320617265206e6f7420736f7274656420616e6420756e697175652e38416c7265616479436c61696d6564040d01205265776172647320666f72207468697320657261206861766520616c7265616479206265656e20636c61696d656420666f7220746869732076616c696461746f722e54496e636f7272656374486973746f7279446570746804c420496e636f72726563742070726576696f757320686973746f727920646570746820696e7075742070726f76696465642e58496e636f7272656374536c617368696e675370616e7304b420496e636f7272656374206e756d626572206f6620736c617368696e67207370616e732070726f76696465642e204261645374617465043d0120496e7465726e616c20737461746520686173206265636f6d6520736f6d65686f7720636f7272757074656420616e6420746865206f7065726174696f6e2063616e6e6f7420636f6e74696e75652e38546f6f4d616e7954617267657473049820546f6f206d616e79206e6f6d696e6174696f6e207461726765747320737570706c6965642e244261645461726765740441012041206e6f6d696e6174696f6e207461726765742077617320737570706c69656420746861742077617320626c6f636b6564206f72206f7468657277697365206e6f7420612076616c696461746f722e091c53657373696f6e011c53657373696f6e1c2856616c696461746f727301004c5665633c543a3a56616c696461746f7249643e0400047c205468652063757272656e7420736574206f662076616c696461746f72732e3043757272656e74496e64657801003053657373696f6e496e646578100000000004782043757272656e7420696e646578206f66207468652073657373696f6e2e345175657565644368616e676564010010626f6f6c040008390120547275652069662074686520756e6465726c79696e672065636f6e6f6d6963206964656e746974696573206f7220776569676874696e6720626568696e64207468652076616c696461746f7273a420686173206368616e67656420696e20746865207175657565642076616c696461746f72207365742e285175657565644b6579730100785665633c28543a3a56616c696461746f7249642c20543a3a4b657973293e0400083d012054686520717565756564206b65797320666f7220746865206e6578742073657373696f6e2e205768656e20746865206e6578742073657373696f6e20626567696e732c207468657365206b657973e02077696c6c206265207573656420746f2064657465726d696e65207468652076616c696461746f7227732073657373696f6e206b6579732e4844697361626c656456616c696461746f72730100205665633c7533323e04000c8020496e6469636573206f662064697361626c65642076616c696461746f72732e003501205468652073657420697320636c6561726564207768656e20606f6e5f73657373696f6e5f656e64696e67602072657475726e732061206e657720736574206f66206964656e7469746965732e204e6578744b65797300010538543a3a56616c696461746f7249641c543a3a4b657973000400049c20546865206e6578742073657373696f6e206b65797320666f7220612076616c696461746f722e204b65794f776e657200010550284b65795479706549642c205665633c75383e2938543a3a56616c696461746f72496400040004090120546865206f776e6572206f662061206b65792e20546865206b65792069732074686520604b657954797065496460202b2074686520656e636f646564206b65792e0108207365745f6b65797308106b6579731c543a3a4b6579731470726f6f661c5665633c75383e38e82053657473207468652073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c657220746f20606b657973602e210120416c6c6f777320616e206163636f756e7420746f20736574206974732073657373696f6e206b6579207072696f7220746f206265636f6d696e6720612076616c696461746f722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a20606f726967696e206163636f756e74602c2060543a3a56616c696461746f7249644f66602c20604e6578744b65797360a4202d2044625772697465733a20606f726967696e206163636f756e74602c20604e6578744b6579736084202d204462526561647320706572206b65792069643a20604b65794f776e65726088202d20446257726974657320706572206b65792069643a20604b65794f776e657260302023203c2f7765696768743e2870757267655f6b6579730030cc2052656d6f76657320616e792073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c65722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743eb4202d20436f6d706c65786974793a20604f2831296020696e206e756d626572206f66206b65792074797065732e590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a2060543a3a56616c696461746f7249644f66602c20604e6578744b657973602c20606f726967696e206163636f756e7460a4202d2044625772697465733a20604e6578744b657973602c20606f726967696e206163636f756e74608c202d20446257726974657320706572206b65792069643a20604b65794f776e64657260302023203c2f7765696768743e0104284e657753657373696f6e043053657373696f6e496e646578086501204e65772073657373696f6e206861732068617070656e65642e204e6f746520746861742074686520617267756d656e7420697320746865205c5b73657373696f6e5f696e6465785c5d2c206e6f742074686520626c6f636b88206e756d626572206173207468652074797065206d6967687420737567676573742e001430496e76616c696450726f6f66046420496e76616c6964206f776e6572736869702070726f6f662e5c4e6f4173736f63696174656456616c696461746f72496404a0204e6f206173736f6369617465642076616c696461746f7220494420666f72206163636f756e742e344475706c6963617465644b657904682052656769737465726564206475706c6963617465206b65792e184e6f4b65797304a8204e6f206b65797320617265206173736f63696174656420776974682074686973206163636f756e742e244e6f4163636f756e74041d01204b65792073657474696e67206163636f756e74206973206e6f74206c6976652c20736f206974277320696d706f737369626c6520746f206173736f6369617465206b6579732e0a2444656d6f6372616379012444656d6f6372616379383c5075626c696350726f70436f756e7401002450726f70496e646578100000000004f420546865206e756d626572206f6620287075626c6963292070726f706f73616c7320746861742068617665206265656e206d61646520736f206661722e2c5075626c696350726f707301009c5665633c2850726f70496e6465782c20543a3a486173682c20543a3a4163636f756e744964293e040004210120546865207075626c69632070726f706f73616c732e20556e736f727465642e20546865207365636f6e64206974656d206973207468652070726f706f73616c277320686173682e244465706f7369744f660001052450726f70496e64657884285665633c543a3a4163636f756e7449643e2c2042616c616e63654f663c543e290004000c842054686f73652077686f2068617665206c6f636b65642061206465706f7369742e00d82054574f582d4e4f54453a20536166652c20617320696e6372656173696e6720696e7465676572206b6579732061726520736166652e24507265696d616765730001061c543a3a48617368e8507265696d6167655374617475733c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e000400086101204d6170206f662068617368657320746f207468652070726f706f73616c20707265696d6167652c20616c6f6e6720776974682077686f207265676973746572656420697420616e64207468656972206465706f7369742ee42054686520626c6f636b206e756d6265722069732074686520626c6f636b20617420776869636820697420776173206465706f73697465642e3c5265666572656e64756d436f756e7401003c5265666572656e64756d496e646578100000000004310120546865206e6578742066726565207265666572656e64756d20696e6465782c20616b6120746865206e756d626572206f66207265666572656e6461207374617274656420736f206661722e344c6f77657374556e62616b656401003c5265666572656e64756d496e646578100000000008250120546865206c6f77657374207265666572656e64756d20696e64657820726570726573656e74696e6720616e20756e62616b6564207265666572656e64756d2e20457175616c20746fdc20605265666572656e64756d436f756e74602069662074686572652069736e2774206120756e62616b6564207265666572656e64756d2e405265666572656e64756d496e666f4f660001053c5265666572656e64756d496e646578d45265666572656e64756d496e666f3c543a3a426c6f636b4e756d6265722c20543a3a486173682c2042616c616e63654f663c543e3e0004000cb420496e666f726d6174696f6e20636f6e6365726e696e6720616e7920676976656e207265666572656e64756d2e0009012054574f582d4e4f54453a205341464520617320696e646578657320617265206e6f7420756e64657220616e2061747461636b6572e280997320636f6e74726f6c2e20566f74696e674f6601010530543a3a4163636f756e744964c8566f74696e673c42616c616e63654f663c543e2c20543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00d8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000105d0120416c6c20766f74657320666f72206120706172746963756c617220766f7465722e2057652073746f7265207468652062616c616e636520666f7220746865206e756d626572206f6620766f74657320746861742077655d012068617665207265636f726465642e20546865207365636f6e64206974656d2069732074686520746f74616c20616d6f756e74206f662064656c65676174696f6e732c20746861742077696c6c2062652061646465642e00e82054574f582d4e4f54453a205341464520617320604163636f756e7449646073206172652063727970746f2068617368657320616e797761792e144c6f636b7300010530543a3a4163636f756e74496438543a3a426c6f636b4e756d626572000400105d01204163636f756e747320666f7220776869636820746865726520617265206c6f636b7320696e20616374696f6e207768696368206d61792062652072656d6f76656420617420736f6d6520706f696e7420696e207468655101206675747572652e205468652076616c75652069732074686520626c6f636b206e756d62657220617420776869636820746865206c6f636b206578706972657320616e64206d61792062652072656d6f7665642e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e544c6173745461626c656457617345787465726e616c010010626f6f6c0400085901205472756520696620746865206c617374207265666572656e64756d207461626c656420776173207375626d69747465642065787465726e616c6c792e2046616c7365206966206974207761732061207075626c6963282070726f706f73616c2e304e65787445787465726e616c00006028543a3a486173682c20566f74655468726573686f6c6429040010590120546865207265666572656e64756d20746f206265207461626c6564207768656e6576657220697420776f756c642062652076616c696420746f207461626c6520616e2065787465726e616c2070726f706f73616c2e550120546869732068617070656e73207768656e2061207265666572656e64756d206e6565647320746f206265207461626c656420616e64206f6e65206f662074776f20636f6e646974696f6e7320617265206d65743aa4202d20604c6173745461626c656457617345787465726e616c60206973206066616c7365603b206f7268202d20605075626c696350726f70736020697320656d7074792e24426c61636b6c6973740001061c543a3a486173688c28543a3a426c6f636b4e756d6265722c205665633c543a3a4163636f756e7449643e290004000851012041207265636f7264206f662077686f207665746f656420776861742e204d6170732070726f706f73616c206861736820746f206120706f737369626c65206578697374656e7420626c6f636b206e756d626572e82028756e74696c207768656e206974206d6179206e6f742062652072657375626d69747465642920616e642077686f207665746f65642069742e3443616e63656c6c6174696f6e730101061c543a3a4861736810626f6f6c000400042901205265636f7264206f6620616c6c2070726f706f73616c7320746861742068617665206265656e207375626a65637420746f20656d657267656e63792063616e63656c6c6174696f6e2e3853746f7261676556657273696f6e00002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e01641c70726f706f7365083470726f706f73616c5f686173681c543a3a486173681476616c756554436f6d706163743c42616c616e63654f663c543e3e2ca02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e00190120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573748420686176652066756e647320746f20636f76657220746865206465706f7369742e00d8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20707265696d6167652e1901202d206076616c7565603a2054686520616d6f756e74206f66206465706f73697420286d757374206265206174206c6561737420604d696e696d756d4465706f73697460292e004820456d697473206050726f706f736564602e003c205765696768743a20604f28702960187365636f6e64082070726f706f73616c48436f6d706163743c50726f70496e6465783e4c7365636f6e64735f75707065725f626f756e6430436f6d706163743c7533323e28b8205369676e616c732061677265656d656e742077697468206120706172746963756c61722070726f706f73616c2e00050120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e6465721501206d75737420686176652066756e647320746f20636f76657220746865206465706f7369742c20657175616c20746f20746865206f726967696e616c206465706f7369742e00cc202d206070726f706f73616c603a2054686520696e646578206f66207468652070726f706f73616c20746f207365636f6e642e4501202d20607365636f6e64735f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e207468652063757272656e74206e756d626572206f66207365636f6e6473206f6e2074686973290120202070726f706f73616c2e2045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e002101205765696768743a20604f28532960207768657265205320697320746865206e756d626572206f66207365636f6e647320612070726f706f73616c20616c7265616479206861732e10766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f7465644163636f756e74566f74653c42616c616e63654f663c543e3e24350120566f746520696e2061207265666572656e64756d2e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374207468652070726f706f73616c3bbc206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00e0202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f20766f746520666f722e88202d2060766f7465603a2054686520766f746520636f6e66696775726174696f6e2e003101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722068617320766f746564206f6e2e40656d657267656e63795f63616e63656c04247265665f696e6465783c5265666572656e64756d496e646578205101205363686564756c6520616e20656d657267656e63792063616e63656c6c6174696f6e206f662061207265666572656e64756d2e2043616e6e6f742068617070656e20747769636520746f207468652073616d6530207265666572656e64756d2e00fc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206043616e63656c6c6174696f6e4f726967696e602e00d4202d607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e0040205765696768743a20604f283129602e4065787465726e616c5f70726f706f7365043470726f706f73616c5f686173681c543a3a48617368243101205363686564756c652061207265666572656e64756d20746f206265207461626c6564206f6e6365206974206973206c6567616c20746f207363686564756c6520616e2065787465726e616c30207265666572656e64756d2e00ec20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206045787465726e616c4f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e001901205765696768743a20604f2856296020776974682056206e756d626572206f66207665746f65727320696e2074686520626c61636b6c697374206f662070726f706f73616c2ebc2020204465636f64696e6720766563206f66206c656e67746820562e2043686172676564206173206d6178696d756d6465787465726e616c5f70726f706f73655f6d616a6f72697479043470726f706f73616c5f686173681c543a3a486173682c5901205363686564756c652061206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f207363686564756c656020616e2065787465726e616c207265666572656e64756d2e00f020546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c4d616a6f726974794f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e003c205765696768743a20604f283129606065787465726e616c5f70726f706f73655f64656661756c74043470726f706f73616c5f686173681c543a3a486173682c4901205363686564756c652061206e656761746976652d7475726e6f75742d62696173207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f84207363686564756c6520616e2065787465726e616c207265666572656e64756d2e00ec20546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c44656661756c744f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e003c205765696768743a20604f2831296028666173745f747261636b0c3470726f706f73616c5f686173681c543a3a4861736834766f74696e675f706572696f6438543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d6265723c5101205363686564756c65207468652063757272656e746c792065787465726e616c6c792d70726f706f736564206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564650120696d6d6564696174656c792e204966207468657265206973206e6f2065787465726e616c6c792d70726f706f736564207265666572656e64756d2063757272656e746c792c206f72206966207468657265206973206f6e65ec20627574206974206973206e6f742061206d616a6f726974792d63617272696573207265666572656e64756d207468656e206974206661696c732e00d420546865206469737061746368206f6620746869732063616c6c206d757374206265206046617374547261636b4f726967696e602e00f8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652063757272656e742065787465726e616c2070726f706f73616c2e6101202d2060766f74696e675f706572696f64603a2054686520706572696f64207468617420697320616c6c6f77656420666f7220766f74696e67206f6e20746869732070726f706f73616c2e20496e6372656173656420746f982020206046617374547261636b566f74696e67506572696f646020696620746f6f206c6f772e5501202d206064656c6179603a20546865206e756d626572206f6620626c6f636b20616674657220766f74696e672068617320656e64656420696e20617070726f76616c20616e6420746869732073686f756c64206265bc202020656e61637465642e205468697320646f65736e277420686176652061206d696e696d756d20616d6f756e742e004420456d697473206053746172746564602e003c205765696768743a20604f28312960347665746f5f65787465726e616c043470726f706f73616c5f686173681c543a3a4861736824bc205665746f20616e6420626c61636b6c697374207468652065787465726e616c2070726f706f73616c20686173682e00dc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520605665746f4f726967696e602e003101202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c20746f207665746f20616e6420626c61636b6c6973742e004020456d69747320605665746f6564602e000101205765696768743a20604f2856202b206c6f6728562929602077686572652056206973206e756d626572206f6620606578697374696e67207665746f657273604463616e63656c5f7265666572656e64756d04247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e1c542052656d6f76652061207265666572656e64756d2e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00d8202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e00482023205765696768743a20604f283129602e3463616e63656c5f717565756564041477686963683c5265666572656e64756d496e6465781ca02043616e63656c20612070726f706f73616c2071756575656420666f7220656e6163746d656e742e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00c8202d20607768696368603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e004d01205765696768743a20604f284429602077686572652060446020697320746865206974656d7320696e207468652064697370617463682071756575652e205765696768746564206173206044203d203130602e2064656c65676174650c08746f30543a3a4163636f756e74496428636f6e76696374696f6e28436f6e76696374696f6e1c62616c616e63653042616c616e63654f663c543e503d012044656c65676174652074686520766f74696e6720706f77657220287769746820736f6d6520676976656e20636f6e76696374696f6e29206f66207468652073656e64696e67206163636f756e742e005901205468652062616c616e63652064656c656761746564206973206c6f636b656420666f72206173206c6f6e6720617320697427732064656c6567617465642c20616e64207468657265616674657220666f7220746865cc2074696d6520617070726f70726961746520666f722074686520636f6e76696374696f6e2773206c6f636b20706572696f642e00610120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e696e67206163636f756e74206d757374206569746865723a782020202d2062652064656c65676174696e6720616c72656164793b206f725d012020202d2068617665206e6f20766f74696e67206163746976697479202869662074686572652069732c207468656e2069742077696c6c206e65656420746f2062652072656d6f7665642f636f6e736f6c6964617465649820202020207468726f7567682060726561705f766f746560206f722060756e766f746560292e004901202d2060746f603a20546865206163636f756e742077686f736520766f74696e6720746865206074617267657460206163636f756e74277320766f74696e6720706f7765722077696c6c20666f6c6c6f772e5901202d2060636f6e76696374696f6e603a2054686520636f6e76696374696f6e20746861742077696c6c20626520617474616368656420746f207468652064656c65676174656420766f7465732e205768656e2074686545012020206163636f756e7420697320756e64656c6567617465642c207468652066756e64732077696c6c206265206c6f636b656420666f722074686520636f72726573706f6e64696e6720706572696f642e5501202d206062616c616e6365603a2054686520616d6f756e74206f6620746865206163636f756e7427732062616c616e636520746f206265207573656420696e2064656c65676174696e672e2054686973206d757374c82020206e6f74206265206d6f7265207468616e20746865206163636f756e7427732063757272656e742062616c616e63652e004c20456d697473206044656c656761746564602e004101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732e28756e64656c65676174650030d020556e64656c65676174652074686520766f74696e6720706f776572206f66207468652073656e64696e67206163636f756e742e00610120546f6b656e73206d617920626520756e6c6f636b656420666f6c6c6f77696e67206f6e636520616e20616d6f756e74206f662074696d6520636f6e73697374656e74207769746820746865206c6f636b20706572696f64e0206f662074686520636f6e76696374696f6e2077697468207768696368207468652064656c65676174696f6e20776173206973737565642e00490120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265582063757272656e746c792064656c65676174696e672e005420456d6974732060556e64656c656761746564602e004101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732e58636c6561725f7075626c69635f70726f706f73616c7300147420436c6561727320616c6c207075626c69632070726f706f73616c732e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e0040205765696768743a20604f283129602e346e6f74655f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e2861012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e205468697320646f65736e27742072657175697265207468652070726f706f73616c20746f206265250120696e207468652064697370617463682071756575652062757420646f657320726571756972652061206465706f7369742c2072657475726e6564206f6e636520656e61637465642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e005101205765696768743a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e646e6f74655f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e040d012053616d6520617320606e6f74655f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e586e6f74655f696d6d696e656e745f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e3045012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e2054686973207265717569726573207468652070726f706f73616c20746f206265410120696e207468652064697370617463682071756575652e204e6f206465706f736974206973206e65656465642e205768656e20746869732063616c6c206973207375636365737366756c2c20692e652e39012074686520707265696d61676520686173206e6f74206265656e2075706c6f61646564206265666f726520616e64206d61746368657320736f6d6520696d6d696e656e742070726f706f73616c2c40206e6f2066656520697320706169642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e005101205765696768743a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e886e6f74655f696d6d696e656e745f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e0431012053616d6520617320606e6f74655f696d6d696e656e745f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e34726561705f707265696d616765083470726f706f73616c5f686173681c543a3a486173686070726f706f73616c5f6c656e5f75707065725f626f756e6430436f6d706163743c7533323e3cf42052656d6f766520616e20657870697265642070726f706f73616c20707265696d61676520616e6420636f6c6c65637420746865206465706f7369742e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00d0202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f6620612070726f706f73616c2e2d01202d206070726f706f73616c5f6c656e6774685f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e206c656e677468206f66207468652070726f706f73616c2e010120202045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e00510120546869732077696c6c206f6e6c7920776f726b2061667465722060566f74696e67506572696f646020626c6f636b732066726f6d207468652074696d6520746861742074686520707265696d616765207761735d01206e6f7465642c2069662069742773207468652073616d65206163636f756e7420646f696e672069742e2049662069742773206120646966666572656e74206163636f756e742c207468656e206974276c6c206f6e6c79b020776f726b20616e206164646974696f6e616c2060456e6163746d656e74506572696f6460206c617465722e006020456d6974732060507265696d616765526561706564602e00b8205765696768743a20604f284429602077686572652044206973206c656e677468206f662070726f706f73616c2e18756e6c6f636b041874617267657430543a3a4163636f756e7449641ca420556e6c6f636b20746f6b656e732074686174206861766520616e2065787069726564206c6f636b2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00bc202d2060746172676574603a20546865206163636f756e7420746f2072656d6f766520746865206c6f636b206f6e2e00c0205765696768743a20604f2852296020776974682052206e756d626572206f6620766f7465206f66207461726765742e2c72656d6f76655f766f74650414696e6465783c5265666572656e64756d496e6465786c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e00102049663a8c202d20746865207265666572656e64756d207761732063616e63656c6c65642c206f7280202d20746865207265666572656e64756d206973206f6e676f696e672c206f7294202d20746865207265666572656e64756d2068617320656e6465642073756368207468617401012020202d2074686520766f7465206f6620746865206163636f756e742077617320696e206f70706f736974696f6e20746f2074686520726573756c743b206f72d82020202d20746865726520776173206e6f20636f6e76696374696f6e20746f20746865206163636f756e74277320766f74653b206f72882020202d20746865206163636f756e74206d61646520612073706c697420766f74656101202e2e2e7468656e2074686520766f74652069732072656d6f76656420636c65616e6c7920616e64206120666f6c6c6f77696e672063616c6c20746f2060756e6c6f636b60206d617920726573756c7420696e206d6f72655c2066756e6473206265696e6720617661696c61626c652e00ac2049662c20686f77657665722c20746865207265666572656e64756d2068617320656e64656420616e643af0202d2069742066696e697368656420636f72726573706f6e64696e6720746f2074686520766f7465206f6620746865206163636f756e742c20616e64e0202d20746865206163636f756e74206d6164652061207374616e6461726420766f7465207769746820636f6e76696374696f6e2c20616e64c0202d20746865206c6f636b20706572696f64206f662074686520636f6e76696374696f6e206973206e6f74206f7665725d01202e2e2e7468656e20746865206c6f636b2077696c6c206265206167677265676174656420696e746f20746865206f766572616c6c206163636f756e742773206c6f636b2c207768696368206d617920696e766f6c76655d01202a6f7665726c6f636b696e672a20287768657265207468652074776f206c6f636b732061726520636f6d62696e656420696e746f20612073696e676c65206c6f636b207468617420697320746865206d6178696d756de8206f6620626f74682074686520616d6f756e74206c6f636b656420616e64207468652074696d65206973206974206c6f636b656420666f72292e004d0120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e6572206d7573742068617665206120766f74658c207265676973746572656420666f72207265666572656e64756d2060696e646578602e00f8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e005901205765696768743a20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652e4472656d6f76655f6f746865725f766f7465081874617267657430543a3a4163636f756e74496414696e6465783c5265666572656e64756d496e6465783c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e0051012049662074686520607461726765746020697320657175616c20746f20746865207369676e65722c207468656e20746869732066756e6374696f6e2069732065786163746c79206571756976616c656e7420746f3101206072656d6f76655f766f7465602e204966206e6f7420657175616c20746f20746865207369676e65722c207468656e2074686520766f7465206d757374206861766520657870697265642c590120656974686572206265636175736520746865207265666572656e64756d207761732063616e63656c6c65642c20626563617573652074686520766f746572206c6f737420746865207265666572656e64756d206f729c20626563617573652074686520636f6e76696374696f6e20706572696f64206973206f7665722e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e005101202d2060746172676574603a20546865206163636f756e74206f662074686520766f746520746f2062652072656d6f7665643b2074686973206163636f756e74206d757374206861766520766f74656420666f72582020207265666572656e64756d2060696e646578602ef8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e005901205765696768743a20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652e38656e6163745f70726f706f73616c083470726f706f73616c5f686173681c543a3a4861736814696e6465783c5265666572656e64756d496e64657804510120456e61637420612070726f706f73616c2066726f6d2061207265666572656e64756d2e20466f72206e6f77207765206a757374206d616b65207468652077656967687420626520746865206d6178696d756d2e24626c61636b6c697374083470726f706f73616c5f686173681c543a3a486173683c6d617962655f7265665f696e6465785c4f7074696f6e3c5265666572656e64756d496e6465783e3c4901205065726d616e656e746c7920706c61636520612070726f706f73616c20696e746f2074686520626c61636b6c6973742e20546869732070726576656e74732069742066726f6d2065766572206265696e67402070726f706f73656420616761696e2e0055012049662063616c6c6564206f6e206120717565756564207075626c6963206f722065787465726e616c2070726f706f73616c2c207468656e20746869732077696c6c20726573756c7420696e206974206265696e6755012072656d6f7665642e2049662074686520607265665f696e6465786020737570706c69656420697320616e20616374697665207265666572656e64756d2077697468207468652070726f706f73616c20686173682c6c207468656e2069742077696c6c2062652063616e63656c6c65642e00f020546865206469737061746368206f726967696e206f6620746869732063616c6c206d7573742062652060426c61636b6c6973744f726967696e602e00fc202d206070726f706f73616c5f68617368603a205468652070726f706f73616c206861736820746f20626c61636b6c697374207065726d616e656e746c792e4901202d20607265665f696e646578603a20416e206f6e676f696e67207265666572656e64756d2077686f73652068617368206973206070726f706f73616c5f68617368602c2077686963682077696c6c2062652c2063616e63656c6c65642e004501205765696768743a20604f28702960202874686f756768206173207468697320697320616e20686967682d70726976696c6567652064697370617463682c20776520617373756d6520697420686173206154202020726561736f6e61626c652076616c7565292e3c63616e63656c5f70726f706f73616c042870726f705f696e64657848436f6d706163743c50726f70496e6465783e1c4c2052656d6f766520612070726f706f73616c2e00050120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206043616e63656c50726f706f73616c4f726967696e602e00d4202d206070726f705f696e646578603a2054686520696e646578206f66207468652070726f706f73616c20746f2063616e63656c2e00e8205765696768743a20604f28702960207768657265206070203d205075626c696350726f70733a3a3c543e3a3a6465636f64655f6c656e28296001482050726f706f736564082450726f70496e6465781c42616c616e63650431012041206d6f74696f6e20686173206265656e2070726f706f7365642062792061207075626c6963206163636f756e742e205c5b70726f706f73616c5f696e6465782c206465706f7369745c5d185461626c65640c2450726f70496e6465781c42616c616e6365385665633c4163636f756e7449643e047d012041207075626c69632070726f706f73616c20686173206265656e207461626c656420666f72207265666572656e64756d20766f74652e205c5b70726f706f73616c5f696e6465782c206465706f7369742c206465706f7369746f72735c5d3845787465726e616c5461626c656400049820416e2065787465726e616c2070726f706f73616c20686173206265656e207461626c65642e1c53746172746564083c5265666572656e64756d496e64657834566f74655468726573686f6c6404c42041207265666572656e64756d2068617320626567756e2e205c5b7265665f696e6465782c207468726573686f6c645c5d18506173736564043c5265666572656e64756d496e64657804e820412070726f706f73616c20686173206265656e20617070726f766564206279207265666572656e64756d2e205c5b7265665f696e6465785c5d244e6f74506173736564043c5265666572656e64756d496e64657804e820412070726f706f73616c20686173206265656e2072656a6563746564206279207265666572656e64756d2e205c5b7265665f696e6465785c5d2443616e63656c6c6564043c5265666572656e64756d496e64657804bc2041207265666572656e64756d20686173206265656e2063616e63656c6c65642e205c5b7265665f696e6465785c5d204578656375746564083c5265666572656e64756d496e64657810626f6f6c04c820412070726f706f73616c20686173206265656e20656e61637465642e205c5b7265665f696e6465782c2069735f6f6b5c5d2444656c65676174656408244163636f756e744964244163636f756e74496404210120416e206163636f756e74206861732064656c65676174656420746865697220766f746520746f20616e6f74686572206163636f756e742e205c5b77686f2c207461726765745c5d2c556e64656c65676174656404244163636f756e74496404f820416e205c5b6163636f756e745c5d206861732063616e63656c6c656420612070726576696f75732064656c65676174696f6e206f7065726174696f6e2e185665746f65640c244163636f756e74496410486173682c426c6f636b4e756d62657204110120416e2065787465726e616c2070726f706f73616c20686173206265656e207665746f65642e205c5b77686f2c2070726f706f73616c5f686173682c20756e74696c5c5d34507265696d6167654e6f7465640c1048617368244163636f756e7449641c42616c616e636504610120412070726f706f73616c277320707265696d61676520776173206e6f7465642c20616e6420746865206465706f7369742074616b656e2e205c5b70726f706f73616c5f686173682c2077686f2c206465706f7369745c5d30507265696d616765557365640c1048617368244163636f756e7449641c42616c616e636508150120412070726f706f73616c20707265696d616765207761732072656d6f76656420616e6420757365642028746865206465706f736974207761732072657475726e6564292e94205c5b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369745c5d3c507265696d616765496e76616c69640810486173683c5265666572656e64756d496e646578080d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d6167652077617320696e76616c69642e74205c5b70726f706f73616c5f686173682c207265665f696e6465785c5d3c507265696d6167654d697373696e670810486173683c5265666572656e64756d496e646578080d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d61676520776173206d697373696e672e74205c5b70726f706f73616c5f686173682c207265665f696e6465785c5d38507265696d616765526561706564101048617368244163636f756e7449641c42616c616e6365244163636f756e744964082d012041207265676973746572656420707265696d616765207761732072656d6f76656420616e6420746865206465706f73697420636f6c6c656374656420627920746865207265617065722eb4205c5b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369742c207265617065725c5d20556e6c6f636b656404244163636f756e74496404bc20416e205c5b6163636f756e745c5d20686173206265656e20756e6c6f636b6564207375636365737366756c6c792e2c426c61636b6c697374656404104861736804d820412070726f706f73616c205c5b686173685c5d20686173206265656e20626c61636b6c6973746564207065726d616e656e746c792e203c456e6163746d656e74506572696f6438543a3a426c6f636b4e756d62657210002f0d0014710120546865206d696e696d756d20706572696f64206f66206c6f636b696e6720616e642074686520706572696f64206265747765656e20612070726f706f73616c206265696e6720617070726f76656420616e6420656e61637465642e0031012049742073686f756c642067656e6572616c6c792062652061206c6974746c65206d6f7265207468616e2074686520756e7374616b6520706572696f6420746f20656e737572652074686174690120766f74696e67207374616b657273206861766520616e206f70706f7274756e69747920746f2072656d6f7665207468656d73656c7665732066726f6d207468652073797374656d20696e2074686520636173652077686572659c207468657920617265206f6e20746865206c6f73696e672073696465206f66206120766f74652e304c61756e6368506572696f6438543a3a426c6f636b4e756d62657210004e0c0004e420486f77206f6674656e2028696e20626c6f636b7329206e6577207075626c6963207265666572656e646120617265206c61756e636865642e30566f74696e67506572696f6438543a3a426c6f636b4e756d62657210004e0c0004b820486f77206f6674656e2028696e20626c6f636b732920746f20636865636b20666f72206e657720766f7465732e384d696e696d756d4465706f7369743042616c616e63654f663c543e400000c16ff2862300000000000000000004350120546865206d696e696d756d20616d6f756e7420746f20626520757365642061732061206465706f73697420666f722061207075626c6963207265666572656e64756d2070726f706f73616c2e5446617374547261636b566f74696e67506572696f6438543a3a426c6f636b4e756d626572108051010004ec204d696e696d756d20766f74696e6720706572696f6420616c6c6f77656420666f7220616e20656d657267656e6379207265666572656e64756d2e34436f6f6c6f6666506572696f6438543a3a426c6f636b4e756d62657210004e0c0004610120506572696f6420696e20626c6f636b7320776865726520616e2065787465726e616c2070726f706f73616c206d6179206e6f742062652072652d7375626d6974746564206166746572206265696e67207665746f65642e4c507265696d616765427974654465706f7369743042616c616e63654f663c543e400010a5d4e800000000000000000000000429012054686520616d6f756e74206f662062616c616e63652074686174206d757374206265206465706f7369746564207065722062797465206f6620707265696d6167652073746f7265642e204d6178566f7465730c753332106400000004b020546865206d6178696d756d206e756d626572206f6620766f74657320666f7220616e206163636f756e742e8c2056616c75654c6f7704382056616c756520746f6f206c6f773c50726f706f73616c4d697373696e6704602050726f706f73616c20646f6573206e6f7420657869737420426164496e646578043820556e6b6e6f776e20696e6465783c416c726561647943616e63656c656404982043616e6e6f742063616e63656c207468652073616d652070726f706f73616c207477696365444475706c696361746550726f706f73616c04582050726f706f73616c20616c7265616479206d6164654c50726f706f73616c426c61636b6c6973746564046c2050726f706f73616c207374696c6c20626c61636b6c6973746564444e6f7453696d706c654d616a6f7269747904ac204e6578742065787465726e616c2070726f706f73616c206e6f742073696d706c65206d616a6f726974792c496e76616c696448617368043420496e76616c69642068617368284e6f50726f706f73616c0454204e6f2065787465726e616c2070726f706f73616c34416c72656164795665746f6564049c204964656e74697479206d6179206e6f74207665746f20612070726f706f73616c207477696365304e6f7444656c6567617465640438204e6f742064656c656761746564444475706c6963617465507265696d616765045c20507265696d61676520616c7265616479206e6f7465642c4e6f74496d6d696e656e740434204e6f7420696d6d696e656e7420546f6f4561726c79042820546f6f206561726c7920496d6d696e656e74042420496d6d696e656e743c507265696d6167654d697373696e67044c20507265696d616765206e6f7420666f756e64445265666572656e64756d496e76616c6964048820566f746520676976656e20666f7220696e76616c6964207265666572656e64756d3c507265696d616765496e76616c6964044420496e76616c696420707265696d6167652c4e6f6e6557616974696e670454204e6f2070726f706f73616c732077616974696e67244e6f744c6f636b656404a42054686520746172676574206163636f756e7420646f6573206e6f7420686176652061206c6f636b2e284e6f744578706972656404f020546865206c6f636b206f6e20746865206163636f756e7420746f20626520756e6c6f636b656420686173206e6f742079657420657870697265642e204e6f74566f74657204c82054686520676976656e206163636f756e7420646964206e6f7420766f7465206f6e20746865207265666572656e64756d2e304e6f5065726d697373696f6e04cc20546865206163746f7220686173206e6f207065726d697373696f6e20746f20636f6e647563742074686520616374696f6e2e44416c726561647944656c65676174696e67048c20546865206163636f756e7420697320616c72656164792064656c65676174696e672e204f766572666c6f7704a420416e20756e657870656374656420696e7465676572206f766572666c6f77206f636375727265642e24556e646572666c6f7704a820416e20756e657870656374656420696e746567657220756e646572666c6f77206f636375727265642e44496e73756666696369656e7446756e647304010120546f6f206869676820612062616c616e6365207761732070726f7669646564207468617420746865206163636f756e742063616e6e6f74206166666f72642e344e6f7444656c65676174696e6704a420546865206163636f756e74206973206e6f742063757272656e746c792064656c65676174696e672e28566f746573457869737408590120546865206163636f756e742063757272656e746c792068617320766f74657320617474616368656420746f20697420616e6420746865206f7065726174696f6e2063616e6e6f74207375636365656420756e74696cec207468657365206172652072656d6f7665642c20656974686572207468726f7567682060756e766f746560206f722060726561705f766f7465602e44496e7374616e744e6f74416c6c6f77656404dc2054686520696e7374616e74207265666572656e64756d206f726967696e2069732063757272656e746c7920646973616c6c6f7765642e204e6f6e73656e736504982044656c65676174696f6e20746f206f6e6573656c66206d616b6573206e6f2073656e73652e3c57726f6e675570706572426f756e64045420496e76616c696420757070657220626f756e642e3c4d6178566f746573526561636865640484204d6178696d756d206e756d626572206f6620766f74657320726561636865642e38496e76616c69645769746e6573730490205468652070726f7669646564207769746e65737320646174612069732077726f6e672e40546f6f4d616e7950726f706f73616c730494204d6178696d756d206e756d626572206f662070726f706f73616c7320726561636865642e0b1c436f756e63696c014c496e7374616e636531436f6c6c656374697665182450726f706f73616c73010090426f756e6465645665633c543a3a486173682c20543a3a4d617850726f706f73616c733e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368683c5420617320436f6e6669673c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e744964040004650120546865207072696d65206d656d62657220746861742068656c70732064657465726d696e65207468652064656661756c7420766f7465206265686176696f7220696e2063617365206f6620616273656e746174696f6e732e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c38f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e004d01205472616e73616374696f6e20666565732077696c6c2062652077616976656420696620746865206d656d62657220697320766f74696e67206f6e20616e7920706172746963756c61722070726f706f73616c690120666f72207468652066697273742074696d6520616e64207468652063616c6c206973207375636365737366756c2e2053756273657175656e7420766f7465206368616e6765732077696c6c206368617267652061206665652e2c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e78510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e0065012049662074686520636c6f7365206f7065726174696f6e20636f6d706c65746573207375636365737366756c6c79207769746820646973617070726f76616c2c20746865207472616e73616374696f6e206665652077696c6c6101206265207761697665642e204f746865727769736520657865637574696f6e206f662074686520617070726f766564206f7065726174696f6e2077696c6c206265206368617267656420746f207468652063616c6c65722e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed8205c5b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645c5d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292eac205c5b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5c5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e6c205c5b70726f706f73616c5f686173682c207965732c206e6f5c5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e0c48546563686e6963616c436f6d6d6974746565014c496e7374616e636532436f6c6c656374697665182450726f706f73616c73010090426f756e6465645665633c543a3a486173682c20543a3a4d617850726f706f73616c733e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368683c5420617320436f6e6669673c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e744964040004650120546865207072696d65206d656d62657220746861742068656c70732064657465726d696e65207468652064656661756c7420766f7465206265686176696f7220696e2063617365206f6620616273656e746174696f6e732e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c38f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e004d01205472616e73616374696f6e20666565732077696c6c2062652077616976656420696620746865206d656d62657220697320766f74696e67206f6e20616e7920706172746963756c61722070726f706f73616c690120666f72207468652066697273742074696d6520616e64207468652063616c6c206973207375636365737366756c2e2053756273657175656e7420766f7465206368616e6765732077696c6c206368617267652061206665652e2c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e78510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e0065012049662074686520636c6f7365206f7065726174696f6e20636f6d706c65746573207375636365737366756c6c79207769746820646973617070726f76616c2c20746865207472616e73616374696f6e206665652077696c6c6101206265207761697665642e204f746865727769736520657865637574696f6e206f662074686520617070726f766564206f7065726174696f6e2077696c6c206265206368617267656420746f207468652063616c6c65722e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed8205c5b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645c5d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292eac205c5b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5c5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e6c205c5b70726f706f73616c5f686173682c207965732c206e6f5c5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e0d24456c656374696f6e730124456c656374696f6e73141c4d656d626572730100ac5665633c53656174486f6c6465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e04000c74205468652063757272656e7420656c6563746564206d656d626572732e00b820496e76617269616e743a20416c7761797320736f72746564206261736564206f6e206163636f756e742069642e2452756e6e65727355700100ac5665633c53656174486f6c6465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e04001084205468652063757272656e742072657365727665642072756e6e6572732d75702e00590120496e76617269616e743a20416c7761797320736f72746564206261736564206f6e2072616e6b2028776f72736520746f2062657374292e2055706f6e2072656d6f76616c206f662061206d656d6265722c20746865bc206c6173742028692e652e205f626573745f292072756e6e65722d75702077696c6c206265207265706c616365642e2843616e646964617465730100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e0400185901205468652070726573656e742063616e646964617465206c6973742e20412063757272656e74206d656d626572206f722072756e6e65722d75702063616e206e6576657220656e746572207468697320766563746f72d020616e6420697320616c7761797320696d706c696369746c7920617373756d656420746f20626520612063616e6469646174652e007c205365636f6e6420656c656d656e7420697320746865206465706f7369742e00b820496e76617269616e743a20416c7761797320736f72746564206261736564206f6e206163636f756e742069642e38456c656374696f6e526f756e647301000c75333210000000000441012054686520746f74616c206e756d626572206f6620766f746520726f756e6473207468617420686176652068617070656e65642c206578636c7564696e6720746865207570636f6d696e67206f6e652e18566f74696e6701010530543a3a4163636f756e74496484566f7465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e00840000000000000000000000000000000000000000000000000000000000000000000cb820566f74657320616e64206c6f636b6564207374616b65206f66206120706172746963756c617220766f7465722e00c42054574f582d4e4f54453a205341464520617320604163636f756e7449646020697320612063727970746f20686173682e011810766f74650814766f746573445665633c543a3a4163636f756e7449643e1476616c756554436f6d706163743c42616c616e63654f663c543e3e5c5d0120566f746520666f72206120736574206f662063616e6469646174657320666f7220746865207570636f6d696e6720726f756e64206f6620656c656374696f6e2e20546869732063616e2062652063616c6c656420746fe4207365742074686520696e697469616c20766f7465732c206f722075706461746520616c7265616479206578697374696e6720766f7465732e0061012055706f6e20696e697469616c20766f74696e672c206076616c75656020756e697473206f66206077686f6027732062616c616e6365206973206c6f636b656420616e642061206465706f73697420616d6f756e7420697351012072657365727665642e20546865206465706f736974206973206261736564206f6e20746865206e756d626572206f6620766f74657320616e642063616e2062652075706461746564206f7665722074696d652e0050205468652060766f746573602073686f756c643a482020202d206e6f7420626520656d7074792e59012020202d206265206c657373207468616e20746865206e756d626572206f6620706f737369626c652063616e646964617465732e204e6f7465207468617420616c6c2063757272656e74206d656d6265727320616e641501202020202072756e6e6572732d75702061726520616c736f206175746f6d61746963616c6c792063616e6469646174657320666f7220746865206e65787420726f756e642e005101204966206076616c756560206973206d6f7265207468616e206077686f60277320746f74616c2062616c616e63652c207468656e20746865206d6178696d756d206f66207468652074776f20697320757365642e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642e003020232323205761726e696e670059012049742069732074686520726573706f6e736962696c697479206f66207468652063616c6c657220746f202a2a4e4f542a2a20706c61636520616c6c206f662074686569722062616c616e636520696e746f20746865ac206c6f636b20616e64206b65657020736f6d6520666f722066757274686572206f7065726174696f6e732e002c2023203c7765696768743e550120576520617373756d6520746865206d6178696d756d2077656967687420616d6f6e6720616c6c20332063617365733a20766f74655f657175616c2c20766f74655f6d6f726520616e6420766f74655f6c6573732e302023203c2f7765696768743e3072656d6f76655f766f7465720014702052656d6f766520606f726967696e60206173206120766f7465722e00bc20546869732072656d6f76657320746865206c6f636b20616e642072657475726e7320746865206465706f7369742e00010120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e656420616e64206265206120766f7465722e407375626d69745f63616e646964616379043c63616e6469646174655f636f756e7430436f6d706163743c7533323e3c1501205375626d6974206f6e6573656c6620666f722063616e6469646163792e204120666978656420616d6f756e74206f66206465706f736974206973207265636f726465642e00610120416c6c2063616e64696461746573206172652077697065642061742074686520656e64206f6620746865207465726d2e205468657920656974686572206265636f6d652061206d656d6265722f72756e6e65722d75702cd0206f72206c65617665207468652073797374656d207768696c65207468656972206465706f73697420697320736c61736865642e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642e003020232323205761726e696e67006101204576656e20696620612063616e64696461746520656e6473207570206265696e672061206d656d6265722c2074686579206d7573742063616c6c205b6043616c6c3a3a72656e6f756e63655f63616e646964616379605d5d0120746f20676574207468656972206465706f736974206261636b2e204c6f73696e67207468652073706f7420696e20616e20656c656374696f6e2077696c6c20616c77617973206c65616420746f206120736c6173682e002c2023203c7765696768743e0d0120546865206e756d626572206f662063757272656e742063616e64696461746573206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e4872656e6f756e63655f63616e646964616379042872656e6f756e63696e672852656e6f756e63696e674451012052656e6f756e6365206f6e65277320696e74656e74696f6e20746f20626520612063616e64696461746520666f7220746865206e65787420656c656374696f6e20726f756e642e203320706f74656e7469616c40206f7574636f6d65732065786973743a004d01202d20606f726967696e6020697320612063616e64696461746520616e64206e6f7420656c656374656420696e20616e79207365742e20496e207468697320636173652c20746865206465706f736974206973f4202020756e72657365727665642c2072657475726e656420616e64206f726967696e2069732072656d6f76656420617320612063616e6469646174652e6501202d20606f726967696e6020697320612063757272656e742072756e6e65722d75702e20496e207468697320636173652c20746865206465706f73697420697320756e72657365727665642c2072657475726e656420616e64902020206f726967696e2069732072656d6f76656420617320612072756e6e65722d75702e5901202d20606f726967696e6020697320612063757272656e74206d656d6265722e20496e207468697320636173652c20746865206465706f73697420697320756e726573657276656420616e64206f726967696e206973590120202072656d6f7665642061732061206d656d6265722c20636f6e73657175656e746c79206e6f74206265696e6720612063616e64696461746520666f7220746865206e65787420726f756e6420616e796d6f72652e550120202053696d696c617220746f205b6072656d6f76655f6d656d62657273605d2c206966207265706c6163656d656e742072756e6e657273206578697374732c20746865792061726520696d6d6564696174656c794d01202020757365642e20496620746865207072696d652069732072656e6f756e63696e672c207468656e206e6f207072696d652077696c6c20657869737420756e74696c20746865206e65787420726f756e642e00490120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642c20616e642068617665206f6e65206f66207468652061626f766520726f6c65732e002c2023203c7765696768743ee4205468652074797065206f662072656e6f756e63696e67206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e3472656d6f76655f6d656d626572080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653c6861735f7265706c6163656d656e7410626f6f6c385d012052656d6f7665206120706172746963756c6172206d656d6265722066726f6d20746865207365742e20546869732069732065666665637469766520696d6d6564696174656c7920616e642074686520626f6e64206f668020746865206f7574676f696e67206d656d62657220697320736c61736865642e00590120496620612072756e6e65722d757020697320617661696c61626c652c207468656e2074686520626573742072756e6e65722d75702077696c6c2062652072656d6f76656420616e64207265706c61636573207468650101206f7574676f696e67206d656d6265722e204f74686572776973652c2061206e65772070687261676d656e20656c656374696f6e20697320737461727465642e00bc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520726f6f742e004501204e6f74652074686174207468697320646f6573206e6f7420616666656374207468652064657369676e6174656420626c6f636b206e756d626572206f6620746865206e65787420656c656374696f6e2e002c2023203c7765696768743e550120496620776520686176652061207265706c6163656d656e742c20776520757365206120736d616c6c207765696768742e20456c73652c2073696e63652074686973206973206120726f6f742063616c6c20616e64d42077696c6c20676f20696e746f2070687261676d656e2c20776520617373756d652066756c6c20626c6f636b20666f72206e6f772e302023203c2f7765696768743e50636c65616e5f646566756e63745f766f74657273082c5f6e756d5f766f746572730c753332305f6e756d5f646566756e63740c75333228490120436c65616e20616c6c20766f746572732077686f2061726520646566756e63742028692e652e207468657920646f206e6f7420736572766520616e7920707572706f736520617420616c6c292e20546865b0206465706f736974206f66207468652072656d6f76656420766f74657273206172652072657475726e65642e000501205468697320697320616e20726f6f742066756e6374696f6e20746f2062652075736564206f6e6c7920666f7220636c65616e696e67207468652073746174652e00bc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520726f6f742e002c2023203c7765696768743e61012054686520746f74616c206e756d626572206f6620766f7465727320616e642074686f736520746861742061726520646566756e6374206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e011c1c4e65775465726d04645665633c284163636f756e7449642c2042616c616e6365293e1459012041206e6577207465726d2077697468205c5b6e65775f6d656d626572735c5d2e205468697320696e64696361746573207468617420656e6f7567682063616e64696461746573206578697374656420746f2072756e59012074686520656c656374696f6e2c206e6f74207468617420656e6f756768206861766520686173206265656e20656c65637465642e2054686520696e6e65722076616c7565206d757374206265206578616d696e6564490120666f72207468697320707572706f73652e204120604e65775465726d285c5b5c5d296020696e64696361746573207468617420736f6d652063616e6469646174657320676f7420746865697220626f6e64590120736c617368656420616e64206e6f6e65207765726520656c65637465642c207768696c73742060456d7074795465726d60206d65616e732074686174206e6f2063616e64696461746573206578697374656420746f3020626567696e20776974682e24456d7074795465726d00083501204e6f20286f72206e6f7420656e6f756768292063616e64696461746573206578697374656420666f72207468697320726f756e642e205468697320697320646966666572656e742066726f6dcc20604e65775465726d285c5b5c5d29602e2053656520746865206465736372697074696f6e206f6620604e65775465726d602e34456c656374696f6e4572726f720004e820496e7465726e616c206572726f722068617070656e6564207768696c6520747279696e6720746f20706572666f726d20656c656374696f6e2e304d656d6265724b69636b656404244163636f756e7449640855012041205c5b6d656d6265725c5d20686173206265656e2072656d6f7665642e20546869732073686f756c6420616c7761797320626520666f6c6c6f7765642062792065697468657220604e65775465726d60206f72342060456d7074795465726d602e2452656e6f756e63656404244163636f756e744964049c20536f6d656f6e65206861732072656e6f756e6365642074686569722063616e6469646163792e4043616e646964617465536c617368656408244163636f756e7449641c42616c616e6365105d012041205c5b63616e6469646174655c5d2077617320736c6173686564206279205c5b616d6f756e745c5d2064756520746f206661696c696e6720746f206f627461696e20612073656174206173206d656d626572206f722c2072756e6e65722d75702e00e8204e6f74652074686174206f6c64206d656d6265727320616e642072756e6e6572732d75702061726520616c736f2063616e646964617465732e4453656174486f6c646572536c617368656408244163636f756e7449641c42616c616e63650459012041205c5b7365617420686f6c6465725c5d2077617320736c6173686564206279205c5b616d6f756e745c5d206279206265696e6720666f72636566756c6c792072656d6f7665642066726f6d20746865207365742e1c2050616c6c65744964384c6f636b4964656e74696669657220706872656c65637404d0204964656e74696669657220666f722074686520656c656374696f6e732d70687261676d656e2070616c6c65742773206c6f636b3443616e646964616379426f6e643042616c616e63654f663c543e400080c6a47e8d0300000000000000000004050120486f77206d7563682073686f756c64206265206c6f636b656420757020696e206f7264657220746f207375626d6974206f6e6527732063616e6469646163792e38566f74696e67426f6e64426173653042616c616e63654f663c543e4000f0436de36a0100000000000000000010942042617365206465706f736974206173736f636961746564207769746820766f74696e672e00550120546869732073686f756c642062652073656e7369626c79206869676820746f2065636f6e6f6d6963616c6c7920656e73757265207468652070616c6c65742063616e6e6f742062652061747461636b656420627994206372656174696e67206120676967616e746963206e756d626572206f6620766f7465732e40566f74696e67426f6e64466163746f723042616c616e63654f663c543e400000cc7b9fae000000000000000000000411012054686520616d6f756e74206f6620626f6e642074686174206e65656420746f206265206c6f636b656420666f72206561636820766f746520283332206279746573292e38446573697265644d656d626572730c753332100d0000000470204e756d626572206f66206d656d6265727320746f20656c6563742e404465736972656452756e6e65727355700c75333210070000000478204e756d626572206f662072756e6e6572735f757020746f206b6565702e305465726d4475726174696f6e38543a3a426c6f636b4e756d62657210801303000c510120486f77206c6f6e6720656163682073656174206973206b6570742e205468697320646566696e657320746865206e65787420626c6f636b206e756d62657220617420776869636820616e20656c656374696f6e5d0120726f756e642077696c6c2068617070656e2e2049662073657420746f207a65726f2c206e6f20656c656374696f6e732061726520657665722074726967676572656420616e6420746865206d6f64756c652077696c6c5020626520696e2070617373697665206d6f64652e4430556e61626c65546f566f746504c42043616e6e6f7420766f7465207768656e206e6f2063616e64696461746573206f72206d656d626572732065786973742e1c4e6f566f7465730498204d75737420766f746520666f72206174206c65617374206f6e652063616e6469646174652e30546f6f4d616e79566f74657304882043616e6e6f7420766f7465206d6f7265207468616e2063616e646964617465732e504d6178696d756d566f7465734578636565646564049c2043616e6e6f7420766f7465206d6f7265207468616e206d6178696d756d20616c6c6f7765642e284c6f7742616c616e636504c82043616e6e6f7420766f74652077697468207374616b65206c657373207468616e206d696e696d756d2062616c616e63652e3c556e61626c65546f506179426f6e64047c20566f7465722063616e206e6f742070617920766f74696e6720626f6e642e2c4d7573744265566f7465720444204d757374206265206120766f7465722e285265706f727453656c6604502043616e6e6f74207265706f72742073656c662e4c4475706c69636174656443616e6469646174650484204475706c6963617465642063616e646964617465207375626d697373696f6e2e304d656d6265725375626d6974048c204d656d6265722063616e6e6f742072652d7375626d69742063616e6469646163792e3852756e6e657255705375626d6974048c2052756e6e65722063616e6e6f742072652d7375626d69742063616e6469646163792e68496e73756666696369656e7443616e64696461746546756e647304982043616e64696461746520646f6573206e6f74206861766520656e6f7567682066756e64732e244e6f744d656d6265720438204e6f742061206d656d6265722e48496e76616c69645769746e6573734461746104e4205468652070726f766964656420636f756e74206f66206e756d626572206f662063616e6469646174657320697320696e636f72726563742e40496e76616c6964566f7465436f756e7404d0205468652070726f766964656420636f756e74206f66206e756d626572206f6620766f74657320697320696e636f72726563742e44496e76616c696452656e6f756e63696e67040101205468652072656e6f756e63696e67206f726967696e2070726573656e74656420612077726f6e67206052656e6f756e63696e676020706172616d657465722e48496e76616c69645265706c6163656d656e740401012050726564696374696f6e20726567617264696e67207265706c6163656d656e74206166746572206d656d6265722072656d6f76616c2069732077726f6e672e0e4c546563686e6963616c4d656d62657273686970014c496e7374616e6365314d656d62657273686970081c4d656d626572730100445665633c543a3a4163636f756e7449643e040004c8205468652063757272656e74206d656d626572736869702c2073746f72656420617320616e206f726465726564205665632e145072696d65000030543a3a4163636f756e744964040004a4205468652063757272656e74207072696d65206d656d6265722c206966206f6e65206578697374732e011c286164645f6d656d626572040c77686f30543a3a4163636f756e7449640c7c204164642061206d656d626572206077686f6020746f20746865207365742e00a0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a4164644f726967696e602e3472656d6f76655f6d656d626572040c77686f30543a3a4163636f756e7449640c902052656d6f76652061206d656d626572206077686f602066726f6d20746865207365742e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656d6f76654f726967696e602e2c737761705f6d656d626572081872656d6f766530543a3a4163636f756e7449640c61646430543a3a4163636f756e74496414c02053776170206f7574206f6e65206d656d626572206072656d6f76656020666f7220616e6f746865722060616464602e00a4204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a537761704f726967696e602e001101205072696d65206d656d62657273686970206973202a6e6f742a207061737365642066726f6d206072656d6f76656020746f2060616464602c20696620657874616e742e3472657365745f6d656d62657273041c6d656d62657273445665633c543a3a4163636f756e7449643e105901204368616e676520746865206d656d6265727368697020746f2061206e6577207365742c20646973726567617264696e6720746865206578697374696e67206d656d626572736869702e204265206e69636520616e646c207061737320606d656d6265727360207072652d736f727465642e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52657365744f726967696e602e286368616e67655f6b6579040c6e657730543a3a4163636f756e74496414d82053776170206f7574207468652073656e64696e67206d656d62657220666f7220736f6d65206f74686572206b657920606e6577602e00f4204d6179206f6e6c792062652063616c6c65642066726f6d20605369676e656460206f726967696e206f6620612063757272656e74206d656d6265722e002101205072696d65206d656d62657273686970206973207061737365642066726f6d20746865206f726967696e206163636f756e7420746f20606e6577602c20696620657874616e742e247365745f7072696d65040c77686f30543a3a4163636f756e7449640cc02053657420746865207072696d65206d656d6265722e204d75737420626520612063757272656e74206d656d6265722e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e2c636c6561725f7072696d65000c982052656d6f766520746865207072696d65206d656d626572206966206974206578697374732e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e01182c4d656d62657241646465640004e42054686520676976656e206d656d626572207761732061646465643b2073656520746865207472616e73616374696f6e20666f722077686f2e344d656d62657252656d6f7665640004ec2054686520676976656e206d656d626572207761732072656d6f7665643b2073656520746865207472616e73616374696f6e20666f722077686f2e384d656d62657273537761707065640004dc2054776f206d656d62657273207765726520737761707065643b2073656520746865207472616e73616374696f6e20666f722077686f2e304d656d6265727352657365740004190120546865206d656d62657273686970207761732072657365743b2073656520746865207472616e73616374696f6e20666f722077686f20746865206e6577207365742069732e284b65794368616e676564000488204f6e65206f6620746865206d656d6265727327206b657973206368616e6765642e1444756d6d7904bc73705f7374643a3a6d61726b65723a3a5068616e746f6d446174613c284163636f756e7449642c204576656e74293e0470205068616e746f6d206d656d6265722c206e6576657220757365642e000834416c72656164794d656d626572044820416c72656164792061206d656d6265722e244e6f744d656d6265720438204e6f742061206d656d6265722e0f1c4772616e647061013c4772616e64706146696e616c6974791814537461746501006c53746f72656453746174653c543a3a426c6f636b4e756d6265723e04000490205374617465206f66207468652063757272656e7420617574686f72697479207365742e3450656e64696e674368616e676500008c53746f72656450656e64696e674368616e67653c543a3a426c6f636b4e756d6265723e040004c42050656e64696e67206368616e67653a20287369676e616c65642061742c207363686564756c6564206368616e6765292e284e657874466f72636564000038543a3a426c6f636b4e756d626572040004bc206e65787420626c6f636b206e756d6265722077686572652077652063616e20666f7263652061206368616e67652e1c5374616c6c656400008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d626572290400049020607472756560206966207765206172652063757272656e746c79207374616c6c65642e3043757272656e7453657449640100145365744964200000000000000000085d0120546865206e756d626572206f66206368616e6765732028626f746820696e207465726d73206f66206b65797320616e6420756e6465726c79696e672065636f6e6f6d696320726573706f6e736962696c697469657329c420696e20746865202273657422206f66204772616e6470612076616c696461746f72732066726f6d2067656e657369732e30536574496453657373696f6e0001051453657449643053657373696f6e496e6465780004001059012041206d617070696e672066726f6d206772616e6470612073657420494420746f2074686520696e646578206f6620746865202a6d6f737420726563656e742a2073657373696f6e20666f722077686963682069747368206d656d62657273207765726520726573706f6e7369626c652e00b82054574f582d4e4f54453a2060536574496460206973206e6f7420756e646572207573657220636f6e74726f6c2e010c4c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66240d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e00110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e306e6f74655f7374616c6c6564081464656c617938543a3a426c6f636b4e756d6265726c626573745f66696e616c697a65645f626c6f636b5f6e756d62657238543a3a426c6f636b4e756d6265721c1d01204e6f74652074686174207468652063757272656e7420617574686f7269747920736574206f6620746865204752414e4450412066696e616c69747920676164676574206861732901207374616c6c65642e20546869732077696c6c2074726967676572206120666f7263656420617574686f7269747920736574206368616e67652061742074686520626567696e6e696e672101206f6620746865206e6578742073657373696f6e2c20746f20626520656e6163746564206064656c61796020626c6f636b7320616674657220746861742e205468652064656c617915012073686f756c64206265206869676820656e6f75676820746f20736166656c7920617373756d6520746861742074686520626c6f636b207369676e616c6c696e6720746865290120666f72636564206368616e67652077696c6c206e6f742062652072652d6f726765642028652e672e203130303020626c6f636b73292e20546865204752414e44504120766f7465727329012077696c6c20737461727420746865206e657720617574686f7269747920736574207573696e672074686520676976656e2066696e616c697a656420626c6f636b20617320626173652e5c204f6e6c792063616c6c61626c6520627920726f6f742e010c384e6577417574686f7269746965730434417574686f726974794c69737404d8204e657720617574686f726974792073657420686173206265656e206170706c6965642e205c5b617574686f726974795f7365745c5d1850617573656400049c2043757272656e7420617574686f726974792073657420686173206265656e207061757365642e1c526573756d65640004a02043757272656e7420617574686f726974792073657420686173206265656e20726573756d65642e001c2c50617573654661696c656408090120417474656d707420746f207369676e616c204752414e445041207061757365207768656e2074686520617574686f72697479207365742069736e2774206c697665a8202865697468657220706175736564206f7220616c72656164792070656e64696e67207061757365292e30526573756d654661696c656408150120417474656d707420746f207369676e616c204752414e44504120726573756d65207768656e2074686520617574686f72697479207365742069736e277420706175736564a42028656974686572206c697665206f7220616c72656164792070656e64696e6720726573756d65292e344368616e676550656e64696e6704ec20417474656d707420746f207369676e616c204752414e445041206368616e67652077697468206f6e6520616c72656164792070656e64696e672e1c546f6f536f6f6e04c02043616e6e6f74207369676e616c20666f72636564206368616e676520736f20736f6f6e206166746572206c6173742e60496e76616c69644b65794f776e65727368697050726f6f660435012041206b6579206f776e6572736869702070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e60496e76616c696445717569766f636174696f6e50726f6f6604350120416e2065717569766f636174696f6e2070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e584475706c69636174654f6666656e63655265706f7274041901204120676976656e2065717569766f636174696f6e207265706f72742069732076616c69642062757420616c72656164792070726576696f75736c79207265706f727465642e10205472656173757279012054726561737572790c3450726f706f73616c436f756e7401003450726f706f73616c496e646578100000000004a4204e756d626572206f662070726f706f73616c7320746861742068617665206265656e206d6164652e2450726f706f73616c730001053450726f706f73616c496e6465789c50726f706f73616c3c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e000400047c2050726f706f73616c7320746861742068617665206265656e206d6164652e24417070726f76616c730100a8426f756e6465645665633c50726f706f73616c496e6465782c20543a3a4d6178417070726f76616c733e040004f82050726f706f73616c20696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f742079657420617761726465642e010c3470726f706f73655f7370656e64081476616c756560436f6d706163743c42616c616e63654f663c542c20493e3e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365242d012050757420666f727761726420612073756767657374696f6e20666f72207370656e64696e672e2041206465706f7369742070726f706f7274696f6e616c20746f207468652076616c7565350120697320726573657276656420616e6420736c6173686564206966207468652070726f706f73616c2069732072656a65637465642e2049742069732072657475726e6564206f6e636520746865542070726f706f73616c20697320617761726465642e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129b4202d20446252656164733a206050726f706f73616c436f756e74602c20606f726967696e206163636f756e7460ec202d2044625772697465733a206050726f706f73616c436f756e74602c206050726f706f73616c73602c20606f726967696e206163636f756e7460302023203c2f7765696768743e3c72656a6563745f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e24fc2052656a65637420612070726f706f736564207370656e642e20546865206f726967696e616c206465706f7369742077696c6c20626520736c61736865642e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656a6563744f726967696e602e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129d0202d20446252656164733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460d4202d2044625772697465733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460302023203c2f7765696768743e40617070726f76655f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e285d0120417070726f766520612070726f706f73616c2e2041742061206c617465722074696d652c207468652070726f706f73616c2077696c6c20626520616c6c6f636174656420746f207468652062656e6566696369617279ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e50202d20436f6d706c65786974793a204f2831292e90202d20446252656164733a206050726f706f73616c73602c2060417070726f76616c73605c202d20446257726974653a2060417070726f76616c7360302023203c2f7765696768743e011c2050726f706f736564043450726f706f73616c496e6465780484204e65772070726f706f73616c2e205c5b70726f706f73616c5f696e6465785c5d205370656e64696e67041c42616c616e6365043d01205765206861766520656e6465642061207370656e6420706572696f6420616e642077696c6c206e6f7720616c6c6f636174652066756e64732e205c5b6275646765745f72656d61696e696e675c5d1c417761726465640c3450726f706f73616c496e6465781c42616c616e6365244163636f756e744964041d0120536f6d652066756e64732068617665206265656e20616c6c6f63617465642e205c5b70726f706f73616c5f696e6465782c2061776172642c2062656e65666963696172795c5d2052656a6563746564083450726f706f73616c496e6465781c42616c616e636504250120412070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e205c5b70726f706f73616c5f696e6465782c20736c61736865645c5d144275726e74041c42616c616e636504b020536f6d65206f66206f75722066756e64732068617665206265656e206275726e742e205c5b6275726e5c5d20526f6c6c6f766572041c42616c616e6365083101205370656e64696e67206861732066696e69736865643b20746869732069732074686520616d6f756e74207468617420726f6c6c73206f76657220756e74696c206e657874207370656e642e54205c5b6275646765745f72656d61696e696e675c5d1c4465706f736974041c42616c616e636504b020536f6d652066756e64732068617665206265656e206465706f73697465642e205c5b6465706f7369745c5d143050726f706f73616c426f6e641c5065726d696c6c1050c30000085501204672616374696f6e206f6620612070726f706f73616c27732076616c756520746861742073686f756c6420626520626f6e64656420696e206f7264657220746f20706c616365207468652070726f706f73616c2e110120416e2061636365707465642070726f706f73616c2067657473207468657365206261636b2e20412072656a65637465642070726f706f73616c20646f6573206e6f742e4c50726f706f73616c426f6e644d696e696d756d3c42616c616e63654f663c542c20493e4000407a10f35a00000000000000000000044901204d696e696d756d20616d6f756e74206f662066756e647320746861742073686f756c6420626520706c6163656420696e2061206465706f73697420666f72206d616b696e6720612070726f706f73616c2e2c5370656e64506572696f6438543a3a426c6f636b4e756d6265721080700000048820506572696f64206265747765656e2073756363657373697665207370656e64732e104275726e1c5065726d696c6c1020a107000411012050657263656e74616765206f662073706172652066756e64732028696620616e7929207468617420617265206275726e7420706572207370656e6420706572696f642e2050616c6c657449642050616c6c657449642070792f7472737279041901205468652074726561737572792773206d6f64756c652069642c207573656420666f72206465726976696e672069747320736f7665726569676e206163636f756e742049442e0c70496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e30496e76616c6964496e6465780494204e6f2070726f706f73616c206f7220626f756e7479206174207468617420696e6465782e40546f6f4d616e79417070726f76616c73048420546f6f206d616e7920617070726f76616c7320696e207468652071756575652e1124436f6e7472616374730124436f6e747261637473183c43757272656e745363686564756c6501002c5363686564756c653c543e450a000000000004000000000200000001000080000000100000000010000000010000200000001f060000d66a0200dd84030026180000bd1c0000430b000003170000ae2800009c000000dd69010063e00200300700000706000065070000b10500006e180000002800006905000072deae08f0070000dc070000710a00006a080000a507000096070000d1070000770900003e09000075090000d809000082090000bc090000120900003c09000072090000dc090000f7080000e108000062090000162000006b1d00002e2000002c1b0000fe080000000900000f090000a7090000f1090000ba090000bb09000065090000d8b82800000000009e9828000000000016902700000000004c705700000000004cc8270000000000e4bc270000000000e8d1270000000000a0685b0000000000484f2700000000009e7627000000000000f45100000000004cab120000000000184a700000000000140100000000000000cd460000000000fc02000000000000d0b570270000000013200000000000007821da3100000000e0200000000000009a120000000000000482b10900000000e03463000000000038d7900000000000de67d00700000000840900000000000006186e000000000016935d1200000000da02000000000000eaced408000000003a240e0200000000e705000000000000fc41d50a00000000d48e9309000000002d0f0000000000003a4225090000000047020000000000002303000000000000ba7c962300000000a5210000000000006d020000000000005403000000000000e50b00000000000026922400000000006110000000000000a4122600000000001d0d000000000000520e2200000000001a0600000000000020222200000000001a0600000000000044b13c000000000004942043757272656e7420636f7374207363686564756c6520666f7220636f6e7472616374732e305072697374696e65436f64650001062c436f6465486173683c543e1c5665633c75383e0004000465012041206d617070696e672066726f6d20616e206f726967696e616c20636f6465206861736820746f20746865206f726967696e616c20636f64652c20756e746f756368656420627920696e737472756d656e746174696f6e2e2c436f646553746f726167650001062c436f6465486173683c543e4c5072656661625761736d4d6f64756c653c543e0004000465012041206d617070696e67206265747765656e20616e206f726967696e616c20636f6465206861736820616e6420696e737472756d656e746564207761736d20636f64652c20726561647920666f7220657865637574696f6e2e384163636f756e74436f756e74657201000c753634200000000000000000045420546865207375627472696520636f756e7465722e38436f6e7472616374496e666f4f6600010530543a3a4163636f756e7449643c436f6e7472616374496e666f3c543e0004000ca82054686520636f6465206173736f6369617465642077697468206120676976656e206163636f756e742e00d02054574f582d4e4f54453a20534146452073696e636520604163636f756e7449646020697320612073656375726520686173682e3444656c6574696f6e51756575650100505665633c44656c65746564436f6e74726163743e040010c8204576696374656420636f6e7472616374732074686174206177616974206368696c6420747269652064656c6574696f6e2e004901204368696c6420747269652064656c6574696f6e2069732061206865617679206f7065726174696f6e20646570656e64696e67206f6e2074686520616d6f756e74206f662073746f72616765206974656d7359012073746f72656420696e207361696420747269652e205468657265666f72652074686973206f7065726174696f6e20697320706572666f726d6564206c617a696c7920696e20606f6e5f696e697469616c697a65602e01143c7570646174655f7363686564756c6504207363686564756c652c5363686564756c653c543e18b4205570646174657320746865207363686564756c6520666f72206d65746572696e6720636f6e7472616374732e003d0120546865207363686564756c6527732076657273696f6e2063616e6e6f74206265206c657373207468616e207468652076657273696f6e206f66207468652073746f726564207363686564756c652e2d012049662061207363686564756c6520646f6573206e6f74206368616e67652074686520696e737472756374696f6e2077656967687473207468652076657273696f6e20646f6573206e6f743901206e65656420746f20626520696e637265617365642e205468657265666f726520776520616c6c6f772073746f72696e672061207363686564756c65207468617420686173207468652073616d656c2076657273696f6e206173207468652073746f726564206f6e652e1063616c6c1010646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e10646174611c5665633c75383e1c0901204d616b657320612063616c6c20746f20616e206163636f756e742c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e002901202a20496620746865206163636f756e74206973206120736d6172742d636f6e7472616374206163636f756e742c20746865206173736f63696174656420636f64652077696c6c206265b020657865637574656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e1901202a20496620746865206163636f756e74206973206120726567756c6172206163636f756e742c20616e792076616c75652077696c6c206265207472616e736665727265642e4901202a204966206e6f206163636f756e742065786973747320616e64207468652063616c6c2076616c7565206973206e6f74206c657373207468616e20606578697374656e7469616c5f6465706f736974602c1501206120726567756c6172206163636f756e742077696c6c206265206372656174656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e54696e7374616e74696174655f776974685f636f64651424656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e10636f64651c5665633c75383e10646174611c5665633c75383e1073616c741c5665633c75383e54350120496e7374616e7469617465732061206e657720636f6e74726163742066726f6d2074686520737570706c6965642060636f646560206f7074696f6e616c6c79207472616e7366657272696e673820736f6d652062616c616e63652e000501205468697320697320746865206f6e6c792066756e6374696f6e20746861742063616e206465706c6f79206e657720636f646520746f2074686520636861696e2e0034202320506172616d6574657273006101202a2060656e646f776d656e74603a205468652062616c616e636520746f207472616e736665722066726f6d2074686520606f726967696e6020746f20746865206e65776c79206372656174656420636f6e74726163742e1901202a20606761735f6c696d6974603a2054686520676173206c696d697420656e666f72636564207768656e20657865637574696e672074686520636f6e7374727563746f722ed0202a2060636f6465603a2054686520636f6e747261637420636f646520746f206465706c6f7920696e207261772062797465732ef8202a206064617461603a2054686520696e707574206461746120746f207061737320746f2074686520636f6e747261637420636f6e7374727563746f722e3501202a206073616c74603a205573656420666f722074686520616464726573732064657269766174696f6e2e20536565205b6050616c6c65743a3a636f6e74726163745f61646472657373605d2e009820496e7374616e74696174696f6e20697320657865637574656420617320666f6c6c6f77733a007501202d2054686520737570706c6965642060636f64656020697320696e737472756d656e7465642c206465706c6f7965642c20616e6420612060636f64655f6861736860206973206372656174656420666f72207468617420636f64652e5d01202d204966207468652060636f64655f686173686020616c726561647920657869737473206f6e2074686520636861696e2074686520756e6465726c79696e672060636f6465602077696c6c206265207368617265642e4d01202d205468652064657374696e6174696f6e206164647265737320697320636f6d7075746564206261736564206f6e207468652073656e6465722c20636f64655f6861736820616e64207468652073616c742e0501202d2054686520736d6172742d636f6e7472616374206163636f756e7420697320637265617465642061742074686520636f6d707574656420616464726573732ed4202d205468652060656e646f776d656e7460206973207472616e7366657272656420746f20746865206e6577206163636f756e742e4501202d2054686520606465706c6f79602066756e6374696f6e20697320657865637574656420696e2074686520636f6e74657874206f6620746865206e65776c792d63726561746564206163636f756e742e2c696e7374616e74696174651424656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e24636f64655f686173682c436f6465486173683c543e10646174611c5665633c75383e1073616c741c5665633c75383e14010120496e7374616e746961746573206120636f6e74726163742066726f6d20612070726576696f75736c79206465706c6f796564207761736d2062696e6172792e00390120546869732066756e6374696f6e206973206964656e746963616c20746f205b6053656c663a3a696e7374616e74696174655f776974685f636f6465605d2062757420776974686f7574207468654d0120636f6465206465706c6f796d656e7420737465702e20496e73746561642c207468652060636f64655f6861736860206f6620616e206f6e2d636861696e206465706c6f796564207761736d2062696e61727948206d75737420626520737570706c6965642e3c636c61696d5f73757263686172676508106465737430543a3a4163636f756e744964286175785f73656e646572504f7074696f6e3c543a3a4163636f756e7449643e244d0120416c6c6f777320626c6f636b2070726f64756365727320746f20636c61696d206120736d616c6c2072657761726420666f72206576696374696e67206120636f6e74726163742e204966206120626c6f636b39012070726f6475636572206661696c7320746f20646f20736f2c206120726567756c61722075736572732077696c6c20626520616c6c6f77656420746f20636c61696d20746865207265776172642e004d0120496e2063617365206f662061207375636365737366756c206576696374696f6e206e6f20666565732061726520636861726765642066726f6d207468652073656e6465722e20486f77657665722c20746865490120726577617264206973206361707065642062792074686520746f74616c20616d6f756e74206f662072656e742074686174207761732070617965642062792074686520636f6e7472616374207768696c65382069742077617320616c6976652e00550120496620636f6e7472616374206973206e6f742065766963746564206173206120726573756c74206f6620746869732063616c6c2c205b604572726f723a3a436f6e74726163744e6f74457669637461626c65605dec2069732072657475726e656420616e64207468652073656e646572206973206e6f7420656c696769626c6520666f7220746865207265776172642e012030496e7374616e74696174656408244163636f756e744964244163636f756e74496404390120436f6e7472616374206465706c6f7965642062792061646472657373206174207468652073706563696669656420616464726573732e205c5b6465706c6f7965722c20636f6e74726163745c5d1c4576696374656404244163636f756e74496404190120436f6e747261637420686173206265656e206576696374656420616e64206973206e6f7720696e20746f6d6273746f6e652073746174652e205c5b636f6e74726163745c5d285465726d696e6174656408244163636f756e744964244163636f756e74496430e820436f6e747261637420686173206265656e207465726d696e6174656420776974686f7574206c656176696e67206120746f6d6273746f6e652e68205c5b636f6e74726163742c2062656e65666963696172795c5d0024202320506172616d7300c0202d2060636f6e7472616374603a2054686520636f6e7472616374207468617420776173207465726d696e617465642e3101202d206062656e6566696369617279603a20546865206163636f756e7420746861742072656365697665642074686520636f6e7472616374732072656d61696e696e672062616c616e63652e001c2023204e6f7465002d0120546865206f6e6c792077617920666f72206120636f6e747261637420746f2062652072656d6f76656420776974686f7574206120746f6d6273746f6e6520616e6420656d697474696e67ac2074686973206576656e742069732062792063616c6c696e6720607365616c5f7465726d696e617465602e20526573746f72656410244163636f756e744964244163636f756e74496410486173681c42616c616e636524bc20526573746f726174696f6e206f66206120636f6e747261637420686173206265656e207375636365737366756c2eb8205c5b726573746f7265722c20646573742c20636f64655f686173682c2072656e745f616c6c6f77616e63655c5d0024202320506172616d7300d0202d2060726573746f726572603a204163636f756e74204944206f662074686520726573746f72696e6720636f6e74726163742ebc202d206064657374603a204163636f756e74204944206f662074686520726573746f72656420636f6e74726163742ecc202d2060636f64655f68617368603a20436f64652068617368206f662074686520726573746f72656420636f6e74726163742ef4202d206072656e745f616c6c6f77616e6365603a2052656e7420616c6c6f77616e6365206f662074686520726573746f72656420636f6e74726163742e28436f646553746f72656404104861736804f020436f646520776974682074686520737065636966696564206861736820686173206265656e2073746f7265642e205c5b636f64655f686173685c5d3c5363686564756c6555706461746564040c75333218c020547269676765726564207768656e207468652063757272656e74207363686564756c6520697320757064617465642e30205c5b76657273696f6e5c5d0024202320506172616d7300d0202d206076657273696f6e603a205468652076657273696f6e206f6620746865206e65776c7920736574207363686564756c652e3c436f6e7472616374456d697474656408244163636f756e7449641c5665633c75383e20a0204120637573746f6d206576656e7420656d69747465642062792074686520636f6e74726163742e4c205c5b636f6e74726163742c20646174615c5d0024202320506172616d7300cc202d2060636f6e7472616374603a2054686520636f6e7472616374207468617420656d697474656420746865206576656e742e3101202d206064617461603a204461746120737570706c6965642062792074686520636f6e74726163742e204d657461646174612067656e65726174656420647572696e6720636f6e7472616374b82020202020202020202020636f6d70696c6174696f6e206973206e656564656420746f206465636f64652069742e2c436f646552656d6f76656404104861736810b0204120636f6465207769746820746865207370656369666965642068617368207761732072656d6f7665642e38205c5b636f64655f686173685c5d00550120546869732068617070656e73207768656e20746865206c61737420636f6e747261637420746861742075736573207468697320636f64652068617368207761732072656d6f766564206f7220657669637465642e304c5369676e6564436c61696d48616e646963617038543a3a426c6f636b4e756d626572100200000010e0204e756d626572206f6620626c6f636b2064656c617920616e2065787472696e73696320636c61696d20737572636861726765206861732e000d01205768656e20636c61696d207375726368617267652069732063616c6c656420627920616e2065787472696e736963207468652072656e7420697320636865636b65646820666f722063757272656e745f626c6f636b202d2064656c617940546f6d6273746f6e654465706f7369743042616c616e63654f663c543e4000f0e8857a9c0200000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f2067656e6572617465206120746f6d6273746f6e652e484465706f736974506572436f6e74726163743042616c616e63654f663c543e4000f0e8857a9c02000000000000000000202101205468652062616c616e636520657665727920636f6e7472616374206e6565647320746f206465706f73697420746f207374617920616c69766520696e646566696e6974656c792e005101205468697320697320646966666572656e742066726f6d20746865205b6053656c663a3a546f6d6273746f6e654465706f736974605d20626563617573652074686973206f6e6c79206e6565647320746f2062654501206465706f7369746564207768696c652074686520636f6e747261637420697320616c6976652e20436f73747320666f72206164646974696f6e616c2073746f726167652061726520616464656420746f402074686973206261736520636f73742e006d01205468697320697320612073696d706c652077617920746f20656e73757265207468617420636f6e747261637473207769746820656d7074792073746f72616765206576656e7475616c6c79206765742064656c657465642062797101206d616b696e67207468656d207061792072656e742e2054686973206372656174657320616e20696e63656e7469766520746f2072656d6f7665207468656d206561726c7920696e206f7264657220746f20736176652072656e742e544465706f73697450657253746f72616765427974653042616c616e63654f663c543e400060defb740500000000000000000000185501205468652062616c616e6365206120636f6e7472616374206e6565647320746f206465706f736974207065722073746f72616765206279746520746f207374617920616c69766520696e646566696e6974656c792e006901204c6574277320737570706f736520746865206465706f73697420697320312c303030204255202862616c616e636520756e697473292f6279746520616e64207468652072656e7420697320312042552f627974652f6461792c5901207468656e206120636f6e7472616374207769746820312c3030302c3030302042552074686174207573657320312c303030206279746573206f662073746f7261676520776f756c6420706179206e6f2072656e742e4d0120427574206966207468652062616c616e6365207265647563656420746f203530302c30303020425520616e64207468652073746f7261676520737461796564207468652073616d6520617420312c3030302c78207468656e20697420776f756c6420706179203530302042552f6461792e544465706f73697450657253746f726167654974656d3042616c616e63654f663c543e4000f0ab75a40d000000000000000000000c5501205468652062616c616e6365206120636f6e7472616374206e6565647320746f206465706f736974207065722073746f72616765206974656d20746f207374617920616c69766520696e646566696e6974656c792e00310120497420776f726b73207468652073616d65206173205b6053656c663a3a4465706f73697450657253746f7261676542797465605d2062757420666f722073746f72616765206974656d732e3052656e744672616374696f6e1c50657262696c6c1085040000140d0120546865206672616374696f6e206f6620746865206465706f73697420746861742073686f756c6420626520757365642061732072656e742070657220626c6f636b2e005101205768656e206120636f6e7472616374206861736e277420656e6f7567682062616c616e6365206465706f736974656420746f207374617920616c69766520696e646566696e6974656c79206974206e65656473450120746f207061792070657220626c6f636b20666f72207468652073746f7261676520697420636f6e73756d65732074686174206973206e6f7420636f766572656420627920746865206465706f7369742e590120546869732064657465726d696e657320686f77206869676820746869732072656e74207061796d656e742069732070657220626c6f636b2061732061206672616374696f6e206f6620746865206465706f7369742e3c5375726368617267655265776172643042616c616e63654f663c543e40005cb2ec22000000000000000000000008e4205265776172642074686174206973207265636569766564206279207468652070617274792077686f736520746f75636820686173206c65646820746f2072656d6f76616c206f66206120636f6e74726163742e204d617844657074680c753332102000000004dc20546865206d6178696d756d206e657374696e67206c6576656c206f6620612063616c6c2f696e7374616e746961746520737461636b2e304d617856616c756553697a650c753332100040000004010120546865206d6178696d756d2073697a65206f6620612073746f726167652076616c756520616e64206576656e74207061796c6f616420696e2062797465732e4844656c6574696f6e517565756544657074680c75333210f000000004f420546865206d6178696d756d206e756d626572206f6620747269657320746861742063616e2062652071756575656420666f722064656c6574696f6e2e4c44656c6574696f6e5765696768744c696d6974185765696768742000d0ed902e000000044d0120546865206d6178696d756d20616d6f756e74206f662077656967687420746861742063616e20626520636f6e73756d65642070657220626c6f636b20666f72206c617a7920747269652072656d6f76616c2e2c4d6178436f646553697a650c75333210000002000c5d0120546865206d6178696d756d206c656e677468206f66206120636f6e747261637420636f646520696e2062797465732e2054686973206c696d6974206170706c69657320746f2074686520696e737472756d656e74656451012076657273696f6e206f662074686520636f64652e205468657265666f72652060696e7374616e74696174655f776974685f636f6465602063616e206661696c206576656e207768656e20737570706c79696e679c2061207761736d2062696e6172792062656c6f772074686973206d6178696d756d2073697a652e7458496e76616c69645363686564756c6556657273696f6e0405012041206e6577207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652063757272656e74206f6e652e54496e76616c6964537572636861726765436c61696d04550120416e206f726967696e206d757374206265207369676e6564206f7220696e686572656e7420616e6420617578696c696172792073656e646572206f6e6c792070726f7669646564206f6e20696e686572656e742e54496e76616c6964536f75726365436f6e747261637404dc2043616e6e6f7420726573746f72652066726f6d206e6f6e6578697374696e67206f7220746f6d6273746f6e6520636f6e74726163742e68496e76616c696444657374696e6174696f6e436f6e747261637404c42043616e6e6f7420726573746f726520746f206e6f6e6578697374696e67206f7220616c69766520636f6e74726163742e40496e76616c6964546f6d6273746f6e65046020546f6d6273746f6e657320646f6e2774206d617463682e54496e76616c6964436f6e74726163744f726967696e04bc20416e206f726967696e20547269654964207772697474656e20696e207468652063757272656e7420626c6f636b2e204f75744f6647617304bc2054686520657865637574656420636f6e7472616374206578686175737465642069747320676173206c696d69742e504f7574707574427566666572546f6f536d616c6c04050120546865206f75747075742062756666657220737570706c69656420746f206120636f6e7472616374204150492063616c6c2077617320746f6f20736d616c6c2e6442656c6f7753756273697374656e63655468726573686f6c6410210120506572666f726d696e672074686520726571756573746564207472616e7366657220776f756c6420686176652062726f756768742074686520636f6e74726163742062656c6f773d01207468652073756273697374656e6365207468726573686f6c642e204e6f207472616e7366657220697320616c6c6f77656420746f20646f207468697320696e206f7264657220746f20616c6c6f77450120666f72206120746f6d6273746f6e6520746f20626520637265617465642e2055736520607365616c5f7465726d696e6174656020746f2072656d6f7665206120636f6e747261637420776974686f757470206c656176696e67206120746f6d6273746f6e6520626568696e642e504e6577436f6e74726163744e6f7446756e64656408390120546865206e65776c79206372656174656420636f6e74726163742069732062656c6f77207468652073756273697374656e6365207468726573686f6c6420616674657220657865637574696e6721012069747320636f6e74727563746f722e204e6f20636f6e7472616374732061726520616c6c6f77656420746f2065786973742062656c6f772074686174207468726573686f6c642e385472616e736665724661696c65640c250120506572666f726d696e672074686520726571756573746564207472616e73666572206661696c656420666f72206120726561736f6e206f726967696e6174696e6720696e2074686531012063686f73656e2063757272656e637920696d706c656d656e746174696f6e206f66207468652072756e74696d652e204d6f73742070726f6261626c79207468652062616c616e63652069738c20746f6f206c6f77206f72206c6f636b732061726520706c61636564206f6e2069742e4c4d617843616c6c44657074685265616368656408250120506572666f726d696e6720612063616c6c207761732064656e6965642062656361757365207468652063616c6c696e67206465707468207265616368656420746865206c696d697498206f6620776861742069732073706563696669656420696e20746865207363686564756c652e2c4e6f7443616c6c61626c650831012054686520636f6e74726163742074686174207761732063616c6c656420697320656974686572206e6f20636f6e747261637420617420616c6c20286120706c61696e206163636f756e74294c206f72206973206120746f6d6273746f6e652e30436f6465546f6f4c617267650841012054686520636f646520737570706c69656420746f2060696e7374616e74696174655f776974685f636f646560206578636565647320746865206c696d69742073706563696669656420696e20746865482063757272656e74207363686564756c652e30436f64654e6f74466f756e6404c8204e6f20636f646520636f756c6420626520666f756e642061742074686520737570706c69656420636f646520686173682e2c4f75744f66426f756e6473042901204120627566666572206f757473696465206f662073616e64626f78206d656d6f7279207761732070617373656420746f206120636f6e7472616374204150492066756e6374696f6e2e384465636f64696e674661696c6564042d0120496e7075742070617373656420746f206120636f6e7472616374204150492066756e6374696f6e206661696c656420746f206465636f646520617320657870656374656420747970652e3c436f6e747261637454726170706564048c20436f6e7472616374207472617070656420647572696e6720657865637574696f6e2e3456616c7565546f6f4c6172676504d0205468652073697a6520646566696e656420696e2060543a3a4d617856616c756553697a6560207761732065786365656465642e405265656e7472616e636544656e6965640c41012054686520616374696f6e20706572666f726d6564206973206e6f7420616c6c6f776564207768696c652074686520636f6e747261637420706572666f726d696e6720697420697320616c72656164793d01206f6e207468652063616c6c20737461636b2e2054686f736520616374696f6e732061726520636f6e74726163742073656c66206465737472756374696f6e20616e6420726573746f726174696f6e40206f66206120746f6d6273746f6e652e40496e707574416c72656164795265616404210120607365616c5f696e70757460207761732063616c6c65642074776963652066726f6d207468652073616d6520636f6e747261637420657865637574696f6e20636f6e746578742e5052616e646f6d5375626a656374546f6f4c6f6e6704dc20546865207375626a6563742070617373656420746f20607365616c5f72616e646f6d60206578636565647320746865206c696d69742e34546f6f4d616e79546f706963730421012054686520616d6f756e74206f6620746f706963732070617373656420746f20607365616c5f6465706f7369745f6576656e747360206578636565647320746865206c696d69742e3c4475706c6963617465546f706963730431012054686520746f706963732070617373656420746f20607365616c5f6465706f7369745f6576656e74736020636f6e7461696e73206174206c65617374206f6e65206475706c69636174652e404e6f436861696e457874656e73696f6e0c49012054686520636861696e20646f6573206e6f742070726f76696465206120636861696e20657874656e73696f6e2e2043616c6c696e672074686520636861696e20657874656e73696f6e20726573756c7473510120696e2074686973206572726f722e204e6f74652074686174207468697320757375616c6c79202073686f756c646e27742068617070656e206173206465706c6f79696e67207375636820636f6e747261637473342069732072656a65637465642e4444656c6574696f6e517565756546756c6c1405012052656d6f76616c206f66206120636f6e7472616374206661696c65642062656361757365207468652064656c6574696f6e2071756575652069732066756c6c2e00550120546869732063616e2068617070656e207768656e206569746865722063616c6c696e67205b6050616c6c65743a3a636c61696d5f737572636861726765605d206f7220607365616c5f7465726d696e617465602e5101205468652071756575652069732066696c6c65642062792064656c6574696e6720636f6e74726163747320616e6420656d7074696564206279206120666978656420616d6f756e74206561636820626c6f636b2e250120547279696e6720616761696e20647572696e6720616e6f7468657220626c6f636b20697320746865206f6e6c792077617920746f207265736f6c766520746869732069737375652e50436f6e74726163744e6f74457669637461626c65102d01204120636f6e747261637420636f756c64206e6f74206265206576696374656420626563617573652069742068617320656e6f7567682062616c616e636520746f207061792072656e742e00250120546869732063616e2062652072657475726e65642066726f6d205b6050616c6c65743a3a636c61696d5f737572636861726765605d20626563617573652074686520746172676574c420636f6e74726163742068617320656e6f7567682062616c616e636520746f2070617920666f72206974732072656e742e4053746f7261676545786861757374656410350120412073746f72616765206d6f64696669636174696f6e20657868617573746564207468652033326269742074797065207468617420686f6c6473207468652073746f726167652073697a652e00350120546869732063616e206569746865722068617070656e207768656e2074686520616363756d756c617465642073746f7261676520696e20627974657320697320746f6f206c61726765206f72ac207768656e206e756d626572206f662073746f72616765206974656d7320697320746f6f206c617267652e444475706c6963617465436f6e747261637404cc204120636f6e74726163742077697468207468652073616d65204163636f756e74496420616c7265616479206578697374732e12105375646f01105375646f040c4b6579010030543a3a4163636f756e74496480000000000000000000000000000000000000000000000000000000000000000004842054686520604163636f756e74496460206f6620746865207375646f206b65792e0110107375646f041063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e547375646f5f756e636865636b65645f776569676874081063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e1c5f776569676874185765696768742839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e310120546869732066756e6374696f6e20646f6573206e6f7420636865636b2074686520776569676874206f66207468652063616c6c2c20616e6420696e737465616420616c6c6f777320746865b4205375646f207573657220746f20737065636966792074686520776569676874206f66207468652063616c6c2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292ed0202d2054686520776569676874206f6620746869732063616c6c20697320646566696e6564206279207468652063616c6c65722e302023203c2f7765696768743e1c7365745f6b6579040c6e65778c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652475012041757468656e74696361746573207468652063757272656e74207375646f206b657920616e6420736574732074686520676976656e204163636f756e7449642028606e6577602920617320746865206e6577207375646f206b65792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e1c7375646f5f6173080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2c51012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c207769746820605369676e656460206f726967696e2066726f6d44206120676976656e206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e010c14537564696404384469737061746368526573756c74048c2041207375646f206a75737420746f6f6b20706c6163652e205c5b726573756c745c5d284b65794368616e67656404244163636f756e74496404010120546865205c5b7375646f65725c5d206a757374207377697463686564206964656e746974793b20746865206f6c64206b657920697320737570706c6965642e285375646f4173446f6e6504384469737061746368526573756c74048c2041207375646f206a75737420746f6f6b20706c6163652e205c5b726573756c745c5d00042c526571756972655375646f04802053656e646572206d75737420626520746865205375646f206163636f756e741320496d4f6e6c696e650120496d4f6e6c696e6510384865617274626561744166746572010038543a3a426c6f636b4e756d62657210000000002c1d012054686520626c6f636b206e756d6265722061667465722077686963682069742773206f6b20746f2073656e64206865617274626561747320696e207468652063757272656e74242073657373696f6e2e0025012041742074686520626567696e6e696e67206f6620656163682073657373696f6e20776520736574207468697320746f20612076616c756520746861742073686f756c642066616c6c350120726f7567686c7920696e20746865206d6964646c65206f66207468652073657373696f6e206475726174696f6e2e20546865206964656120697320746f206669727374207761697420666f721901207468652076616c696461746f727320746f2070726f64756365206120626c6f636b20696e207468652063757272656e742073657373696f6e2c20736f207468617420746865a820686561727462656174206c61746572206f6e2077696c6c206e6f74206265206e65636573736172792e00390120546869732076616c75652077696c6c206f6e6c79206265207573656420617320612066616c6c6261636b206966207765206661696c20746f2067657420612070726f7065722073657373696f6e2d012070726f677265737320657374696d6174652066726f6d20604e65787453657373696f6e526f746174696f6e602c2061732074686f736520657374696d617465732073686f756c642062650101206d6f7265206163637572617465207468656e207468652076616c75652077652063616c63756c61746520666f7220604865617274626561744166746572602e104b65797301004c5665633c543a3a417574686f7269747949643e040004d0205468652063757272656e7420736574206f66206b6579732074686174206d61792069737375652061206865617274626561742e485265636569766564486561727462656174730002053053657373696f6e496e6465782441757468496e6465781c5665633c75383e05040008f020466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206041757468496e6465786020746f8020606f6666636861696e3a3a4f70617175654e6574776f726b5374617465602e38417574686f726564426c6f636b730102053053657373696f6e496e6465783856616c696461746f7249643c543e0c75333205100000000008150120466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206056616c696461746f7249643c543e6020746f20746865c8206e756d626572206f6620626c6f636b7320617574686f7265642062792074686520676976656e20617574686f726974792e0104246865617274626561740824686561727462656174644865617274626561743c543a3a426c6f636b4e756d6265723e285f7369676e6174757265bc3c543a3a417574686f7269747949642061732052756e74696d654170705075626c69633e3a3a5369676e6174757265242c2023203c7765696768743e4101202d20436f6d706c65786974793a20604f284b202b20452960207768657265204b206973206c656e677468206f6620604b6579736020286865617274626561742e76616c696461746f72735f6c656e290101202020616e642045206973206c656e677468206f6620606865617274626561742e6e6574776f726b5f73746174652e65787465726e616c5f61646472657373608c2020202d20604f284b29603a206465636f64696e67206f66206c656e67746820604b60b02020202d20604f284529603a206465636f64696e672f656e636f64696e67206f66206c656e677468206045603d01202d20446252656164733a2070616c6c65745f73657373696f6e206056616c696461746f7273602c2070616c6c65745f73657373696f6e206043757272656e74496e646578602c20604b657973602c5c202020605265636569766564486561727462656174736084202d2044625772697465733a206052656365697665644865617274626561747360302023203c2f7765696768743e010c444865617274626561745265636569766564042c417574686f7269747949640405012041206e657720686561727462656174207761732072656365697665642066726f6d2060417574686f72697479496460205c5b617574686f726974795f69645c5d1c416c6c476f6f640004d42041742074686520656e64206f66207468652073657373696f6e2c206e6f206f6666656e63652077617320636f6d6d69747465642e2c536f6d654f66666c696e6504605665633c4964656e74696669636174696f6e5475706c653e043d012041742074686520656e64206f66207468652073657373696f6e2c206174206c65617374206f6e652076616c696461746f722077617320666f756e6420746f206265205c5b6f66666c696e655c5d2e000828496e76616c69644b65790464204e6f6e206578697374656e74207075626c6963206b65792e4c4475706c6963617465644865617274626561740458204475706c696361746564206865617274626561742e1448417574686f72697479446973636f7665727900010000000015204f6666656e63657301204f6666656e636573101c5265706f727473000105345265706f727449644f663c543ed04f6666656e636544657461696c733c543a3a4163636f756e7449642c20543a3a4964656e74696669636174696f6e5475706c653e00040004490120546865207072696d61727920737472756374757265207468617420686f6c647320616c6c206f6666656e6365207265636f726473206b65796564206279207265706f7274206964656e746966696572732e4044656665727265644f6666656e6365730100645665633c44656665727265644f6666656e63654f663c543e3e0400086501204465666572726564207265706f72747320746861742068617665206265656e2072656a656374656420627920746865206f6666656e63652068616e646c657220616e64206e65656420746f206265207375626d6974746564442061742061206c617465722074696d652e58436f6e63757272656e745265706f727473496e646578010205104b696e64384f706171756554696d65536c6f74485665633c5265706f727449644f663c543e3e050400042901204120766563746f72206f66207265706f727473206f66207468652073616d65206b696e6420746861742068617070656e6564206174207468652073616d652074696d6520736c6f742e485265706f72747342794b696e64496e646578010105104b696e641c5665633c75383e00040018110120456e756d65726174657320616c6c207265706f727473206f662061206b696e6420616c6f6e672077697468207468652074696d6520746865792068617070656e65642e00bc20416c6c207265706f7274732061726520736f72746564206279207468652074696d65206f66206f6666656e63652e004901204e6f74652074686174207468652061637475616c2074797065206f662074686973206d617070696e6720697320605665633c75383e602c207468697320697320626563617573652076616c756573206f66690120646966666572656e7420747970657320617265206e6f7420737570706f7274656420617420746865206d6f6d656e7420736f2077652061726520646f696e6720746865206d616e75616c2073657269616c697a6174696f6e2e010001041c4f6666656e63650c104b696e64384f706171756554696d65536c6f7410626f6f6c10550120546865726520697320616e206f6666656e6365207265706f72746564206f662074686520676976656e20606b696e64602068617070656e656420617420746865206073657373696f6e5f696e6465786020616e644d0120286b696e642d7370656369666963292074696d6520736c6f742e2054686973206576656e74206973206e6f74206465706f736974656420666f72206475706c696361746520736c61736865732e206c617374190120656c656d656e7420696e64696361746573206f6620746865206f6666656e636520776173206170706c69656420287472756529206f7220717565756564202866616c73652974205c5b6b696e642c2074696d65736c6f742c206170706c6965645c5d2e00001628486973746f726963616c0000000000176052616e646f6d6e657373436f6c6c656374697665466c6970016052616e646f6d6e657373436f6c6c656374697665466c6970043852616e646f6d4d6174657269616c0100305665633c543a3a486173683e04000c610120536572696573206f6620626c6f636b20686561646572732066726f6d20746865206c61737420383120626c6f636b73207468617420616374732061732072616e646f6d2073656564206d6174657269616c2e2054686973610120697320617272616e67656420617320612072696e672062756666657220776974682060626c6f636b5f6e756d626572202520383160206265696e672074686520696e64657820696e746f20746865206056656360206f664420746865206f6c6465737420686173682e010000000018204964656e7469747901204964656e7469747910284964656e746974794f6600010530543a3a4163636f756e74496468526567697374726174696f6e3c42616c616e63654f663c543e3e0004000c210120496e666f726d6174696f6e20746861742069732070657274696e656e7420746f206964656e746966792074686520656e7469747920626568696e6420616e206163636f756e742e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e1c53757065724f6600010230543a3a4163636f756e7449645028543a3a4163636f756e7449642c204461746129000400086101205468652073757065722d6964656e74697479206f6620616e20616c7465726e6174697665202273756222206964656e7469747920746f676574686572207769746820697473206e616d652c2077697468696e2074686174510120636f6e746578742e20496620746865206163636f756e74206973206e6f7420736f6d65206f74686572206163636f756e742773207375622d6964656e746974792c207468656e206a75737420604e6f6e65602e18537562734f6601010530543a3a4163636f756e744964842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e290044000000000000000000000000000000000014b820416c7465726e6174697665202273756222206964656e746974696573206f662074686973206163636f756e742e001d0120546865206669727374206974656d20697320746865206465706f7369742c20746865207365636f6e64206973206120766563746f72206f6620746865206163636f756e74732e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e28526567697374726172730100d85665633c4f7074696f6e3c526567697374726172496e666f3c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e3e0400104d012054686520736574206f6620726567697374726172732e204e6f7420657870656374656420746f206765742076657279206269672061732063616e206f6e6c79206265206164646564207468726f7567682061a8207370656369616c206f726967696e20286c696b656c79206120636f756e63696c206d6f74696f6e292e0029012054686520696e64657820696e746f20746869732063616e206265206361737420746f2060526567697374726172496e6465786020746f2067657420612076616c69642076616c75652e013c346164645f726567697374726172041c6163636f756e7430543a3a4163636f756e744964347c2041646420612072656769737472617220746f207468652073797374656d2e00010120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060543a3a5265676973747261724f726967696e602e00ac202d20606163636f756e74603a20746865206163636f756e74206f6620746865207265676973747261722e009820456d6974732060526567697374726172416464656460206966207375636365737366756c2e002c2023203c7765696768743e2901202d20604f2852296020776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e64656420616e6420636f64652d626f756e646564292e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e307365745f6964656e746974790410696e666f304964656e74697479496e666f4c2d012053657420616e206163636f756e742773206964656e7469747920696e666f726d6174696f6e20616e6420726573657276652074686520617070726f707269617465206465706f7369742e00590120496620746865206163636f756e7420616c726561647920686173206964656e7469747920696e666f726d6174696f6e2c20746865206465706f7369742069732074616b656e2061732070617274207061796d656e745420666f7220746865206e6577206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0090202d2060696e666f603a20546865206964656e7469747920696e666f726d6174696f6e2e008c20456d69747320604964656e7469747953657460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2858202b205827202b2052296021012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e64656429e42020202d20776865726520605260206a756467656d656e74732d636f756e7420287265676973747261722d636f756e742d626f756e6465642984202d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e2501202d204f6e652073746f72616765206d75746174696f6e2028636f6465632d7265616420604f285827202b205229602c20636f6465632d777269746520604f2858202b20522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e207365745f73756273041073756273645665633c28543a3a4163636f756e7449642c2044617461293e54902053657420746865207375622d6163636f756e7473206f66207468652073656e6465722e005901205061796d656e743a20416e79206167677265676174652062616c616e63652072657365727665642062792070726576696f757320607365745f73756273602063616c6c732077696c6c2062652072657475726e6564310120616e6420616e20616d6f756e7420605375624163636f756e744465706f736974602077696c6c20626520726573657276656420666f722065616368206974656d20696e206073756273602e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e00b4202d206073756273603a20546865206964656e74697479277320286e657729207375622d6163636f756e74732e002c2023203c7765696768743e34202d20604f2850202b20532960e82020202d20776865726520605060206f6c642d737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e88202d204174206d6f7374206f6e652062616c616e6365206f7065726174696f6e732e18202d2044423ae02020202d206050202b2053602073746f72616765206d75746174696f6e732028636f64656320636f6d706c657869747920604f2831296029c02020202d204f6e652073746f7261676520726561642028636f64656320636f6d706c657869747920604f28502960292ec42020202d204f6e652073746f726167652077726974652028636f64656320636f6d706c657869747920604f28532960292ed42020202d204f6e652073746f726167652d6578697374732028604964656e746974794f663a3a636f6e7461696e735f6b657960292e302023203c2f7765696768743e38636c6561725f6964656e7469747900483d0120436c65617220616e206163636f756e742773206964656e7469747920696e666f20616e6420616c6c207375622d6163636f756e747320616e642072657475726e20616c6c206465706f736974732e00f0205061796d656e743a20416c6c2072657365727665642062616c616e636573206f6e20746865206163636f756e74206172652072657475726e65642e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e009c20456d69747320604964656e74697479436c656172656460206966207375636365737366756c2e002c2023203c7765696768743e44202d20604f2852202b2053202b20582960d02020202d20776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e25012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e646564292e8c202d204f6e652062616c616e63652d756e72657365727665206f7065726174696f6e2ecc202d206032602073746f7261676520726561647320616e64206053202b2032602073746f726167652064656c6574696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e44726571756573745f6a756467656d656e7408247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e1c6d61785f66656554436f6d706163743c42616c616e63654f663c543e3e5c9820526571756573742061206a756467656d656e742066726f6d2061207265676973747261722e005901205061796d656e743a204174206d6f737420606d61785f666565602077696c6c20626520726573657276656420666f72207061796d656e7420746f2074686520726567697374726172206966206a756467656d656e741c20676976656e2e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e002101202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973207265717565737465642e5901202d20606d61785f666565603a20546865206d6178696d756d206665652074686174206d617920626520706169642e20546869732073686f756c64206a757374206265206175746f2d706f70756c617465642061733a0034206060606e6f636f6d70696c65bc2053656c663a3a7265676973747261727328292e676574287265675f696e646578292e756e7772617028292e666565102060606000a820456d69747320604a756467656d656e7452657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2858202b205229602e34202d204f6e65206576656e742e302023203c2f7765696768743e3863616e63656c5f7265717565737404247265675f696e64657838526567697374726172496e646578446c2043616e63656c20612070726576696f757320726571756573742e00fc205061796d656e743a20412070726576696f75736c79207265736572766564206465706f7369742069732072657475726e6564206f6e20737563636573732e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e004901202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206e6f206c6f6e676572207265717565737465642e00b020456d69747320604a756467656d656e74556e72657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e8c202d204f6e652073746f72616765206d75746174696f6e20604f2852202b205829602e30202d204f6e65206576656e74302023203c2f7765696768743e1c7365745f6665650814696e6465785c436f6d706163743c526567697374726172496e6465783e0c66656554436f6d706163743c42616c616e63654f663c543e3e341d0120536574207468652066656520726571756972656420666f722061206a756467656d656e7420746f206265207265717565737465642066726f6d2061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e58202d2060666565603a20746865206e6577206665652e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e333135202b2052202a20302e33323920c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e387365745f6163636f756e745f69640814696e6465785c436f6d706163743c526567697374726172496e6465783e0c6e657730543a3a4163636f756e74496434c0204368616e676520746865206163636f756e74206173736f63696174656420776974682061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e74202d20606e6577603a20746865206e6577206163636f756e742049442e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee4202d2042656e63686d61726b3a20382e383233202b2052202a20302e333220c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e287365745f6669656c64730814696e6465785c436f6d706163743c526567697374726172496e6465783e186669656c6473384964656e746974794669656c647334ac2053657420746865206669656c6420696e666f726d6174696f6e20666f722061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e1101202d20606669656c6473603a20746865206669656c64732074686174207468652072656769737472617220636f6e6365726e73207468656d73656c76657320776974682e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e343634202b2052202a20302e33323520c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e4470726f766964655f6a756467656d656e740c247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365246a756467656d656e745c4a756467656d656e743c42616c616e63654f663c543e3e4cbc2050726f766964652061206a756467656d656e7420666f7220616e206163636f756e742773206964656e746974792e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74b4206f6620746865207265676973747261722077686f736520696e64657820697320607265675f696e646578602e002501202d20607265675f696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206265696e67206d6164652e5901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e4d01202d20606a756467656d656e74603a20746865206a756467656d656e74206f662074686520726567697374726172206f6620696e64657820607265675f696e646578602061626f75742060746172676574602e009820456d69747320604a756467656d656e74476976656e60206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e88202d204f6e652062616c616e63652d7472616e73666572206f7065726174696f6e2e98202d20557020746f206f6e65206163636f756e742d6c6f6f6b7570206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2852202b205829602e34202d204f6e65206576656e742e302023203c2f7765696768743e346b696c6c5f6964656e7469747904187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654c45012052656d6f766520616e206163636f756e742773206964656e7469747920616e64207375622d6163636f756e7420696e666f726d6174696f6e20616e6420736c61736820746865206465706f736974732e006501205061796d656e743a2052657365727665642062616c616e6365732066726f6d20607365745f737562736020616e6420607365745f6964656e74697479602061726520736c617368656420616e642068616e646c656420627949012060536c617368602e20566572696669636174696f6e2072657175657374206465706f7369747320617265206e6f742072657475726e65643b20746865792073686f756c642062652063616e63656c6c656484206d616e75616c6c79207573696e67206063616e63656c5f72657175657374602e00fc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206d617463682060543a3a466f7263654f726967696e602e005901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e009820456d69747320604964656e746974794b696c6c656460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2852202b2053202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e74202d206053202b2032602073746f72616765206d75746174696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e1c6164645f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365106461746110446174611cb0204164642074686520676976656e206163636f756e7420746f207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656e616d655f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651064617461104461746110d020416c74657220746865206173736f636961746564206e616d65206f662074686520676976656e207375622d6163636f756e742e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656d6f76655f737562040c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651cc42052656d6f76652074686520676976656e206163636f756e742066726f6d207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e20717569745f7375620028902052656d6f7665207468652073656e6465722061732061207375622d6163636f756e742e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c206265207265706174726961746564b820746f207468652073656e64657220282a6e6f742a20746865206f726967696e616c206465706f7369746f72292e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206861766520612072656769737465726564402073757065722d6964656e746974792e004901204e4f54453a20546869732073686f756c64206e6f74206e6f726d616c6c7920626520757365642c206275742069732070726f766964656420696e207468652063617365207468617420746865206e6f6e2d150120636f6e74726f6c6c6572206f6620616e206163636f756e74206973206d616c6963696f75736c7920726567697374657265642061732061207375622d6163636f756e742e01282c4964656e7469747953657404244163636f756e7449640411012041206e616d652077617320736574206f72207265736574202877686963682077696c6c2072656d6f766520616c6c206a756467656d656e7473292e205c5b77686f5c5d3c4964656e74697479436c656172656408244163636f756e7449641c42616c616e63650415012041206e616d652077617320636c65617265642c20616e642074686520676976656e2062616c616e63652072657475726e65642e205c5b77686f2c206465706f7369745c5d384964656e746974794b696c6c656408244163636f756e7449641c42616c616e6365040d012041206e616d65207761732072656d6f76656420616e642074686520676976656e2062616c616e636520736c61736865642e205c5b77686f2c206465706f7369745c5d484a756467656d656e7452657175657374656408244163636f756e74496438526567697374726172496e6465780405012041206a756467656d656e74207761732061736b65642066726f6d2061207265676973747261722e205c5b77686f2c207265676973747261725f696e6465785c5d504a756467656d656e74556e72657175657374656408244163636f756e74496438526567697374726172496e64657804f02041206a756467656d656e74207265717565737420776173207265747261637465642e205c5b77686f2c207265676973747261725f696e6465785c5d384a756467656d656e74476976656e08244163636f756e74496438526567697374726172496e6465780409012041206a756467656d656e742077617320676976656e2062792061207265676973747261722e205c5b7461726765742c207265676973747261725f696e6465785c5d3852656769737472617241646465640438526567697374726172496e64657804ac204120726567697374726172207761732061646465642e205c5b7265676973747261725f696e6465785c5d405375624964656e7469747941646465640c244163636f756e744964244163636f756e7449641c42616c616e63650455012041207375622d6964656e746974792077617320616464656420746f20616e206964656e7469747920616e6420746865206465706f73697420706169642e205c5b7375622c206d61696e2c206465706f7369745c5d485375624964656e7469747952656d6f7665640c244163636f756e744964244163636f756e7449641c42616c616e6365080d012041207375622d6964656e74697479207761732072656d6f7665642066726f6d20616e206964656e7469747920616e6420746865206465706f7369742066726565642e5c205c5b7375622c206d61696e2c206465706f7369745c5d485375624964656e746974795265766f6b65640c244163636f756e744964244163636f756e7449641c42616c616e6365081d012041207375622d6964656e746974792077617320636c65617265642c20616e642074686520676976656e206465706f7369742072657061747269617465642066726f6d207468652901206d61696e206964656e74697479206163636f756e7420746f20746865207375622d6964656e74697479206163636f756e742e205c5b7375622c206d61696e2c206465706f7369745c5d183042617369634465706f7369743042616c616e63654f663c543e400080c6a47e8d0300000000000000000004d82054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564206964656e746974792e304669656c644465706f7369743042616c616e63654f663c543e4000a031a95fe300000000000000000000042d012054686520616d6f756e742068656c64206f6e206465706f73697420706572206164646974696f6e616c206669656c6420666f7220612072656769737465726564206964656e746974792e445375624163636f756e744465706f7369743042616c616e63654f663c543e400080f420e6b5000000000000000000000c65012054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564207375626163636f756e742e20546869732073686f756c64206163636f756e7420666f7220746865206661637471012074686174206f6e652073746f72616765206974656d27732076616c75652077696c6c20696e637265617365206279207468652073697a65206f6620616e206163636f756e742049442c20616e642074686572652077696c6c206265290120616e6f746865722074726965206974656d2077686f73652076616c7565206973207468652073697a65206f6620616e206163636f756e7420494420706c75732033322062797465732e384d61785375624163636f756e74730c7533321064000000040d0120546865206d6178696d756d206e756d626572206f66207375622d6163636f756e747320616c6c6f77656420706572206964656e746966696564206163636f756e742e4c4d61784164646974696f6e616c4669656c64730c7533321064000000086501204d6178696d756d206e756d626572206f66206164646974696f6e616c206669656c64732074686174206d61792062652073746f72656420696e20616e2049442e204e656564656420746f20626f756e642074686520492f4fe020726571756972656420746f2061636365737320616e206964656e746974792c206275742063616e2062652070726574747920686967682e344d6178526567697374726172730c7533321014000000085101204d61786d696d756d206e756d626572206f66207265676973747261727320616c6c6f77656420696e207468652073797374656d2e204e656564656420746f20626f756e642074686520636f6d706c65786974797c206f662c20652e672e2c207570646174696e67206a756467656d656e74732e4048546f6f4d616e795375624163636f756e7473046020546f6f206d616e7920737562732d6163636f756e74732e204e6f74466f756e640454204163636f756e742069736e277420666f756e642e204e6f744e616d65640454204163636f756e742069736e2774206e616d65642e28456d707479496e646578043420456d70747920696e6465782e284665654368616e676564044020466565206973206368616e6765642e284e6f4964656e74697479044c204e6f206964656e7469747920666f756e642e3c537469636b794a756467656d656e74044820537469636b79206a756467656d656e742e384a756467656d656e74476976656e0444204a756467656d656e7420676976656e2e40496e76616c69644a756467656d656e74044c20496e76616c6964206a756467656d656e742e30496e76616c6964496e64657804582054686520696e64657820697320696e76616c69642e34496e76616c6964546172676574045c205468652074617267657420697320696e76616c69642e34546f6f4d616e794669656c6473047020546f6f206d616e79206164646974696f6e616c206669656c64732e44546f6f4d616e795265676973747261727304ec204d6178696d756d20616d6f756e74206f66207265676973747261727320726561636865642e2043616e6e6f742061646420616e79206d6f72652e38416c7265616479436c61696d65640474204163636f756e7420494420697320616c7265616479206e616d65642e184e6f7453756204742053656e646572206973206e6f742061207375622d6163636f756e742e204e6f744f776e6564048c205375622d6163636f756e742069736e2774206f776e65642062792073656e6465722e191c536f6369657479011c536f6369657479401c466f756e646572000030543a3a4163636f756e7449640400044820546865206669727374206d656d6265722e1452756c657300001c543a3a48617368040008510120412068617368206f66207468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e2043616e206f6e6c7920626520736574206f6e636520616e6454206f6e6c792062792074686520666f756e6465722e2843616e6469646174657301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e0400043901205468652063757272656e7420736574206f662063616e646964617465733b206269646465727320746861742061726520617474656d7074696e6720746f206265636f6d65206d656d626572732e4c53757370656e64656443616e6469646174657300010530543a3a4163636f756e744964e42842616c616e63654f663c542c20493e2c204269644b696e643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e2900040004842054686520736574206f662073757370656e6465642063616e646964617465732e0c506f7401003c42616c616e63654f663c542c20493e400000000000000000000000000000000004410120416d6f756e74206f66206f7572206163636f756e742062616c616e63652074686174206973207370656369666963616c6c7920666f7220746865206e65787420726f756e642773206269642873292e1048656164000030543a3a4163636f756e744964040004e820546865206d6f7374207072696d6172792066726f6d20746865206d6f737420726563656e746c7920617070726f766564206d656d626572732e1c4d656d626572730100445665633c543a3a4163636f756e7449643e04000494205468652063757272656e7420736574206f66206d656d626572732c206f7264657265642e4053757370656e6465644d656d6265727301010530543a3a4163636f756e74496410626f6f6c00040004782054686520736574206f662073757370656e646564206d656d626572732e104269647301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e040004e8205468652063757272656e7420626964732c2073746f726564206f726465726564206279207468652076616c7565206f6620746865206269642e20566f756368696e6700010530543a3a4163636f756e74496438566f756368696e6753746174757300040004e4204d656d626572732063757272656e746c7920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e1c5061796f75747301010530543a3a4163636f756e744964985665633c28543a3a426c6f636b4e756d6265722c2042616c616e63654f663c542c20493e293e000400044d012050656e64696e67207061796f7574733b206f72646572656420627920626c6f636b206e756d6265722c20776974682074686520616d6f756e7420746861742073686f756c642062652070616964206f75742e1c537472696b657301010530543a3a4163636f756e7449642c537472696b65436f756e7400100000000004dc20546865206f6e676f696e67206e756d626572206f66206c6f73696e6720766f746573206361737420627920746865206d656d6265722e14566f74657300020530543a3a4163636f756e74496430543a3a4163636f756e74496410566f746505040004d020446f75626c65206d61702066726f6d2043616e646964617465202d3e20566f746572202d3e20284d617962652920566f74652e20446566656e646572000030543a3a4163636f756e744964040004c42054686520646566656e64696e67206d656d6265722063757272656e746c79206265696e67206368616c6c656e6765642e34446566656e646572566f74657300010530543a3a4163636f756e74496410566f7465000400046020566f74657320666f722074686520646566656e6465722e284d61784d656d6265727301000c753332100000000004dc20546865206d6178206e756d626572206f66206d656d6265727320666f722074686520736f6369657479206174206f6e652074696d652e01300c626964041476616c75653c42616c616e63654f663c542c20493e84e020412075736572206f757473696465206f662074686520736f63696574792063616e206d616b6520612062696420666f7220656e7472792e003901205061796d656e743a206043616e6469646174654465706f736974602077696c6c20626520726573657276656420666f72206d616b696e672061206269642e2049742069732072657475726e6564f0207768656e2074686520626964206265636f6d65732061206d656d6265722c206f7220696620746865206269642063616c6c732060756e626964602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a5901202d206076616c7565603a2041206f6e652074696d65207061796d656e74207468652062696420776f756c64206c696b6520746f2072656365697665207768656e206a6f696e696e672074686520736f63696574792e002c2023203c7765696768743e5501204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520726573657276652944202d2053746f726167652052656164733aec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f284329c820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d2948202d2053746f72616765205772697465733a810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3a2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6820092d204f6e65206576656e7420666f72206e6577206269642efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e14756e626964040c706f730c7533324cd82041206269646465722063616e2072656d6f76652074686569722062696420666f7220656e74727920696e746f20736f63696574792e010120427920646f696e6720736f2c20746865792077696c6c20686176652074686569722063616e646964617465206465706f7369742072657475726e6564206f728420746865792077696c6c20756e766f75636820746865697220766f75636865722e00fc205061796d656e743a2054686520626964206465706f73697420697320756e7265736572766564206966207468652075736572206d6164652061206269642e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206269646465722e003020506172616d65746572733a1901202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2077616e747320746f20756e6269642e002c2023203c7765696768743eb0204b65793a204220286c656e206f662062696473292c2058202862616c616e636520756e72657365727665290d01202d204f6e652073746f72616765207265616420616e6420777269746520746f20726574726965766520616e64207570646174652074686520626964732e204f2842294501202d20456974686572206f6e6520756e726573657276652062616c616e636520616374696f6e204f285829206f72206f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2842202b205829302023203c2f7765696768743e14766f7563680c0c77686f30543a3a4163636f756e7449641476616c75653c42616c616e63654f663c542c20493e0c7469703c42616c616e63654f663c542c20493eb045012041732061206d656d6265722c20766f75636820666f7220736f6d656f6e6520746f206a6f696e20736f636965747920627920706c6163696e67206120626964206f6e20746865697220626568616c662e005501205468657265206973206e6f206465706f73697420726571756972656420746f20766f75636820666f722061206e6577206269642c206275742061206d656d6265722063616e206f6e6c7920766f75636820666f725d01206f6e652062696420617420612074696d652e2049662074686520626964206265636f6d657320612073757370656e6465642063616e64696461746520616e6420756c74696d6174656c792072656a65637465642062794101207468652073757370656e73696f6e206a756467656d656e74206f726967696e2c20746865206d656d6265722077696c6c2062652062616e6e65642066726f6d20766f756368696e6720616761696e2e005901204173206120766f756368696e67206d656d6265722c20796f752063616e20636c61696d206120746970206966207468652063616e6469646174652069732061636365707465642e2054686973207469702077696c6c51012062652070616964206173206120706f7274696f6e206f66207468652072657761726420746865206d656d6265722077696c6c207265636569766520666f72206a6f696e696e672074686520736f63696574792e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733acc202d206077686f603a2054686520757365722077686f20796f7520776f756c64206c696b6520746f20766f75636820666f722e5101202d206076616c7565603a2054686520746f74616c2072657761726420746f2062652070616964206265747765656e20796f7520616e64207468652063616e6469646174652069662074686579206265636f6d65642061206d656d62657220696e2074686520736f63696574792e4901202d2060746970603a20596f757220637574206f662074686520746f74616c206076616c756560207061796f7574207768656e207468652063616e64696461746520697320696e64756374656420696e746f15012074686520736f63696574792e2054697073206c6172676572207468616e206076616c7565602077696c6c206265207361747572617465642075706f6e207061796f75742e002c2023203c7765696768743e0101204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d626572732944202d2053746f726167652052656164733ac820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d29090120092d204f6e652073746f72616765207265616420746f20636865636b206d656d626572206973206e6f7420616c726561647920766f756368696e672e204f283129ec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f28432948202d2053746f72616765205772697465733a0d0120092d204f6e652073746f7261676520777269746520746f20696e7365727420766f756368696e672073746174757320746f20746865206d656d6265722e204f283129810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3ac020092d204f286c6f67204d292073656172636820746f20636865636b2073656e6465722069732061206d656d6265722e2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6020092d204f6e65206576656e7420666f7220766f7563682efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e1c756e766f756368040c706f730c753332442d01204173206120766f756368696e67206d656d6265722c20756e766f7563682061206269642e2054686973206f6e6c7920776f726b73207768696c6520766f7563686564207573657220697394206f6e6c792061206269646465722028616e64206e6f7420612063616e646964617465292e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206120766f756368696e67206d656d6265722e003020506172616d65746572733a2d01202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2073686f756c6420626520756e766f75636865642e002c2023203c7765696768743e54204b65793a204220286c656e206f662062696473290901202d204f6e652073746f726167652072656164204f28312920746f20636865636b20746865207369676e6572206973206120766f756368696e67206d656d6265722eec202d204f6e652073746f72616765206d757461746520746f20726574726965766520616e64207570646174652074686520626964732e204f28422994202d204f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f284229302023203c2f7765696768743e10766f7465082463616e6469646174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c617070726f766510626f6f6c4c882041732061206d656d6265722c20766f7465206f6e20612063616e6469646174652e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733a0d01202d206063616e646964617465603a205468652063616e646964617465207468617420746865206d656d62657220776f756c64206c696b6520746f20626964206f6e2ef4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265d82020202020202020202020202020617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743ebc204b65793a204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722e58202d204f6e65206163636f756e74206c6f6f6b75702e2d01202d204f6e652073746f726167652072656164204f28432920616e64204f2843292073656172636820746f20636865636b2074686174207573657220697320612063616e6469646174652ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204329302023203c2f7765696768743e34646566656e6465725f766f7465041c617070726f766510626f6f6c408c2041732061206d656d6265722c20766f7465206f6e2074686520646566656e6465722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733af4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265a420617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743e68202d204b65793a204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e007820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d29302023203c2f7765696768743e187061796f757400504501205472616e7366657220746865206669727374206d617475726564207061796f757420666f72207468652073656e64657220616e642072656d6f76652069742066726f6d20746865207265636f7264732e006901204e4f54453a20546869732065787472696e736963206e6565647320746f2062652063616c6c6564206d756c7469706c652074696d657320746f20636c61696d206d756c7469706c65206d617475726564207061796f7574732e002101205061796d656e743a20546865206d656d6265722077696c6c20726563656976652061207061796d656e7420657175616c20746f207468656972206669727374206d61747572656478207061796f757420746f20746865697220667265652062616c616e63652e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d62657220776974684c207061796f7574732072656d61696e696e672e002c2023203c7765696768743e1d01204b65793a204d20286c656e206f66206d656d62657273292c205020286e756d626572206f66207061796f75747320666f72206120706172746963756c6172206d656d626572292501202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b207369676e65722069732061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28502920746f2067657420616c6c207061796f75747320666f722061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28312920746f20676574207468652063757272656e7420626c6f636b206e756d6265722e8c202d204f6e652063757272656e6379207472616e736665722063616c6c2e204f2858291101202d204f6e652073746f72616765207772697465206f722072656d6f76616c20746f2075706461746520746865206d656d6265722773207061796f7574732e204f285029009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2050202b205829302023203c2f7765696768743e14666f756e640c1c666f756e64657230543a3a4163636f756e7449642c6d61785f6d656d626572730c7533321472756c65731c5665633c75383e4c4c20466f756e642074686520736f63696574792e00f0205468697320697320646f6e65206173206120646973637265746520616374696f6e20696e206f7264657220746f20616c6c6f7720666f72207468651901206d6f64756c6520746f20626520696e636c7564656420696e746f20612072756e6e696e6720636861696e20616e642063616e206f6e6c7920626520646f6e65206f6e63652e001d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f466f756e6465725365744f726967696e5f2e003020506172616d65746572733a1901202d2060666f756e64657260202d20546865206669727374206d656d62657220616e642068656164206f6620746865206e65776c7920666f756e64656420736f63696574792e1501202d20606d61785f6d656d6265727360202d2054686520696e697469616c206d6178206e756d626572206f66206d656d6265727320666f722074686520736f63696574792ef4202d206072756c657360202d205468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e002c2023203c7765696768743ee0202d2054776f2073746f72616765206d75746174657320746f207365742060486561646020616e642060466f756e646572602e204f283129f4202d204f6e652073746f7261676520777269746520746f2061646420746865206669727374206d656d62657220746f20736f63696574792e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e1c756e666f756e6400348c20416e6e756c2074686520666f756e64696e67206f662074686520736f63696574792e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205369676e65642c20616e6420746865207369676e696e67206163636f756e74206d75737420626520626f74685901207468652060466f756e6465726020616e6420746865206048656164602e205468697320696d706c6965732074686174206974206d6179206f6e6c7920626520646f6e65207768656e207468657265206973206f6e6520206d656d6265722e002c2023203c7765696768743e68202d2054776f2073746f72616765207265616473204f2831292e78202d20466f75722073746f726167652072656d6f76616c73204f2831292e34202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e586a756467655f73757370656e6465645f6d656d626572080c77686f30543a3a4163636f756e7449641c666f726769766510626f6f6c6c2d0120416c6c6f772073757370656e73696f6e206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e646564206d656d6265722e00590120496620612073757370656e646564206d656d62657220697320666f72676976656e2c2077652073696d706c7920616464207468656d206261636b2061732061206d656d6265722c206e6f7420616666656374696e67cc20616e79206f6620746865206578697374696e672073746f72616765206974656d7320666f722074686174206d656d6265722e00490120496620612073757370656e646564206d656d6265722069732072656a65637465642c2072656d6f766520616c6c206173736f6369617465642073746f72616765206974656d732c20696e636c7564696e670101207468656972207061796f7574732c20616e642072656d6f766520616e7920766f7563686564206269647320746865792063757272656e746c7920686176652e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ab4202d206077686f60202d205468652073757370656e646564206d656d62657220746f206265206a75646765642e3501202d2060666f726769766560202d204120626f6f6c65616e20726570726573656e74696e672077686574686572207468652073757370656e73696f6e206a756467656d656e74206f726967696e2501202020202020202020202020202020666f726769766573202860747275656029206f722072656a6563747320286066616c7365602920612073757370656e646564206d656d6265722e002c2023203c7765696768743ea4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d6265727329f8202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e646564206d656d6265722e204f2831297101202d20557020746f206f6e652073746f72616765207772697465204f284d292077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d626572206261636b20746f20736f63696574792ef8202d20557020746f20332073746f726167652072656d6f76616c73204f28312920746f20636c65616e20757020612072656d6f766564206d656d6265722e4501202d20557020746f206f6e652073746f72616765207772697465204f2842292077697468204f2842292073656172636820746f2072656d6f766520766f7563686564206269642066726f6d20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e70202d204f6e652073746f726167652072656d6f76616c2e204f2831297c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204229302023203c2f7765696768743e646a756467655f73757370656e6465645f63616e646964617465080c77686f30543a3a4163636f756e744964246a756467656d656e74244a756467656d656e74a0350120416c6c6f772073757370656e646564206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e6465642063616e6469646174652e005d0120496620746865206a756467656d656e742069732060417070726f7665602c20776520616464207468656d20746f20736f63696574792061732061206d656d62657220776974682074686520617070726f70726961746574207061796d656e7420666f72206a6f696e696e6720736f63696574792e00550120496620746865206a756467656d656e74206973206052656a656374602c2077652065697468657220736c61736820746865206465706f736974206f6620746865206269642c20676976696e67206974206261636b110120746f2074686520736f63696574792074726561737572792c206f722077652062616e2074686520766f75636865722066726f6d20766f756368696e6720616761696e2e005d0120496620746865206a756467656d656e7420697320605265626964602c20776520707574207468652063616e646964617465206261636b20696e207468652062696420706f6f6c20616e64206c6574207468656d20676f94207468726f7567682074686520696e64756374696f6e2070726f6365737320616761696e2e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ac0202d206077686f60202d205468652073757370656e6465642063616e64696461746520746f206265206a75646765642ec4202d20606a756467656d656e7460202d2060417070726f7665602c206052656a656374602c206f7220605265626964602e002c2023203c7765696768743ef4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520616374696f6e29f0202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e6465642063616e6469646174652ec8202d204f6e652073746f726167652072656d6f76616c206f66207468652073757370656e6465642063616e6469646174652e40202d20417070726f7665204c6f676963150120092d204f6e652073746f72616765207265616420746f206765742074686520617661696c61626c6520706f7420746f2070617920757365727320776974682e204f283129dc20092d204f6e652073746f7261676520777269746520746f207570646174652074686520617661696c61626c6520706f742e204f283129e820092d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f283129b420092d204f6e652073746f72616765207265616420746f2067657420616c6c206d656d626572732e204f284d29a020092d20557020746f206f6e6520756e726573657276652063757272656e637920616374696f6e2eb020092d20557020746f2074776f206e65772073746f726167652077726974657320746f207061796f7574732e4d0120092d20557020746f206f6e652073746f726167652077726974652077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d62657220746f20736f63696574792e3c202d2052656a656374204c6f676963dc20092d20557020746f206f6e6520726570617472696174652072657365727665642063757272656e637920616374696f6e2e204f2858292d0120092d20557020746f206f6e652073746f7261676520777269746520746f2062616e2074686520766f756368696e67206d656d6265722066726f6d20766f756368696e6720616761696e2e38202d205265626964204c6f676963410120092d2053746f72616765206d75746174652077697468204f286c6f672042292062696e6172792073656172636820746f20706c616365207468652075736572206261636b20696e746f20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e5c202d204f6e652073746f726167652072656d6f76616c2e7c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2042202b205829302023203c2f7765696768743e3c7365745f6d61785f6d656d62657273040c6d61780c753332381d0120416c6c6f777320726f6f74206f726967696e20746f206368616e676520746865206d6178696d756d206e756d626572206f66206d656d6265727320696e20736f63696574792eb4204d6178206d656d6265727368697020636f756e74206d7573742062652067726561746572207468616e20312e00dc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d205f524f4f545f2e003020506172616d65746572733ae4202d20606d617860202d20546865206d6178696d756d206e756d626572206f66206d656d6265727320666f722074686520736f63696574792e002c2023203c7765696768743eb0202d204f6e652073746f7261676520777269746520746f2075706461746520746865206d61782e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e01401c466f756e64656404244163636f756e74496404e82054686520736f636965747920697320666f756e6465642062792074686520676976656e206964656e746974792e205c5b666f756e6465725c5d0c42696408244163636f756e7449641c42616c616e63650861012041206d656d6265727368697020626964206a7573742068617070656e65642e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e64207468656972206f666665729c20697320746865207365636f6e642e205c5b63616e6469646174655f69642c206f666665725c5d14566f7563680c244163636f756e7449641c42616c616e6365244163636f756e7449640861012041206d656d6265727368697020626964206a7573742068617070656e656420627920766f756368696e672e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e647901207468656972206f6666657220697320746865207365636f6e642e2054686520766f756368696e67207061727479206973207468652074686972642e205c5b63616e6469646174655f69642c206f666665722c20766f756368696e675c5d244175746f556e62696404244163636f756e7449640419012041205c5b63616e6469646174655c5d207761732064726f70706564202864756520746f20616e20657863657373206f66206269647320696e207468652073797374656d292e14556e62696404244163636f756e74496404c02041205c5b63616e6469646174655c5d207761732064726f70706564202862792074686569722072657175657374292e1c556e766f75636804244163636f756e7449640409012041205c5b63616e6469646174655c5d207761732064726f70706564202862792072657175657374206f662077686f20766f756368656420666f72207468656d292e20496e64756374656408244163636f756e744964385665633c4163636f756e7449643e08590120412067726f7570206f662063616e646964617465732068617665206265656e20696e6475637465642e205468652062617463682773207072696d617279206973207468652066697273742076616c75652c20746865d420626174636820696e2066756c6c20697320746865207365636f6e642e205c5b7072696d6172792c2063616e646964617465735c5d6053757370656e6465644d656d6265724a756467656d656e7408244163636f756e74496410626f6f6c04d020412073757370656e646564206d656d62657220686173206265656e206a75646765642e205c5b77686f2c206a75646765645c5d4843616e64696461746553757370656e64656404244163636f756e744964048c2041205c5b63616e6469646174655c5d20686173206265656e2073757370656e6465643c4d656d62657253757370656e64656404244163636f756e74496404802041205c5b6d656d6265725c5d20686173206265656e2073757370656e646564284368616c6c656e67656404244163636f756e74496404842041205c5b6d656d6265725c5d20686173206265656e206368616c6c656e67656410566f74650c244163636f756e744964244163636f756e74496410626f6f6c04c8204120766f746520686173206265656e20706c61636564205c5b63616e6469646174652c20766f7465722c20766f74655c5d30446566656e646572566f746508244163636f756e74496410626f6f6c04f8204120766f746520686173206265656e20706c6163656420666f72206120646566656e64696e67206d656d626572205c5b766f7465722c20766f74655c5d344e65774d61784d656d62657273040c75333204a02041206e6577205c5b6d61785c5d206d656d62657220636f756e7420686173206265656e2073657424556e666f756e64656404244163636f756e744964048820536f636965747920697320756e666f756e6465642e205c5b666f756e6465725c5d1c4465706f736974041c42616c616e636504f820536f6d652066756e64732077657265206465706f736974656420696e746f2074686520736f6369657479206163636f756e742e205c5b76616c75655c5d204043616e6469646174654465706f7369743c42616c616e63654f663c542c20493e400080c6a47e8d0300000000000000000004fc20546865206d696e696d756d20616d6f756e74206f662061206465706f73697420726571756972656420666f7220612062696420746f206265206d6164652e4857726f6e6753696465446564756374696f6e3c42616c616e63654f663c542c20493e400080f420e6b5000000000000000000000855012054686520616d6f756e74206f662074686520756e70616964207265776172642074686174206765747320646564756374656420696e207468652063617365207468617420656974686572206120736b6570746963c020646f65736e277420766f7465206f7220736f6d656f6e6520766f74657320696e207468652077726f6e67207761792e284d6178537472696b65730c753332100a00000008750120546865206e756d626572206f662074696d65732061206d656d626572206d617920766f7465207468652077726f6e672077617920286f72206e6f7420617420616c6c2c207768656e207468657920617265206120736b65707469632978206265666f72652074686579206265636f6d652073757370656e6465642e2c506572696f645370656e643c42616c616e63654f663c542c20493e400000c52ebca2b1000000000000000000042d012054686520616d6f756e74206f6620696e63656e7469766520706169642077697468696e206561636820706572696f642e20446f65736e277420696e636c75646520566f7465725469702e38526f746174696f6e506572696f6438543a3a426c6f636b4e756d626572100077010004110120546865206e756d626572206f6620626c6f636b73206265747765656e2063616e6469646174652f6d656d6265727368697020726f746174696f6e20706572696f64732e3c4368616c6c656e6765506572696f6438543a3a426c6f636b4e756d626572108013030004d020546865206e756d626572206f6620626c6f636b73206265747765656e206d656d62657273686970206368616c6c656e6765732e2050616c6c657449642050616c6c657449642070792f736f63696504682054686520736f636965746965732773206d6f64756c65206964484d617843616e646964617465496e74616b650c753332100a0000000490204d6178696d756d2063616e64696461746520696e74616b652070657220726f756e642e482c426164506f736974696f6e049020416e20696e636f727265637420706f736974696f6e207761732070726f76696465642e244e6f744d656d62657204582055736572206973206e6f742061206d656d6265722e34416c72656164794d656d6265720468205573657220697320616c72656164792061206d656d6265722e2453757370656e646564044c20557365722069732073757370656e6465642e304e6f7453757370656e646564045c2055736572206973206e6f742073757370656e6465642e204e6f5061796f7574044c204e6f7468696e6720746f207061796f75742e38416c7265616479466f756e646564046420536f636965747920616c726561647920666f756e6465642e3c496e73756666696369656e74506f74049c204e6f7420656e6f75676820696e20706f7420746f206163636570742063616e6469646174652e3c416c7265616479566f756368696e6704e8204d656d62657220697320616c726561647920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e2e2c4e6f74566f756368696e670460204d656d626572206973206e6f7420766f756368696e672e104865616404942043616e6e6f742072656d6f7665207468652068656164206f662074686520636861696e2e1c466f756e646572046c2043616e6e6f742072656d6f76652074686520666f756e6465722e28416c7265616479426964047420557365722068617320616c7265616479206d6164652061206269642e40416c726561647943616e6469646174650474205573657220697320616c726561647920612063616e6469646174652e304e6f7443616e64696461746504642055736572206973206e6f7420612063616e6469646174652e284d61784d656d62657273048420546f6f206d616e79206d656d6265727320696e2074686520736f63696574792e284e6f74466f756e646572047c205468652063616c6c6572206973206e6f742074686520666f756e6465722e1c4e6f74486561640470205468652063616c6c6572206973206e6f742074686520686561642e1a205265636f7665727901205265636f766572790c2c5265636f76657261626c6500010530543a3a4163636f756e744964e85265636f76657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e0004000409012054686520736574206f66207265636f76657261626c65206163636f756e747320616e64207468656972207265636f7665727920636f6e66696775726174696f6e2e404163746976655265636f76657269657300020530543a3a4163636f756e74496430543a3a4163636f756e744964e84163746976655265636f766572793c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e050400106820416374697665207265636f7665727920617474656d7074732e001501204669727374206163636f756e7420697320746865206163636f756e7420746f206265207265636f76657265642c20616e6420746865207365636f6e64206163636f756e74ac20697320746865207573657220747279696e6720746f207265636f76657220746865206163636f756e742e1450726f787900010230543a3a4163636f756e74496430543a3a4163636f756e7449640004000c9020546865206c697374206f6620616c6c6f7765642070726f7879206163636f756e74732e00f8204d61702066726f6d2074686520757365722077686f2063616e2061636365737320697420746f20746865207265636f7665726564206163636f756e742e01243061735f7265636f7665726564081c6163636f756e7430543a3a4163636f756e7449641063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e34a42053656e6420612063616c6c207468726f7567682061207265636f7665726564206163636f756e742e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a2501202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f752077616e7420746f206d616b6520612063616c6c206f6e2d626568616c662d6f662e0101202d206063616c6c603a205468652063616c6c20796f752077616e7420746f206d616b65207769746820746865207265636f7665726564206163636f756e742e002c2023203c7765696768743e94202d2054686520776569676874206f6620746865206063616c6c60202b2031302c3030302e0901202d204f6e652073746f72616765206c6f6f6b757020746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e347365745f7265636f766572656408106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e744964341d0120416c6c6f7720524f4f5420746f2062797061737320746865207265636f766572792070726f6365737320616e642073657420616e20612072657363756572206163636f756e747420666f722061206c6f7374206163636f756e74206469726563746c792e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f524f4f545f2e003020506172616d65746572733ab8202d20606c6f7374603a2054686520226c6f7374206163636f756e742220746f206265207265636f76657265642e1d01202d206072657363756572603a20546865202272657363756572206163636f756e74222077686963682063616e2063616c6c20617320746865206c6f7374206163636f756e742e002c2023203c7765696768743e64202d204f6e652073746f72616765207772697465204f28312930202d204f6e65206576656e74302023203c2f7765696768743e3c6372656174655f7265636f766572790c1c667269656e6473445665633c543a3a4163636f756e7449643e247468726573686f6c640c7531363064656c61795f706572696f6438543a3a426c6f636b4e756d6265726c5d01204372656174652061207265636f7665727920636f6e66696775726174696f6e20666f7220796f7572206163636f756e742e2054686973206d616b657320796f7572206163636f756e74207265636f76657261626c652e003101205061796d656e743a2060436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732062616c616e636549012077696c6c20626520726573657276656420666f722073746f72696e6720746865207265636f7665727920636f6e66696775726174696f6e2e2054686973206465706f7369742069732072657475726e6564bc20696e2066756c6c207768656e2074686520757365722063616c6c73206072656d6f76655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2501202d2060667269656e6473603a2041206c697374206f6620667269656e647320796f7520747275737420746f20766f75636820666f72207265636f7665727920617474656d7074732ed420202053686f756c64206265206f72646572656420616e6420636f6e7461696e206e6f206475706c69636174652076616c7565732e3101202d20607468726573686f6c64603a20546865206e756d626572206f6620667269656e64732074686174206d75737420766f75636820666f722061207265636f7665727920617474656d70741d012020206265666f726520746865206163636f756e742063616e206265207265636f76657265642e2053686f756c64206265206c657373207468616e206f7220657175616c20746f94202020746865206c656e677468206f6620746865206c697374206f6620667269656e64732e3d01202d206064656c61795f706572696f64603a20546865206e756d626572206f6620626c6f636b732061667465722061207265636f7665727920617474656d707420697320696e697469616c697a6564e820202074686174206e6565647320746f2070617373206265666f726520746865206163636f756e742063616e206265207265636f76657265642e002c2023203c7765696768743e68202d204b65793a204620286c656e206f6620667269656e6473292d01202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973206e6f7420616c7265616479207265636f76657261626c652e204f2831292eec202d204120636865636b20746861742074686520667269656e6473206c69737420697320736f7274656420616e6420756e697175652e204f2846299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f2858299c202d204f6e652073746f726167652077726974652e204f2831292e20436f646563204f2846292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e44696e6974696174655f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496458ec20496e697469617465207468652070726f6365737320666f72207265636f766572696e672061207265636f76657261626c65206163636f756e742e001d01205061796d656e743a20605265636f766572794465706f736974602062616c616e63652077696c6c20626520726573657276656420666f7220696e6974696174696e67207468652501207265636f766572792070726f636573732e2054686973206465706f7369742077696c6c20616c7761797320626520726570617472696174656420746f20746865206163636f756e74b820747279696e6720746f206265207265636f76657265642e205365652060636c6f73655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e2054686973206163636f756e7401012020206e6565647320746f206265207265636f76657261626c652028692e652e20686176652061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743ef8202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973207265636f76657261626c652e204f2846295101202d204f6e652073746f72616765207265616420746f20636865636b20746861742074686973207265636f766572792070726f63657373206861736e277420616c726561647920737461727465642e204f2831299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f285829e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831296c202d204f6e652073746f726167652077726974652e204f2831292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e38766f7563685f7265636f7665727908106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e74496464290120416c6c6f7720612022667269656e6422206f662061207265636f76657261626c65206163636f756e7420746f20766f75636820666f7220616e20616374697665207265636f76657279682070726f6365737320666f722074686174206163636f756e742e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d75737420626520612022667269656e64227420666f7220746865207265636f76657261626c65206163636f756e742e003020506172616d65746572733ad4202d20606c6f7374603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f2072657363756520746865206c6f7374206163636f756e74207468617420796f755420202077616e7420746f20766f75636820666f722e0025012054686520636f6d62696e6174696f6e206f662074686573652074776f20706172616d6574657273206d75737420706f696e7420746f20616e20616374697665207265636f76657279242070726f636573732e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629ec202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c6572206973206120667269656e642e204f286c6f6746291d01202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c657220686173206e6f7420616c726561647920766f75636865642e204f286c6f6756299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e00a420546f74616c20436f6d706c65786974793a204f2846202b206c6f6746202b2056202b206c6f675629302023203c2f7765696768743e38636c61696d5f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496450f420416c6c6f772061207375636365737366756c207265736375657220746f20636c61696d207468656972207265636f7665726564206163636f756e742e002d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061202272657363756572221d012077686f20686173207375636365737366756c6c7920636f6d706c6574656420746865206163636f756e74207265636f766572792070726f636573733a20636f6c6c6563746564310120607468726573686f6c6460206f72206d6f726520766f75636865732c20776169746564206064656c61795f706572696f646020626c6f636b732073696e636520696e6974696174696f6e2e003020506172616d65746572733a2d01202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f20636c61696d20686173206265656e207375636365737366756c6c79502020207265636f766572656420627920796f752e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205629302023203c2f7765696768743e38636c6f73655f7265636f76657279041c7265736375657230543a3a4163636f756e7449645015012041732074686520636f6e74726f6c6c6572206f662061207265636f76657261626c65206163636f756e742c20636c6f736520616e20616374697665207265636f76657279682070726f6365737320666f7220796f7572206163636f756e742e002101205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e2c20746865207265636f76657261626c65206163636f756e742077696c6c2072656365697665f820746865207265636f76657279206465706f73697420605265636f766572794465706f7369746020706c616365642062792074686520726573637565722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061f0207265636f76657261626c65206163636f756e74207769746820616e20616374697665207265636f766572792070726f6365737320666f722069742e003020506172616d65746572733a1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f207265736375652074686973207265636f76657261626c65206163636f756e742e002c2023203c7765696768743e84204b65793a205620286c656e206f6620766f756368696e6720667269656e6473293d01202d204f6e652073746f7261676520726561642f72656d6f766520746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629c0202d204f6e652062616c616e63652063616c6c20746f20726570617472696174652072657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2856202b205829302023203c2f7765696768743e3c72656d6f76655f7265636f7665727900545d012052656d6f766520746865207265636f766572792070726f6365737320666f7220796f7572206163636f756e742e205265636f7665726564206163636f756e747320617265207374696c6c2061636365737369626c652e001501204e4f54453a205468652075736572206d757374206d616b65207375726520746f2063616c6c2060636c6f73655f7265636f7665727960206f6e20616c6c206163746976650901207265636f7665727920617474656d707473206265666f72652063616c6c696e6720746869732066756e6374696f6e20656c73652069742077696c6c206661696c2e002501205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e20746865207265636f76657261626c65206163636f756e742077696c6c20756e7265736572766598207468656972207265636f7665727920636f6e66696775726174696f6e206465706f7369742ef4202860436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732900050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061e4207265636f76657261626c65206163636f756e742028692e652e206861732061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743e60204b65793a204620286c656e206f6620667269656e6473292901202d204f6e652073746f72616765207265616420746f206765742074686520707265666978206974657261746f7220666f7220616374697665207265636f7665726965732e204f2831293901202d204f6e652073746f7261676520726561642f72656d6f766520746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846299c202d204f6e652062616c616e63652063616c6c20746f20756e72657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e4063616e63656c5f7265636f7665726564041c6163636f756e7430543a3a4163636f756e7449642ce02043616e63656c20746865206162696c69747920746f20757365206061735f7265636f76657265646020666f7220606163636f756e74602e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a1901202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f75206172652061626c6520746f2063616c6c206f6e2d626568616c662d6f662e002c2023203c7765696768743e1101202d204f6e652073746f72616765206d75746174696f6e20746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e01183c5265636f766572794372656174656404244163636f756e74496404dc2041207265636f766572792070726f6365737320686173206265656e2073657420757020666f7220616e205c5b6163636f756e745c5d2e445265636f76657279496e6974696174656408244163636f756e744964244163636f756e744964082d012041207265636f766572792070726f6365737320686173206265656e20696e6974696174656420666f72206c6f7374206163636f756e742062792072657363756572206163636f756e742e48205c5b6c6f73742c20726573637565725c5d3c5265636f76657279566f75636865640c244163636f756e744964244163636f756e744964244163636f756e744964085d012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20766f756368656420666f722062792073656e6465722e68205c5b6c6f73742c20726573637565722c2073656e6465725c5d385265636f76657279436c6f73656408244163636f756e744964244163636f756e7449640821012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20636c6f7365642e48205c5b6c6f73742c20726573637565725c5d404163636f756e745265636f766572656408244163636f756e744964244163636f756e744964080501204c6f7374206163636f756e7420686173206265656e207375636365737366756c6c79207265636f76657265642062792072657363756572206163636f756e742e48205c5b6c6f73742c20726573637565725c5d3c5265636f7665727952656d6f76656404244163636f756e74496404e02041207265636f766572792070726f6365737320686173206265656e2072656d6f76656420666f7220616e205c5b6163636f756e745c5d2e1044436f6e6669674465706f736974426173653042616c616e63654f663c543e4000406352bfc60100000000000000000004550120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e4c467269656e644465706f736974466163746f723042616c616e63654f663c543e4000203d88792d000000000000000000000469012054686520616d6f756e74206f662063757272656e6379206e656564656420706572206164646974696f6e616c2075736572207768656e206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e284d6178467269656e64730c753136080900040d0120546865206d6178696d756d20616d6f756e74206f6620667269656e647320616c6c6f77656420696e2061207265636f7665727920636f6e66696775726174696f6e2e3c5265636f766572794465706f7369743042616c616e63654f663c543e4000406352bfc601000000000000000000041d0120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72207374617274696e672061207265636f766572792e44284e6f74416c6c6f77656404f42055736572206973206e6f7420616c6c6f77656420746f206d616b6520612063616c6c206f6e20626568616c66206f662074686973206163636f756e74345a65726f5468726573686f6c640490205468726573686f6c64206d7573742062652067726561746572207468616e207a65726f404e6f74456e6f756768467269656e647304d420467269656e6473206c697374206d7573742062652067726561746572207468616e207a65726f20616e64207468726573686f6c64284d6178467269656e647304ac20467269656e6473206c697374206d757374206265206c657373207468616e206d617820667269656e6473244e6f74536f7274656404cc20467269656e6473206c697374206d75737420626520736f7274656420616e642066726565206f66206475706c696361746573384e6f745265636f76657261626c6504a02054686973206163636f756e74206973206e6f742073657420757020666f72207265636f7665727948416c72656164795265636f76657261626c6504b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f7665727938416c72656164795374617274656404e02041207265636f766572792070726f636573732068617320616c7265616479207374617274656420666f722074686973206163636f756e74284e6f745374617274656404d02041207265636f766572792070726f6365737320686173206e6f74207374617274656420666f7220746869732072657363756572244e6f74467269656e6404ac2054686973206163636f756e74206973206e6f74206120667269656e642077686f2063616e20766f7563682c44656c6179506572696f64041d012054686520667269656e64206d757374207761697420756e74696c207468652064656c617920706572696f6420746f20766f75636820666f722074686973207265636f7665727938416c7265616479566f756368656404c0205468697320757365722068617320616c726561647920766f756368656420666f722074686973207265636f76657279245468726573686f6c6404ec20546865207468726573686f6c6420666f72207265636f766572696e672074686973206163636f756e7420686173206e6f74206265656e206d65742c5374696c6c41637469766504010120546865726520617265207374696c6c20616374697665207265636f7665727920617474656d7074732074686174206e65656420746f20626520636c6f736564204f766572666c6f77049c2054686572652077617320616e206f766572666c6f7720696e20612063616c63756c6174696f6e30416c726561647950726f787904b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f76657279204261645374617465047c20536f6d6520696e7465726e616c2073746174652069732062726f6b656e2e1b1c56657374696e67011c56657374696e67041c56657374696e6700010230543a3a4163636f756e744964a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e00040004d820496e666f726d6174696f6e20726567617264696e67207468652076657374696e67206f66206120676976656e206163636f756e742e011010766573740034bc20556e6c6f636b20616e79207665737465642066756e6473206f66207468652073656e646572206163636f756e742e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652066756e6473207374696c6c68206c6f636b656420756e64657220746869732070616c6c65742e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20322052656164732c203220577269746573fc20202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d010120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d302023203c2f7765696768743e28766573745f6f7468657204187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653cbc20556e6c6f636b20616e79207665737465642066756e6473206f662061206074617267657460206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501202d2060746172676574603a20546865206163636f756e742077686f7365207665737465642066756e64732073686f756c6420626520756e6c6f636b65642e204d75737420686176652066756e6473207374696c6c68206c6f636b656420756e64657220746869732070616c6c65742e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c203320577269746573f420202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e74f820202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e74302023203c2f7765696768743e3c7665737465645f7472616e7366657208187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e406820437265617465206120766573746564207472616e736665722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e001501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c2033205772697465733d0120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745d410120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745d302023203c2f7765696768743e54666f7263655f7665737465645f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e446420466f726365206120766573746564207472616e736665722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00ec202d2060736f75726365603a20546865206163636f756e742077686f73652066756e64732073686f756c64206265207472616e736665727265642e1501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20342052656164732c203420577269746573350120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74390120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74302023203c2f7765696768743e01083856657374696e675570646174656408244163636f756e7449641c42616c616e63650c59012054686520616d6f756e742076657374656420686173206265656e20757064617465642e205468697320636f756c6420696e646963617465206d6f72652066756e64732061726520617661696c61626c652e2054686519012062616c616e636520676976656e2069732074686520616d6f756e74207768696368206973206c65667420756e7665737465642028616e642074687573206c6f636b6564292e58205c5b6163636f756e742c20756e7665737465645c5d4056657374696e67436f6d706c6574656404244163636f756e744964041d0120416e205c5b6163636f756e745c5d20686173206265636f6d652066756c6c79207665737465642e204e6f20667572746865722076657374696e672063616e2068617070656e2e04444d696e5665737465645472616e736665723042616c616e63654f663c543e400000c16ff2862300000000000000000004e820546865206d696e696d756d20616d6f756e74207472616e7366657272656420746f2063616c6c20607665737465645f7472616e73666572602e0c284e6f7456657374696e67048820546865206163636f756e7420676976656e206973206e6f742076657374696e672e5c4578697374696e6756657374696e675363686564756c65045d0120416e206578697374696e672076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e7420746861742063616e6e6f7420626520636c6f6262657265642e24416d6f756e744c6f7704090120416d6f756e74206265696e67207472616e7366657272656420697320746f6f206c6f7720746f2063726561746520612076657374696e67207363686564756c652e1c245363686564756c657201245363686564756c65720c184167656e646101010538543a3a426c6f636b4e756d62657271015665633c4f7074696f6e3c5363686564756c65643c3c5420617320436f6e6669673e3a3a43616c6c2c20543a3a426c6f636b4e756d6265722c20543a3a0a50616c6c6574734f726967696e2c20543a3a4163636f756e7449643e3e3e000400044d01204974656d7320746f2062652065786563757465642c20696e64657865642062792074686520626c6f636b206e756d626572207468617420746865792073686f756c64206265206578656375746564206f6e2e184c6f6f6b75700001051c5665633c75383e6c5461736b416464726573733c543a3a426c6f636b4e756d6265723e000400040101204c6f6f6b75702066726f6d206964656e7469747920746f2074686520626c6f636b206e756d62657220616e6420696e646578206f6620746865207461736b2e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e0118207363686564756c6510107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e287420416e6f6e796d6f75736c79207363686564756c652061207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7390202d2042617365205765696768743a2032322e3239202b202e313236202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64615020202020202d2057726974653a204167656e64613d01202d2057696c6c20757365206261736520776569676874206f662032352077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e1863616e63656c08107768656e38543a3a426c6f636b4e756d62657214696e6465780c75333228982043616e63656c20616e20616e6f6e796d6f75736c79207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032322e3135202b20322e383639202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64617020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f6e616d6564140869641c5665633c75383e107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e285c205363686564756c652061206e616d6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c738c202d2042617365205765696768743a2032392e36202b202e313539202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704d01202d2057696c6c20757365206261736520776569676874206f662033352077686963682073686f756c6420626520676f6f6420666f72206d6f7265207468616e203330207363686564756c65642063616c6c73302023203c2f7765696768743e3063616e63656c5f6e616d6564040869641c5665633c75383e287c2043616e63656c2061206e616d6564207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032342e3931202b20322e393037202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f61667465721014616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e14ac20416e6f6e796d6f75736c79207363686564756c652061207461736b20616674657220612064656c61792e002c2023203c7765696768743e582053616d65206173205b607363686564756c65605d2e302023203c2f7765696768743e507363686564756c655f6e616d65645f6166746572140869641c5665633c75383e14616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e1494205363686564756c652061206e616d6564207461736b20616674657220612064656c61792e002c2023203c7765696768743e702053616d65206173205b607363686564756c655f6e616d6564605d2e302023203c2f7765696768743e010c245363686564756c6564082c426c6f636b4e756d6265720c7533320494205363686564756c656420736f6d65207461736b2e205c5b7768656e2c20696e6465785c5d2043616e63656c6564082c426c6f636b4e756d6265720c75333204902043616e63656c656420736f6d65207461736b2e205c5b7768656e2c20696e6465785c5d28446973706174636865640c605461736b416464726573733c426c6f636b4e756d6265723e3c4f7074696f6e3c5665633c75383e3e384469737061746368526573756c7404ac204469737061746368656420736f6d65207461736b2e205c5b7461736b2c2069642c20726573756c745c5d0010404661696c6564546f5363686564756c650468204661696c656420746f207363686564756c6520612063616c6c204e6f74466f756e6404802043616e6e6f742066696e6420746865207363686564756c65642063616c6c2e5c546172676574426c6f636b4e756d626572496e5061737404a820476976656e2074617267657420626c6f636b206e756d62657220697320696e2074686520706173742e4852657363686564756c654e6f4368616e676504f42052657363686564756c65206661696c6564206265636175736520697420646f6573206e6f74206368616e6765207363686564756c65642074696d652e1d1450726f7879011450726f7879081c50726f7869657301010530543a3a4163636f756e7449644501285665633c50726f7879446566696e6974696f6e3c543a3a4163636f756e7449642c20543a3a50726f7879547970652c20543a3a426c6f636b4e756d6265723e3e2c0a2042616c616e63654f663c543e29004400000000000000000000000000000000000845012054686520736574206f66206163636f756e742070726f786965732e204d61707320746865206163636f756e74207768696368206861732064656c65676174656420746f20746865206163636f756e7473210120776869636820617265206265696e672064656c65676174656420746f2c20746f67657468657220776974682074686520616d6f756e742068656c64206f6e206465706f7369742e34416e6e6f756e63656d656e747301010530543a3a4163636f756e7449643d01285665633c416e6e6f756e63656d656e743c543a3a4163636f756e7449642c2043616c6c486173684f663c543e2c20543a3a426c6f636b4e756d6265723e3e2c0a2042616c616e63654f663c543e290044000000000000000000000000000000000004ac2054686520616e6e6f756e63656d656e7473206d616465206279207468652070726f787920286b6579292e01281470726f78790c107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e3c51012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f726973656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e246164645f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d62657234490120526567697374657220612070726f7879206163636f756e7420666f72207468652073656e64657220746861742069732061626c6520746f206d616b652063616c6c73206f6e2069747320626568616c662e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f206d616b6520612070726f78792e0101202d206070726f78795f74797065603a20546865207065726d697373696f6e7320616c6c6f77656420666f7220746869732070726f7879206163636f756e742e5101202d206064656c6179603a2054686520616e6e6f756e63656d656e7420706572696f64207265717569726564206f662074686520696e697469616c2070726f78792e2057696c6c2067656e6572616c6c7920626518207a65726f2e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3072656d6f76655f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d6265722cac20556e726567697374657220612070726f7879206163636f756e7420666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2901202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f2072656d6f766520617320612070726f78792e4501202d206070726f78795f74797065603a20546865207065726d697373696f6e732063757272656e746c7920656e61626c656420666f72207468652072656d6f7665642070726f7879206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3872656d6f76655f70726f786965730028b820556e726567697374657220616c6c2070726f7879206163636f756e747320666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901205741524e494e473a2054686973206d61792062652063616c6c6564206f6e206163636f756e747320637265617465642062792060616e6f6e796d6f7573602c20686f776576657220696620646f6e652c207468656e5d012074686520756e726573657276656420666565732077696c6c20626520696e61636365737369626c652e202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e24616e6f6e796d6f75730c2870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d62657214696e6465780c7531365c3d0120537061776e2061206672657368206e6577206163636f756e7420746861742069732067756172616e7465656420746f206265206f746865727769736520696e61636365737369626c652c20616e64010120696e697469616c697a65206974207769746820612070726f7879206f66206070726f78795f747970656020666f7220606f726967696e602073656e6465722e0070205265717569726573206120605369676e656460206f726967696e2e005501202d206070726f78795f74797065603a205468652074797065206f66207468652070726f78792074686174207468652073656e6465722077696c6c2062652072656769737465726564206173206f766572207468655101206e6577206163636f756e742e20546869732077696c6c20616c6d6f737420616c7761797320626520746865206d6f7374207065726d697373697665206050726f7879547970656020706f737369626c6520746f7c20616c6c6f7720666f72206d6178696d756d20666c65786962696c6974792e5501202d2060696e646578603a204120646973616d626967756174696f6e20696e6465782c20696e206361736520746869732069732063616c6c6564206d756c7469706c652074696d657320696e207468652073616d656101207472616e73616374696f6e2028652e672e207769746820607574696c6974793a3a626174636860292e20556e6c65737320796f75277265207573696e67206062617463686020796f752070726f6261626c79206a757374442077616e7420746f20757365206030602e5101202d206064656c6179603a2054686520616e6e6f756e63656d656e7420706572696f64207265717569726564206f662074686520696e697469616c2070726f78792e2057696c6c2067656e6572616c6c7920626518207a65726f2e005501204661696c73207769746820604475706c69636174656020696620746869732068617320616c7265616479206265656e2063616c6c656420696e2074686973207472616e73616374696f6e2c2066726f6d207468659c2073616d652073656e6465722c2077697468207468652073616d6520706172616d65746572732e00e8204661696c732069662074686572652061726520696e73756666696369656e742066756e647320746f2070617920666f72206465706f7369742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e9020544f444f3a204d69676874206265206f76657220636f756e74696e6720312072656164386b696c6c5f616e6f6e796d6f7573141c737061776e657230543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f78795479706514696e6465780c753136186865696768745c436f6d706163743c543a3a426c6f636b4e756d6265723e246578745f696e64657830436f6d706163743c7533323e50b82052656d6f76657320612070726576696f75736c7920737061776e656420616e6f6e796d6f75732070726f78792e004d01205741524e494e473a202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a20416e792066756e64732068656c6420696e2069742077696c6c2062653820696e61636365737369626c652e005d01205265717569726573206120605369676e656460206f726967696e2c20616e64207468652073656e646572206163636f756e74206d7573742068617665206265656e206372656174656420627920612063616c6c20746fac2060616e6f6e796d6f757360207769746820636f72726573706f6e64696e6720706172616d65746572732e005101202d2060737061776e6572603a20546865206163636f756e742074686174206f726967696e616c6c792063616c6c65642060616e6f6e796d6f75736020746f206372656174652074686973206163636f756e742e5101202d2060696e646578603a2054686520646973616d626967756174696f6e20696e646578206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e2050726f6261626c79206030602e0501202d206070726f78795f74797065603a205468652070726f78792074797065206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e4101202d2060686569676874603a2054686520686569676874206f662074686520636861696e207768656e207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e4d01202d20606578745f696e646578603a205468652065787472696e73696320696e64657820696e207768696368207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e004d01204661696c73207769746820604e6f5065726d697373696f6e6020696e2063617365207468652063616c6c6572206973206e6f7420612070726576696f75736c79206372656174656420616e6f6e796d6f7573f4206163636f756e742077686f73652060616e6f6e796d6f7573602063616c6c2068617320636f72726573706f6e64696e6720706172616d65746572732e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e20616e6e6f756e636508107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e540901205075626c697368207468652068617368206f6620612070726f78792d63616c6c20746861742077696c6c206265206d61646520696e20746865206675747572652e0061012054686973206d7573742062652063616c6c656420736f6d65206e756d626572206f6620626c6f636b73206265666f72652074686520636f72726573706f6e64696e67206070726f78796020697320617474656d707465642901206966207468652064656c6179206173736f6369617465642077697468207468652070726f78792072656c6174696f6e736869702069732067726561746572207468616e207a65726f2e001501204e6f206d6f7265207468616e20604d617850656e64696e676020616e6e6f756e63656d656e7473206d6179206265206d61646520617420616e79206f6e652074696d652e000d0120546869732077696c6c2074616b652061206465706f736974206f662060416e6e6f756e63656d656e744465706f736974466163746f72602061732077656c6c2061731d012060416e6e6f756e63656d656e744465706f736974426173656020696620746865726520617265206e6f206f746865722070656e64696e6720616e6e6f756e63656d656e74732e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420612070726f7879206f6620607265616c602e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656d6f76655f616e6e6f756e63656d656e7408107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40742052656d6f7665206120676976656e20616e6e6f756e63656d656e742e005d01204d61792062652063616c6c656420627920612070726f7879206163636f756e7420746f2072656d6f766520612063616c6c20746865792070726576696f75736c7920616e6e6f756e63656420616e642072657475726e3420746865206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656a6563745f616e6e6f756e63656d656e74082064656c656761746530543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40b42052656d6f76652074686520676976656e20616e6e6f756e63656d656e74206f6620612064656c65676174652e006501204d61792062652063616c6c6564206279206120746172676574202870726f7869656429206163636f756e7420746f2072656d6f766520612063616c6c2074686174206f6e65206f662074686569722064656c656761746573290120286064656c656761746560292068617320616e6e6f756e63656420746865792077616e7420746f20657865637574652e20546865206465706f7369742069732072657475726e65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733af8202d206064656c6567617465603a20546865206163636f756e7420746861742070726576696f75736c7920616e6e6f756e636564207468652063616c6c2ec0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e3c70726f78795f616e6e6f756e636564102064656c656761746530543a3a4163636f756e744964107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e4451012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f72697a656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e010c3450726f7879457865637574656404384469737061746368526573756c7404ec20412070726f78792077617320657865637574656420636f72726563746c792c20776974682074686520676976656e205c5b726573756c745c5d2e40416e6f6e796d6f75734372656174656410244163636f756e744964244163636f756e7449642450726f7879547970650c75313608ec20416e6f6e796d6f7573206163636f756e7420686173206265656e2063726561746564206279206e65772070726f7879207769746820676976656e690120646973616d626967756174696f6e20696e64657820616e642070726f787920747970652e205c5b616e6f6e796d6f75732c2077686f2c2070726f78795f747970652c20646973616d626967756174696f6e5f696e6465785c5d24416e6e6f756e6365640c244163636f756e744964244163636f756e744964104861736804510120416e20616e6e6f756e63656d656e742077617320706c6163656420746f206d616b6520612063616c6c20696e20746865206675747572652e205c5b7265616c2c2070726f78792c2063616c6c5f686173685c5d184050726f78794465706f736974426173653042616c616e63654f663c543e4000f09e544c390000000000000000000010110120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e6720612070726f78792e00010120546869732069732068656c6420666f7220616e206164646974696f6e616c2073746f72616765206974656d2077686f73652076616c75652073697a652069732501206073697a656f662842616c616e6365296020627974657320616e642077686f7365206b65792073697a65206973206073697a656f66284163636f756e74496429602062797465732e4850726f78794465706f736974466163746f723042616c616e63654f663c543e400060aa7714b40000000000000000000014bc2054686520616d6f756e74206f662063757272656e6379206e6565646564207065722070726f78792061646465642e00690120546869732069732068656c6420666f7220616464696e6720333220627974657320706c757320616e20696e7374616e6365206f66206050726f78795479706560206d6f726520696e746f2061207072652d6578697374696e6761012073746f726167652076616c75652e20546875732c207768656e20636f6e6669677572696e67206050726f78794465706f736974466163746f7260206f6e652073686f756c642074616b6520696e746f206163636f756e74c020603332202b2070726f78795f747970652e656e636f646528292e6c656e282960206279746573206f6620646174612e284d617850726f786965730c75313608200004f020546865206d6178696d756d20616d6f756e74206f662070726f7869657320616c6c6f77656420666f7220612073696e676c65206163636f756e742e284d617850656e64696e670c753332102000000004450120546865206d6178696d756d20616d6f756e74206f662074696d652d64656c6179656420616e6e6f756e63656d656e747320746861742061726520616c6c6f77656420746f2062652070656e64696e672e5c416e6e6f756e63656d656e744465706f736974426173653042616c616e63654f663c543e4000f09e544c39000000000000000000000c310120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e6720616e20616e6e6f756e63656d656e742e00690120546869732069732068656c64207768656e2061206e65772073746f72616765206974656d20686f6c64696e672061206042616c616e636560206973206372656174656420287479706963616c6c79203136206279746573292e64416e6e6f756e63656d656e744465706f736974466163746f723042616c616e63654f663c543e4000c054ef28680100000000000000000010d42054686520616d6f756e74206f662063757272656e6379206e65656465642070657220616e6e6f756e63656d656e74206d6164652e00590120546869732069732068656c6420666f7220616464696e6720616e20604163636f756e744964602c2060486173686020616e642060426c6f636b4e756d6265726020287479706963616c6c79203638206279746573298c20696e746f2061207072652d6578697374696e672073746f726167652076616c75652e201c546f6f4d616e790425012054686572652061726520746f6f206d616e792070726f786965732072656769737465726564206f7220746f6f206d616e7920616e6e6f756e63656d656e74732070656e64696e672e204e6f74466f756e6404782050726f787920726567697374726174696f6e206e6f7420666f756e642e204e6f7450726f787904d02053656e646572206973206e6f7420612070726f7879206f6620746865206163636f756e7420746f2062652070726f786965642e2c556e70726f787961626c6504250120412063616c6c20776869636820697320696e636f6d70617469626c652077697468207468652070726f7879207479706527732066696c7465722077617320617474656d707465642e244475706c69636174650470204163636f756e7420697320616c726561647920612070726f78792e304e6f5065726d697373696f6e0419012043616c6c206d6179206e6f74206265206d6164652062792070726f78792062656361757365206974206d617920657363616c617465206974732070726976696c656765732e2c556e616e6e6f756e63656404d420416e6e6f756e63656d656e742c206966206d61646520617420616c6c2c20776173206d61646520746f6f20726563656e746c792e2c4e6f53656c6650726f787904682043616e6e6f74206164642073656c662061732070726f78792e1e204d756c746973696701204d756c746973696708244d756c74697369677300020530543a3a4163636f756e744964205b75383b2033325dd04d756c74697369673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e02040004942054686520736574206f66206f70656e206d756c7469736967206f7065726174696f6e732e1443616c6c73000106205b75383b2033325da0284f706171756543616c6c2c20543a3a4163636f756e7449642c2042616c616e63654f663c543e290004000001105061735f6d756c74695f7468726573686f6c645f3108446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e40550120496d6d6564696174656c792064697370617463682061206d756c74692d7369676e61747572652063616c6c207573696e6720612073696e676c6520617070726f76616c2066726f6d207468652063616c6c65722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e004101202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f206172652070617274206f66207468650501206d756c74692d7369676e61747572652c2062757420646f206e6f7420706172746963697061746520696e2074686520617070726f76616c2070726f636573732e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e00bc20526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c742e002c2023203c7765696768743e1d01204f285a202b204329207768657265205a20697320746865206c656e677468206f66207468652063616c6c20616e6420432069747320657865637574696f6e207765696768742e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d48202d204442205765696768743a204e6f6e654c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e2061735f6d756c746918247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e1063616c6c284f706171756543616c6c2873746f72655f63616c6c10626f6f6c286d61785f77656967687418576569676874b8590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e00b42049662074686572652061726520656e6f7567682c207468656e206469737061746368207468652063616c6c2e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e002101204e4f54453a20556e6c6573732074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2067656e6572616c6c792077616e7420746f207573651d012060617070726f76655f61735f6d756c74696020696e73746561642c2073696e6365206974206f6e6c7920726571756972657320612068617368206f66207468652063616c6c2e005d0120526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c7420696620607468726573686f6c64602069732065786163746c79206031602e204f74686572776973655901206f6e20737563636573732c20726573756c7420697320604f6b6020616e642074686520726573756c742066726f6d2074686520696e746572696f722063616c6c2c206966206974207761732065786563757465642ce0206d617920626520666f756e6420696e20746865206465706f736974656420604d756c7469736967457865637574656460206576656e742e002c2023203c7765696768743e54202d20604f2853202b205a202b2043616c6c29602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2e2501202d204f6e652063616c6c20656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285a296020776865726520605a602069732074782d6c656e2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e70202d2054686520776569676874206f6620746865206063616c6c602e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a250120202020202d2052656164733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c6029290120202020202d205772697465733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c60294c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e40617070726f76655f61735f6d756c746914247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e2463616c6c5f68617368205b75383b2033325d286d61785f7765696768741857656967687490590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e003901204e4f54453a2049662074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2077616e7420746f20757365206061735f6d756c74696020696e73746561642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743abc20202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745dc020202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d302023203c2f7765696768743e3c63616e63656c5f61735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e2474696d65706f696e746454696d65706f696e743c543a3a426c6f636b4e756d6265723e2463616c6c5f68617368205b75383b2033325d6859012043616e63656c2061207072652d6578697374696e672c206f6e2d676f696e67206d756c7469736967207472616e73616374696f6e2e20416e79206465706f7369742072657365727665642070726576696f75736c79c820666f722074686973206f7065726174696f6e2077696c6c20626520756e7265736572766564206f6e20737563636573732e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e6101202d206074696d65706f696e74603a205468652074696d65706f696e742028626c6f636b206e756d62657220616e64207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c7c207472616e73616374696f6e20666f7220746869732064697370617463682ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602e34202d204f6e65206576656e742e88202d20492f4f3a2031207265616420604f285329602c206f6e652072656d6f76652e74202d2053746f726167653a2072656d6f766573206f6e65206974656d2e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a190120202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c731d0120202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c73302023203c2f7765696768743e01102c4e65774d756c74697369670c244163636f756e744964244163636f756e7449642043616c6c48617368041d012041206e6577206d756c7469736967206f7065726174696f6e2068617320626567756e2e205c5b617070726f76696e672c206d756c74697369672c2063616c6c5f686173685c5d404d756c7469736967417070726f76616c10244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c4861736808cc2041206d756c7469736967206f7065726174696f6e20686173206265656e20617070726f76656420627920736f6d656f6e652eb8205c5b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d404d756c7469736967457865637574656414244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c48617368384469737061746368526573756c740459012041206d756c7469736967206f7065726174696f6e20686173206265656e2065786563757465642e205c5b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d444d756c746973696743616e63656c6c656410244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c486173680461012041206d756c7469736967206f7065726174696f6e20686173206265656e2063616e63656c6c65642e205c5b63616e63656c6c696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d0c2c4465706f736974426173653042616c616e63654f663c543e4000f01c0adbed0100000000000000000008710120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e672061206d756c746973696720657865637574696f6e206f7220746f2073746f72656c20612064697370617463682063616c6c20666f72206c617465722e344465706f736974466163746f723042616c616e63654f663c543e400000cc7b9fae000000000000000000000455012054686520616d6f756e74206f662063757272656e6379206e65656465642070657220756e6974207468726573686f6c64207768656e206372656174696e672061206d756c746973696720657865637574696f6e2e384d61785369676e61746f726965730c75313608640004010120546865206d6178696d756d20616d6f756e74206f66207369676e61746f7269657320616c6c6f77656420666f72206120676976656e206d756c74697369672e38404d696e696d756d5468726573686f6c640480205468726573686f6c64206d7573742062652032206f7220677265617465722e3c416c7265616479417070726f76656404b02043616c6c20697320616c726561647920617070726f7665642062792074686973207369676e61746f72792e444e6f417070726f76616c734e656564656404a02043616c6c20646f65736e2774206e65656420616e7920286d6f72652920617070726f76616c732e44546f6f4665775369676e61746f7269657304ac2054686572652061726520746f6f20666577207369676e61746f7269657320696e20746865206c6973742e48546f6f4d616e795369676e61746f7269657304b02054686572652061726520746f6f206d616e79207369676e61746f7269657320696e20746865206c6973742e545369676e61746f726965734f75744f664f7264657204110120546865207369676e61746f7269657320776572652070726f7669646564206f7574206f66206f726465723b20746865792073686f756c64206265206f7264657265642e4c53656e646572496e5369676e61746f72696573041101205468652073656e6465722077617320636f6e7461696e656420696e20746865206f74686572207369676e61746f726965733b2069742073686f756c646e27742062652e204e6f74466f756e6404e0204d756c7469736967206f7065726174696f6e206e6f7420666f756e64207768656e20617474656d7074696e6720746f2063616e63656c2e204e6f744f776e6572043101204f6e6c7920746865206163636f756e742074686174206f726967696e616c6c79206372656174656420746865206d756c74697369672069732061626c6520746f2063616e63656c2069742e2c4e6f54696d65706f696e74042101204e6f2074696d65706f696e742077617320676976656e2c2079657420746865206d756c7469736967206f7065726174696f6e20697320616c726561647920756e6465727761792e3857726f6e6754696d65706f696e74043101204120646966666572656e742074696d65706f696e742077617320676976656e20746f20746865206d756c7469736967206f7065726174696f6e207468617420697320756e6465727761792e4c556e657870656374656454696d65706f696e7404f820412074696d65706f696e742077617320676976656e2c20796574206e6f206d756c7469736967206f7065726174696f6e20697320756e6465727761792e3c4d6178576569676874546f6f4c6f7704d420546865206d6178696d756d2077656967687420696e666f726d6174696f6e2070726f76696465642077617320746f6f206c6f772e34416c726561647953746f72656404a420546865206461746120746f2062652073746f72656420697320616c72656164792073746f7265642e1f20426f756e7469657301205472656173757279102c426f756e7479436f756e7401002c426f756e7479496e646578100000000004c0204e756d626572206f6620626f756e74792070726f706f73616c7320746861742068617665206265656e206d6164652e20426f756e746965730001052c426f756e7479496e646578c8426f756e74793c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e000400047820426f756e7469657320746861742068617665206265656e206d6164652e48426f756e74794465736372697074696f6e730001052c426f756e7479496e6465781c5665633c75383e000400048020546865206465736372697074696f6e206f66206561636820626f756e74792e3c426f756e7479417070726f76616c730100405665633c426f756e7479496e6465783e040004ec20426f756e747920696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f74207965742066756e6465642e01243870726f706f73655f626f756e7479081476616c756554436f6d706163743c42616c616e63654f663c543e3e2c6465736372697074696f6e1c5665633c75383e30582050726f706f73652061206e657720626f756e74792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c20617355012060446174614465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e2049742077696c6c20626520756e72657365727665642075706f6e20617070726f76616c2c68206f7220736c6173686564207768656e2072656a65637465642e00fc202d206063757261746f72603a205468652063757261746f72206163636f756e742077686f6d2077696c6c206d616e616765207468697320626f756e74792e68202d2060666565603a205468652063757261746f72206665652e2901202d206076616c7565603a2054686520746f74616c207061796d656e7420616d6f756e74206f66207468697320626f756e74792c2063757261746f722066656520696e636c756465642ec4202d20606465736372697074696f6e603a20546865206465736372697074696f6e206f66207468697320626f756e74792e38617070726f76655f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e20610120417070726f7665206120626f756e74792070726f706f73616c2e2041742061206c617465722074696d652c2074686520626f756e74792077696c6c2062652066756e64656420616e64206265636f6d6520616374697665ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e3c70726f706f73655f63757261746f720c24626f756e74795f696450436f6d706163743c426f756e7479496e6465783e1c63757261746f728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263650c66656554436f6d706163743c42616c616e63654f663c543e3e1c942041737369676e20612063757261746f7220746f20612066756e64656420626f756e74792e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e40756e61737369676e5f63757261746f720424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e488020556e61737369676e2063757261746f722066726f6d206120626f756e74792e00210120546869732066756e6374696f6e2063616e206f6e6c792062652063616c6c656420627920746865206052656a6563744f726967696e602061207369676e6564206f726967696e2e00690120496620746869732066756e6374696f6e2069732063616c6c656420627920746865206052656a6563744f726967696e602c20776520617373756d652074686174207468652063757261746f72206973206d616c6963696f75730d01206f7220696e6163746976652e204173206120726573756c742c2077652077696c6c20736c617368207468652063757261746f72207768656e20706f737369626c652e00650120496620746865206f726967696e206973207468652063757261746f722c2077652074616b6520746869732061732061207369676e20746865792061726520756e61626c6520746f20646f207468656972206a6f6220616e64610120746865792077696c6c696e676c7920676976652075702e20576520636f756c6420736c617368207468656d2c2062757420666f72206e6f7720776520616c6c6f77207468656d20746f207265636f7665722074686569723901206465706f73697420616e64206578697420776974686f75742069737375652e20285765206d61792077616e7420746f206368616e67652074686973206966206974206973206162757365642e290061012046696e616c6c792c20746865206f726967696e2063616e20626520616e796f6e6520696620616e64206f6e6c79206966207468652063757261746f722069732022696e616374697665222e205468697320616c6c6f7773650120616e796f6e6520696e2074686520636f6d6d756e69747920746f2063616c6c206f7574207468617420612063757261746f72206973206e6f7420646f696e67207468656972206475652064696c6967656e63652c20616e643d012077652073686f756c64207069636b2061206e65772063757261746f722e20496e20746869732063617365207468652063757261746f722073686f756c6420616c736f20626520736c61736865642e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e386163636570745f63757261746f720424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e209820416363657074207468652063757261746f7220726f6c6520666f72206120626f756e74792e2d012041206465706f7369742077696c6c2062652072657365727665642066726f6d2063757261746f7220616e6420726566756e642075706f6e207375636365737366756c207061796f75742e0094204d6179206f6e6c792062652063616c6c65642066726f6d207468652063757261746f722e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e3061776172645f626f756e74790824626f756e74795f696450436f6d706163743c426f756e7479496e6465783e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528990120417761726420626f756e747920746f20612062656e6566696369617279206163636f756e742e205468652062656e65666963696172792077696c6c2062652061626c6520746f20636c61696d207468652066756e647320616674657220612064656c61792e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652063757261746f72206f66207468697320626f756e74792e008c202d2060626f756e74795f6964603a20426f756e747920494420746f2061776172642e1d01202d206062656e6566696369617279603a205468652062656e6566696369617279206163636f756e742077686f6d2077696c6c207265636569766520746865207061796f75742e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e30636c61696d5f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e24f020436c61696d20746865207061796f75742066726f6d20616e206177617264656420626f756e7479206166746572207061796f75742064656c61792e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652062656e6566696369617279206f66207468697320626f756e74792e008c202d2060626f756e74795f6964603a20426f756e747920494420746f20636c61696d2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e30636c6f73655f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e283d012043616e63656c20612070726f706f736564206f722061637469766520626f756e74792e20416c6c207468652066756e64732077696c6c2062652073656e7420746f20747265617375727920616e64d0207468652063757261746f72206465706f7369742077696c6c20626520756e726573657276656420696620706f737369626c652e00cc204f6e6c792060543a3a52656a6563744f726967696e602069732061626c6520746f2063616e63656c206120626f756e74792e0090202d2060626f756e74795f6964603a20426f756e747920494420746f2063616e63656c2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e50657874656e645f626f756e74795f6578706972790824626f756e74795f696450436f6d706163743c426f756e7479496e6465783e1c5f72656d61726b1c5665633c75383e28b020457874656e6420746865206578706972792074696d65206f6620616e2061637469766520626f756e74792e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652063757261746f72206f66207468697320626f756e74792e0090202d2060626f756e74795f6964603a20426f756e747920494420746f20657874656e642e90202d206072656d61726b603a206164646974696f6e616c20696e666f726d6174696f6e2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e011c38426f756e747950726f706f736564042c426f756e7479496e646578047c204e657720626f756e74792070726f706f73616c2e205c5b696e6465785c5d38426f756e747952656a6563746564082c426f756e7479496e6465781c42616c616e6365041101204120626f756e74792070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e205c5b696e6465782c20626f6e645c5d48426f756e7479426563616d65416374697665042c426f756e7479496e64657804e4204120626f756e74792070726f706f73616c2069732066756e64656420616e6420626563616d65206163746976652e205c5b696e6465785c5d34426f756e747941776172646564082c426f756e7479496e646578244163636f756e74496404f4204120626f756e7479206973206177617264656420746f20612062656e65666963696172792e205c5b696e6465782c2062656e65666963696172795c5d34426f756e7479436c61696d65640c2c426f756e7479496e6465781c42616c616e6365244163636f756e744964040d01204120626f756e747920697320636c61696d65642062792062656e65666963696172792e205c5b696e6465782c207061796f75742c2062656e65666963696172795c5d38426f756e747943616e63656c6564042c426f756e7479496e6465780484204120626f756e74792069732063616e63656c6c65642e205c5b696e6465785c5d38426f756e7479457874656e646564042c426f756e7479496e646578049c204120626f756e74792065787069727920697320657874656e6465642e205c5b696e6465785c5d1c48446174614465706f736974506572427974653042616c616e63654f663c543e400010a5d4e8000000000000000000000004fc2054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e20626f756e7479206465736372697074696f6e2e44426f756e74794465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004e82054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120626f756e74792070726f706f73616c2e60426f756e74794465706f7369745061796f757444656c617938543a3a426c6f636b4e756d6265721080700000045901205468652064656c617920706572696f6420666f72207768696368206120626f756e74792062656e6566696369617279206e65656420746f2077616974206265666f726520636c61696d20746865207061796f75742e48426f756e7479557064617465506572696f6438543a3a426c6f636b4e756d6265721000270600046c20426f756e7479206475726174696f6e20696e20626c6f636b732e50426f756e747943757261746f724465706f7369741c5065726d696c6c1020a10700046d012050657263656e74616765206f66207468652063757261746f722066656520746861742077696c6c20626520726573657276656420757066726f6e74206173206465706f73697420666f7220626f756e74792063757261746f722e48426f756e747956616c75654d696e696d756d3042616c616e63654f663c543e4000406352bfc6010000000000000000000470204d696e696d756d2076616c756520666f72206120626f756e74792e4c4d6178696d756d526561736f6e4c656e6774680c75333210004000000488204d6178696d756d2061636365707461626c6520726561736f6e206c656e6774682e2470496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e30496e76616c6964496e6465780494204e6f2070726f706f73616c206f7220626f756e7479206174207468617420696e6465782e30526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e40556e657870656374656453746174757304842054686520626f756e74792073746174757320697320756e65787065637465642e385265717569726543757261746f720460205265717569726520626f756e74792063757261746f722e30496e76616c696456616c7565045820496e76616c696420626f756e74792076616c75652e28496e76616c6964466565045020496e76616c696420626f756e7479206665652e3450656e64696e675061796f75740870204120626f756e7479207061796f75742069732070656e64696e672efc20546f2063616e63656c2074686520626f756e74792c20796f75206d75737420756e61737369676e20616e6420736c617368207468652063757261746f722e245072656d61747572650449012054686520626f756e746965732063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e201054697073012054726561737572790810546970730001051c543a3a48617368f04f70656e5469703c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265722c20543a3a486173683e0004000c650120546970734d6170207468617420617265206e6f742079657420636f6d706c657465642e204b65796564206279207468652068617368206f66206028726561736f6e2c2077686f29602066726f6d207468652076616c75652e3d012054686973206861732074686520696e73656375726520656e756d657261626c6520686173682066756e6374696f6e2073696e636520746865206b657920697473656c6620697320616c7265616479802067756172616e7465656420746f20626520612073656375726520686173682e1c526561736f6e730001061c543a3a486173681c5665633c75383e0004000849012053696d706c6520707265696d616765206c6f6f6b75702066726f6d2074686520726561736f6e2773206861736820746f20746865206f726967696e616c20646174612e20416761696e2c2068617320616e610120696e73656375726520656e756d657261626c6520686173682073696e636520746865206b65792069732067756172616e7465656420746f2062652074686520726573756c74206f6620612073656375726520686173682e0118387265706f72745f617765736f6d650818726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e7449644c5d01205265706f727420736f6d657468696e672060726561736f6e60207468617420646573657276657320612074697020616e6420636c61696d20616e79206576656e7475616c207468652066696e6465722773206665652e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c206173c02060446174614465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743ecc202d20436f6d706c65786974793a20604f2852296020776865726520605260206c656e677468206f662060726561736f6e602e942020202d20656e636f64696e6720616e642068617368696e67206f662027726561736f6e2774202d20446252656164733a2060526561736f6e73602c2060546970736078202d2044625772697465733a2060526561736f6e73602c20605469707360302023203c2f7765696768743e2c726574726163745f7469700410686173681c543a3a486173684c550120526574726163742061207072696f72207469702d7265706f72742066726f6d20607265706f72745f617765736f6d65602c20616e642063616e63656c207468652070726f63657373206f662074697070696e672e00e0204966207375636365737366756c2c20746865206f726967696e616c206465706f7369742077696c6c20626520756e72657365727665642e00510120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642074686520746970206964656e746966696564206279206068617368604501206d7573742068617665206265656e207265706f7274656420627920746865207369676e696e67206163636f756e74207468726f75676820607265706f72745f617765736f6d65602028616e64206e6f7450207468726f75676820607469705f6e657760292e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e009020456d697473206054697052657472616374656460206966207375636365737366756c2e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960dc2020202d20446570656e6473206f6e20746865206c656e677468206f662060543a3a48617368602077686963682069732066697865642e90202d20446252656164733a206054697073602c20606f726967696e206163636f756e7460c0202d2044625772697465733a2060526561736f6e73602c206054697073602c20606f726967696e206163636f756e7460302023203c2f7765696768743e1c7469705f6e65770c18726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e744964247469705f76616c756554436f6d706163743c42616c616e63654f663c543e3e58f4204769766520612074697020666f7220736f6d657468696e67206e65773b206e6f2066696e6465722773206665652077696c6c2062652074616b656e2e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743e5501202d20436f6d706c65786974793a20604f2852202b2054296020776865726520605260206c656e677468206f662060726561736f6e602c2060546020697320746865206e756d626572206f6620746970706572732ec02020202d20604f285429603a206465636f64696e6720605469707065726020766563206f66206c656e6774682060546009012020202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e0d0120202020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602ee42020202d20604f285229603a2068617368696e6720616e6420656e636f64696e67206f6620726561736f6e206f66206c656e6774682060526080202d20446252656164733a206054697070657273602c2060526561736f6e736078202d2044625772697465733a2060526561736f6e73602c20605469707360302023203c2f7765696768743e0c7469700810686173681c543a3a48617368247469705f76616c756554436f6d706163743c42616c616e63654f663c543e3e64b4204465636c6172652061207469702076616c756520666f7220616e20616c72656164792d6f70656e207469702e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f66207468652068617368206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279382020206163636f756e742049442e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e00650120456d6974732060546970436c6f73696e676020696620746865207468726573686f6c64206f66207469707065727320686173206265656e207265616368656420616e642074686520636f756e74646f776e20706572696f64342068617320737461727465642e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e15012020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602c20696e736572742074697020616e6420636865636b20636c6f73696e672c0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602e00610120202041637475616c6c792077656967687420636f756c64206265206c6f77657220617320697420646570656e6473206f6e20686f77206d616e7920746970732061726520696e20604f70656e5469706020627574206974d4202020697320776569676874656420617320696620616c6d6f73742066756c6c20692e65206f66206c656e6774682060542d31602e74202d20446252656164733a206054697070657273602c206054697073604c202d2044625772697465733a20605469707360302023203c2f7765696768743e24636c6f73655f7469700410686173681c543a3a48617368446020436c6f736520616e64207061796f75742061207469702e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0019012054686520746970206964656e74696669656420627920606861736860206d75737420686176652066696e69736865642069747320636f756e74646f776e20706572696f642e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e9c2020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602e0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602eac202d20446252656164733a206054697073602c206054697070657273602c20607469702066696e64657260dc202d2044625772697465733a2060526561736f6e73602c206054697073602c206054697070657273602c20607469702066696e64657260302023203c2f7765696768743e24736c6173685f7469700410686173681c543a3a4861736830982052656d6f766520616e6420736c61736820616e20616c72656164792d6f70656e207469702e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656a6563744f726967696e602e00f8204173206120726573756c742c207468652066696e64657220697320736c617368656420616e6420746865206465706f7369747320617265206c6f73742e008820456d6974732060546970536c617368656460206966207375636365737366756c2e002c2023203c7765696768743e0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602e302023203c2f7765696768743e0114184e657754697004104861736804cc2041206e6577207469702073756767657374696f6e20686173206265656e206f70656e65642e205c5b7469705f686173685c5d28546970436c6f73696e670410486173680411012041207469702073756767657374696f6e206861732072656163686564207468726573686f6c6420616e6420697320636c6f73696e672e205c5b7469705f686173685c5d24546970436c6f7365640c1048617368244163636f756e7449641c42616c616e636504f02041207469702073756767657374696f6e20686173206265656e20636c6f7365642e205c5b7469705f686173682c2077686f2c207061796f75745c5d3054697052657472616374656404104861736804c82041207469702073756767657374696f6e20686173206265656e207265747261637465642e205c5b7469705f686173685c5d28546970536c61736865640c1048617368244163636f756e7449641c42616c616e63650405012041207469702073756767657374696f6e20686173206265656e20736c61736865642e205c5b7469705f686173682c2066696e6465722c206465706f7369745c5d1430546970436f756e74646f776e38543a3a426c6f636b4e756d62657210807000000445012054686520706572696f6420666f722077686963682061207469702072656d61696e73206f70656e20616674657220697320686173206163686965766564207468726573686f6c6420746970706572732e3454697046696e646572734665651c50657263656e7404140431012054686520616d6f756e74206f66207468652066696e616c2074697020776869636820676f657320746f20746865206f726967696e616c207265706f72746572206f6620746865207469702e505469705265706f72744465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004d42054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120746970207265706f72742e48446174614465706f736974506572427974653042616c616e63654f663c543e400010a5d4e800000000000000000000000409012054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e2074686520746970207265706f727420726561736f6e2e4c4d6178696d756d526561736f6e4c656e6774680c75333210004000000488204d6178696d756d2061636365707461626c6520726561736f6e206c656e6774682e1830526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e30416c72656164794b6e6f776e048c20546865207469702077617320616c726561647920666f756e642f737461727465642e28556e6b6e6f776e54697004642054686520746970206861736820697320756e6b6e6f776e2e244e6f7446696e64657204210120546865206163636f756e7420617474656d7074696e6720746f20726574726163742074686520746970206973206e6f74207468652066696e646572206f6620746865207469702e245374696c6c4f70656e042d0120546865207469702063616e6e6f7420626520636c61696d65642f636c6f736564206265636175736520746865726520617265206e6f7420656e6f7567682074697070657273207965742e245072656d617475726504350120546865207469702063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e211841737365747301184173736574731014417373657400010228543a3a41737365744964f8417373657444657461696c733c543a3a42616c616e63652c20543a3a4163636f756e7449642c204465706f73697442616c616e63654f663c542c20493e3e00040004542044657461696c73206f6620616e2061737365742e1c4163636f756e7401020228543a3a4173736574496430543a3a4163636f756e74496488417373657442616c616e63653c543a3a42616c616e63652c20543a3a45787472613e02280000000000000000000004e420546865206e756d626572206f6620756e697473206f66206173736574732068656c6420627920616e7920676976656e206163636f756e742e24417070726f76616c7300020228543a3a4173736574496464417070726f76616c4b65793c543a3a4163636f756e7449643eb0417070726f76616c3c543a3a42616c616e63652c204465706f73697442616c616e63654f663c542c20493e3e02040008590120417070726f7665642062616c616e6365207472616e73666572732e2046697273742062616c616e63652069732074686520616d6f756e7420617070726f76656420666f72207472616e736665722e205365636f6e64e82069732074686520616d6f756e74206f662060543a3a43757272656e63796020726573657276656420666f722073746f72696e6720746869732e204d6574616461746101010228543a3a417373657449649441737365744d657461646174613c4465706f73697442616c616e63654f663c542c20493e3e005000000000000000000000000000000000000000000458204d65746164617461206f6620616e2061737365742e015c186372656174650c0869644c436f6d706163743c543a3a417373657449643e1461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c6d696e5f62616c616e636528543a3a42616c616e63654cec2049737375652061206e657720636c617373206f662066756e6769626c65206173736574732066726f6d2061207075626c6963206f726967696e2e0029012054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c7920616e6420697473206f776e657220697320746865206f726967696e2e00290120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d75737420686176652073756666696369656e742066756e647320667265652e00c02046756e6473206f662073656e64657220617265207265736572766564206279206041737365744465706f736974602e003020506172616d65746572733a5d01202d20606964603a20546865206964656e746966696572206f6620746865206e65772061737365742e2054686973206d757374206e6f742062652063757272656e746c7920696e2075736520746f206964656e746966794c20616e206578697374696e672061737365742e5d01202d206061646d696e603a205468652061646d696e206f66207468697320636c617373206f66206173736574732e205468652061646d696e2069732074686520696e697469616c2061646472657373206f662065616368a0206d656d626572206f662074686520617373657420636c61737327732061646d696e207465616d2e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e009c20456d69747320604372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f2831296030666f7263655f637265617465100869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653469735f73756666696369656e7410626f6f6c2c6d696e5f62616c616e63654c436f6d706163743c543a3a42616c616e63653e54fc2049737375652061206e657720636c617373206f662066756e6769626c65206173736574732066726f6d20612070726976696c65676564206f726967696e2e00b82054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c792e00a820546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e602e00a020556e6c696b652060637265617465602c206e6f2066756e6473206172652072657365727665642e005d01202d20606964603a20546865206964656e746966696572206f6620746865206e65772061737365742e2054686973206d757374206e6f742062652063757272656e746c7920696e2075736520746f206964656e746966794c20616e206578697374696e672061737365742e5d01202d20606f776e6572603a20546865206f776e6572206f66207468697320636c617373206f66206173736574732e20546865206f776e6572206861732066756c6c20737570657275736572207065726d697373696f6e737d01206f76657220746869732061737365742c20627574206d6179206c61746572206368616e676520616e6420636f6e66696775726520746865207065726d697373696f6e73207573696e6720607472616e736665725f6f776e657273686970604020616e6420607365745f7465616d602e5901202d20606d61785f7a6f6d62696573603a2054686520746f74616c206e756d626572206f66206163636f756e7473207768696368206d617920686f6c642061737365747320696e207468697320636c61737320796574742068617665206e6f206578697374656e7469616c206465706f7369742e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e00b020456d6974732060466f7263654372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f283129601c64657374726f79080869644c436f6d706163743c543a3a417373657449643e1c7769746e6573733844657374726f795769746e65737338902044657374726f79206120636c617373206f662066756e6769626c65206173736574732e00590120546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e60206f72206d757374206265205369676e656420616e64207468652073656e646572206d7573742062652074686564206f776e6572206f662074686520617373657420606964602e005101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652064657374726f7965642e2054686973206d757374206964656e7469667920616e206578697374696e671c2061737365742e00a420456d697473206044657374726f79656460206576656e74207768656e207375636365737366756c2e0078205765696768743a20604f2863202b2070202b206129602077686572653ac4202d206063203d20287769746e6573732e6163636f756e7473202d207769746e6573732e73756666696369656e7473296070202d206073203d207769746e6573732e73756666696369656e74736068202d206061203d207769746e6573732e617070726f76616c7360106d696e740c0869644c436f6d706163743c543a3a417373657449643e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e308c204d696e7420617373657473206f66206120706172746963756c617220636c6173732e003d0120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d7573742062652074686520497373756572206f662074686520617373657420606964602e000101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74206d696e7465642e1101202d206062656e6566696369617279603a20546865206163636f756e7420746f206265206372656469746564207769746820746865206d696e746564206173736574732ec8202d2060616d6f756e74603a2054686520616d6f756e74206f662074686520617373657420746f206265206d696e7465642e00a420456d697473206044657374726f79656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f283129605901204d6f6465733a205072652d6578697374696e672062616c616e6365206f66206062656e6566696369617279603b204163636f756e74207072652d6578697374656e6365206f66206062656e6566696369617279602e106275726e0c0869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e3c490120526564756365207468652062616c616e6365206f66206077686f60206279206173206d75636820617320706f737369626c6520757020746f2060616d6f756e746020617373657473206f6620606964602e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204d616e61676572206f662074686520617373657420606964602e00dc204261696c732077697468206042616c616e63655a65726f6020696620746865206077686f6020697320616c726561647920646561642e000101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74206275726e65642ea4202d206077686f603a20546865206163636f756e7420746f20626520646562697465642066726f6d2e2d01202d2060616d6f756e74603a20546865206d6178696d756d20616d6f756e74206279207768696368206077686f6027732062616c616e63652073686f756c6420626520726564756365642e00550120456d69747320604275726e6564602077697468207468652061637475616c20616d6f756e74206275726e65642e20496620746869732074616b6573207468652062616c616e636520746f2062656c6f77207468653d01206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74206275726e656420697320696e6372656173656420746f2074616b6520697420746f207a65726f2e003c205765696768743a20604f283129600d01204d6f6465733a20506f73742d6578697374656e6365206f66206077686f603b20507265202620706f7374205a6f6d6269652d737461747573206f66206077686f602e207472616e736665720c0869644c436f6d706163743c543a3a417373657449643e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e48d4204d6f766520736f6d65206173736574732066726f6d207468652073656e646572206163636f756e7420746f20616e6f746865722e005c204f726967696e206d757374206265205369676e65642e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642ea0202d2060746172676574603a20546865206163636f756e7420746f2062652063726564697465642e5501202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652073656e64657227732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e64650120607461726765746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e6101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652073656e6465722062616c616e63652061626f7665207a65726f206275742062656c6f77c020746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605d01204d6f6465733a205072652d6578697374656e6365206f662060746172676574603b20506f73742d6578697374656e6365206f662073656e6465723b205072696f72202620706f7374207a6f6d6269652d737461747573b8206f662073656e6465723b204163636f756e74207072652d6578697374656e6365206f662060746172676574602e4c7472616e736665725f6b6565705f616c6976650c0869644c436f6d706163743c543a3a417373657449643e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e485d01204d6f766520736f6d65206173736574732066726f6d207468652073656e646572206163636f756e7420746f20616e6f746865722c206b656570696e67207468652073656e646572206163636f756e7420616c6976652e005c204f726967696e206d757374206265205369676e65642e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642ea0202d2060746172676574603a20546865206163636f756e7420746f2062652063726564697465642e5501202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652073656e64657227732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e64650120607461726765746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e6101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652073656e6465722062616c616e63652061626f7665207a65726f206275742062656c6f77c020746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605d01204d6f6465733a205072652d6578697374656e6365206f662060746172676574603b20506f73742d6578697374656e6365206f662073656e6465723b205072696f72202620706f7374207a6f6d6269652d737461747573b8206f662073656e6465723b204163636f756e74207072652d6578697374656e6365206f662060746172676574602e38666f7263655f7472616e73666572100869644c436f6d706163743c543a3a417373657449643e18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e4cb8204d6f766520736f6d65206173736574732066726f6d206f6e65206163636f756e7420746f20616e6f746865722e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642e9c202d2060736f75726365603a20546865206163636f756e7420746f20626520646562697465642e98202d206064657374603a20546865206163636f756e7420746f2062652063726564697465642e5d01202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652060736f757263656027732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e645d012060646573746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e5101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652060736f75726365602062616c616e63652061626f7665207a65726f20627574d82062656c6f7720746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605d01204d6f6465733a205072652d6578697374656e6365206f66206064657374603b20506f73742d6578697374656e6365206f662060736f75726365603b205072696f72202620706f7374207a6f6d6269652d737461747573b8206f662060736f75726365603b204163636f756e74207072652d6578697374656e6365206f66206064657374602e18667265657a65080869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528e420446973616c6c6f77206675727468657220756e70726976696c65676564207472616e73666572732066726f6d20616e206163636f756e742e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e8c202d206077686f603a20546865206163636f756e7420746f2062652066726f7a656e2e004020456d697473206046726f7a656e602e003c205765696768743a20604f283129601074686177080869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528d020416c6c6f7720756e70726976696c65676564207472616e73666572732066726f6d20616e206163636f756e7420616761696e2e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e94202d206077686f603a20546865206163636f756e7420746f20626520756e66726f7a656e2e004020456d6974732060546861776564602e003c205765696768743a20604f2831296030667265657a655f6173736574040869644c436f6d706163743c543a3a417373657449643e24f420446973616c6c6f77206675727468657220756e70726976696c65676564207472616e736665727320666f722074686520617373657420636c6173732e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e004020456d697473206046726f7a656e602e003c205765696768743a20604f2831296028746861775f6173736574040869644c436f6d706163743c543a3a417373657449643e24c820416c6c6f7720756e70726976696c65676564207472616e736665727320666f722074686520617373657420616761696e2e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e004020456d6974732060546861776564602e003c205765696768743a20604f28312960487472616e736665725f6f776e657273686970080869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652878204368616e676520746865204f776e6572206f6620616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742ea0202d20606f776e6572603a20546865206e6577204f776e6572206f6620746869732061737365742e005820456d69747320604f776e65724368616e676564602e003c205765696768743a20604f28312960207365745f7465616d100869644c436f6d706163743c543a3a417373657449643e186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636530c8204368616e676520746865204973737565722c2041646d696e20616e6420467265657a6572206f6620616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2ea8202d2060697373756572603a20546865206e657720497373756572206f6620746869732061737365742ea0202d206061646d696e603a20546865206e65772041646d696e206f6620746869732061737365742eb0202d2060667265657a6572603a20546865206e657720467265657a6572206f6620746869732061737365742e005420456d69747320605465616d4368616e676564602e003c205765696768743a20604f28312960307365745f6d65746164617461100869644c436f6d706163743c543a3a417373657449643e106e616d651c5665633c75383e1873796d626f6c1c5665633c75383e20646563696d616c73087538407c2053657420746865206d6574616461746120666f7220616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00dc2046756e6473206f662073656e64657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613a550120604d657461646174614465706f73697442617365202b204d657461646174614465706f73697450657242797465202a20286e616d652e6c656e202b2073796d626f6c2e6c656e29602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e00bc202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f207570646174652e5101202d20606e616d65603a20546865207573657220667269656e646c79206e616d65206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e5101202d206073796d626f6c603a205468652065786368616e67652073796d626f6c20666f7220746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3101202d2060646563696d616c73603a20546865206e756d626572206f6620646563696d616c732074686973206173736574207573657320746f20726570726573656e74206f6e6520756e69742e005420456d69747320604d65746164617461536574602e003c205765696768743a20604f2831296038636c6561725f6d65746164617461040869644c436f6d706163743c543a3a417373657449643e2c8420436c65617220746865206d6574616461746120666f7220616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00a820416e79206465706f73697420697320667265656420666f7220746865206173736574206f776e65722e00b8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f20636c6561722e006420456d69747320604d65746164617461436c6561726564602e003c205765696768743a20604f2831296048666f7263655f7365745f6d65746164617461140869644c436f6d706163743c543a3a417373657449643e106e616d651c5665633c75383e1873796d626f6c1c5665633c75383e20646563696d616c730875382469735f66726f7a656e10626f6f6c38bc20466f72636520746865206d6574616461746120666f7220616e20617373657420746f20736f6d652076616c75652e0070204f726967696e206d75737420626520466f7263654f726967696e2e006c20416e79206465706f736974206973206c65667420616c6f6e652e00bc202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f207570646174652e5101202d20606e616d65603a20546865207573657220667269656e646c79206e616d65206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e5101202d206073796d626f6c603a205468652065786368616e67652073796d626f6c20666f7220746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3101202d2060646563696d616c73603a20546865206e756d626572206f6620646563696d616c732074686973206173736574207573657320746f20726570726573656e74206f6e6520756e69742e005420456d69747320604d65746164617461536574602e005501205765696768743a20604f284e202b20532960207768657265204e20616e6420532061726520746865206c656e677468206f6620746865206e616d6520616e642073796d626f6c20726573706563746976656c792e50666f7263655f636c6561725f6d65746164617461040869644c436f6d706163743c543a3a417373657449643e2c8420436c65617220746865206d6574616461746120666f7220616e2061737365742e0070204f726967696e206d75737420626520466f7263654f726967696e2e006420416e79206465706f7369742069732072657475726e65642e00b8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f20636c6561722e006420456d69747320604d65746164617461436c6561726564602e003c205765696768743a20604f2831296048666f7263655f61737365745f737461747573200869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c6d696e5f62616c616e63654c436f6d706163743c543a3a42616c616e63653e3469735f73756666696369656e7410626f6f6c2469735f66726f7a656e10626f6f6c589c20416c746572207468652061747472696275746573206f66206120676976656e2061737365742e0078204f726967696e206d7573742062652060466f7263654f726967696e602e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742ea0202d20606f776e6572603a20546865206e6577204f776e6572206f6620746869732061737365742ea8202d2060697373756572603a20546865206e657720497373756572206f6620746869732061737365742ea0202d206061646d696e603a20546865206e65772041646d696e206f6620746869732061737365742eb0202d2060667265657a6572603a20546865206e657720467265657a6572206f6620746869732061737365742e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e5501202d206069735f73756666696369656e74603a20576865746865722061206e6f6e2d7a65726f2062616c616e6365206f662074686973206173736574206973206465706f736974206f662073756666696369656e7451012076616c756520746f206163636f756e7420666f722074686520737461746520626c6f6174206173736f6369617465642077697468206974732062616c616e63652073746f726167652e2049662073657420746f5901206074727565602c207468656e206e6f6e2d7a65726f2062616c616e636573206d61792062652073746f72656420776974686f757420612060636f6e73756d657260207265666572656e63652028616e642074687573510120616e20454420696e207468652042616c616e6365732070616c6c6574206f7220776861746576657220656c7365206973207573656420746f20636f6e74726f6c20757365722d6163636f756e74207374617465242067726f777468292e4101202d206069735f66726f7a656e603a2057686574686572207468697320617373657420636c6173732069732066726f7a656e2065786365707420666f72207065726d697373696f6e65642f61646d696e3820696e737472756374696f6e732e00ec20456d697473206041737365745374617475734368616e67656460207769746820746865206964656e74697479206f66207468652061737365742e003c205765696768743a20604f2831296040617070726f76655f7472616e736665720c0869644c436f6d706163743c543a3a417373657449643e2064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e50310120417070726f766520616e20616d6f756e74206f6620617373657420666f72207472616e7366657220627920612064656c6567617465642074686972642d7061727479206163636f756e742e005c204f726967696e206d757374206265205369676e65642e00510120456e737572657320746861742060417070726f76616c4465706f7369746020776f727468206f66206043757272656e6379602069732072657365727665642066726f6d207369676e696e67206163636f756e74590120666f722074686520707572706f7365206f6620686f6c64696e672074686520617070726f76616c2e20496620736f6d65206e6f6e2d7a65726f20616d6f756e74206f662061737365747320697320616c72656164794d0120617070726f7665642066726f6d207369676e696e67206163636f756e7420746f206064656c6567617465602c207468656e20697420697320746f70706564207570206f7220756e726573657276656420746f58206d656574207468652072696768742076616c75652e004901204e4f54453a20546865207369676e696e67206163636f756e7420646f6573206e6f74206e65656420746f206f776e2060616d6f756e7460206f66206173736574732061742074686520706f696e74206f6648206d616b696e6720746869732063616c6c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e1101202d206064656c6567617465603a20546865206163636f756e7420746f2064656c6567617465207065726d697373696f6e20746f207472616e736665722061737365742e4d01202d2060616d6f756e74603a2054686520616d6f756e74206f662061737365742074686174206d6179206265207472616e73666572726564206279206064656c6567617465602e204966207468657265206973e420616c726561647920616e20617070726f76616c20696e20706c6163652c207468656e207468697320616374732061646469746976656c792e009420456d6974732060417070726f7665645472616e7366657260206f6e20737563636573732e003c205765696768743a20604f283129603c63616e63656c5f617070726f76616c080869644c436f6d706163743c543a3a417373657449643e2064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365344d012043616e63656c20616c6c206f6620736f6d6520617373657420617070726f76656420666f722064656c656761746564207472616e7366657220627920612074686972642d7061727479206163636f756e742e004101204f726967696e206d757374206265205369676e656420616e64207468657265206d75737420626520616e20617070726f76616c20696e20706c616365206265747765656e207369676e657220616e6430206064656c6567617465602e004d0120556e726573657276657320616e79206465706f7369742070726576696f75736c792072657365727665642062792060617070726f76655f7472616e736665726020666f722074686520617070726f76616c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e0901202d206064656c6567617465603a20546865206163636f756e742064656c656761746564207065726d697373696f6e20746f207472616e736665722061737365742e009820456d6974732060417070726f76616c43616e63656c6c656460206f6e20737563636573732e003c205765696768743a20604f2831296054666f7263655f63616e63656c5f617070726f76616c0c0869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365344d012043616e63656c20616c6c206f6620736f6d6520617373657420617070726f76656420666f722064656c656761746564207472616e7366657220627920612074686972642d7061727479206163636f756e742e004d01204f726967696e206d7573742062652065697468657220466f7263654f726967696e206f72205369676e6564206f726967696e207769746820746865207369676e6572206265696e67207468652041646d696e6c206163636f756e74206f662074686520617373657420606964602e004d0120556e726573657276657320616e79206465706f7369742070726576696f75736c792072657365727665642062792060617070726f76655f7472616e736665726020666f722074686520617070726f76616c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e0901202d206064656c6567617465603a20546865206163636f756e742064656c656761746564207065726d697373696f6e20746f207472616e736665722061737365742e009820456d6974732060417070726f76616c43616e63656c6c656460206f6e20737563636573732e003c205765696768743a20604f28312960447472616e736665725f617070726f766564100869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c64657374696e6174696f6e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e485101205472616e7366657220736f6d652061737365742062616c616e63652066726f6d20612070726576696f75736c792064656c656761746564206163636f756e7420746f20736f6d652074686972642d706172747924206163636f756e742e004d01204f726967696e206d757374206265205369676e656420616e64207468657265206d75737420626520616e20617070726f76616c20696e20706c6163652062792074686520606f776e65726020746f2074686520207369676e65722e005d012049662074686520656e7469726520616d6f756e7420617070726f76656420666f72207472616e73666572206973207472616e736665727265642c207468656e20616e79206465706f7369742070726576696f75736c79b82072657365727665642062792060617070726f76655f7472616e736665726020697320756e72657365727665642e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e6501202d20606f776e6572603a20546865206163636f756e742077686963682070726576696f75736c7920617070726f76656420666f722061207472616e73666572206f66206174206c656173742060616d6f756e746020616e64c02066726f6d207768696368207468652061737365742062616c616e63652077696c6c2062652077697468647261776e2e6501202d206064657374696e6174696f6e603a20546865206163636f756e7420746f207768696368207468652061737365742062616c616e6365206f662060616d6f756e74602077696c6c206265207472616e736665727265642eb8202d2060616d6f756e74603a2054686520616d6f756e74206f662061737365747320746f207472616e736665722e00a020456d69747320605472616e73666572726564417070726f76656460206f6e20737563636573732e003c205765696768743a20604f2831296001481c437265617465640c1c41737365744964244163636f756e744964244163636f756e74496404ec20536f6d6520617373657420636c6173732077617320637265617465642e205c5b61737365745f69642c2063726561746f722c206f776e65725c5d184973737565640c1c41737365744964244163636f756e7449641c42616c616e636504ec20536f6d65206173736574732077657265206973737565642e205c5b61737365745f69642c206f776e65722c20746f74616c5f737570706c795c5d2c5472616e73666572726564101c41737365744964244163636f756e744964244163636f756e7449641c42616c616e636504f420536f6d65206173736574732077657265207472616e736665727265642e205c5b61737365745f69642c2066726f6d2c20746f2c20616d6f756e745c5d184275726e65640c1c41737365744964244163636f756e7449641c42616c616e636504e420536f6d652061737365747320776572652064657374726f7965642e205c5b61737365745f69642c206f776e65722c2062616c616e63655c5d2c5465616d4368616e676564101c41737365744964244163636f756e744964244163636f756e744964244163636f756e74496404050120546865206d616e6167656d656e74207465616d206368616e676564205c5b61737365745f69642c206973737565722c2061646d696e2c20667265657a65725c5d304f776e65724368616e676564081c41737365744964244163636f756e744964049820546865206f776e6572206368616e676564205c5b61737365745f69642c206f776e65725c5d1846726f7a656e081c41737365744964244163636f756e74496404c420536f6d65206163636f756e74206077686f60207761732066726f7a656e2e205c5b61737365745f69642c2077686f5c5d18546861776564081c41737365744964244163636f756e74496404c420536f6d65206163636f756e74206077686f6020776173207468617765642e205c5b61737365745f69642c2077686f5c5d2c417373657446726f7a656e041c4173736574496404bc20536f6d65206173736574206061737365745f696460207761732066726f7a656e2e205c5b61737365745f69645c5d2c4173736574546861776564041c4173736574496404bc20536f6d65206173736574206061737365745f69646020776173207468617765642e205c5b61737365745f69645c5d2444657374726f796564041c41737365744964047820416e20617373657420636c617373207761732064657374726f7965642e30466f72636543726561746564081c41737365744964244163636f756e74496404e020536f6d6520617373657420636c6173732077617320666f7263652d637265617465642e205c5b61737365745f69642c206f776e65725c5d2c4d65746164617461536574141c417373657449641c5665633c75383e1c5665633c75383e08753810626f6f6c046101204e6577206d6574616461746120686173206265656e2073657420666f7220616e2061737365742e205c5b61737365745f69642c206e616d652c2073796d626f6c2c20646563696d616c732c2069735f66726f7a656e5c5d3c4d65746164617461436c6561726564041c4173736574496404d4204d6574616461746120686173206265656e20636c656172656420666f7220616e2061737365742e205c5b61737365745f69645c5d40417070726f7665645472616e73666572101c41737365744964244163636f756e744964244163636f756e7449641c42616c616e636508350120284164646974696f6e616c292066756e64732068617665206265656e20617070726f76656420666f72207472616e7366657220746f20612064657374696e6174696f6e206163636f756e742e9c205c5b61737365745f69642c20736f757263652c2064656c65676174652c20616d6f756e745c5d44417070726f76616c43616e63656c6c65640c1c41737365744964244163636f756e744964244163636f756e74496408f420416e20617070726f76616c20666f72206163636f756e74206064656c656761746560207761732063616e63656c6c656420627920606f776e6572602e60205c5b69642c206f776e65722c2064656c65676174655c5d4c5472616e73666572726564417070726f766564141c41737365744964244163636f756e744964244163636f756e744964244163636f756e7449641c42616c616e63650c350120416e2060616d6f756e746020776173207472616e7366657272656420696e2069747320656e7469726574792066726f6d20606f776e65726020746f206064657374696e6174696f6e60206279642074686520617070726f766564206064656c6567617465602e94205c5b69642c206f776e65722c2064656c65676174652c2064657374696e6174696f6e5c5d4841737365745374617475734368616e676564041c4173736574496408fc20416e2061737365742068617320686164206974732061747472696275746573206368616e676564206279207468652060466f72636560206f726967696e2e1c205c5b69645c5d00342842616c616e63654c6f77041901204163636f756e742062616c616e6365206d7573742062652067726561746572207468616e206f7220657175616c20746f20746865207472616e7366657220616d6f756e742e2c42616c616e63655a65726f04702042616c616e63652073686f756c64206265206e6f6e2d7a65726f2e304e6f5065726d697373696f6e04ec20546865207369676e696e67206163636f756e7420686173206e6f207065726d697373696f6e20746f20646f20746865206f7065726174696f6e2e1c556e6b6e6f776e047c2054686520676976656e20617373657420494420697320756e6b6e6f776e2e1846726f7a656e047820546865206f726967696e206163636f756e742069732066726f7a656e2e14496e557365047c2054686520617373657420494420697320616c72656164792074616b656e2e284261645769746e657373047020496e76616c6964207769746e657373206461746120676976656e2e384d696e42616c616e63655a65726f0490204d696e696d756d2062616c616e63652073686f756c64206265206e6f6e2d7a65726f2e204f766572666c6f7704982041206d696e74206f7065726174696f6e206c65616420746f20616e206f766572666c6f772e284e6f50726f7669646572046501204e6f2070726f7669646572207265666572656e63652065786973747320746f20616c6c6f772061206e6f6e2d7a65726f2062616c616e6365206f662061206e6f6e2d73656c662d73756666696369656e742061737365742e2c4261644d65746164617461046020496e76616c6964206d6574616461746120676976656e2e28556e617070726f76656404c8204e6f20617070726f76616c20657869737473207468617420776f756c6420616c6c6f7720746865207472616e736665722e20576f756c644469650439012054686520736f75726365206163636f756e7420776f756c64206e6f74207375727669766520746865207472616e7366657220616e64206974206e6565647320746f207374617920616c6976652e220c4d6d72014c4d65726b6c654d6f756e7461696e52616e67650c20526f6f74486173680100583c5420617320436f6e6669673c493e3e3a3a486173688000000000000000000000000000000000000000000000000000000000000000000458204c6174657374204d4d5220526f6f7420686173682e384e756d6265724f664c656176657301000c75363420000000000000000004b02043757272656e742073697a65206f6620746865204d4d5220286e756d626572206f66206c6561766573292e144e6f6465730001060c753634583c5420617320436f6e6669673c493e3e3a3a48617368000400108020486173686573206f6620746865206e6f64657320696e20746865204d4d522e002d01204e6f7465207468697320636f6c6c656374696f6e206f6e6c7920636f6e7461696e73204d4d52207065616b732c2074686520696e6e6572206e6f6465732028616e64206c656176657329bc20617265207072756e656420616e64206f6e6c792073746f72656420696e20746865204f6666636861696e2044422e00000000231c4c6f7474657279011c4c6f747465727918304c6f7474657279496e64657801000c7533321000000000001c4c6f74746572790000ac4c6f7474657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e3e040004ac2054686520636f6e66696775726174696f6e20666f72207468652063757272656e74206c6f74746572792e305061727469636970616e747301010530543a3a4163636f756e74496454287533322c205665633c43616c6c496e6465783e29001400000000000419012055736572732077686f2068617665207075726368617365642061207469636b65742e20284c6f747465727920496e6465782c205469636b6574732050757263686173656429305469636b657473436f756e7401000c7533321000000000047820546f74616c206e756d626572206f66207469636b65747320736f6c642e1c5469636b6574730001050c75333230543a3a4163636f756e74496400040010542045616368207469636b65742773206f776e65722e006101204d6179206861766520726573696475616c2073746f726167652066726f6d2070726576696f7573206c6f747465726965732e2055736520605469636b657473436f756e746020746f20736565207768696368206f6e657390206172652061637475616c6c792076616c6964207469636b6574206d617070696e67732e2c43616c6c496e64696365730100385665633c43616c6c496e6465783e0400083901205468652063616c6c732073746f72656420696e20746869732070616c6c657420746f206265207573656420696e20616e20616374697665206c6f747465727920696620636f6e666967757265646c2062792060436f6e6669673a3a56616c696461746543616c6c602e0110286275795f7469636b6574041063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2c8c204275792061207469636b657420746f20656e74657220746865206c6f74746572792e00050120546869732065787472696e7369632061637473206173206120706173737468726f7567682066756e6374696f6e20666f72206063616c6c602e20496e20616c6c0d0120736974756174696f6e73207768657265206063616c6c6020616c6f6e6520776f756c6420737563636565642c20746869732065787472696e7369632073686f756c642420737563636565642e001101204966206063616c6c60206973207375636365737366756c2c207468656e2077652077696c6c20617474656d707420746f2070757263686173652061207469636b65742c1501207768696368206d6179206661696c2073696c656e746c792e20546f206465746563742073756363657373206f662061207469636b65742070757263686173652c20796f75b02073686f756c64206c697374656e20666f722074686520605469636b6574426f7567687460206576656e742e00c820546869732065787472696e736963206d7573742062652063616c6c65642062792061207369676e6564206f726967696e2e247365745f63616c6c73041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e181501205365742063616c6c7320696e2073746f726167652077686963682063616e206265207573656420746f2070757263686173652061206c6f7474657279207469636b65742e00210120546869732066756e6374696f6e206f6e6c79206d61747465727320696620796f752075736520746865206056616c696461746543616c6c6020696d706c656d656e746174696f6e29012070726f766964656420627920746869732070616c6c65742c20776869636820757365732073746f7261676520746f2064657465726d696e65207468652076616c69642063616c6c732e00d420546869732065787472696e736963206d7573742062652063616c6c656420627920746865204d616e61676572206f726967696e2e3473746172745f6c6f7474657279101470726963653042616c616e63654f663c543e186c656e67746838543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d6265721872657065617410626f6f6c28c82053746172742061206c6f7474657279207573696e67207468652070726f766964656420636f6e66696775726174696f6e2e00d820546869732065787472696e736963206d7573742062652063616c6c65642062792074686520604d616e616765724f726967696e602e003020506172616d65746572733a00a0202a20607072696365603a2054686520636f7374206f6620612073696e676c65207469636b65742e3d01202a20606c656e677468603a20486f77206c6f6e6720746865206c6f74746572792073686f756c642072756e20666f72207374617274696e67206174207468652063757272656e7420626c6f636b2e4901202a206064656c6179603a20486f77206c6f6e6720616674657220746865206c6f747465727920656e642077652073686f756c642077616974206265666f7265207069636b696e6720612077696e6e65722ee4202a2060726570656174603a20496620746865206c6f74746572792073686f756c6420726570656174207768656e20636f6d706c657465642e2c73746f705f726570656174001001012049662061206c6f747465727920697320726570656174696e672c20796f752063616e20757365207468697320746f2073746f7020746865207265706561742ec020546865206c6f74746572792077696c6c20636f6e74696e756520746f2072756e20746f20636f6d706c6574696f6e2e00d820546869732065787472696e736963206d7573742062652063616c6c65642062792074686520604d616e616765724f726967696e602e0110384c6f7474657279537461727465640004702041206c6f747465727920686173206265656e2073746172746564213043616c6c73557064617465640004882041206e657720736574206f662063616c6c732068617665206265656e20736574211857696e6e657208244163636f756e7449641c42616c616e6365046820412077696e6e657220686173206265656e2063686f73656e21305469636b6574426f7567687408244163636f756e7449642443616c6c496e64657804682041207469636b657420686173206265656e20626f7567687421082050616c6c657449642050616c6c657449642070792f6c6f74746f00204d617843616c6c730c753332100a0000000020204f766572666c6f77046820416e206f766572666c6f7720686173206f636375727265642e344e6f74436f6e66696775726564048c2041206c6f747465727920686173206e6f74206265656e20636f6e666967757265642e28496e50726f677265737304882041206c6f747465727920697320616c726561647920696e2070726f67726573732e30416c7265616479456e64656404742041206c6f74746572792068617320616c726561647920656e6465642e2c496e76616c696443616c6c04ac205468652063616c6c206973206e6f742076616c696420666f7220616e206f70656e206c6f74746572792e50416c726561647950617274696369706174696e6704f420596f752061726520616c72656164792070617274696369706174696e6720696e20746865206c6f7474657279207769746820746869732063616c6c2e30546f6f4d616e7943616c6c73049420546f6f206d616e792063616c6c7320666f7220612073696e676c65206c6f74746572792e38456e636f64696e674661696c6564045c204661696c656420746f20656e636f64652063616c6c73241047696c74011047696c74102c5175657565546f74616c730100605665633c287533322c2042616c616e63654f663c543e293e04001461012054686520746f74616c73206f66206974656d7320616e642062616c616e6365732077697468696e20656163682071756575652e2053617665732061206c6f74206f662073746f7261676520726561647320696e20746865802063617365206f66207370617273656c79207061636b6564207175657565732e006d012054686520766563746f7220697320696e6465786564206279206475726174696f6e20696e2060506572696f6460732c206f6666736574206279206f6e652c20736f20696e666f726d6174696f6e206f6e20746865207175657565d42077686f7365206475726174696f6e206973206f6e652060506572696f646020776f756c642062652073746f72616765206030602e185175657565730101020c753332a05665633c47696c744269643c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e0004000439012054686520717565756573206f66206269647320726561647920746f206265636f6d652067696c74732e20496e6465786564206279206475726174696f6e2028696e2060506572696f646073292e2c416374697665546f74616c01007841637469766547696c7473546f74616c3c42616c616e63654f663c543e3e9000000000000000000000000000000000000000000000000000000000000000000000000004d020496e666f726d6174696f6e2072656c6174696e6720746f207468652067696c74732063757272656e746c79206163746976652e184163746976650001022c416374697665496e646578a50141637469766547696c743c42616c616e63654f663c543e2c3c54206173206672616d655f73797374656d3a3a436f6e6669673e3a3a4163636f756e7449642c3c0a54206173206672616d655f73797374656d3a3a436f6e6669673e3a3a426c6f636b4e756d6265723e000400042101205468652063757272656e746c79206163746976652067696c74732c20696e6465786564206163636f7264696e6720746f20746865206f72646572206f66206372656174696f6e2e011024706c6163655f6269640818616d6f756e7454436f6d706163743c42616c616e63654f663c543e3e206475726174696f6e0c753332349420506c61636520612062696420666f7220612067696c7420746f206265206973737565642e004101204f726967696e206d757374206265205369676e65642c20616e64206163636f756e74206d7573742068617665206174206c656173742060616d6f756e746020696e20667265652062616c616e63652e003d01202d2060616d6f756e74603a2054686520616d6f756e74206f6620746865206269643b2074686573652066756e64732077696c6c2062652072657365727665642e20496620746865206269642069734101207375636365737366756c6c7920656c65766174656420696e746f20616e206973737565642067696c742c207468656e2074686573652066756e64732077696c6c20636f6e74696e756520746f206265fc20726573657276656420756e74696c207468652067696c7420657870697265732e204d757374206265206174206c6561737420604d696e467265657a65602e5901202d20606475726174696f6e603a20546865206e756d626572206f6620706572696f647320666f72207768696368207468652066756e64732077696c6c206265206c6f636b6564206966207468652067696c742069735d01206973737565642e2049742077696c6c20657870697265206f6e6c79206166746572207468697320706572696f642068617320656c61707365642061667465722074686520706f696e74206f662069737375616e63652ed8204d7573742062652067726561746572207468616e203120616e64206e6f206d6f7265207468616e20605175657565436f756e74602e003820436f6d706c657869746965733ab0202d20605175657565735b6475726174696f6e5d2e6c656e28296020286a7573742074616b65206d6178292e2c726574726163745f6269640818616d6f756e7454436f6d706163743c42616c616e63654f663c543e3e206475726174696f6e0c7533321c84205265747261637420612070726576696f75736c7920706c61636564206269642e006101204f726967696e206d757374206265205369676e65642c20616e6420746865206163636f756e742073686f756c6420686176652070726576696f75736c79206973737565642061207374696c6c2d6163746976652062696470206f662060616d6f756e746020666f7220606475726174696f6e602e00b0202d2060616d6f756e74603a2054686520616d6f756e74206f66207468652070726576696f7573206269642ec0202d20606475726174696f6e603a20546865206475726174696f6e206f66207468652070726576696f7573206269642e287365745f746172676574041874617267657450436f6d706163743c5065727175696e74696c6c3e189420536574207461726765742070726f706f7274696f6e206f662067696c742d66756e64732e0078204f726967696e206d757374206265206041646d696e4f726967696e602e005d01202d2060746172676574603a20546865207461726765742070726f706f7274696f6e206f6620656666656374697665206973737565642066756e647320746861742073686f756c6420626520756e6465722067696c74734420617420616e79206f6e652074696d652e10746861770414696e64657850436f6d706163743c416374697665496e6465783e1c59012052656d6f766520616e206163746976652062757420657870697265642067696c742e2052657365727665642066756e647320756e6465722067696c742061726520667265656420616e642062616c616e63652069735d012061646a757374656420746f20656e737572652074686174207468652066756e64732067726f77206f7220736872696e6b20746f206d61696e7461696e20746865206571756976616c656e742070726f706f7274696f6e84206f662065666665637469766520746f74616c206973737565642066756e64732e006101204f726967696e206d757374206265205369676e656420616e6420746865206163636f756e74206d75737420626520746865206f776e6572206f66207468652067696c74206f662074686520676976656e20696e6465782e00bc202d2060696e646578603a2054686520696e646578206f66207468652067696c7420746f206265207468617765642e011024426964506c616365640c244163636f756e7449643042616c616e63654f663c543e0c753332087c20412062696420776173207375636365737366756c6c7920706c616365642e70205c5b2077686f2c20616d6f756e742c206475726174696f6e205c5d304269645265747261637465640c244163636f756e7449643042616c616e63654f663c543e0c75333208090120412062696420776173207375636365737366756c6c792072656d6f76656420286265666f7265206265696e6720616363657074656420617320612067696c74292e70205c5b2077686f2c20616d6f756e742c206475726174696f6e205c5d2847696c74497373756564102c416374697665496e64657838543a3a426c6f636b4e756d626572244163636f756e7449643042616c616e63654f663c543e0831012041206269642077617320616363657074656420617320612067696c742e205468652062616c616e6365206d6179206e6f742062652072656c656173656420756e74696c206578706972792e84205c5b20696e6465782c206578706972792c2077686f2c20616d6f756e74205c5d2847696c74546861776564102c416374697665496e646578244163636f756e7449643042616c616e63654f663c543e3042616c616e63654f663c543e088420416e20657870697265642067696c7420686173206265656e207468617765642ed4205c5b20696e6465782c2077686f2c206f726967696e616c5f616d6f756e742c206164646974696f6e616c5f616d6f756e74205c5d1c285175657565436f756e740c753332102c010000085d01204e756d626572206f66206475726174696f6e2071756575657320696e20746f74616c2e2054686973207365747320746865206d6178696d756d206475726174696f6e20737570706f727465642c2077686963682069738c20746869732076616c7565206d756c7469706c6965642062792060506572696f64602e2c4d617851756575654c656e0c75333210e803000004f0204d6178696d756d206e756d626572206f66206974656d732074686174206d617920626520696e2065616368206475726174696f6e2071756575652e304669666f51756575654c656e0c75333210f40100000c090120506f7274696f6e206f662074686520717565756520776869636820697320667265652066726f6d206f72646572696e6720616e64206a7573742061204649464f2e009c204d757374206265206e6f2067726561746572207468616e20604d617851756575654c656e602e18506572696f6438543a3a426c6f636b4e756d62657210002f0d0008410120546865206261736520706572696f6420666f7220746865206475726174696f6e207175657565732e20546869732069732074686520636f6d6d6f6e206d756c7469706c65206163726f737320616c6ccc20737570706f7274656420667265657a696e67206475726174696f6e7320746861742063616e206265206269642075706f6e2e244d696e467265657a653042616c616e63654f663c543e400000c16ff2862300000000000000000018550120546865206d696e696d756d20616d6f756e74206f662066756e64732074686174206d6179206265206f66666572656420746f20667265657a6520666f7220612067696c742e204e6f746520746861742074686973510120646f6573206e6f742061637475616c6c79206c696d69742074686520616d6f756e74207768696368206d61792062652066726f7a656e20696e20612067696c742073696e63652067696c7473206d617920626519012073706c697420757020696e206f7264657220746f207361746973667920746865206465736972656420616d6f756e74206f662066756e647320756e6465722067696c74732e0065012049742073686f756c64206265206174206c656173742062696720656e6f75676820746f20656e737572652074686174207468657265206973206e6f20706f737369626c652073746f72616765207370616d2061747461636b64206f722071756575652d66696c6c696e672061747461636b2e30496e74616b65506572696f6438543a3a426c6f636b4e756d626572100a00000014590120546865206e756d626572206f6620626c6f636b73206265747765656e20636f6e736563757469766520617474656d70747320746f206973737565206d6f72652067696c747320696e20616e206566666f727420746f9c2067657420746f207468652074617267657420616d6f756e7420746f2062652066726f7a656e2e005d012041206c61726765722076616c756520726573756c747320696e2066657765722073746f726167652068697473206561636820626c6f636b2c20627574206120736c6f77657220706572696f6420746f2067657420746f3020746865207461726765742e344d6178496e74616b65426964730c753332100a0000000c550120546865206d6178696d756d20616d6f756e74206f66206269647320746861742063616e206265207475726e656420696e746f206973737565642067696c7473206561636820626c6f636b2e2041206c617267657261012076616c75652068657265206d65616e73206c657373206f662074686520626c6f636b20617661696c61626c6520666f72207472616e73616374696f6e732073686f756c64207468657265206265206120676c7574206f66b4206269647320746f206d616b6520696e746f2067696c747320746f20726561636820746865207461726765742e20404475726174696f6e546f6f536d616c6c04a820546865206475726174696f6e206f662074686520626964206973206c657373207468616e206f6e652e384475726174696f6e546f6f42696704f820546865206475726174696f6e20697320746865206269642069732067726561746572207468616e20746865206e756d626572206f66207175657565732e38416d6f756e74546f6f536d616c6c04e02054686520616d6f756e74206f662074686520626964206973206c657373207468616e20746865206d696e696d756d20616c6c6f7765642e24426964546f6f4c6f770865012054686520717565756520666f7220746865206269642773206475726174696f6e2069732066756c6c20616e642074686520616d6f756e742062696420697320746f6f206c6f7720746f2067657420696e207468726f7567686c207265706c6163696e6720616e206578697374696e67206269642e1c556e6b6e6f776e045c2047696c7420696e64657820697320756e6b6e6f776e2e204e6f744f776e6572046c204e6f7420746865206f776e6572206f66207468652067696c742e284e6f744578706972656404742047696c74206e6f74207965742061742065787069727920646174652e204e6f74466f756e6404ac2054686520676976656e2062696420666f722072657472616374696f6e206973206e6f7420666f756e642e25041c40436865636b5370656356657273696f6e38436865636b547856657273696f6e30436865636b47656e6573697338436865636b4d6f7274616c69747928436865636b4e6f6e63652c436865636b576569676874604368617267655472616e73616374696f6e5061796d656e74 \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v12.json b/packages/polkadot/tests/meta/v12.json new file mode 100644 index 00000000..05e5482e --- /dev/null +++ b/packages/polkadot/tests/meta/v12.json @@ -0,0 +1,14399 @@ +{ + "magicNumber": 1635018093, + "metadata": { + "v12": { + "modules": [ + { + "name": "System", + "storage": { + "prefix": "System", + "items": [ + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountInfo", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The full account information for a particular account ID." + ] + }, + { + "name": "ExtrinsicCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total extrinsics count for the current block." + ] + }, + { + "name": "BlockWeight", + "modifier": "Default", + "type": { + "plain": "ConsumedWeight" + }, + "fallback": "0x000000000000000000000000000000000000000000000000", + "docs": [ + " The current weight for the block." + ] + }, + { + "name": "AllExtrinsicsLen", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total length (in bytes) for all extrinsics put together, for the current block." + ] + }, + { + "name": "BlockHash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Map of block numbers to block hashes." + ] + }, + { + "name": "ExtrinsicData", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Extrinsics data for the current block (maps an extrinsic's index to its data)." + ] + }, + { + "name": "Number", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The current block number being processed. Set by `execute_block`." + ] + }, + { + "name": "ParentHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Hash of the previous block." + ] + }, + { + "name": "Digest", + "modifier": "Default", + "type": { + "plain": "DigestOf" + }, + "fallback": "0x00", + "docs": [ + " Digest of the current block, also part of the block header." + ] + }, + { + "name": "Events", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Events deposited for the current block." + ] + }, + { + "name": "EventCount", + "modifier": "Default", + "type": { + "plain": "EventIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of events in the `Events` list." + ] + }, + { + "name": "EventTopics", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "Hash", + "value": "Vec<(BlockNumber,EventIndex)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Mapping between a topic (represented by T::Hash) and a vector of indexes", + " of events in the `>` list.", + "", + " All topic vectors have deterministic storage locations depending on the topic. This", + " allows light-clients to leverage the changes trie storage tracking mechanism and", + " in case of changes fetch the list of events of interest.", + "", + " The value has the type `(T::BlockNumber, EventIndex)` because if we used only just", + " the `EventIndex` then in case if the topic has the same contents on the next block", + " no notification will be triggered thus the event might be lost." + ] + }, + { + "name": "LastRuntimeUpgrade", + "modifier": "Optional", + "type": { + "plain": "LastRuntimeUpgradeInfo" + }, + "fallback": "0x00", + "docs": [ + " Stores the `spec_version` and `spec_name` of when the last runtime upgrade happened." + ] + }, + { + "name": "UpgradedToU32RefCount", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if we have upgraded so that `type RefCount` is `u32`. False (default) if not." + ] + }, + { + "name": "UpgradedToTripleRefCount", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if we have upgraded so that AccountInfo contains three types of `RefCount`. False", + " (default) if not." + ] + }, + { + "name": "ExecutionPhase", + "modifier": "Optional", + "type": { + "plain": "Phase" + }, + "fallback": "0x00", + "docs": [ + " The execution phase of the block." + ] + } + ] + }, + "calls": [ + { + "name": "fill_block", + "args": [ + { + "name": "_ratio", + "type": "Perbill" + } + ], + "docs": [ + " A dispatch that will fill the block weight up to the given ratio." + ] + }, + { + "name": "remark", + "args": [ + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark.", + "", + " # ", + " - `O(1)`", + " # " + ] + }, + { + "name": "set_heap_pages", + "args": [ + { + "name": "pages", + "type": "u64" + } + ], + "docs": [ + " Set the number of pages in the WebAssembly environment's heap.", + "", + " # ", + " - `O(1)`", + " - 1 storage write.", + " - Base Weight: 1.405 µs", + " - 1 write to HEAP_PAGES", + " # " + ] + }, + { + "name": "set_code", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code.", + "", + " # ", + " - `O(C + S)` where `C` length of `code` and `S` complexity of `can_set_code`", + " - 1 storage write (codec `O(C)`).", + " - 1 call to `can_set_code`: `O(S)` (calls `sp_io::misc::runtime_version` which is expensive).", + " - 1 event.", + " The weight of this function is dependent on the runtime, but generally this is very expensive.", + " We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_code_without_checks", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code without doing any checks of the given `code`.", + "", + " # ", + " - `O(C)` where `C` length of `code`", + " - 1 storage write (codec `O(C)`).", + " - 1 event.", + " The weight of this function is dependent on the runtime. We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_changes_trie_config", + "args": [ + { + "name": "changes_trie_config", + "type": "Option" + } + ], + "docs": [ + " Set the new changes trie configuration.", + "", + " # ", + " - `O(1)`", + " - 1 storage write or delete (codec `O(1)`).", + " - 1 call to `deposit_log`: Uses `append` API, so O(1)", + " - Base Weight: 7.218 µs", + " - DB Weight:", + " - Writes: Changes Trie, System Digest", + " # " + ] + }, + { + "name": "set_storage", + "args": [ + { + "name": "items", + "type": "Vec" + } + ], + "docs": [ + " Set some items of storage.", + "", + " # ", + " - `O(I)` where `I` length of `items`", + " - `I` storage writes (`O(1)`).", + " - Base Weight: 0.568 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_storage", + "args": [ + { + "name": "keys", + "type": "Vec" + } + ], + "docs": [ + " Kill some items from storage.", + "", + " # ", + " - `O(IK)` where `I` length of `keys` and `K` length of one key", + " - `I` storage deletions.", + " - Base Weight: .378 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_prefix", + "args": [ + { + "name": "prefix", + "type": "Key" + }, + { + "name": "_subkeys", + "type": "u32" + } + ], + "docs": [ + " Kill all storage items with a key that starts with the given prefix.", + "", + " **NOTE:** We rely on the Root origin to provide us the number of subkeys under", + " the prefix we are removing to accurately calculate the weight of this function.", + "", + " # ", + " - `O(P)` where `P` amount of keys with prefix `prefix`", + " - `P` storage deletions.", + " - Base Weight: 0.834 * P µs", + " - Writes: Number of subkeys + 1", + " # " + ] + }, + { + "name": "remark_with_event", + "args": [ + { + "name": "remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark and emit event.", + "", + " # ", + " - `O(b)` where b is the length of the remark.", + " - 1 event.", + " # " + ] + } + ], + "events": [ + { + "name": "ExtrinsicSuccess", + "args": [ + "DispatchInfo" + ], + "docs": [ + " An extrinsic completed successfully. \\[info\\]" + ] + }, + { + "name": "ExtrinsicFailed", + "args": [ + "DispatchError", + "DispatchInfo" + ], + "docs": [ + " An extrinsic failed. \\[error, info\\]" + ] + }, + { + "name": "CodeUpdated", + "args": [], + "docs": [ + " `:code` was updated." + ] + }, + { + "name": "NewAccount", + "args": [ + "AccountId" + ], + "docs": [ + " A new \\[account\\] was created." + ] + }, + { + "name": "KilledAccount", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] was reaped." + ] + }, + { + "name": "Remarked", + "args": [ + "AccountId", + "Hash" + ], + "docs": [ + " On on-chain remark happened. \\[origin, remark_hash\\]" + ] + } + ], + "constants": [ + { + "name": "BlockWeights", + "type": "BlockWeights", + "value": "0x00f2052a0100000000204aa9d1010000405973070000000001c06e96a62e010000010098f73e5d010000010000000000000000405973070000000001c0f6e810a30100000100204aa9d1010000010088526a740000004059730700000000000000", + "docs": [ + " Block & extrinsics weights: base values and limits." + ] + }, + { + "name": "BlockLength", + "type": "BlockLength", + "value": "0x00003c000000500000005000", + "docs": [ + " The maximum length of a block (in bytes)." + ] + }, + { + "name": "BlockHashCount", + "type": "BlockNumber", + "value": "0x60090000", + "docs": [ + " Maximum number of block number to block hash mappings to keep (oldest pruned first)." + ] + }, + { + "name": "DbWeight", + "type": "RuntimeDbWeight", + "value": "0x40787d010000000000e1f50500000000", + "docs": [ + " The weight of runtime database operations the runtime can invoke." + ] + }, + { + "name": "Version", + "type": "RuntimeVersion", + "value": "0x106e6f6465387375627374726174652d6e6f64650a000000090100000100000034df6acb689907609b0300000037e397fc7c91f5e40100000040fe3ad401f8959a04000000d2bc9897eed08f1502000000f78b278be53f454c02000000ed99c5acb25eedf502000000cbca25e39f14238702000000687ad44ad37f03c201000000bc9d89904f5b923f0100000068b66ba122c93fa70100000037c8bb1350a9a2a80100000091d5df18b0d2cf5801000000ab3c0572291feb8b0100000002000000", + "docs": [ + " Get the chain's current version." + ] + }, + { + "name": "SS58Prefix", + "type": "u8", + "value": "0x2a", + "docs": [ + " The designated SS85 prefix of this chain.", + "", + " This replaces the \"ss58Format\" property declared in the chain spec. Reason is", + " that the runtime should know about the prefix in order to make use of it as", + " an identifier of the chain." + ] + } + ], + "errors": [ + { + "name": "InvalidSpecName", + "docs": [ + " The name of specification does not match between the current runtime", + " and the new runtime." + ] + }, + { + "name": "SpecVersionNeedsToIncrease", + "docs": [ + " The specification version is not allowed to decrease between the current runtime", + " and the new runtime." + ] + }, + { + "name": "FailedToExtractRuntimeVersion", + "docs": [ + " Failed to extract the runtime version from the new runtime.", + "", + " Either calling `Core_version` or decoding `RuntimeVersion` failed." + ] + }, + { + "name": "NonDefaultComposite", + "docs": [ + " Suicide called when the account has non-default composite data." + ] + }, + { + "name": "NonZeroRefCount", + "docs": [ + " There is a non-zero reference count preventing the account from being purged." + ] + } + ], + "index": 0 + }, + { + "name": "Utility", + "storage": null, + "calls": [ + { + "name": "batch", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " If origin is root then call are dispatch without checking origin filter. (This includes", + " bypassing `frame_system::Config::BaseCallFilter`).", + "", + " # ", + " - Complexity: O(C) where C is the number of calls to be batched.", + " # ", + "", + " This will return `Ok` in all circumstances. To determine the success of the batch, an", + " event is deposited. If a call failed and the batch was interrupted, then the", + " `BatchInterrupted` event is deposited, along with the number of successful calls made", + " and the error of the failed call. If all were successful, then the `BatchCompleted`", + " event is deposited." + ] + }, + { + "name": "as_derivative", + "args": [ + { + "name": "index", + "type": "u16" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through an indexed pseudonym of the sender.", + "", + " Filter from origin are passed along. The call will be dispatched with an origin which", + " use the same filter as the origin of this call.", + "", + " NOTE: If you need to ensure that any account-based filtering is not honored (i.e.", + " because you expect `proxy` to have been used prior in the call stack and you do not want", + " the call restrictions to apply to any sub-accounts), then use `as_multi_threshold_1`", + " in the Multisig pallet instead.", + "", + " NOTE: Prior to version *12, this was called `as_limited_sub`.", + "", + " The dispatch origin for this call must be _Signed_." + ] + }, + { + "name": "batch_all", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls and atomically execute them.", + " The whole transaction will rollback and fail if any of the calls failed.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " If origin is root then call are dispatch without checking origin filter. (This includes", + " bypassing `frame_system::Config::BaseCallFilter`).", + "", + " # ", + " - Complexity: O(C) where C is the number of calls to be batched.", + " # " + ] + } + ], + "events": [ + { + "name": "BatchInterrupted", + "args": [ + "u32", + "DispatchError" + ], + "docs": [ + " Batch of dispatches did not complete fully. Index of first failing dispatch given, as", + " well as the error. \\[index, error\\]" + ] + }, + { + "name": "BatchCompleted", + "args": [], + "docs": [ + " Batch of dispatches completed fully with no error." + ] + } + ], + "constants": [], + "errors": [], + "index": 1 + }, + { + "name": "Babe", + "storage": { + "prefix": "Babe", + "items": [ + { + "name": "EpochIndex", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current epoch index." + ] + }, + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Current epoch authorities." + ] + }, + { + "name": "GenesisSlot", + "modifier": "Default", + "type": { + "plain": "Slot" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The slot at which the first epoch actually started. This is 0", + " until the first block of the chain." + ] + }, + { + "name": "CurrentSlot", + "modifier": "Default", + "type": { + "plain": "Slot" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current slot number." + ] + }, + { + "name": "Randomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The epoch randomness for the *current* epoch.", + "", + " # Security", + "", + " This MUST NOT be used for gambling, as it can be influenced by a", + " malicious validator in the short term. It MAY be used in many", + " cryptographic protocols, however, so long as one remembers that this", + " (like everything else on-chain) it is public. For example, it can be", + " used where a number is needed that cannot have been chosen by an", + " adversary, for purposes such as public-coin zero-knowledge proofs." + ] + }, + { + "name": "PendingEpochConfigChange", + "modifier": "Optional", + "type": { + "plain": "NextConfigDescriptor" + }, + "fallback": "0x00", + "docs": [ + " Pending epoch configuration change that will be applied when the next epoch is enacted." + ] + }, + { + "name": "NextRandomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Next epoch randomness." + ] + }, + { + "name": "NextAuthorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Next epoch authorities." + ] + }, + { + "name": "SegmentIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Randomness under construction.", + "", + " We make a tradeoff between storage accesses and list length.", + " We store the under-construction randomness in segments of up to", + " `UNDER_CONSTRUCTION_SEGMENT_LENGTH`.", + "", + " Once a segment reaches this length, we begin the next one.", + " We reset all segments and return to `0` at the beginning of every", + " epoch." + ] + }, + { + "name": "UnderConstruction", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " TWOX-NOTE: `SegmentIndex` is an increasing integer, so this is okay." + ] + }, + { + "name": "Initialized", + "modifier": "Optional", + "type": { + "plain": "MaybeRandomness" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) which is `Some`", + " if per-block initialization has already been called for current block." + ] + }, + { + "name": "AuthorVrfRandomness", + "modifier": "Default", + "type": { + "plain": "MaybeRandomness" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) that includes the VRF output generated", + " at this block. This field should always be populated during block processing unless", + " secondary plain slots are enabled (which don't contain a VRF output)." + ] + }, + { + "name": "EpochStart", + "modifier": "Default", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The block numbers when the last and current epoch have started, respectively `N-1` and", + " `N`.", + " NOTE: We track this is in order to annotate the block number when a given pool of", + " entropy was fixed (i.e. it was known to chain observers). Since epochs are defined in", + " slots, which may be skipped, the block numbers may not line up with the slot numbers." + ] + }, + { + "name": "Lateness", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " How late the current block is compared to its parent.", + "", + " This entry is populated as part of block execution and is cleaned up", + " on block finalization. Querying this storage entry outside of block", + " execution context should always yield zero." + ] + }, + { + "name": "EpochConfig", + "modifier": "Optional", + "type": { + "plain": "BabeEpochConfiguration" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the current epoch. Should never be `None` as it is initialized in genesis." + ] + }, + { + "name": "NextEpochConfig", + "modifier": "Optional", + "type": { + "plain": "BabeEpochConfiguration" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the next epoch, `None` if the config will not change", + " (you can fallback to `EpochConfig` instead in that case)." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported.", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + }, + { + "name": "plan_config_change", + "args": [ + { + "name": "config", + "type": "NextConfigDescriptor" + } + ], + "docs": [ + " Plan an epoch config change. The epoch config change is recorded and will be enacted on", + " the next call to `enact_epoch_change`. The config will be activated one epoch after.", + " Multiple calls to this method will replace any existing planned config change that had", + " not been enacted yet." + ] + } + ], + "events": null, + "constants": [ + { + "name": "EpochDuration", + "type": "u64", + "value": "0xc800000000000000", + "docs": [ + " The amount of time, in slots, that each epoch should last.", + " NOTE: Currently it is not possible to change the epoch duration after", + " the chain has started. Attempting to do so will brick block production." + ] + }, + { + "name": "ExpectedBlockTime", + "type": "Moment", + "value": "0xb80b000000000000", + "docs": [ + " The expected average block time at which BABE should be creating", + " blocks. Since BABE is probabilistic it is not trivial to figure out", + " what the expected average block time should be based on the slot", + " duration and the security parameter `c` (where `1 - c` represents", + " the probability of a slot being empty)." + ] + } + ], + "errors": [ + { + "name": "InvalidEquivocationProof", + "docs": [ + " An equivocation proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "InvalidKeyOwnershipProof", + "docs": [ + " A key ownership proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "DuplicateOffenceReport", + "docs": [ + " A given equivocation report is valid but already previously reported." + ] + } + ], + "index": 2 + }, + { + "name": "Timestamp", + "storage": { + "prefix": "Timestamp", + "items": [ + { + "name": "Now", + "modifier": "Default", + "type": { + "plain": "Moment" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current time for the current block." + ] + }, + { + "name": "DidUpdate", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Did the timestamp get updated in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "set", + "args": [ + { + "name": "now", + "type": "Compact" + } + ], + "docs": [ + " Set the current time.", + "", + " This call should be invoked exactly once per block. It will panic at the finalization", + " phase, if this call hasn't been invoked by that time.", + "", + " The timestamp should be greater than the previous one by the amount specified by", + " `MinimumPeriod`.", + "", + " The dispatch origin for this call must be `Inherent`.", + "", + " # ", + " - `O(1)` (Note that implementations of `OnTimestampSet` must also be `O(1)`)", + " - 1 storage read and 1 storage mutation (codec `O(1)`). (because of `DidUpdate::take` in `on_finalize`)", + " - 1 event handler `on_timestamp_set`. Must be `O(1)`.", + " # " + ] + } + ], + "events": null, + "constants": [ + { + "name": "MinimumPeriod", + "type": "Moment", + "value": "0xdc05000000000000", + "docs": [ + " The minimum period between blocks. Beware that this is different to the *expected* period", + " that the block production apparatus provides. Your chosen consensus system will generally", + " work with this to determine a sensible block time. e.g. For Aura, it will be double this", + " period on default settings." + ] + } + ], + "errors": [], + "index": 3 + }, + { + "name": "Authorship", + "storage": { + "prefix": "Authorship", + "items": [ + { + "name": "Uncles", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Uncles" + ] + }, + { + "name": "Author", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " Author of current block." + ] + }, + { + "name": "DidSetUncles", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Whether uncles were already set in this block." + ] + } + ] + }, + "calls": [ + { + "name": "set_uncles", + "args": [ + { + "name": "new_uncles", + "type": "Vec
" + } + ], + "docs": [ + " Provide a set of uncles." + ] + } + ], + "events": null, + "constants": [], + "errors": [ + { + "name": "InvalidUncleParent", + "docs": [ + " The uncle parent not in the chain." + ] + }, + { + "name": "UnclesAlreadySet", + "docs": [ + " Uncles already set in the block." + ] + }, + { + "name": "TooManyUncles", + "docs": [ + " Too many uncles." + ] + }, + { + "name": "GenesisUncle", + "docs": [ + " The uncle is genesis." + ] + }, + { + "name": "TooHighUncle", + "docs": [ + " The uncle is too high in chain." + ] + }, + { + "name": "UncleAlreadyIncluded", + "docs": [ + " The uncle is already included." + ] + }, + { + "name": "OldUncle", + "docs": [ + " The uncle isn't recent enough to be included." + ] + } + ], + "index": 4 + }, + { + "name": "Indices", + "storage": { + "prefix": "Indices", + "items": [ + { + "name": "Accounts", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountIndex", + "value": "(AccountId,BalanceOf,bool)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The lookup from index to account." + ] + } + ] + }, + "calls": [ + { + "name": "claim", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an previously unassigned index.", + "", + " Payment: `Deposit` is reserved from the sender account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be claimed. This must not be in use.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an index already owned by the sender to another account. The balance reservation", + " is effectively transferred to the new account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be re-assigned. This must be owned by the sender.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One transfer operation.", + " - One event.", + " -------------------", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (recipient)", + " - Writes: Indices Accounts, System Account (recipient)", + " # " + ] + }, + { + "name": "free", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Free up an index owned by the sender.", + "", + " Payment: Any previous deposit placed for the index is unreserved in the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must own the index.", + "", + " - `index`: the index to be freed. This must be owned by the sender.", + "", + " Emits `IndexFreed` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + }, + { + "name": "freeze", + "type": "bool" + } + ], + "docs": [ + " Force an index to an account. This doesn't require a deposit. If the index is already", + " held, then any deposit is reimbursed to its current owner.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `index`: the index to be (re-)assigned.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + " - `freeze`: if set to `true`, will freeze the index so it cannot be transferred.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one reserve operation.", + " - One event.", + " -------------------", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (original owner)", + " - Writes: Indices Accounts, System Account (original owner)", + " # " + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Freeze an index so it will always point to the sender account. This consumes the deposit.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must have a", + " non-frozen account `index`.", + "", + " - `index`: the index to be frozen in place.", + "", + " Emits `IndexFrozen` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one slash operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + } + ], + "events": [ + { + "name": "IndexAssigned", + "args": [ + "AccountId", + "AccountIndex" + ], + "docs": [ + " A account index was assigned. \\[index, who\\]" + ] + }, + { + "name": "IndexFreed", + "args": [ + "AccountIndex" + ], + "docs": [ + " A account index has been freed up (unassigned). \\[index\\]" + ] + }, + { + "name": "IndexFrozen", + "args": [ + "AccountIndex", + "AccountId" + ], + "docs": [ + " A account index has been frozen to its current account ID. \\[index, who\\]" + ] + } + ], + "constants": [ + { + "name": "Deposit", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The deposit needed for reserving an index." + ] + } + ], + "errors": [ + { + "name": "NotAssigned", + "docs": [ + " The index was not already assigned." + ] + }, + { + "name": "NotOwner", + "docs": [ + " The index is assigned to another account." + ] + }, + { + "name": "InUse", + "docs": [ + " The index was not available." + ] + }, + { + "name": "NotTransfer", + "docs": [ + " The source and destination accounts are identical." + ] + }, + { + "name": "Permanent", + "docs": [ + " The index is permanent and may not be freed/changed." + ] + } + ], + "index": 5 + }, + { + "name": "Balances", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "TotalIssuance", + "modifier": "Default", + "type": { + "plain": "Balance" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total units issued in the system." + ] + }, + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountData", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The balance of an account.", + "", + " NOTE: This is only used in the case that this pallet is used to store balances." + ] + }, + { + "name": "Locks", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Any liquidity locks on some account balances.", + " NOTE: Should only be accessed when setting, changing and freeing a lock." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " This is set to v2.0.0 for new networks." + ] + } + ] + }, + "calls": [ + { + "name": "transfer", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Transfer some liquid free balance to another account.", + "", + " `transfer` will set the `FreeBalance` of the sender and receiver.", + " It will decrease the total issuance of the system by the `TransferFee`.", + " If the sender's account is below the existential deposit as a result", + " of the transfer, the account will be reaped.", + "", + " The dispatch origin for this call must be `Signed` by the transactor.", + "", + " # ", + " - Dependent on arguments but not critical, given proper implementations for", + " input config types. See related functions below.", + " - It contains a limited number of reads and writes internally and no complex computation.", + "", + " Related functions:", + "", + " - `ensure_can_withdraw` is always called internally but has a bounded complexity.", + " - Transferring balances to accounts that did not exist before will cause", + " `T::OnNewAccount::on_new_account` to be called.", + " - Removing enough funds from an account will trigger `T::DustRemoval::on_unbalanced`.", + " - `transfer_keep_alive` works the same way as `transfer`, but has an additional", + " check that the transfer will not kill the origin account.", + " ---------------------------------", + " - Base Weight: 73.64 µs, worst case scenario (account created, account removed)", + " - DB Weight: 1 Read and 1 Write to destination account", + " - Origin account is already in memory, so no DB operations for them.", + " # " + ] + }, + { + "name": "set_balance", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "new_free", + "type": "Compact" + }, + { + "name": "new_reserved", + "type": "Compact" + } + ], + "docs": [ + " Set the balances of a given account.", + "", + " This will alter `FreeBalance` and `ReservedBalance` in storage. it will", + " also decrease the total issuance of the system (`TotalIssuance`).", + " If the new free or reserved balance is below the existential deposit,", + " it will reset the account nonce (`frame_system::AccountNonce`).", + "", + " The dispatch origin for this call is `root`.", + "", + " # ", + " - Independent of the arguments.", + " - Contains a limited number of reads and writes.", + " ---------------------", + " - Base Weight:", + " - Creating: 27.56 µs", + " - Killing: 35.11 µs", + " - DB Weight: 1 Read, 1 Write to `who`", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Exactly as `transfer`, except the origin must be root and the source account may be", + " specified.", + " # ", + " - Same as transfer, but additional read and write because the source account is", + " not assumed to be in the overlay.", + " # " + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Same as the [`transfer`] call, but with a check that the transfer will not kill the", + " origin account.", + "", + " 99% of the time you want [`transfer`] instead.", + "", + " [`transfer`]: struct.Pallet.html#method.transfer", + " # ", + " - Cheaper than transfer because account cannot be killed.", + " - Base Weight: 51.4 µs", + " - DB Weight: 1 Read and 1 Write to dest (sender is in overlay already)", + " #" + ] + } + ], + "events": [ + { + "name": "Endowed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was created with some free balance. \\[account, free_balance\\]" + ] + }, + { + "name": "DustLost", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was removed whose balance was non-zero but below ExistentialDeposit,", + " resulting in an outright loss. \\[account, balance\\]" + ] + }, + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " Transfer succeeded. \\[from, to, value\\]" + ] + }, + { + "name": "BalanceSet", + "args": [ + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " A balance was set by root. \\[who, free, reserved\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some amount was deposited (e.g. for transaction fees). \\[who, deposit\\]" + ] + }, + { + "name": "Reserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was reserved (moved from free to reserved). \\[who, value\\]" + ] + }, + { + "name": "Unreserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was unreserved (moved from reserved to free). \\[who, value\\]" + ] + }, + { + "name": "ReserveRepatriated", + "args": [ + "AccountId", + "AccountId", + "Balance", + "BalanceStatus" + ], + "docs": [ + " Some balance was moved from the reserve of the first account to the second account.", + " Final argument indicates the destination balance type.", + " \\[from, to, balance, destination_status\\]" + ] + } + ], + "constants": [ + { + "name": "ExistentialDeposit", + "type": "Balance", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to keep an account open." + ] + } + ], + "errors": [ + { + "name": "VestingBalance", + "docs": [ + " Vesting balance too high to send value" + ] + }, + { + "name": "LiquidityRestrictions", + "docs": [ + " Account liquidity restrictions prevent withdrawal" + ] + }, + { + "name": "Overflow", + "docs": [ + " Got an overflow after adding" + ] + }, + { + "name": "InsufficientBalance", + "docs": [ + " Balance too low to send value" + ] + }, + { + "name": "ExistentialDeposit", + "docs": [ + " Value too low to create account due to existential deposit" + ] + }, + { + "name": "KeepAlive", + "docs": [ + " Transfer/payment would kill account" + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " A vesting schedule already exists for this account" + ] + }, + { + "name": "DeadAccount", + "docs": [ + " Beneficiary account must pre-exist" + ] + } + ], + "index": 6 + }, + { + "name": "TransactionPayment", + "storage": { + "prefix": "TransactionPayment", + "items": [ + { + "name": "NextFeeMultiplier", + "modifier": "Default", + "type": { + "plain": "Multiplier" + }, + "fallback": "0x000064a7b3b6e00d0000000000000000", + "docs": [] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": null, + "events": null, + "constants": [ + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + }, + { + "name": "WeightToFee", + "type": "Vec", + "value": "0x0401000000000000000000000000000000000000000001", + "docs": [ + " The polynomial that is applied in order to derive fee from weight." + ] + } + ], + "errors": [], + "index": 7 + }, + { + "name": "ElectionProviderMultiPhase", + "storage": { + "prefix": "ElectionProviderMultiPhase", + "items": [ + { + "name": "Round", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x01000000", + "docs": [ + " Internal counter for the number of rounds.", + "", + " This is useful for de-duplication of transactions submitted to the pool, and general", + " diagnostics of the pallet.", + "", + " This is merely incremented once per every time that an upstream `elect` is called." + ] + }, + { + "name": "CurrentPhase", + "modifier": "Default", + "type": { + "plain": "ElectionPhase" + }, + "fallback": "0x00", + "docs": [ + " Current phase." + ] + }, + { + "name": "QueuedSolution", + "modifier": "Optional", + "type": { + "plain": "ReadySolution" + }, + "fallback": "0x00", + "docs": [ + " Current best solution, signed or unsigned, queued to be returned upon `elect`." + ] + }, + { + "name": "Snapshot", + "modifier": "Optional", + "type": { + "plain": "RoundSnapshot" + }, + "fallback": "0x00", + "docs": [ + " Snapshot data of the round.", + "", + " This is created at the beginning of the signed phase and cleared upon calling `elect`." + ] + }, + { + "name": "DesiredTargets", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Desired number of targets to elect for this round.", + "", + " Only exists when [`Snapshot`] is present." + ] + }, + { + "name": "SnapshotMetadata", + "modifier": "Optional", + "type": { + "plain": "SolutionOrSnapshotSize" + }, + "fallback": "0x00", + "docs": [ + " The metadata of the [`RoundSnapshot`]", + "", + " Only exists when [`Snapshot`] is present." + ] + } + ] + }, + "calls": [ + { + "name": "submit_unsigned", + "args": [ + { + "name": "solution", + "type": "RawSolution" + }, + { + "name": "witness", + "type": "SolutionOrSnapshotSize" + } + ], + "docs": [ + " Submit a solution for the unsigned phase.", + "", + " The dispatch origin fo this call must be __none__.", + "", + " This submission is checked on the fly. Moreover, this unsigned solution is only", + " validated when submitted to the pool from the **local** node. Effectively, this means", + " that only active validators can submit this transaction when authoring a block (similar", + " to an inherent).", + "", + " To prevent any incorrect solution (and thus wasted time/weight), this transaction will", + " panic if the solution submitted by the validator is invalid in any way, effectively", + " putting their authoring reward at risk.", + "", + " No deposit or reward is associated with this submission." + ] + } + ], + "events": [ + { + "name": "SolutionStored", + "args": [ + "ElectionCompute" + ], + "docs": [ + " A solution was stored with the given compute.", + "", + " If the solution is signed, this means that it hasn't yet been processed. If the", + " solution is unsigned, this means that it has also been processed." + ] + }, + { + "name": "ElectionFinalized", + "args": [ + "Option" + ], + "docs": [ + " The election has been finalized, with `Some` of the given computation, or else if the", + " election failed, `None`." + ] + }, + { + "name": "Rewarded", + "args": [ + "AccountId" + ], + "docs": [ + " An account has been rewarded for their signed submission being finalized." + ] + }, + { + "name": "Slashed", + "args": [ + "AccountId" + ], + "docs": [ + " An account has been slashed for submitting an invalid signed submission." + ] + }, + { + "name": "SignedPhaseStarted", + "args": [ + "u32" + ], + "docs": [ + " The signed phase of the given round has started." + ] + }, + { + "name": "UnsignedPhaseStarted", + "args": [ + "u32" + ], + "docs": [ + " The unsigned phase of the given round has started." + ] + } + ], + "constants": [ + { + "name": "UnsignedPhase", + "type": "BlockNumber", + "value": "0x32000000", + "docs": [ + " Duration of the unsigned phase." + ] + }, + { + "name": "SignedPhase", + "type": "BlockNumber", + "value": "0x32000000", + "docs": [ + " Duration of the signed phase." + ] + }, + { + "name": "SolutionImprovementThreshold", + "type": "Perbill", + "value": "0xa0860100", + "docs": [ + " The minimum amount of improvement to the solution score that defines a solution as", + " \"better\" (in any phase)." + ] + } + ], + "errors": [ + { + "name": "PreDispatchEarlySubmission", + "docs": [ + " Submission was too early." + ] + }, + { + "name": "PreDispatchWrongWinnerCount", + "docs": [ + " Wrong number of winners presented." + ] + }, + { + "name": "PreDispatchWeakSubmission", + "docs": [ + " Submission was too weak, score-wise." + ] + } + ], + "index": 8 + }, + { + "name": "Staking", + "storage": { + "prefix": "Staking", + "items": [ + { + "name": "HistoryDepth", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x54000000", + "docs": [ + " Number of eras to keep in history.", + "", + " Information is kept for eras in `[current_era - history_depth; current_era]`.", + "", + " Must be more than the number of eras delayed by session otherwise. I.e. active era must", + " always be in history. I.e. `active_era > current_era - history_depth` must be", + " guaranteed." + ] + }, + { + "name": "ValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The ideal number of staking participants." + ] + }, + { + "name": "MinimumValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Minimum number of staking participants before emergency conditions are imposed." + ] + }, + { + "name": "Invulnerables", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Any validators that may never be slashed or forcibly kicked. It's a Vec since they're", + " easy to initialize and the performance hit is minimal (we expect no more than four", + " invulnerables) and restricted to testnets." + ] + }, + { + "name": "Bonded", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all locked \"stash\" accounts to the controller account." + ] + }, + { + "name": "Ledger", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "StakingLedger", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all (unlocked) \"controller\" accounts to the info regarding the staking." + ] + }, + { + "name": "Payee", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RewardDestination", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Where the reward payment should be made. Keyed by stash." + ] + }, + { + "name": "Validators", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ValidatorPrefs", + "linked": false + } + }, + "fallback": "0x0000", + "docs": [ + " The map from (wannabe) validator stash key to the preferences of that validator." + ] + }, + { + "name": "Nominators", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Nominations", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The map from nominator stash key to the set of stash keys of all validators to nominate." + ] + }, + { + "name": "CurrentEra", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The current era index.", + "", + " This is the latest planned era, depending on how the Session pallet queues the validator", + " set, it might be active or not." + ] + }, + { + "name": "ActiveEra", + "modifier": "Optional", + "type": { + "plain": "ActiveEraInfo" + }, + "fallback": "0x00", + "docs": [ + " The active era information, it holds index and start.", + "", + " The active era is the era being currently rewarded. Validator set of this era must be", + " equal to [`SessionInterface::validators`]." + ] + }, + { + "name": "ErasStartSessionIndex", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The session index at which the era start for the last `HISTORY_DEPTH` eras.", + "", + " Note: This tracks the starting session (i.e. session index when era start being active)", + " for the eras in `[CurrentEra - HISTORY_DEPTH, CurrentEra]`." + ] + }, + { + "name": "ErasStakers", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Exposure of validator at era.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasStakersClipped", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Clipped Exposure of validator at era.", + "", + " This is similar to [`ErasStakers`] but number of nominators exposed is reduced to the", + " `T::MaxNominatorRewardedPerValidator` biggest stakers.", + " (Note: the field `total` and `own` of the exposure remains unchanged).", + " This is used to limit the i/o cost for the nominator payout.", + "", + " This is keyed fist by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasValidatorPrefs", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "ValidatorPrefs", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x0000", + "docs": [ + " Similar to `ErasStakers`, this holds the preferences of validators.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras." + ] + }, + { + "name": "ErasValidatorReward", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The total validator era payout for the last `HISTORY_DEPTH` eras.", + "", + " Eras that haven't finished yet or has been removed doesn't have reward." + ] + }, + { + "name": "ErasRewardPoints", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "EraRewardPoints", + "linked": false + } + }, + "fallback": "0x0000000000", + "docs": [ + " Rewards for the last `HISTORY_DEPTH` eras.", + " If reward hasn't been set or has been removed then 0 reward is returned." + ] + }, + { + "name": "ErasTotalStake", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total amount staked for the last `HISTORY_DEPTH` eras.", + " If total hasn't been set or has been removed then 0 stake is returned." + ] + }, + { + "name": "ForceEra", + "modifier": "Default", + "type": { + "plain": "Forcing" + }, + "fallback": "0x00", + "docs": [ + " Mode of era forcing." + ] + }, + { + "name": "SlashRewardFraction", + "modifier": "Default", + "type": { + "plain": "Perbill" + }, + "fallback": "0x00000000", + "docs": [ + " The percentage of the slash that is distributed to reporters.", + "", + " The rest of the slashed value is handled by the `Slash`." + ] + }, + { + "name": "CanceledSlashPayout", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of currency given to reporters of a slash event which was", + " canceled by extraordinary circumstances (e.g. governance)." + ] + }, + { + "name": "UnappliedSlashes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " All unapplied slashes that are queued for later." + ] + }, + { + "name": "BondedEras", + "modifier": "Default", + "type": { + "plain": "Vec<(EraIndex,SessionIndex)>" + }, + "fallback": "0x00", + "docs": [ + " A mapping from still-bonded eras to the first session index of that era.", + "", + " Must contains information for eras for the range:", + " `[active_era - bounding_duration; active_era]`" + ] + }, + { + "name": "ValidatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "(Perbill,BalanceOf)", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on validators, mapped by era to the highest slash proportion", + " and slash value of the era." + ] + }, + { + "name": "NominatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "BalanceOf", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on nominators, mapped by era to the highest slash value of the era." + ] + }, + { + "name": "SlashingSpans", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SlashingSpans", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Slashing spans for stash accounts." + ] + }, + { + "name": "SpanSlash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(AccountId,SpanIndex)", + "value": "SpanRecord", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Records information about the maximum slash of a stash within a slashing span,", + " as well as how much reward has been paid out." + ] + }, + { + "name": "EarliestUnappliedSlash", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The earliest era for which we have a pending, unapplied slash." + ] + }, + { + "name": "CurrentPlannedSession", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The last planned session scheduled by the session pallet.", + "", + " This is basically in sync with the call to [`SessionManager::new_session`]." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x05", + "docs": [ + " True if network has been upgraded to this version.", + " Storage version of the pallet.", + "", + " This is set to v6.0.0 for new networks." + ] + } + ] + }, + "calls": [ + { + "name": "bond", + "args": [ + { + "name": "controller", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " Take the origin account as a stash and lock up `value` of its balance. `controller` will", + " be the account that controls it.", + "", + " `value` must be more than the `minimum_balance` specified by `T::Currency`.", + "", + " The dispatch origin for this call must be _Signed_ by the stash account.", + "", + " Emits `Bonded`.", + "", + " # ", + " - Independent of the arguments. Moderate complexity.", + " - O(1).", + " - Three extra DB entries.", + "", + " NOTE: Two of the storage writes (`Self::bonded`, `Self::payee`) are _never_ cleaned", + " unless the `origin` falls below _existential deposit_ and gets removed as dust.", + " ------------------", + " Weight: O(1)", + " DB Weight:", + " - Read: Bonded, Ledger, [Origin Account], Current Era, History Depth, Locks", + " - Write: Bonded, Payee, [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "bond_extra", + "args": [ + { + "name": "max_additional", + "type": "Compact" + } + ], + "docs": [ + " Add some extra amount that have appeared in the stash `free_balance` into the balance up", + " for staking.", + "", + " Use this if there are additional funds in your stash account that you wish to bond.", + " Unlike [`bond`] or [`unbond`] this function does not impose any limitation on the amount", + " that can be added.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller and", + " it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Bonded`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - O(1).", + " - One DB entry.", + " ------------", + " DB Weight:", + " - Read: Era Election Status, Bonded, Ledger, [Origin Account], Locks", + " - Write: [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "unbond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Schedule a portion of the stash to be unlocked ready for transfer out after the bond", + " period ends. If this leaves an amount actively bonded less than", + " T::Currency::minimum_balance(), then it is increased to the full amount.", + "", + " Once the unlock period is done, you can call `withdraw_unbonded` to actually move", + " the funds out of management ready for transfer.", + "", + " No more than a limited number of unlocking chunks (see `MAX_UNLOCKING_CHUNKS`)", + " can co-exists at the same time. In that case, [`Call::withdraw_unbonded`] need", + " to be called first to remove some of the chunks (if possible).", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Unbonded`.", + "", + " See also [`Call::withdraw_unbonded`].", + "", + " # ", + " - Independent of the arguments. Limited but potentially exploitable complexity.", + " - Contains a limited number of reads.", + " - Each call (requires the remainder of the bonded balance to be above `minimum_balance`)", + " will cause a new entry to be inserted into a vector (`Ledger.unlocking`) kept in storage.", + " The only way to clean the aforementioned storage item is also user-controlled via", + " `withdraw_unbonded`.", + " - One DB entry.", + " ----------", + " Weight: O(1)", + " DB Weight:", + " - Read: EraElectionStatus, Ledger, CurrentEra, Locks, BalanceOf Stash,", + " - Write: Locks, Ledger, BalanceOf Stash,", + " " + ] + }, + { + "name": "withdraw_unbonded", + "args": [ + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove any unlocked chunks from the `unlocking` queue from our management.", + "", + " This essentially frees up that balance to be used by the stash account to do", + " whatever it wants.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " Emits `Withdrawn`.", + "", + " See also [`Call::unbond`].", + "", + " # ", + " - Could be dependent on the `origin` argument and how much `unlocking` chunks exist.", + " It implies `consolidate_unlocked` which loops over `Ledger.unlocking`, which is", + " indirectly user-controlled. See [`unbond`] for more detail.", + " - Contains a limited number of reads, yet the size of which could be large based on `ledger`.", + " - Writes are limited to the `origin` account key.", + " ---------------", + " Complexity O(S) where S is the number of slashing spans to remove", + " Update:", + " - Reads: EraElectionStatus, Ledger, Current Era, Locks, [Origin Account]", + " - Writes: [Origin Account], Locks, Ledger", + " Kill:", + " - Reads: EraElectionStatus, Ledger, Current Era, Bonded, Slashing Spans, [Origin", + " Account], Locks, BalanceOf stash", + " - Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators,", + " [Origin Account], Locks, BalanceOf stash.", + " - Writes Each: SpanSlash * S", + " NOTE: Weight annotation is the kill scenario, we refund otherwise.", + " # " + ] + }, + { + "name": "validate", + "args": [ + { + "name": "prefs", + "type": "ValidatorPrefs" + } + ], + "docs": [ + " Declare the desire to validate for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " -----------", + " Weight: O(1)", + " DB Weight:", + " - Read: Era Election Status, Ledger", + " - Write: Nominators, Validators", + " # " + ] + }, + { + "name": "nominate", + "args": [ + { + "name": "targets", + "type": "Vec" + } + ], + "docs": [ + " Declare the desire to nominate `targets` for the origin controller.", + "", + " Effects will be felt at the beginning of the next era. This can only be called when", + " [`EraElectionStatus`] is `Closed`.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - The transaction's complexity is proportional to the size of `targets` (N)", + " which is capped at CompactAssignments::LIMIT (MAX_NOMINATIONS).", + " - Both the reads and writes follow a similar pattern.", + " ---------", + " Weight: O(N)", + " where N is the number of targets", + " DB Weight:", + " - Reads: Era Election Status, Ledger, Current Era", + " - Writes: Validators, Nominators", + " # " + ] + }, + { + "name": "chill", + "args": [], + "docs": [ + " Declare no desire to either validate or nominate.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains one read.", + " - Writes are limited to the `origin` account key.", + " --------", + " Weight: O(1)", + " DB Weight:", + " - Read: EraElectionStatus, Ledger", + " - Write: Validators, Nominators", + " # " + ] + }, + { + "name": "set_payee", + "args": [ + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " (Re-)set the payment target for a controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ---------", + " - Weight: O(1)", + " - DB Weight:", + " - Read: Ledger", + " - Write: Payee", + " # " + ] + }, + { + "name": "set_controller", + "args": [ + { + "name": "controller", + "type": "LookupSource" + } + ], + "docs": [ + " (Re-)set the controller of a stash.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ----------", + " Weight: O(1)", + " DB Weight:", + " - Read: Bonded, Ledger New Controller, Ledger Old Controller", + " - Write: Bonded, Ledger New Controller, Ledger Old Controller", + " # " + ] + }, + { + "name": "set_validator_count", + "args": [ + { + "name": "new", + "type": "Compact" + } + ], + "docs": [ + " Sets the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Weight: O(1)", + " Write: Validator Count", + " # " + ] + }, + { + "name": "increase_validator_count", + "args": [ + { + "name": "additional", + "type": "Compact" + } + ], + "docs": [ + " Increments the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Same as [`set_validator_count`].", + " # " + ] + }, + { + "name": "scale_validator_count", + "args": [ + { + "name": "factor", + "type": "Percent" + } + ], + "docs": [ + " Scale up the ideal number of validators by a factor.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Same as [`set_validator_count`].", + " # " + ] + }, + { + "name": "force_no_eras", + "args": [], + "docs": [ + " Force there to be no new eras indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - No arguments.", + " - Weight: O(1)", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "force_new_era", + "args": [], + "docs": [ + " Force there to be a new era at the end of the next session. After this, it will be", + " reset to normal (non-forced) behaviour.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - No arguments.", + " - Weight: O(1)", + " - Write ForceEra", + " # " + ] + }, + { + "name": "set_invulnerables", + "args": [ + { + "name": "invulnerables", + "type": "Vec" + } + ], + "docs": [ + " Set the validators who cannot be slashed (if any).", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - O(V)", + " - Write: Invulnerables", + " # " + ] + }, + { + "name": "force_unstake", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Force a current staker to become completely unstaked, immediately.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " O(S) where S is the number of slashing spans to be removed", + " Reads: Bonded, Slashing Spans, Account, Locks", + " Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Account, Locks", + " Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "force_new_era_always", + "args": [], + "docs": [ + " Force there to be a new era at the end of sessions indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - Weight: O(1)", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "cancel_deferred_slash", + "args": [ + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "slash_indices", + "type": "Vec" + } + ], + "docs": [ + " Cancel enactment of a deferred slash.", + "", + " Can be called by the `T::SlashCancelOrigin`.", + "", + " Parameters: era and indices of the slashes for that era to kill.", + "", + " # ", + " Complexity: O(U + S)", + " with U unapplied slashes weighted with U=1000", + " and S is the number of slash indices to be canceled.", + " - Read: Unapplied Slashes", + " - Write: Unapplied Slashes", + " # " + ] + }, + { + "name": "payout_stakers", + "args": [ + { + "name": "validator_stash", + "type": "AccountId" + }, + { + "name": "era", + "type": "EraIndex" + } + ], + "docs": [ + " Pay out all the stakers behind a single validator for a single era.", + "", + " - `validator_stash` is the stash account of the validator. Their nominators, up to", + " `T::MaxNominatorRewardedPerValidator`, will also receive their rewards.", + " - `era` may be any era between `[current_era - history_depth; current_era]`.", + "", + " The origin of this call must be _Signed_. Any account can call this function, even if", + " it is not one of the stakers.", + "", + " This can only be called when [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Time complexity: at most O(MaxNominatorRewardedPerValidator).", + " - Contains a limited number of reads and writes.", + " -----------", + " N is the Number of payouts for the validator (including the validator)", + " Weight:", + " - Reward Destination Staked: O(N)", + " - Reward Destination Controller (Creating): O(N)", + " DB Weight:", + " - Read: EraElectionStatus, CurrentEra, HistoryDepth, ErasValidatorReward,", + " ErasStakersClipped, ErasRewardPoints, ErasValidatorPrefs (8 items)", + " - Read Each: Bonded, Ledger, Payee, Locks, System Account (5 items)", + " - Write Each: System Account, Locks, Ledger (3 items)", + "", + " NOTE: weights are assuming that payouts are made to alive stash account (Staked).", + " Paying even a dead controller is cheaper weight-wise. We don't do any refunds here.", + " # " + ] + }, + { + "name": "rebond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Rebond a portion of the stash scheduled to be unlocked.", + "", + " The dispatch origin must be signed by the controller, and it can be only called when", + " [`EraElectionStatus`] is `Closed`.", + "", + " # ", + " - Time complexity: O(L), where L is unlocking chunks", + " - Bounded by `MAX_UNLOCKING_CHUNKS`.", + " - Storage changes: Can't increase storage, only decrease it.", + " ---------------", + " - DB Weight:", + " - Reads: EraElectionStatus, Ledger, Locks, [Origin Account]", + " - Writes: [Origin Account], Locks, Ledger", + " # " + ] + }, + { + "name": "set_history_depth", + "args": [ + { + "name": "new_history_depth", + "type": "Compact" + }, + { + "name": "_era_items_deleted", + "type": "Compact" + } + ], + "docs": [ + " Set `HistoryDepth` value. This function will delete any history information", + " when `HistoryDepth` is reduced.", + "", + " Parameters:", + " - `new_history_depth`: The new history depth you would like to set.", + " - `era_items_deleted`: The number of items that will be deleted by this dispatch.", + " This should report all the storage items that will be deleted by clearing old", + " era history. Needed to report an accurate weight for the dispatch. Trusted by", + " `Root` to report an accurate number.", + "", + " Origin must be root.", + "", + " # ", + " - E: Number of history depths removed, i.e. 10 -> 7 = 3", + " - Weight: O(E)", + " - DB Weight:", + " - Reads: Current Era, History Depth", + " - Writes: History Depth", + " - Clear Prefix Each: Era Stakers, EraStakersClipped, ErasValidatorPrefs", + " - Writes Each: ErasValidatorReward, ErasRewardPoints, ErasTotalStake, ErasStartSessionIndex", + " # " + ] + }, + { + "name": "reap_stash", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove all data structure concerning a staker/stash once its balance is at the minimum.", + " This is essentially equivalent to `withdraw_unbonded` except it can be called by anyone", + " and the target `stash` must have no funds left beyond the ED.", + "", + " This can be called from any origin.", + "", + " - `stash`: The stash account to reap. Its balance must be zero.", + "", + " # ", + " Complexity: O(S) where S is the number of slashing spans on the account.", + " DB Weight:", + " - Reads: Stash Account, Bonded, Slashing Spans, Locks", + " - Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Stash Account, Locks", + " - Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "kick", + "args": [ + { + "name": "who", + "type": "Vec" + } + ], + "docs": [ + " Remove the given nominations from the calling validator.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + " And, it can be only called when [`EraElectionStatus`] is `Closed`. The controller", + " account should represent a validator.", + "", + " - `who`: A list of nominator stash accounts who are nominating this validator which", + " should no longer be nominating this validator.", + "", + " Note: Making this call only makes sense if you first set the validator preferences to", + " block any further nominations." + ] + } + ], + "events": [ + { + "name": "EraPayout", + "args": [ + "EraIndex", + "Balance", + "Balance" + ], + "docs": [ + " The era payout has been set; the first balance is the validator-payout; the second is", + " the remainder from the maximum amount of reward.", + " \\[era_index, validator_payout, remainder\\]" + ] + }, + { + "name": "Reward", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The staker has been rewarded by this amount. \\[stash, amount\\]" + ] + }, + { + "name": "Slash", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " One validator (and its nominators) has been slashed by the given amount.", + " \\[validator, amount\\]" + ] + }, + { + "name": "OldSlashingReportDiscarded", + "args": [ + "SessionIndex" + ], + "docs": [ + " An old slashing report from a prior era was discarded because it could", + " not be processed. \\[session_index\\]" + ] + }, + { + "name": "StakingElection", + "args": [], + "docs": [ + " A new set of stakers was elected." + ] + }, + { + "name": "Bonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has bonded this amount. \\[stash, amount\\]", + "", + " NOTE: This event is only emitted when funds are bonded via a dispatchable. Notably,", + " it will not be emitted for staking rewards when they are added to stake." + ] + }, + { + "name": "Unbonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has unbonded this amount. \\[stash, amount\\]" + ] + }, + { + "name": "Withdrawn", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has called `withdraw_unbonded` and removed unbonding chunks worth `Balance`", + " from the unlocking queue. \\[stash, amount\\]" + ] + }, + { + "name": "Kicked", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A nominator has been kicked from a validator. \\[nominator, stash\\]" + ] + } + ], + "constants": [ + { + "name": "SessionsPerEra", + "type": "SessionIndex", + "value": "0x06000000", + "docs": [ + " Number of sessions per era." + ] + }, + { + "name": "BondingDuration", + "type": "EraIndex", + "value": "0xa0020000", + "docs": [ + " Number of eras that staked funds must remain bonded for." + ] + }, + { + "name": "SlashDeferDuration", + "type": "EraIndex", + "value": "0xa8000000", + "docs": [ + " Number of eras that slashes are deferred by, after computation.", + "", + " This should be less than the bonding duration.", + " Set to 0 if slashes should be applied immediately, without opportunity for", + " intervention." + ] + }, + { + "name": "MaxNominatorRewardedPerValidator", + "type": "u32", + "value": "0x00010000", + "docs": [ + " The maximum number of nominators rewarded for each validator.", + "", + " For each validator only the `$MaxNominatorRewardedPerValidator` biggest stakers can claim", + " their reward. This used to limit the i/o cost for the nominator payout." + ] + }, + { + "name": "MaxNominations", + "type": "u32", + "value": "0x10000000", + "docs": [ + " Maximum number of nominations per nominator." + ] + } + ], + "errors": [ + { + "name": "NotController", + "docs": [ + " Not a controller account." + ] + }, + { + "name": "NotStash", + "docs": [ + " Not a stash account." + ] + }, + { + "name": "AlreadyBonded", + "docs": [ + " Stash is already bonded." + ] + }, + { + "name": "AlreadyPaired", + "docs": [ + " Controller is already paired." + ] + }, + { + "name": "EmptyTargets", + "docs": [ + " Targets cannot be empty." + ] + }, + { + "name": "DuplicateIndex", + "docs": [ + " Duplicate index." + ] + }, + { + "name": "InvalidSlashIndex", + "docs": [ + " Slash record index out of bounds." + ] + }, + { + "name": "InsufficientValue", + "docs": [ + " Can not bond with value less than minimum balance." + ] + }, + { + "name": "NoMoreChunks", + "docs": [ + " Can not schedule more unlock chunks." + ] + }, + { + "name": "NoUnlockChunk", + "docs": [ + " Can not rebond without unlocking chunks." + ] + }, + { + "name": "FundedTarget", + "docs": [ + " Attempting to target a stash that still has funds." + ] + }, + { + "name": "InvalidEraToReward", + "docs": [ + " Invalid era to reward." + ] + }, + { + "name": "InvalidNumberOfNominations", + "docs": [ + " Invalid number of nominations." + ] + }, + { + "name": "NotSortedAndUnique", + "docs": [ + " Items are not sorted and unique." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Rewards for this era have already been claimed for this validator." + ] + }, + { + "name": "IncorrectHistoryDepth", + "docs": [ + " Incorrect previous history depth input provided." + ] + }, + { + "name": "IncorrectSlashingSpans", + "docs": [ + " Incorrect number of slashing spans provided." + ] + }, + { + "name": "BadState", + "docs": [ + " Internal state has become somehow corrupted and the operation cannot continue." + ] + }, + { + "name": "TooManyTargets", + "docs": [ + " Too many nomination targets supplied." + ] + }, + { + "name": "BadTarget", + "docs": [ + " A nomination target was supplied that was blocked or otherwise not a validator." + ] + } + ], + "index": 9 + }, + { + "name": "Session", + "storage": { + "prefix": "Session", + "items": [ + { + "name": "Validators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of validators." + ] + }, + { + "name": "CurrentIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Current index of the session." + ] + }, + { + "name": "QueuedChanged", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the underlying economic identities or weighting behind the validators", + " has changed in the queued validator set." + ] + }, + { + "name": "QueuedKeys", + "modifier": "Default", + "type": { + "plain": "Vec<(ValidatorId,Keys)>" + }, + "fallback": "0x00", + "docs": [ + " The queued keys for the next session. When the next session begins, these keys", + " will be used to determine the validator's session keys." + ] + }, + { + "name": "DisabledValidators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Indices of disabled validators.", + "", + " The set is cleared when `on_session_ending` returns a new set of identities." + ] + }, + { + "name": "NextKeys", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ValidatorId", + "value": "Keys", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The next session keys for a validator." + ] + }, + { + "name": "KeyOwner", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(KeyTypeId,Bytes)", + "value": "ValidatorId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The owner of a key. The key is the `KeyTypeId` + the encoded key." + ] + } + ] + }, + "calls": [ + { + "name": "set_keys", + "args": [ + { + "name": "keys", + "type": "Keys" + }, + { + "name": "proof", + "type": "Bytes" + } + ], + "docs": [ + " Sets the session key(s) of the function caller to `keys`.", + " Allows an account to set its session key prior to becoming a validator.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)`", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `origin account`, `T::ValidatorIdOf`, `NextKeys`", + " - DbWrites: `origin account`, `NextKeys`", + " - DbReads per key id: `KeyOwner`", + " - DbWrites per key id: `KeyOwner`", + " # " + ] + }, + { + "name": "purge_keys", + "args": [], + "docs": [ + " Removes any session key(s) of the function caller.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)` in number of key types.", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `T::ValidatorIdOf`, `NextKeys`, `origin account`", + " - DbWrites: `NextKeys`, `origin account`", + " - DbWrites per key id: `KeyOwnder`", + " # " + ] + } + ], + "events": [ + { + "name": "NewSession", + "args": [ + "SessionIndex" + ], + "docs": [ + " New session has happened. Note that the argument is the \\[session_index\\], not the block", + " number as the type might suggest." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidProof", + "docs": [ + " Invalid ownership proof." + ] + }, + { + "name": "NoAssociatedValidatorId", + "docs": [ + " No associated validator ID for account." + ] + }, + { + "name": "DuplicatedKey", + "docs": [ + " Registered duplicate key." + ] + }, + { + "name": "NoKeys", + "docs": [ + " No keys are associated with this account." + ] + }, + { + "name": "NoAccount", + "docs": [ + " Key setting account is not live, so it's impossible to associate keys." + ] + } + ], + "index": 10 + }, + { + "name": "Democracy", + "storage": { + "prefix": "Democracy", + "items": [ + { + "name": "PublicPropCount", + "modifier": "Default", + "type": { + "plain": "PropIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of (public) proposals that have been made so far." + ] + }, + { + "name": "PublicProps", + "modifier": "Default", + "type": { + "plain": "Vec<(PropIndex,Hash,AccountId)>" + }, + "fallback": "0x00", + "docs": [ + " The public proposals. Unsorted. The second item is the proposal's hash." + ] + }, + { + "name": "DepositOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "PropIndex", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Those who have locked a deposit.", + "", + " TWOX-NOTE: Safe, as increasing integer keys are safe." + ] + }, + { + "name": "Preimages", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "PreimageStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map of hashes to the proposal preimage, along with who registered it and their deposit.", + " The block number is the block at which it was deposited." + ] + }, + { + "name": "ReferendumCount", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free referendum index, aka the number of referenda started so far." + ] + }, + { + "name": "LowestUnbaked", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The lowest referendum index representing an unbaked referendum. Equal to", + " `ReferendumCount` if there isn't a unbaked referendum." + ] + }, + { + "name": "ReferendumInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReferendumIndex", + "value": "ReferendumInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information concerning any given referendum.", + "", + " TWOX-NOTE: SAFE as indexes are not under an attacker’s control." + ] + }, + { + "name": "VotingOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Voting", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " All votes for a particular voter. We store the balance for the number of votes that we", + " have recorded. The second item is the total amount of delegations, that will be added.", + "", + " TWOX-NOTE: SAFE as `AccountId`s are crypto hashes anyway." + ] + }, + { + "name": "Locks", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "BlockNumber", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Accounts for which there are locks in action which may be removed at some point in the", + " future. The value is the block number at which the lock expires and may be removed.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "LastTabledWasExternal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the last referendum tabled was submitted externally. False if it was a public", + " proposal." + ] + }, + { + "name": "NextExternal", + "modifier": "Optional", + "type": { + "plain": "(Hash,VoteThreshold)" + }, + "fallback": "0x00", + "docs": [ + " The referendum to be tabled whenever it would be valid to table an external proposal.", + " This happens when a referendum needs to be tabled and one of two conditions are met:", + " - `LastTabledWasExternal` is `false`; or", + " - `PublicProps` is empty." + ] + }, + { + "name": "Blacklist", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "(BlockNumber,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A record of who vetoed what. Maps proposal hash to a possible existent block number", + " (until when it may not be resubmitted) and who vetoed it." + ] + }, + { + "name": "Cancellations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Record of all proposals that have been subject to emergency cancellation." + ] + }, + { + "name": "StorageVersion", + "modifier": "Optional", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " The dispatch origin of this call must be _Signed_ and the sender must", + " have funds to cover the deposit.", + "", + " - `proposal_hash`: The hash of the proposal preimage.", + " - `value`: The amount of deposit (must be at least `MinimumDeposit`).", + "", + " Emits `Proposed`.", + "", + " Weight: `O(p)`" + ] + }, + { + "name": "second", + "args": [ + { + "name": "proposal", + "type": "Compact" + }, + { + "name": "seconds_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Signals agreement with a particular proposal.", + "", + " The dispatch origin of this call must be _Signed_ and the sender", + " must have funds to cover the deposit, equal to the original deposit.", + "", + " - `proposal`: The index of the proposal to second.", + " - `seconds_upper_bound`: an upper bound on the current number of seconds on this", + " proposal. Extrinsic is weighted according to this value with no refund.", + "", + " Weight: `O(S)` where S is the number of seconds a proposal already has." + ] + }, + { + "name": "vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "AccountVote" + } + ], + "docs": [ + " Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;", + " otherwise it is a vote to keep the status quo.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `ref_index`: The index of the referendum to vote for.", + " - `vote`: The vote configuration.", + "", + " Weight: `O(R)` where R is the number of referendums the voter has voted on." + ] + }, + { + "name": "emergency_cancel", + "args": [ + { + "name": "ref_index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Schedule an emergency cancellation of a referendum. Cannot happen twice to the same", + " referendum.", + "", + " The dispatch origin of this call must be `CancellationOrigin`.", + "", + " -`ref_index`: The index of the referendum to cancel.", + "", + " Weight: `O(1)`." + ] + }, + { + "name": "external_propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a referendum to be tabled once it is legal to schedule an external", + " referendum.", + "", + " The dispatch origin of this call must be `ExternalOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Weight: `O(V)` with V number of vetoers in the blacklist of proposal.", + " Decoding vec of length V. Charged as maximum" + ] + }, + { + "name": "external_propose_majority", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a majority-carries referendum to be tabled next once it is legal to schedule", + " an external referendum.", + "", + " The dispatch of this call must be `ExternalMajorityOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "external_propose_default", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a negative-turnout-bias referendum to be tabled next once it is legal to", + " schedule an external referendum.", + "", + " The dispatch of this call must be `ExternalDefaultOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "fast_track", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "voting_period", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Schedule the currently externally-proposed majority-carries referendum to be tabled", + " immediately. If there is no externally-proposed referendum currently, or if there is one", + " but it is not a majority-carries referendum then it fails.", + "", + " The dispatch of this call must be `FastTrackOrigin`.", + "", + " - `proposal_hash`: The hash of the current external proposal.", + " - `voting_period`: The period that is allowed for voting on this proposal. Increased to", + " `FastTrackVotingPeriod` if too low.", + " - `delay`: The number of block after voting has ended in approval and this should be", + " enacted. This doesn't have a minimum amount.", + "", + " Emits `Started`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "veto_external", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Veto and blacklist the external proposal hash.", + "", + " The dispatch origin of this call must be `VetoOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal to veto and blacklist.", + "", + " Emits `Vetoed`.", + "", + " Weight: `O(V + log(V))` where V is number of `existing vetoers`" + ] + }, + { + "name": "cancel_referendum", + "args": [ + { + "name": "ref_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a referendum.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `ref_index`: The index of the referendum to cancel.", + "", + " # Weight: `O(1)`." + ] + }, + { + "name": "cancel_queued", + "args": [ + { + "name": "which", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Cancel a proposal queued for enactment.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `which`: The index of the referendum to cancel.", + "", + " Weight: `O(D)` where `D` is the items in the dispatch queue. Weighted as `D = 10`." + ] + }, + { + "name": "delegate", + "args": [ + { + "name": "to", + "type": "AccountId" + }, + { + "name": "conviction", + "type": "Conviction" + }, + { + "name": "balance", + "type": "BalanceOf" + } + ], + "docs": [ + " Delegate the voting power (with some given conviction) of the sending account.", + "", + " The balance delegated is locked for as long as it's delegated, and thereafter for the", + " time appropriate for the conviction's lock period.", + "", + " The dispatch origin of this call must be _Signed_, and the signing account must either:", + " - be delegating already; or", + " - have no voting activity (if there is, then it will need to be removed/consolidated", + " through `reap_vote` or `unvote`).", + "", + " - `to`: The account whose voting the `target` account's voting power will follow.", + " - `conviction`: The conviction that will be attached to the delegated votes. When the", + " account is undelegated, the funds will be locked for the corresponding period.", + " - `balance`: The amount of the account's balance to be used in delegating. This must", + " not be more than the account's current balance.", + "", + " Emits `Delegated`.", + "", + " Weight: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes." + ] + }, + { + "name": "undelegate", + "args": [], + "docs": [ + " Undelegate the voting power of the sending account.", + "", + " Tokens may be unlocked following once an amount of time consistent with the lock period", + " of the conviction with which the delegation was issued.", + "", + " The dispatch origin of this call must be _Signed_ and the signing account must be", + " currently delegating.", + "", + " Emits `Undelegated`.", + "", + " Weight: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes." + ] + }, + { + "name": "clear_public_proposals", + "args": [], + "docs": [ + " Clears all public proposals.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " Weight: `O(1)`." + ] + }, + { + "name": "note_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This doesn't require the proposal to be", + " in the dispatch queue but does require a deposit, returned once enacted.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " Weight: `O(E)` with E size of `encoded_proposal` (protected by a required deposit)." + ] + }, + { + "name": "note_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "note_imminent_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This requires the proposal to be", + " in the dispatch queue. No deposit is needed. When this call is successful, i.e.", + " the preimage has not been uploaded before and matches some imminent proposal,", + " no fee is paid.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " Weight: `O(E)` with E size of `encoded_proposal` (protected by a required deposit)." + ] + }, + { + "name": "note_imminent_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_imminent_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "reap_preimage", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "proposal_len_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Remove an expired proposal preimage and collect the deposit.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `proposal_hash`: The preimage hash of a proposal.", + " - `proposal_length_upper_bound`: an upper bound on length of the proposal.", + " Extrinsic is weighted according to this value with no refund.", + "", + " This will only work after `VotingPeriod` blocks from the time that the preimage was", + " noted, if it's the same account doing it. If it's a different account, then it'll only", + " work an additional `EnactmentPeriod` later.", + "", + " Emits `PreimageReaped`.", + "", + " Weight: `O(D)` where D is length of proposal." + ] + }, + { + "name": "unlock", + "args": [ + { + "name": "target", + "type": "AccountId" + } + ], + "docs": [ + " Unlock tokens that have an expired lock.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account to remove the lock on.", + "", + " Weight: `O(R)` with R number of vote of target." + ] + }, + { + "name": "remove_vote", + "args": [ + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If:", + " - the referendum was cancelled, or", + " - the referendum is ongoing, or", + " - the referendum has ended such that", + " - the vote of the account was in opposition to the result; or", + " - there was no conviction to the account's vote; or", + " - the account made a split vote", + " ...then the vote is removed cleanly and a following call to `unlock` may result in more", + " funds being available.", + "", + " If, however, the referendum has ended and:", + " - it finished corresponding to the vote of the account, and", + " - the account made a standard vote with conviction, and", + " - the lock period of the conviction is not over", + " ...then the lock will be aggregated into the overall account's lock, which may involve", + " *overlocking* (where the two locks are combined into a single lock that is the maximum", + " of both the amount locked and the time is it locked for).", + "", + " The dispatch origin of this call must be _Signed_, and the signer must have a vote", + " registered for referendum `index`.", + "", + " - `index`: The index of referendum of the vote to be removed.", + "", + " Weight: `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote." + ] + }, + { + "name": "remove_other_vote", + "args": [ + { + "name": "target", + "type": "AccountId" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If the `target` is equal to the signer, then this function is exactly equivalent to", + " `remove_vote`. If not equal to the signer, then the vote must have expired,", + " either because the referendum was cancelled, because the voter lost the referendum or", + " because the conviction period is over.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account of the vote to be removed; this account must have voted for", + " referendum `index`.", + " - `index`: The index of referendum of the vote to be removed.", + "", + " Weight: `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote." + ] + }, + { + "name": "enact_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Enact a proposal from a referendum. For now we just make the weight be the maximum." + ] + }, + { + "name": "blacklist", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "maybe_ref_index", + "type": "Option" + } + ], + "docs": [ + " Permanently place a proposal into the blacklist. This prevents it from ever being", + " proposed again.", + "", + " If called on a queued public or external proposal, then this will result in it being", + " removed. If the `ref_index` supplied is an active referendum with the proposal hash,", + " then it will be cancelled.", + "", + " The dispatch origin of this call must be `BlacklistOrigin`.", + "", + " - `proposal_hash`: The proposal hash to blacklist permanently.", + " - `ref_index`: An ongoing referendum whose hash is `proposal_hash`, which will be", + " cancelled.", + "", + " Weight: `O(p)` (though as this is an high-privilege dispatch, we assume it has a", + " reasonable value)." + ] + }, + { + "name": "cancel_proposal", + "args": [ + { + "name": "prop_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a proposal.", + "", + " The dispatch origin of this call must be `CancelProposalOrigin`.", + "", + " - `prop_index`: The index of the proposal to cancel.", + "", + " Weight: `O(p)` where `p = PublicProps::::decode_len()`" + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "PropIndex", + "Balance" + ], + "docs": [ + " A motion has been proposed by a public account. \\[proposal_index, deposit\\]" + ] + }, + { + "name": "Tabled", + "args": [ + "PropIndex", + "Balance", + "Vec" + ], + "docs": [ + " A public proposal has been tabled for referendum vote. \\[proposal_index, deposit, depositors\\]" + ] + }, + { + "name": "ExternalTabled", + "args": [], + "docs": [ + " An external proposal has been tabled." + ] + }, + { + "name": "Started", + "args": [ + "ReferendumIndex", + "VoteThreshold" + ], + "docs": [ + " A referendum has begun. \\[ref_index, threshold\\]" + ] + }, + { + "name": "Passed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been approved by referendum. \\[ref_index\\]" + ] + }, + { + "name": "NotPassed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been rejected by referendum. \\[ref_index\\]" + ] + }, + { + "name": "Cancelled", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A referendum has been cancelled. \\[ref_index\\]" + ] + }, + { + "name": "Executed", + "args": [ + "ReferendumIndex", + "bool" + ], + "docs": [ + " A proposal has been enacted. \\[ref_index, is_ok\\]" + ] + }, + { + "name": "Delegated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " An account has delegated their vote to another account. \\[who, target\\]" + ] + }, + { + "name": "Undelegated", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has cancelled a previous delegation operation." + ] + }, + { + "name": "Vetoed", + "args": [ + "AccountId", + "Hash", + "BlockNumber" + ], + "docs": [ + " An external proposal has been vetoed. \\[who, proposal_hash, until\\]" + ] + }, + { + "name": "PreimageNoted", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal's preimage was noted, and the deposit taken. \\[proposal_hash, who, deposit\\]" + ] + }, + { + "name": "PreimageUsed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal preimage was removed and used (the deposit was returned).", + " \\[proposal_hash, provider, deposit\\]" + ] + }, + { + "name": "PreimageInvalid", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was invalid.", + " \\[proposal_hash, ref_index\\]" + ] + }, + { + "name": "PreimageMissing", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was missing.", + " \\[proposal_hash, ref_index\\]" + ] + }, + { + "name": "PreimageReaped", + "args": [ + "Hash", + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A registered preimage was removed and the deposit collected by the reaper.", + " \\[proposal_hash, provider, deposit, reaper\\]" + ] + }, + { + "name": "Unlocked", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has been unlocked successfully." + ] + }, + { + "name": "Blacklisted", + "args": [ + "Hash" + ], + "docs": [ + " A proposal \\[hash\\] has been blacklisted permanently." + ] + } + ], + "constants": [ + { + "name": "EnactmentPeriod", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The minimum period of locking and the period between a proposal being approved and enacted.", + "", + " It should generally be a little more than the unstake period to ensure that", + " voting stakers have an opportunity to remove themselves from the system in the case where", + " they are on the losing side of a vote." + ] + }, + { + "name": "LaunchPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) new public referenda are launched." + ] + }, + { + "name": "VotingPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) to check for new votes." + ] + }, + { + "name": "MinimumDeposit", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be used as a deposit for a public referendum proposal." + ] + }, + { + "name": "FastTrackVotingPeriod", + "type": "BlockNumber", + "value": "0x80510100", + "docs": [ + " Minimum voting period allowed for an emergency referendum." + ] + }, + { + "name": "CooloffPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " Period in blocks where an external proposal may not be re-submitted after being vetoed." + ] + }, + { + "name": "PreimageByteDeposit", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of balance that must be deposited per byte of preimage stored." + ] + }, + { + "name": "MaxVotes", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of votes for an account." + ] + } + ], + "errors": [ + { + "name": "ValueLow", + "docs": [ + " Value too low" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal does not exist" + ] + }, + { + "name": "BadIndex", + "docs": [ + " Unknown index" + ] + }, + { + "name": "AlreadyCanceled", + "docs": [ + " Cannot cancel the same proposal twice" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Proposal already made" + ] + }, + { + "name": "ProposalBlacklisted", + "docs": [ + " Proposal still blacklisted" + ] + }, + { + "name": "NotSimpleMajority", + "docs": [ + " Next external proposal not simple majority" + ] + }, + { + "name": "InvalidHash", + "docs": [ + " Invalid hash" + ] + }, + { + "name": "NoProposal", + "docs": [ + " No external proposal" + ] + }, + { + "name": "AlreadyVetoed", + "docs": [ + " Identity may not veto a proposal twice" + ] + }, + { + "name": "NotDelegated", + "docs": [ + " Not delegated" + ] + }, + { + "name": "DuplicatePreimage", + "docs": [ + " Preimage already noted" + ] + }, + { + "name": "NotImminent", + "docs": [ + " Not imminent" + ] + }, + { + "name": "TooEarly", + "docs": [ + " Too early" + ] + }, + { + "name": "Imminent", + "docs": [ + " Imminent" + ] + }, + { + "name": "PreimageMissing", + "docs": [ + " Preimage not found" + ] + }, + { + "name": "ReferendumInvalid", + "docs": [ + " Vote given for invalid referendum" + ] + }, + { + "name": "PreimageInvalid", + "docs": [ + " Invalid preimage" + ] + }, + { + "name": "NoneWaiting", + "docs": [ + " No proposals waiting" + ] + }, + { + "name": "NotLocked", + "docs": [ + " The target account does not have a lock." + ] + }, + { + "name": "NotExpired", + "docs": [ + " The lock on the account to be unlocked has not yet expired." + ] + }, + { + "name": "NotVoter", + "docs": [ + " The given account did not vote on the referendum." + ] + }, + { + "name": "NoPermission", + "docs": [ + " The actor has no permission to conduct the action." + ] + }, + { + "name": "AlreadyDelegating", + "docs": [ + " The account is already delegating." + ] + }, + { + "name": "Overflow", + "docs": [ + " An unexpected integer overflow occurred." + ] + }, + { + "name": "Underflow", + "docs": [ + " An unexpected integer underflow occurred." + ] + }, + { + "name": "InsufficientFunds", + "docs": [ + " Too high a balance was provided that the account cannot afford." + ] + }, + { + "name": "NotDelegating", + "docs": [ + " The account is not currently delegating." + ] + }, + { + "name": "VotesExist", + "docs": [ + " The account currently has votes attached to it and the operation cannot succeed until", + " these are removed, either through `unvote` or `reap_vote`." + ] + }, + { + "name": "InstantNotAllowed", + "docs": [ + " The instant referendum origin is currently disallowed." + ] + }, + { + "name": "Nonsense", + "docs": [ + " Delegation to oneself makes no sense." + ] + }, + { + "name": "WrongUpperBound", + "docs": [ + " Invalid upper bound." + ] + }, + { + "name": "MaxVotesReached", + "docs": [ + " Maximum number of votes reached." + ] + }, + { + "name": "InvalidWitness", + "docs": [ + " The provided witness data is wrong." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " Maximum number of proposals reached." + ] + } + ], + "index": 11 + }, + { + "name": "Council", + "storage": { + "prefix": "Instance1Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The prime member that helps determine the default vote behavior in case of absentations." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " Transaction fees will be waived if the member is voting on any particular proposal", + " for the first time and the call is successful. Subsequent vote changes will charge a fee.", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " If the close operation completes successfully with disapproval, the transaction fee will", + " be waived. Otherwise execution of the approved operation will be charged to the caller.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " \\[account, proposal_index, proposal_hash, threshold\\]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " \\[account, proposal_hash, voted, yes, no\\]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " \\[proposal_hash, yes, no\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ], + "index": 12 + }, + { + "name": "TechnicalCommittee", + "storage": { + "prefix": "Instance2Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The prime member that helps determine the default vote behavior in case of absentations." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " Transaction fees will be waived if the member is voting on any particular proposal", + " for the first time and the call is successful. Subsequent vote changes will charge a fee.", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " If the close operation completes successfully with disapproval, the transaction fee will", + " be waived. Otherwise execution of the approved operation will be charged to the caller.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " \\[account, proposal_index, proposal_hash, threshold\\]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " \\[account, proposal_hash, voted, yes, no\\]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " \\[proposal_hash, yes, no\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ], + "index": 13 + }, + { + "name": "Elections", + "storage": { + "prefix": "Elections", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current elected members.", + "", + " Invariant: Always sorted based on account id." + ] + }, + { + "name": "RunnersUp", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current reserved runners-up.", + "", + " Invariant: Always sorted based on rank (worse to best). Upon removal of a member, the", + " last (i.e. _best_) runner-up will be replaced." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The present candidate list. A current member or runner-up can never enter this vector", + " and is always implicitly assumed to be a candidate.", + "", + " Second element is the deposit.", + "", + " Invariant: Always sorted based on account id." + ] + }, + { + "name": "ElectionRounds", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The total number of vote rounds that have happened, excluding the upcoming one." + ] + }, + { + "name": "Voting", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Voter", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Votes and locked stake of a particular voter.", + "", + " TWOX-NOTE: SAFE as `AccountId` is a crypto hash." + ] + } + ] + }, + "calls": [ + { + "name": "vote", + "args": [ + { + "name": "votes", + "type": "Vec" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Vote for a set of candidates for the upcoming round of election. This can be called to", + " set the initial votes, or update already existing votes.", + "", + " Upon initial voting, `value` units of `who`'s balance is locked and a deposit amount is", + " reserved. The deposit is based on the number of votes and can be updated over time.", + "", + " The `votes` should:", + " - not be empty.", + " - be less than the number of possible candidates. Note that all current members and", + " runners-up are also automatically candidates for the next round.", + "", + " If `value` is more than `who`'s total balance, then the maximum of the two is used.", + "", + " The dispatch origin of this call must be signed.", + "", + " ### Warning", + "", + " It is the responsibility of the caller to **NOT** place all of their balance into the", + " lock and keep some for further operations.", + "", + " # ", + " We assume the maximum weight among all 3 cases: vote_equal, vote_more and vote_less.", + " # " + ] + }, + { + "name": "remove_voter", + "args": [], + "docs": [ + " Remove `origin` as a voter.", + "", + " This removes the lock and returns the deposit.", + "", + " The dispatch origin of this call must be signed and be a voter." + ] + }, + { + "name": "submit_candidacy", + "args": [ + { + "name": "candidate_count", + "type": "Compact" + } + ], + "docs": [ + " Submit oneself for candidacy. A fixed amount of deposit is recorded.", + "", + " All candidates are wiped at the end of the term. They either become a member/runner-up,", + " or leave the system while their deposit is slashed.", + "", + " The dispatch origin of this call must be signed.", + "", + " ### Warning", + "", + " Even if a candidate ends up being a member, they must call [`Call::renounce_candidacy`]", + " to get their deposit back. Losing the spot in an election will always lead to a slash.", + "", + " # ", + " The number of current candidates must be provided as witness data.", + " # " + ] + }, + { + "name": "renounce_candidacy", + "args": [ + { + "name": "renouncing", + "type": "Renouncing" + } + ], + "docs": [ + " Renounce one's intention to be a candidate for the next election round. 3 potential", + " outcomes exist:", + "", + " - `origin` is a candidate and not elected in any set. In this case, the deposit is", + " unreserved, returned and origin is removed as a candidate.", + " - `origin` is a current runner-up. In this case, the deposit is unreserved, returned and", + " origin is removed as a runner-up.", + " - `origin` is a current member. In this case, the deposit is unreserved and origin is", + " removed as a member, consequently not being a candidate for the next round anymore.", + " Similar to [`remove_members`], if replacement runners exists, they are immediately", + " used. If the prime is renouncing, then no prime will exist until the next round.", + "", + " The dispatch origin of this call must be signed, and have one of the above roles.", + "", + " # ", + " The type of renouncing must be provided as witness data.", + " # " + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "has_replacement", + "type": "bool" + } + ], + "docs": [ + " Remove a particular member from the set. This is effective immediately and the bond of", + " the outgoing member is slashed.", + "", + " If a runner-up is available, then the best runner-up will be removed and replaces the", + " outgoing member. Otherwise, a new phragmen election is started.", + "", + " The dispatch origin of this call must be root.", + "", + " Note that this does not affect the designated block number of the next election.", + "", + " # ", + " If we have a replacement, we use a small weight. Else, since this is a root call and", + " will go into phragmen, we assume full block for now.", + " # " + ] + }, + { + "name": "clean_defunct_voters", + "args": [ + { + "name": "_num_voters", + "type": "u32" + }, + { + "name": "_num_defunct", + "type": "u32" + } + ], + "docs": [ + " Clean all voters who are defunct (i.e. they do not serve any purpose at all). The", + " deposit of the removed voters are returned.", + "", + " This is an root function to be used only for cleaning the state.", + "", + " The dispatch origin of this call must be root.", + "", + " # ", + " The total number of voters and those that are defunct must be provided as witness data.", + " # " + ] + } + ], + "events": [ + { + "name": "NewTerm", + "args": [ + "Vec<(AccountId,Balance)>" + ], + "docs": [ + " A new term with \\[new_members\\]. This indicates that enough candidates existed to run", + " the election, not that enough have has been elected. The inner value must be examined", + " for this purpose. A `NewTerm(\\[\\])` indicates that some candidates got their bond", + " slashed and none were elected, whilst `EmptyTerm` means that no candidates existed to", + " begin with." + ] + }, + { + "name": "EmptyTerm", + "args": [], + "docs": [ + " No (or not enough) candidates existed for this round. This is different from", + " `NewTerm(\\[\\])`. See the description of `NewTerm`." + ] + }, + { + "name": "ElectionError", + "args": [], + "docs": [ + " Internal error happened while trying to perform election." + ] + }, + { + "name": "MemberKicked", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been removed. This should always be followed by either `NewTerm` or", + " `EmptyTerm`." + ] + }, + { + "name": "Renounced", + "args": [ + "AccountId" + ], + "docs": [ + " Someone has renounced their candidacy." + ] + }, + { + "name": "CandidateSlashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A \\[candidate\\] was slashed by \\[amount\\] due to failing to obtain a seat as member or", + " runner-up.", + "", + " Note that old members and runners-up are also candidates." + ] + }, + { + "name": "SeatHolderSlashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A \\[seat holder\\] was slashed by \\[amount\\] by being forcefully removed from the set." + ] + } + ], + "constants": [ + { + "name": "PalletId", + "type": "LockIdentifier", + "value": "0x706872656c656374", + "docs": [ + " Identifier for the elections-phragmen pallet's lock" + ] + }, + { + "name": "CandidacyBond", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " How much should be locked up in order to submit one's candidacy." + ] + }, + { + "name": "VotingBondBase", + "type": "BalanceOf", + "value": "0x00f0436de36a01000000000000000000", + "docs": [ + " Base deposit associated with voting.", + "", + " This should be sensibly high to economically ensure the pallet cannot be attacked by", + " creating a gigantic number of votes." + ] + }, + { + "name": "VotingBondFactor", + "type": "BalanceOf", + "value": "0x0000cc7b9fae00000000000000000000", + "docs": [ + " The amount of bond that need to be locked for each vote (32 bytes)." + ] + }, + { + "name": "DesiredMembers", + "type": "u32", + "value": "0x0d000000", + "docs": [ + " Number of members to elect." + ] + }, + { + "name": "DesiredRunnersUp", + "type": "u32", + "value": "0x07000000", + "docs": [ + " Number of runners_up to keep." + ] + }, + { + "name": "TermDuration", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " How long each seat is kept. This defines the next block number at which an election", + " round will happen. If set to zero, no elections are ever triggered and the module will", + " be in passive mode." + ] + } + ], + "errors": [ + { + "name": "UnableToVote", + "docs": [ + " Cannot vote when no candidates or members exist." + ] + }, + { + "name": "NoVotes", + "docs": [ + " Must vote for at least one candidate." + ] + }, + { + "name": "TooManyVotes", + "docs": [ + " Cannot vote more than candidates." + ] + }, + { + "name": "MaximumVotesExceeded", + "docs": [ + " Cannot vote more than maximum allowed." + ] + }, + { + "name": "LowBalance", + "docs": [ + " Cannot vote with stake less than minimum balance." + ] + }, + { + "name": "UnableToPayBond", + "docs": [ + " Voter can not pay voting bond." + ] + }, + { + "name": "MustBeVoter", + "docs": [ + " Must be a voter." + ] + }, + { + "name": "ReportSelf", + "docs": [ + " Cannot report self." + ] + }, + { + "name": "DuplicatedCandidate", + "docs": [ + " Duplicated candidate submission." + ] + }, + { + "name": "MemberSubmit", + "docs": [ + " Member cannot re-submit candidacy." + ] + }, + { + "name": "RunnerUpSubmit", + "docs": [ + " Runner cannot re-submit candidacy." + ] + }, + { + "name": "InsufficientCandidateFunds", + "docs": [ + " Candidate does not have enough funds." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + }, + { + "name": "InvalidWitnessData", + "docs": [ + " The provided count of number of candidates is incorrect." + ] + }, + { + "name": "InvalidVoteCount", + "docs": [ + " The provided count of number of votes is incorrect." + ] + }, + { + "name": "InvalidRenouncing", + "docs": [ + " The renouncing origin presented a wrong `Renouncing` parameter." + ] + }, + { + "name": "InvalidReplacement", + "docs": [ + " Prediction regarding replacement after member removal is wrong." + ] + } + ], + "index": 14 + }, + { + "name": "TechnicalMembership", + "storage": { + "prefix": "Instance1Membership", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current membership, stored as an ordered Vec." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The current prime member, if one exists." + ] + } + ] + }, + "calls": [ + { + "name": "add_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Add a member `who` to the set.", + "", + " May only be called from `T::AddOrigin`." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Remove a member `who` from the set.", + "", + " May only be called from `T::RemoveOrigin`." + ] + }, + { + "name": "swap_member", + "args": [ + { + "name": "remove", + "type": "AccountId" + }, + { + "name": "add", + "type": "AccountId" + } + ], + "docs": [ + " Swap out one member `remove` for another `add`.", + "", + " May only be called from `T::SwapOrigin`.", + "", + " Prime membership is *not* passed from `remove` to `add`, if extant." + ] + }, + { + "name": "reset_members", + "args": [ + { + "name": "members", + "type": "Vec" + } + ], + "docs": [ + " Change the membership to a new set, disregarding the existing membership. Be nice and", + " pass `members` pre-sorted.", + "", + " May only be called from `T::ResetOrigin`." + ] + }, + { + "name": "change_key", + "args": [ + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Swap out the sending member for some other key `new`.", + "", + " May only be called from `Signed` origin of a current member.", + "", + " Prime membership is passed from the origin account to `new`, if extant." + ] + }, + { + "name": "set_prime", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Set the prime member. Must be a current member.", + "", + " May only be called from `T::PrimeOrigin`." + ] + }, + { + "name": "clear_prime", + "args": [], + "docs": [ + " Remove the prime member if it exists.", + "", + " May only be called from `T::PrimeOrigin`." + ] + } + ], + "events": [ + { + "name": "MemberAdded", + "args": [], + "docs": [ + " The given member was added; see the transaction for who." + ] + }, + { + "name": "MemberRemoved", + "args": [], + "docs": [ + " The given member was removed; see the transaction for who." + ] + }, + { + "name": "MembersSwapped", + "args": [], + "docs": [ + " Two members were swapped; see the transaction for who." + ] + }, + { + "name": "MembersReset", + "args": [], + "docs": [ + " The membership was reset; see the transaction for who the new set is." + ] + }, + { + "name": "KeyChanged", + "args": [], + "docs": [ + " One of the members' keys changed." + ] + }, + { + "name": "Dummy", + "args": [ + "PhantomData" + ], + "docs": [ + " Phantom member, never used." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "AlreadyMember", + "docs": [ + " Already a member." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + } + ], + "index": 15 + }, + { + "name": "Grandpa", + "storage": { + "prefix": "GrandpaFinality", + "items": [ + { + "name": "State", + "modifier": "Default", + "type": { + "plain": "StoredState" + }, + "fallback": "0x00", + "docs": [ + " State of the current authority set." + ] + }, + { + "name": "PendingChange", + "modifier": "Optional", + "type": { + "plain": "StoredPendingChange" + }, + "fallback": "0x00", + "docs": [ + " Pending change: (signaled at, scheduled change)." + ] + }, + { + "name": "NextForced", + "modifier": "Optional", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00", + "docs": [ + " next block number where we can force a change." + ] + }, + { + "name": "Stalled", + "modifier": "Optional", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x00", + "docs": [ + " `true` if we are currently stalled." + ] + }, + { + "name": "CurrentSetId", + "modifier": "Default", + "type": { + "plain": "SetId" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The number of changes (both in terms of keys and underlying economic responsibilities)", + " in the \"set\" of Grandpa validators from genesis." + ] + }, + { + "name": "SetIdSession", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "SetId", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from grandpa set ID to the index of the *most recent* session for which its", + " members were responsible.", + "", + " TWOX-NOTE: `SetId` is not under user control." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported.", + "", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + }, + { + "name": "note_stalled", + "args": [ + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "best_finalized_block_number", + "type": "BlockNumber" + } + ], + "docs": [ + " Note that the current authority set of the GRANDPA finality gadget has", + " stalled. This will trigger a forced authority set change at the beginning", + " of the next session, to be enacted `delay` blocks after that. The delay", + " should be high enough to safely assume that the block signalling the", + " forced change will not be re-orged (e.g. 1000 blocks). The GRANDPA voters", + " will start the new authority set using the given finalized block as base.", + " Only callable by root." + ] + } + ], + "events": [ + { + "name": "NewAuthorities", + "args": [ + "AuthorityList" + ], + "docs": [ + " New authority set has been applied. \\[authority_set\\]" + ] + }, + { + "name": "Paused", + "args": [], + "docs": [ + " Current authority set has been paused." + ] + }, + { + "name": "Resumed", + "args": [], + "docs": [ + " Current authority set has been resumed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "PauseFailed", + "docs": [ + " Attempt to signal GRANDPA pause when the authority set isn't live", + " (either paused or already pending pause)." + ] + }, + { + "name": "ResumeFailed", + "docs": [ + " Attempt to signal GRANDPA resume when the authority set isn't paused", + " (either live or already pending resume)." + ] + }, + { + "name": "ChangePending", + "docs": [ + " Attempt to signal GRANDPA change with one already pending." + ] + }, + { + "name": "TooSoon", + "docs": [ + " Cannot signal forced change so soon after last." + ] + }, + { + "name": "InvalidKeyOwnershipProof", + "docs": [ + " A key ownership proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "InvalidEquivocationProof", + "docs": [ + " An equivocation proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "DuplicateOffenceReport", + "docs": [ + " A given equivocation report is valid but already previously reported." + ] + } + ], + "index": 16 + }, + { + "name": "Treasury", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "ProposalIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of proposals that have been made." + ] + }, + { + "name": "Proposals", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ProposalIndex", + "value": "TreasuryProposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Proposals that have been made." + ] + }, + { + "name": "Approvals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Proposal indices that have been approved but not yet awarded." + ] + } + ] + }, + "calls": [ + { + "name": "propose_spend", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Put forward a suggestion for spending. A deposit proportional to the value", + " is reserved and slashed if the proposal is rejected. It is returned once the", + " proposal is awarded.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `ProposalCount`, `origin account`", + " - DbWrites: `ProposalCount`, `Proposals`, `origin account`", + " # " + ] + }, + { + "name": "reject_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Reject a proposed spend. The original deposit will be slashed.", + "", + " May only be called from `T::RejectOrigin`.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `Proposals`, `rejected proposer account`", + " - DbWrites: `Proposals`, `rejected proposer account`", + " # " + ] + }, + { + "name": "approve_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a proposal. At a later time, the proposal will be allocated to the beneficiary", + " and the original deposit will be returned.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - Complexity: O(1).", + " - DbReads: `Proposals`, `Approvals`", + " - DbWrite: `Approvals`", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "ProposalIndex" + ], + "docs": [ + " New proposal. \\[proposal_index\\]" + ] + }, + { + "name": "Spending", + "args": [ + "Balance" + ], + "docs": [ + " We have ended a spend period and will now allocate funds. \\[budget_remaining\\]" + ] + }, + { + "name": "Awarded", + "args": [ + "ProposalIndex", + "Balance", + "AccountId" + ], + "docs": [ + " Some funds have been allocated. \\[proposal_index, award, beneficiary\\]" + ] + }, + { + "name": "Rejected", + "args": [ + "ProposalIndex", + "Balance" + ], + "docs": [ + " A proposal was rejected; funds were slashed. \\[proposal_index, slashed\\]" + ] + }, + { + "name": "Burnt", + "args": [ + "Balance" + ], + "docs": [ + " Some of our funds have been burnt. \\[burn\\]" + ] + }, + { + "name": "Rollover", + "args": [ + "Balance" + ], + "docs": [ + " Spending has finished; this is the amount that rolls over until next spend.", + " \\[budget_remaining\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds have been deposited. \\[deposit\\]" + ] + } + ], + "constants": [ + { + "name": "ProposalBond", + "type": "Permill", + "value": "0x50c30000", + "docs": [ + " Fraction of a proposal's value that should be bonded in order to place the proposal.", + " An accepted proposal gets these back. A rejected proposal does not." + ] + }, + { + "name": "ProposalBondMinimum", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Minimum amount of funds that should be placed in a deposit for making a proposal." + ] + }, + { + "name": "SpendPeriod", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " Period between successive spends." + ] + }, + { + "name": "Burn", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of spare funds (if any) that are burnt per spend period." + ] + }, + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f7472737279", + "docs": [ + " The treasury's module id, used for deriving its sovereign account ID." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " No proposal or bounty at that index." + ] + }, + { + "name": "TooManyApprovals", + "docs": [ + " Too many approvals in the queue." + ] + } + ], + "index": 17 + }, + { + "name": "Contracts", + "storage": { + "prefix": "Contracts", + "items": [ + { + "name": "CurrentSchedule", + "modifier": "Default", + "type": { + "plain": "Schedule" + }, + "fallback": "0x000000000004000000000200000001000080000000100000000010000000010000200000001f060000d66a0200dd84030026180000bd1c0000430b000003170000ae2800009c000000dd69010063e00200300700000706000065070000b10500006e180000002800006905000072deae08f0070000dc070000710a00006a080000a507000096070000d1070000770900003e09000075090000d809000082090000bc090000120900003c09000072090000dc090000f7080000e108000062090000162000006b1d00002e2000002c1b0000fe080000000900000f090000a7090000f1090000ba090000bb09000065090000d8b82800000000009e9828000000000016902700000000004c705700000000004cc8270000000000e4bc270000000000e8d1270000000000a0685b0000000000484f2700000000009e7627000000000000f45100000000004cab120000000000184a700000000000140100000000000000cd460000000000fc02000000000000d0b570270000000013200000000000007821da3100000000e0200000000000009a120000000000000482b10900000000e03463000000000038d7900000000000de67d00700000000840900000000000006186e000000000016935d1200000000da02000000000000eaced408000000003a240e0200000000e705000000000000fc41d50a00000000d48e9309000000002d0f0000000000003a4225090000000047020000000000002303000000000000ba7c962300000000a5210000000000006d020000000000005403000000000000e50b00000000000026922400000000006110000000000000a4122600000000001d0d000000000000520e2200000000001a0600000000000020222200000000001a0600000000000044b13c0000000000", + "docs": [ + " Current cost schedule for contracts." + ] + }, + { + "name": "PristineCode", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from an original code hash to the original code, untouched by instrumentation." + ] + }, + { + "name": "CodeStorage", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "PrefabWasmModule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping between an original code hash and instrumented wasm code, ready for execution." + ] + }, + { + "name": "AccountCounter", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The subtrie counter." + ] + }, + { + "name": "ContractInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ContractInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The code associated with a given account.", + "", + " TWOX-NOTE: SAFE since `AccountId` is a secure hash." + ] + }, + { + "name": "DeletionQueue", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Evicted contracts that await child trie deletion.", + "", + " Child trie deletion is a heavy operation depending on the amount of storage items", + " stored in said trie. Therefore this operation is performed lazily in `on_initialize`." + ] + } + ] + }, + "calls": [ + { + "name": "update_schedule", + "args": [ + { + "name": "schedule", + "type": "Schedule" + } + ], + "docs": [ + " Updates the schedule for metering contracts.", + "", + " The schedule's version cannot be less than the version of the stored schedule.", + " If a schedule does not change the instruction weights the version does not", + " need to be increased. Therefore we allow storing a schedule that has the same", + " version as the stored one." + ] + }, + { + "name": "call", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Makes a call to an account, optionally transferring some balance.", + "", + " * If the account is a smart-contract account, the associated code will be", + " executed and any value will be transferred.", + " * If the account is a regular account, any value will be transferred.", + " * If no account exists and the call value is not less than `existential_deposit`,", + " a regular account will be created and any value will be transferred." + ] + }, + { + "name": "instantiate_with_code", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code", + "type": "Bytes" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "salt", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a new contract from the supplied `code` optionally transferring", + " some balance.", + "", + " This is the only function that can deploy new code to the chain.", + "", + " # Parameters", + "", + " * `endowment`: The balance to transfer from the `origin` to the newly created contract.", + " * `gas_limit`: The gas limit enforced when executing the constructor.", + " * `code`: The contract code to deploy in raw bytes.", + " * `data`: The input data to pass to the contract constructor.", + " * `salt`: Used for the address derivation. See [`Pallet::contract_address`].", + "", + " Instantiation is executed as follows:", + "", + " - The supplied `code` is instrumented, deployed, and a `code_hash` is created for that code.", + " - If the `code_hash` already exists on the chain the underlying `code` will be shared.", + " - The destination address is computed based on the sender, code_hash and the salt.", + " - The smart-contract account is created at the computed address.", + " - The `endowment` is transferred to the new account.", + " - The `deploy` function is executed in the context of the newly-created account." + ] + }, + { + "name": "instantiate", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code_hash", + "type": "CodeHash" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "salt", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a contract from a previously deployed wasm binary.", + "", + " This function is identical to [`Self::instantiate_with_code`] but without the", + " code deployment step. Instead, the `code_hash` of an on-chain deployed wasm binary", + " must be supplied." + ] + }, + { + "name": "claim_surcharge", + "args": [ + { + "name": "dest", + "type": "AccountId" + }, + { + "name": "aux_sender", + "type": "Option" + } + ], + "docs": [ + " Allows block producers to claim a small reward for evicting a contract. If a block", + " producer fails to do so, a regular users will be allowed to claim the reward.", + "", + " In case of a successful eviction no fees are charged from the sender. However, the", + " reward is capped by the total amount of rent that was payed by the contract while", + " it was alive.", + "", + " If contract is not evicted as a result of this call, [`Error::ContractNotEvictable`]", + " is returned and the sender is not eligible for the reward." + ] + } + ], + "events": [ + { + "name": "Instantiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract deployed by address at the specified address. \\[deployer, contract\\]" + ] + }, + { + "name": "Evicted", + "args": [ + "AccountId" + ], + "docs": [ + " Contract has been evicted and is now in tombstone state. \\[contract\\]" + ] + }, + { + "name": "Terminated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract has been terminated without leaving a tombstone.", + " \\[contract, beneficiary\\]", + "", + " # Params", + "", + " - `contract`: The contract that was terminated.", + " - `beneficiary`: The account that received the contracts remaining balance.", + "", + " # Note", + "", + " The only way for a contract to be removed without a tombstone and emitting", + " this event is by calling `seal_terminate`." + ] + }, + { + "name": "Restored", + "args": [ + "AccountId", + "AccountId", + "Hash", + "Balance" + ], + "docs": [ + " Restoration of a contract has been successful.", + " \\[restorer, dest, code_hash, rent_allowance\\]", + "", + " # Params", + "", + " - `restorer`: Account ID of the restoring contract.", + " - `dest`: Account ID of the restored contract.", + " - `code_hash`: Code hash of the restored contract.", + " - `rent_allowance`: Rent allowance of the restored contract." + ] + }, + { + "name": "CodeStored", + "args": [ + "Hash" + ], + "docs": [ + " Code with the specified hash has been stored. \\[code_hash\\]" + ] + }, + { + "name": "ScheduleUpdated", + "args": [ + "u32" + ], + "docs": [ + " Triggered when the current schedule is updated.", + " \\[version\\]", + "", + " # Params", + "", + " - `version`: The version of the newly set schedule." + ] + }, + { + "name": "ContractEmitted", + "args": [ + "AccountId", + "Bytes" + ], + "docs": [ + " A custom event emitted by the contract.", + " \\[contract, data\\]", + "", + " # Params", + "", + " - `contract`: The contract that emitted the event.", + " - `data`: Data supplied by the contract. Metadata generated during contract", + " compilation is needed to decode it." + ] + }, + { + "name": "CodeRemoved", + "args": [ + "Hash" + ], + "docs": [ + " A code with the specified hash was removed.", + " \\[code_hash\\]", + "", + " This happens when the last contract that uses this code hash was removed or evicted." + ] + } + ], + "constants": [ + { + "name": "SignedClaimHandicap", + "type": "BlockNumber", + "value": "0x02000000", + "docs": [ + " Number of block delay an extrinsic claim surcharge has.", + "", + " When claim surcharge is called by an extrinsic the rent is checked", + " for current_block - delay" + ] + }, + { + "name": "TombstoneDeposit", + "type": "BalanceOf", + "value": "0x00f0e8857a9c02000000000000000000", + "docs": [ + " The minimum amount required to generate a tombstone." + ] + }, + { + "name": "DepositPerContract", + "type": "BalanceOf", + "value": "0x00f0e8857a9c02000000000000000000", + "docs": [ + " The balance every contract needs to deposit to stay alive indefinitely.", + "", + " This is different from the [`Self::TombstoneDeposit`] because this only needs to be", + " deposited while the contract is alive. Costs for additional storage are added to", + " this base cost.", + "", + " This is a simple way to ensure that contracts with empty storage eventually get deleted by", + " making them pay rent. This creates an incentive to remove them early in order to save rent." + ] + }, + { + "name": "DepositPerStorageByte", + "type": "BalanceOf", + "value": "0x0060defb740500000000000000000000", + "docs": [ + " The balance a contract needs to deposit per storage byte to stay alive indefinitely.", + "", + " Let's suppose the deposit is 1,000 BU (balance units)/byte and the rent is 1 BU/byte/day,", + " then a contract with 1,000,000 BU that uses 1,000 bytes of storage would pay no rent.", + " But if the balance reduced to 500,000 BU and the storage stayed the same at 1,000,", + " then it would pay 500 BU/day." + ] + }, + { + "name": "DepositPerStorageItem", + "type": "BalanceOf", + "value": "0x00f0ab75a40d00000000000000000000", + "docs": [ + " The balance a contract needs to deposit per storage item to stay alive indefinitely.", + "", + " It works the same as [`Self::DepositPerStorageByte`] but for storage items." + ] + }, + { + "name": "RentFraction", + "type": "Perbill", + "value": "0x85040000", + "docs": [ + " The fraction of the deposit that should be used as rent per block.", + "", + " When a contract hasn't enough balance deposited to stay alive indefinitely it needs", + " to pay per block for the storage it consumes that is not covered by the deposit.", + " This determines how high this rent payment is per block as a fraction of the deposit." + ] + }, + { + "name": "SurchargeReward", + "type": "BalanceOf", + "value": "0x005cb2ec220000000000000000000000", + "docs": [ + " Reward that is received by the party whose touch has led", + " to removal of a contract." + ] + }, + { + "name": "MaxDepth", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum nesting level of a call/instantiate stack." + ] + }, + { + "name": "MaxValueSize", + "type": "u32", + "value": "0x00400000", + "docs": [ + " The maximum size of a storage value and event payload in bytes." + ] + }, + { + "name": "DeletionQueueDepth", + "type": "u32", + "value": "0xf0000000", + "docs": [ + " The maximum number of tries that can be queued for deletion." + ] + }, + { + "name": "DeletionWeightLimit", + "type": "Weight", + "value": "0x00d0ed902e000000", + "docs": [ + " The maximum amount of weight that can be consumed per block for lazy trie removal." + ] + }, + { + "name": "MaxCodeSize", + "type": "u32", + "value": "0x00000200", + "docs": [ + " The maximum length of a contract code in bytes. This limit applies to the instrumented", + " version of the code. Therefore `instantiate_with_code` can fail even when supplying", + " a wasm binary below this maximum size." + ] + } + ], + "errors": [ + { + "name": "InvalidScheduleVersion", + "docs": [ + " A new schedule must have a greater version than the current one." + ] + }, + { + "name": "InvalidSurchargeClaim", + "docs": [ + " An origin must be signed or inherent and auxiliary sender only provided on inherent." + ] + }, + { + "name": "InvalidSourceContract", + "docs": [ + " Cannot restore from nonexisting or tombstone contract." + ] + }, + { + "name": "InvalidDestinationContract", + "docs": [ + " Cannot restore to nonexisting or alive contract." + ] + }, + { + "name": "InvalidTombstone", + "docs": [ + " Tombstones don't match." + ] + }, + { + "name": "InvalidContractOrigin", + "docs": [ + " An origin TrieId written in the current block." + ] + }, + { + "name": "OutOfGas", + "docs": [ + " The executed contract exhausted its gas limit." + ] + }, + { + "name": "OutputBufferTooSmall", + "docs": [ + " The output buffer supplied to a contract API call was too small." + ] + }, + { + "name": "BelowSubsistenceThreshold", + "docs": [ + " Performing the requested transfer would have brought the contract below", + " the subsistence threshold. No transfer is allowed to do this in order to allow", + " for a tombstone to be created. Use `seal_terminate` to remove a contract without", + " leaving a tombstone behind." + ] + }, + { + "name": "NewContractNotFunded", + "docs": [ + " The newly created contract is below the subsistence threshold after executing", + " its contructor. No contracts are allowed to exist below that threshold." + ] + }, + { + "name": "TransferFailed", + "docs": [ + " Performing the requested transfer failed for a reason originating in the", + " chosen currency implementation of the runtime. Most probably the balance is", + " too low or locks are placed on it." + ] + }, + { + "name": "MaxCallDepthReached", + "docs": [ + " Performing a call was denied because the calling depth reached the limit", + " of what is specified in the schedule." + ] + }, + { + "name": "NotCallable", + "docs": [ + " The contract that was called is either no contract at all (a plain account)", + " or is a tombstone." + ] + }, + { + "name": "CodeTooLarge", + "docs": [ + " The code supplied to `instantiate_with_code` exceeds the limit specified in the", + " current schedule." + ] + }, + { + "name": "CodeNotFound", + "docs": [ + " No code could be found at the supplied code hash." + ] + }, + { + "name": "OutOfBounds", + "docs": [ + " A buffer outside of sandbox memory was passed to a contract API function." + ] + }, + { + "name": "DecodingFailed", + "docs": [ + " Input passed to a contract API function failed to decode as expected type." + ] + }, + { + "name": "ContractTrapped", + "docs": [ + " Contract trapped during execution." + ] + }, + { + "name": "ValueTooLarge", + "docs": [ + " The size defined in `T::MaxValueSize` was exceeded." + ] + }, + { + "name": "ReentranceDenied", + "docs": [ + " The action performed is not allowed while the contract performing it is already", + " on the call stack. Those actions are contract self destruction and restoration", + " of a tombstone." + ] + }, + { + "name": "InputAlreadyRead", + "docs": [ + " `seal_input` was called twice from the same contract execution context." + ] + }, + { + "name": "RandomSubjectTooLong", + "docs": [ + " The subject passed to `seal_random` exceeds the limit." + ] + }, + { + "name": "TooManyTopics", + "docs": [ + " The amount of topics passed to `seal_deposit_events` exceeds the limit." + ] + }, + { + "name": "DuplicateTopics", + "docs": [ + " The topics passed to `seal_deposit_events` contains at least one duplicate." + ] + }, + { + "name": "NoChainExtension", + "docs": [ + " The chain does not provide a chain extension. Calling the chain extension results", + " in this error. Note that this usually shouldn't happen as deploying such contracts", + " is rejected." + ] + }, + { + "name": "DeletionQueueFull", + "docs": [ + " Removal of a contract failed because the deletion queue is full.", + "", + " This can happen when either calling [`Pallet::claim_surcharge`] or `seal_terminate`.", + " The queue is filled by deleting contracts and emptied by a fixed amount each block.", + " Trying again during another block is the only way to resolve this issue." + ] + }, + { + "name": "ContractNotEvictable", + "docs": [ + " A contract could not be evicted because it has enough balance to pay rent.", + "", + " This can be returned from [`Pallet::claim_surcharge`] because the target", + " contract has enough balance to pay for its rent." + ] + }, + { + "name": "StorageExhausted", + "docs": [ + " A storage modification exhausted the 32bit type that holds the storage size.", + "", + " This can either happen when the accumulated storage in bytes is too large or", + " when number of storage items is too large." + ] + }, + { + "name": "DuplicateContract", + "docs": [ + " A contract with the same AccountId already exists." + ] + } + ], + "index": 18 + }, + { + "name": "Sudo", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "Key", + "modifier": "Default", + "type": { + "plain": "AccountId" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The `AccountId` of the sudo key." + ] + } + ] + }, + "calls": [ + { + "name": "sudo", + "args": [ + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + }, + { + "name": "sudo_unchecked_weight", + "args": [ + { + "name": "call", + "type": "Call" + }, + { + "name": "_weight", + "type": "Weight" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + " This function does not check the weight of the call, and instead allows the", + " Sudo user to specify the weight of the call.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - The weight of this call is defined by the caller.", + " # " + ] + }, + { + "name": "set_key", + "args": [ + { + "name": "new", + "type": "LookupSource" + } + ], + "docs": [ + " Authenticates the current sudo key and sets the given AccountId (`new`) as the new sudo key.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "sudo_as", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Signed` origin from", + " a given account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + } + ], + "events": [ + { + "name": "Sudid", + "args": [ + "DispatchResult" + ], + "docs": [ + " A sudo just took place. \\[result\\]" + ] + }, + { + "name": "KeyChanged", + "args": [ + "AccountId" + ], + "docs": [ + " The \\[sudoer\\] just switched identity; the old key is supplied." + ] + }, + { + "name": "SudoAsDone", + "args": [ + "DispatchResult" + ], + "docs": [ + " A sudo just took place. \\[result\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "RequireSudo", + "docs": [ + " Sender must be the Sudo account" + ] + } + ], + "index": 19 + }, + { + "name": "ImOnline", + "storage": { + "prefix": "ImOnline", + "items": [ + { + "name": "HeartbeatAfter", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The block number after which it's ok to send heartbeats in the current", + " session.", + "", + " At the beginning of each session we set this to a value that should fall", + " roughly in the middle of the session duration. The idea is to first wait for", + " the validators to produce a block in the current session, so that the", + " heartbeat later on will not be necessary.", + "", + " This value will only be used as a fallback if we fail to get a proper session", + " progress estimate from `NextSessionRotation`, as those estimates should be", + " more accurate then the value we calculate for `HeartbeatAfter`." + ] + }, + { + "name": "Keys", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of keys that may issue a heartbeat." + ] + }, + { + "name": "ReceivedHeartbeats", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "AuthIndex", + "value": "Bytes", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " For each session index, we keep a mapping of `AuthIndex` to", + " `offchain::OpaqueNetworkState`." + ] + }, + { + "name": "AuthoredBlocks", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "ValidatorId", + "value": "u32", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00000000", + "docs": [ + " For each session index, we keep a mapping of `ValidatorId` to the", + " number of blocks authored by the given authority." + ] + } + ] + }, + "calls": [ + { + "name": "heartbeat", + "args": [ + { + "name": "heartbeat", + "type": "Heartbeat" + }, + { + "name": "_signature", + "type": "Signature" + } + ], + "docs": [ + " # ", + " - Complexity: `O(K + E)` where K is length of `Keys` (heartbeat.validators_len)", + " and E is length of `heartbeat.network_state.external_address`", + " - `O(K)`: decoding of length `K`", + " - `O(E)`: decoding/encoding of length `E`", + " - DbReads: pallet_session `Validators`, pallet_session `CurrentIndex`, `Keys`,", + " `ReceivedHeartbeats`", + " - DbWrites: `ReceivedHeartbeats`", + " # " + ] + } + ], + "events": [ + { + "name": "HeartbeatReceived", + "args": [ + "AuthorityId" + ], + "docs": [ + " A new heartbeat was received from `AuthorityId` \\[authority_id\\]" + ] + }, + { + "name": "AllGood", + "args": [], + "docs": [ + " At the end of the session, no offence was committed." + ] + }, + { + "name": "SomeOffline", + "args": [ + "Vec" + ], + "docs": [ + " At the end of the session, at least one validator was found to be \\[offline\\]." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidKey", + "docs": [ + " Non existent public key." + ] + }, + { + "name": "DuplicatedHeartbeat", + "docs": [ + " Duplicated heartbeat." + ] + } + ], + "index": 20 + }, + { + "name": "AuthorityDiscovery", + "storage": null, + "calls": [], + "events": null, + "constants": [], + "errors": [], + "index": 21 + }, + { + "name": "Offences", + "storage": { + "prefix": "Offences", + "items": [ + { + "name": "Reports", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReportIdOf", + "value": "OffenceDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The primary structure that holds all offence records keyed by report identifiers." + ] + }, + { + "name": "DeferredOffences", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Deferred reports that have been rejected by the offence handler and need to be submitted", + " at a later time." + ] + }, + { + "name": "ConcurrentReportsIndex", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Kind", + "key2": "OpaqueTimeSlot", + "value": "Vec", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " A vector of reports of the same kind that happened at the same time slot." + ] + }, + { + "name": "ReportsByKindIndex", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Kind", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Enumerates all reports of a kind along with the time they happened.", + "", + " All reports are sorted by the time of offence.", + "", + " Note that the actual type of this mapping is `Vec`, this is because values of", + " different types are not supported at the moment so we are doing the manual serialization." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "Offence", + "args": [ + "Kind", + "OpaqueTimeSlot", + "bool" + ], + "docs": [ + " There is an offence reported of the given `kind` happened at the `session_index` and", + " (kind-specific) time slot. This event is not deposited for duplicate slashes. last", + " element indicates of the offence was applied (true) or queued (false)", + " \\[kind, timeslot, applied\\]." + ] + } + ], + "constants": [], + "errors": [], + "index": 22 + }, + { + "name": "Historical", + "storage": null, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 23 + }, + { + "name": "RandomnessCollectiveFlip", + "storage": { + "prefix": "RandomnessCollectiveFlip", + "items": [ + { + "name": "RandomMaterial", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Series of block headers from the last 81 blocks that acts as random seed material. This", + " is arranged as a ring buffer with `block_number % 81` being the index into the `Vec` of", + " the oldest hash." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [], + "errors": [], + "index": 24 + }, + { + "name": "Identity", + "storage": { + "prefix": "Identity", + "items": [ + { + "name": "IdentityOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Registration", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information that is pertinent to identify the entity behind an account.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "SuperOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "(AccountId,Data)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The super-identity of an alternative \"sub\" identity together with its name, within that", + " context. If the account is not some other account's sub-identity, then just `None`." + ] + }, + { + "name": "SubsOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " Alternative \"sub\" identities of this account.", + "", + " The first item is the deposit, the second is a vector of the accounts.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "Registrars", + "modifier": "Default", + "type": { + "plain": "Vec>" + }, + "fallback": "0x00", + "docs": [ + " The set of registrars. Not expected to get very big as can only be added through a", + " special origin (likely a council motion).", + "", + " The index into this can be cast to `RegistrarIndex` to get a valid value." + ] + } + ] + }, + "calls": [ + { + "name": "add_registrar", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Add a registrar to the system.", + "", + " The dispatch origin for this call must be `T::RegistrarOrigin`.", + "", + " - `account`: the account of the registrar.", + "", + " Emits `RegistrarAdded` if successful.", + "", + " # ", + " - `O(R)` where `R` registrar-count (governance-bounded and code-bounded).", + " - One storage mutation (codec `O(R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_identity", + "args": [ + { + "name": "info", + "type": "IdentityInfo" + } + ], + "docs": [ + " Set an account's identity information and reserve the appropriate deposit.", + "", + " If the account already has identity information, the deposit is taken as part payment", + " for the new deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `info`: The identity information.", + "", + " Emits `IdentitySet` if successful.", + "", + " # ", + " - `O(X + X' + R)`", + " - where `X` additional-field-count (deposit-bounded and code-bounded)", + " - where `R` judgements-count (registrar-count-bounded)", + " - One balance reserve operation.", + " - One storage mutation (codec-read `O(X' + R)`, codec-write `O(X + R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_subs", + "args": [ + { + "name": "subs", + "type": "Vec<(AccountId,Data)>" + } + ], + "docs": [ + " Set the sub-accounts of the sender.", + "", + " Payment: Any aggregate balance reserved by previous `set_subs` calls will be returned", + " and an amount `SubAccountDeposit` will be reserved for each item in `subs`.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " - `subs`: The identity's (new) sub-accounts.", + "", + " # ", + " - `O(P + S)`", + " - where `P` old-subs-count (hard- and deposit-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - At most one balance operations.", + " - DB:", + " - `P + S` storage mutations (codec complexity `O(1)`)", + " - One storage read (codec complexity `O(P)`).", + " - One storage write (codec complexity `O(S)`).", + " - One storage-exists (`IdentityOf::contains_key`).", + " # " + ] + }, + { + "name": "clear_identity", + "args": [], + "docs": [ + " Clear an account's identity info and all sub-accounts and return all deposits.", + "", + " Payment: All reserved balances on the account are returned.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " Emits `IdentityCleared` if successful.", + "", + " # ", + " - `O(R + S + X)`", + " - where `R` registrar-count (governance-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - where `X` additional-field-count (deposit-bounded and code-bounded).", + " - One balance-unreserve operation.", + " - `2` storage reads and `S + 2` storage deletions.", + " - One event.", + " # " + ] + }, + { + "name": "request_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "max_fee", + "type": "Compact" + } + ], + "docs": [ + " Request a judgement from a registrar.", + "", + " Payment: At most `max_fee` will be reserved for payment to the registrar if judgement", + " given.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is requested.", + " - `max_fee`: The maximum fee that may be paid. This should just be auto-populated as:", + "", + " ```nocompile", + " Self::registrars().get(reg_index).unwrap().fee", + " ```", + "", + " Emits `JudgementRequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(X + R)`.", + " - One event.", + " # " + ] + }, + { + "name": "cancel_request", + "args": [ + { + "name": "reg_index", + "type": "RegistrarIndex" + } + ], + "docs": [ + " Cancel a previous request.", + "", + " Payment: A previously reserved deposit is returned on success.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is no longer requested.", + "", + " Emits `JudgementUnrequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - One storage mutation `O(R + X)`.", + " - One event", + " # " + ] + }, + { + "name": "set_fee", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Set the fee required for a judgement to be requested from a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fee`: the new fee.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.315 + R * 0.329 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_account_id", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Change the account associated with a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `new`: the new account ID.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 8.823 + R * 0.32 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_fields", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fields", + "type": "IdentityFields" + } + ], + "docs": [ + " Set the field information for a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fields`: the fields that the registrar concerns themselves with.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.464 + R * 0.325 µs (min squares analysis)", + " # " + ] + }, + { + "name": "provide_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "judgement", + "type": "IdentityJudgement" + } + ], + "docs": [ + " Provide a judgement for an account's identity.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `reg_index`.", + "", + " - `reg_index`: the index of the registrar whose judgement is being made.", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + " - `judgement`: the judgement of the registrar of index `reg_index` about `target`.", + "", + " Emits `JudgementGiven` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-transfer operation.", + " - Up to one account-lookup operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(R + X)`.", + " - One event.", + " # " + ] + }, + { + "name": "kill_identity", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Remove an account's identity and sub-account information and slash the deposits.", + "", + " Payment: Reserved balances from `set_subs` and `set_identity` are slashed and handled by", + " `Slash`. Verification request deposits are not returned; they should be cancelled", + " manually using `cancel_request`.", + "", + " The dispatch origin for this call must match `T::ForceOrigin`.", + "", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + "", + " Emits `IdentityKilled` if successful.", + "", + " # ", + " - `O(R + S + X)`.", + " - One balance-reserve operation.", + " - `S + 2` storage mutations.", + " - One event.", + " # " + ] + }, + { + "name": "add_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Add the given account to the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "rename_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Alter the associated name of the given sub-account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "remove_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + } + ], + "docs": [ + " Remove the given account from the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "quit_sub", + "args": [], + "docs": [ + " Remove the sender as a sub-account.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender (*not* the original depositor).", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " super-identity.", + "", + " NOTE: This should not normally be used, but is provided in the case that the non-", + " controller of an account is maliciously registered as a sub-account." + ] + } + ], + "events": [ + { + "name": "IdentitySet", + "args": [ + "AccountId" + ], + "docs": [ + " A name was set or reset (which will remove all judgements). \\[who\\]" + ] + }, + { + "name": "IdentityCleared", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was cleared, and the given balance returned. \\[who, deposit\\]" + ] + }, + { + "name": "IdentityKilled", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was removed and the given balance slashed. \\[who, deposit\\]" + ] + }, + { + "name": "JudgementRequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was asked from a registrar. \\[who, registrar_index\\]" + ] + }, + { + "name": "JudgementUnrequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement request was retracted. \\[who, registrar_index\\]" + ] + }, + { + "name": "JudgementGiven", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was given by a registrar. \\[target, registrar_index\\]" + ] + }, + { + "name": "RegistrarAdded", + "args": [ + "RegistrarIndex" + ], + "docs": [ + " A registrar was added. \\[registrar_index\\]" + ] + }, + { + "name": "SubIdentityAdded", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was added to an identity and the deposit paid. \\[sub, main, deposit\\]" + ] + }, + { + "name": "SubIdentityRemoved", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was removed from an identity and the deposit freed.", + " \\[sub, main, deposit\\]" + ] + }, + { + "name": "SubIdentityRevoked", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was cleared, and the given deposit repatriated from the", + " main identity account to the sub-identity account. \\[sub, main, deposit\\]" + ] + } + ], + "constants": [ + { + "name": "BasicDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The amount held on deposit for a registered identity." + ] + }, + { + "name": "FieldDeposit", + "type": "BalanceOf", + "value": "0x00a031a95fe300000000000000000000", + "docs": [ + " The amount held on deposit per additional field for a registered identity." + ] + }, + { + "name": "SubAccountDeposit", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount held on deposit for a registered subaccount. This should account for the fact", + " that one storage item's value will increase by the size of an account ID, and there will be", + " another trie item whose value is the size of an account ID plus 32 bytes." + ] + }, + { + "name": "MaxSubAccounts", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of sub-accounts allowed per identified account." + ] + }, + { + "name": "MaxAdditionalFields", + "type": "u32", + "value": "0x64000000", + "docs": [ + " Maximum number of additional fields that may be stored in an ID. Needed to bound the I/O", + " required to access an identity, but can be pretty high." + ] + }, + { + "name": "MaxRegistrars", + "type": "u32", + "value": "0x14000000", + "docs": [ + " Maxmimum number of registrars allowed in the system. Needed to bound the complexity", + " of, e.g., updating judgements." + ] + } + ], + "errors": [ + { + "name": "TooManySubAccounts", + "docs": [ + " Too many subs-accounts." + ] + }, + { + "name": "NotFound", + "docs": [ + " Account isn't found." + ] + }, + { + "name": "NotNamed", + "docs": [ + " Account isn't named." + ] + }, + { + "name": "EmptyIndex", + "docs": [ + " Empty index." + ] + }, + { + "name": "FeeChanged", + "docs": [ + " Fee is changed." + ] + }, + { + "name": "NoIdentity", + "docs": [ + " No identity found." + ] + }, + { + "name": "StickyJudgement", + "docs": [ + " Sticky judgement." + ] + }, + { + "name": "JudgementGiven", + "docs": [ + " Judgement given." + ] + }, + { + "name": "InvalidJudgement", + "docs": [ + " Invalid judgement." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " The index is invalid." + ] + }, + { + "name": "InvalidTarget", + "docs": [ + " The target is invalid." + ] + }, + { + "name": "TooManyFields", + "docs": [ + " Too many additional fields." + ] + }, + { + "name": "TooManyRegistrars", + "docs": [ + " Maximum amount of registrars reached. Cannot add any more." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Account ID is already named." + ] + }, + { + "name": "NotSub", + "docs": [ + " Sender is not a sub-account." + ] + }, + { + "name": "NotOwned", + "docs": [ + " Sub-account isn't owned by sender." + ] + } + ], + "index": 25 + }, + { + "name": "Society", + "storage": { + "prefix": "Society", + "items": [ + { + "name": "Founder", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The first member." + ] + }, + { + "name": "Rules", + "modifier": "Optional", + "type": { + "plain": "Hash" + }, + "fallback": "0x00", + "docs": [ + " A hash of the rules of this society concerning membership. Can only be set once and", + " only by the founder." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of candidates; bidders that are attempting to become members." + ] + }, + { + "name": "SuspendedCandidates", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,BidKind)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended candidates." + ] + }, + { + "name": "Pot", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Amount of our account balance that is specifically for the next round's bid(s)." + ] + }, + { + "name": "Head", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The most primary from the most recently approved members." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of members, ordered." + ] + }, + { + "name": "SuspendedMembers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended members." + ] + }, + { + "name": "Bids", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current bids, stored ordered by the value of the bid." + ] + }, + { + "name": "Vouching", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "VouchingStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Members currently vouching or banned from vouching again" + ] + }, + { + "name": "Payouts", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Vec<(BlockNumber,BalanceOf)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Pending payouts; ordered by block number, with the amount that should be paid out." + ] + }, + { + "name": "Strikes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "StrikeCount", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " The ongoing number of losing votes cast by the member." + ] + }, + { + "name": "Votes", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "SocietyVote", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Double map from Candidate -> Voter -> (Maybe) Vote." + ] + }, + { + "name": "Defender", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The defending member currently being challenged." + ] + }, + { + "name": "DefenderVotes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SocietyVote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes for the defender." + ] + }, + { + "name": "MaxMembers", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The max number of members for the society at one time." + ] + } + ] + }, + "calls": [ + { + "name": "bid", + "args": [ + { + "name": "value", + "type": "BalanceOf" + } + ], + "docs": [ + " A user outside of the society can make a bid for entry.", + "", + " Payment: `CandidateDeposit` will be reserved for making a bid. It is returned", + " when the bid becomes a member, or if the bid calls `unbid`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `value`: A one time payment the bid would like to receive when joining the society.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members), X (balance reserve)", + " - Storage Reads:", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " \t- One storage read to retrieve all members. O(M)", + " - Storage Writes:", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for new bid.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unbid", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " A bidder can remove their bid for entry into society.", + " By doing so, they will have their candidate deposit returned or", + " they will unvouch their voucher.", + "", + " Payment: The bid deposit is unreserved if the user made a bid.", + "", + " The dispatch origin for this call must be _Signed_ and a bidder.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who wants to unbid.", + "", + " # ", + " Key: B (len of bids), X (balance unreserve)", + " - One storage read and write to retrieve and update the bids. O(B)", + " - Either one unreserve balance action O(X) or one vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B + X)", + " # " + ] + }, + { + "name": "vouch", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "value", + "type": "BalanceOf" + }, + { + "name": "tip", + "type": "BalanceOf" + } + ], + "docs": [ + " As a member, vouch for someone to join society by placing a bid on their behalf.", + "", + " There is no deposit required to vouch for a new bid, but a member can only vouch for", + " one bid at a time. If the bid becomes a suspended candidate and ultimately rejected by", + " the suspension judgement origin, the member will be banned from vouching again.", + "", + " As a vouching member, you can claim a tip if the candidate is accepted. This tip will", + " be paid as a portion of the reward the member will receive for joining the society.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `who`: The user who you would like to vouch for.", + " - `value`: The total reward to be paid between you and the candidate if they become", + " a member in the society.", + " - `tip`: Your cut of the total `value` payout when the candidate is inducted into", + " the society. Tips larger than `value` will be saturated upon payout.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members)", + " - Storage Reads:", + " \t- One storage read to retrieve all members. O(M)", + " \t- One storage read to check member is not already vouching. O(1)", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " - Storage Writes:", + " \t- One storage write to insert vouching status to the member. O(1)", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(log M) search to check sender is a member.", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for vouch.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unvouch", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " As a vouching member, unvouch a bid. This only works while vouched user is", + " only a bidder (and not a candidate).", + "", + " The dispatch origin for this call must be _Signed_ and a vouching member.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who should be unvouched.", + "", + " # ", + " Key: B (len of bids)", + " - One storage read O(1) to check the signer is a vouching member.", + " - One storage mutate to retrieve and update the bids. O(B)", + " - One vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B)", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "candidate", + "type": "LookupSource" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on a candidate.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `candidate`: The candidate that the member would like to bid on.", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " Key: C (len of candidates), M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One account lookup.", + " - One storage read O(C) and O(C) search to check that user is a candidate.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM + C)", + " # " + ] + }, + { + "name": "defender_vote", + "args": [ + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on the defender.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " - Key: M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM)", + " # " + ] + }, + { + "name": "payout", + "args": [], + "docs": [ + " Transfer the first matured payout for the sender and remove it from the records.", + "", + " NOTE: This extrinsic needs to be called multiple times to claim multiple matured payouts.", + "", + " Payment: The member will receive a payment equal to their first matured", + " payout to their free balance.", + "", + " The dispatch origin for this call must be _Signed_ and a member with", + " payouts remaining.", + "", + " # ", + " Key: M (len of members), P (number of payouts for a particular member)", + " - One storage read O(M) and O(log M) search to check signer is a member.", + " - One storage read O(P) to get all payouts for a member.", + " - One storage read O(1) to get the current block number.", + " - One currency transfer call. O(X)", + " - One storage write or removal to update the member's payouts. O(P)", + "", + " Total Complexity: O(M + logM + P + X)", + " # " + ] + }, + { + "name": "found", + "args": [ + { + "name": "founder", + "type": "AccountId" + }, + { + "name": "max_members", + "type": "u32" + }, + { + "name": "rules", + "type": "Bytes" + } + ], + "docs": [ + " Found the society.", + "", + " This is done as a discrete action in order to allow for the", + " module to be included into a running chain and can only be done once.", + "", + " The dispatch origin for this call must be from the _FounderSetOrigin_.", + "", + " Parameters:", + " - `founder` - The first member and head of the newly founded society.", + " - `max_members` - The initial max number of members for the society.", + " - `rules` - The rules of this society concerning membership.", + "", + " # ", + " - Two storage mutates to set `Head` and `Founder`. O(1)", + " - One storage write to add the first member to society. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "unfound", + "args": [], + "docs": [ + " Annul the founding of the society.", + "", + " The dispatch origin for this call must be Signed, and the signing account must be both", + " the `Founder` and the `Head`. This implies that it may only be done when there is one", + " member.", + "", + " # ", + " - Two storage reads O(1).", + " - Four storage removals O(1).", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "judge_suspended_member", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "forgive", + "type": "bool" + } + ], + "docs": [ + " Allow suspension judgement origin to make judgement on a suspended member.", + "", + " If a suspended member is forgiven, we simply add them back as a member, not affecting", + " any of the existing storage items for that member.", + "", + " If a suspended member is rejected, remove all associated storage items, including", + " their payouts, and remove any vouched bids they currently have.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended member to be judged.", + " - `forgive` - A boolean representing whether the suspension judgement origin", + " forgives (`true`) or rejects (`false`) a suspended member.", + "", + " # ", + " Key: B (len of bids), M (len of members)", + " - One storage read to check `who` is a suspended member. O(1)", + " - Up to one storage write O(M) with O(log M) binary search to add a member back to society.", + " - Up to 3 storage removals O(1) to clean up a removed member.", + " - Up to one storage write O(B) with O(B) search to remove vouched bid from bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal. O(1)", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B)", + " # " + ] + }, + { + "name": "judge_suspended_candidate", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "judgement", + "type": "SocietyJudgement" + } + ], + "docs": [ + " Allow suspended judgement origin to make judgement on a suspended candidate.", + "", + " If the judgement is `Approve`, we add them to society as a member with the appropriate", + " payment for joining society.", + "", + " If the judgement is `Reject`, we either slash the deposit of the bid, giving it back", + " to the society treasury, or we ban the voucher from vouching again.", + "", + " If the judgement is `Rebid`, we put the candidate back in the bid pool and let them go", + " through the induction process again.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended candidate to be judged.", + " - `judgement` - `Approve`, `Reject`, or `Rebid`.", + "", + " # ", + " Key: B (len of bids), M (len of members), X (balance action)", + " - One storage read to check `who` is a suspended candidate.", + " - One storage removal of the suspended candidate.", + " - Approve Logic", + " \t- One storage read to get the available pot to pay users with. O(1)", + " \t- One storage write to update the available pot. O(1)", + " \t- One storage read to get the current block number. O(1)", + " \t- One storage read to get all members. O(M)", + " \t- Up to one unreserve currency action.", + " \t- Up to two new storage writes to payouts.", + " \t- Up to one storage write with O(log M) binary search to add a member to society.", + " - Reject Logic", + " \t- Up to one repatriate reserved currency action. O(X)", + " \t- Up to one storage write to ban the vouching member from vouching again.", + " - Rebid Logic", + " \t- Storage mutate with O(log B) binary search to place the user back into bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal.", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B + X)", + " # " + ] + }, + { + "name": "set_max_members", + "args": [ + { + "name": "max", + "type": "u32" + } + ], + "docs": [ + " Allows root origin to change the maximum number of members in society.", + " Max membership count must be greater than 1.", + "", + " The dispatch origin for this call must be from _ROOT_.", + "", + " Parameters:", + " - `max` - The maximum number of members for the society.", + "", + " # ", + " - One storage write to update the max. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "Founded", + "args": [ + "AccountId" + ], + "docs": [ + " The society is founded by the given identity. \\[founder\\]" + ] + }, + { + "name": "Bid", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A membership bid just happened. The given account is the candidate's ID and their offer", + " is the second. \\[candidate_id, offer\\]" + ] + }, + { + "name": "Vouch", + "args": [ + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A membership bid just happened by vouching. The given account is the candidate's ID and", + " their offer is the second. The vouching party is the third. \\[candidate_id, offer, vouching\\]" + ] + }, + { + "name": "AutoUnbid", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (due to an excess of bids in the system)." + ] + }, + { + "name": "Unbid", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (by their request)." + ] + }, + { + "name": "Unvouch", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (by request of who vouched for them)." + ] + }, + { + "name": "Inducted", + "args": [ + "AccountId", + "Vec" + ], + "docs": [ + " A group of candidates have been inducted. The batch's primary is the first value, the", + " batch in full is the second. \\[primary, candidates\\]" + ] + }, + { + "name": "SuspendedMemberJudgement", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A suspended member has been judged. \\[who, judged\\]" + ] + }, + { + "name": "CandidateSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] has been suspended" + ] + }, + { + "name": "MemberSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been suspended" + ] + }, + { + "name": "Challenged", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been challenged" + ] + }, + { + "name": "Vote", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed \\[candidate, voter, vote\\]" + ] + }, + { + "name": "DefenderVote", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed for a defending member \\[voter, vote\\]" + ] + }, + { + "name": "NewMaxMembers", + "args": [ + "u32" + ], + "docs": [ + " A new \\[max\\] member count has been set" + ] + }, + { + "name": "Unfounded", + "args": [ + "AccountId" + ], + "docs": [ + " Society is unfounded. \\[founder\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds were deposited into the society account. \\[value\\]" + ] + } + ], + "constants": [ + { + "name": "CandidateDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The minimum amount of a deposit required for a bid to be made." + ] + }, + { + "name": "WrongSideDeduction", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount of the unpaid reward that gets deducted in the case that either a skeptic", + " doesn't vote or someone votes in the wrong way." + ] + }, + { + "name": "MaxStrikes", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The number of times a member may vote the wrong way (or not at all, when they are a skeptic)", + " before they become suspended." + ] + }, + { + "name": "PeriodSpend", + "type": "BalanceOf", + "value": "0x0000c52ebca2b1000000000000000000", + "docs": [ + " The amount of incentive paid within each period. Doesn't include VoterTip." + ] + }, + { + "name": "RotationPeriod", + "type": "BlockNumber", + "value": "0x00770100", + "docs": [ + " The number of blocks between candidate/membership rotation periods." + ] + }, + { + "name": "ChallengePeriod", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " The number of blocks between membership challenges." + ] + }, + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f736f636965", + "docs": [ + " The societies's module id" + ] + }, + { + "name": "MaxCandidateIntake", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Maximum candidate intake per round." + ] + } + ], + "errors": [ + { + "name": "BadPosition", + "docs": [ + " An incorrect position was provided." + ] + }, + { + "name": "NotMember", + "docs": [ + " User is not a member." + ] + }, + { + "name": "AlreadyMember", + "docs": [ + " User is already a member." + ] + }, + { + "name": "Suspended", + "docs": [ + " User is suspended." + ] + }, + { + "name": "NotSuspended", + "docs": [ + " User is not suspended." + ] + }, + { + "name": "NoPayout", + "docs": [ + " Nothing to payout." + ] + }, + { + "name": "AlreadyFounded", + "docs": [ + " Society already founded." + ] + }, + { + "name": "InsufficientPot", + "docs": [ + " Not enough in pot to accept candidate." + ] + }, + { + "name": "AlreadyVouching", + "docs": [ + " Member is already vouching or banned from vouching again." + ] + }, + { + "name": "NotVouching", + "docs": [ + " Member is not vouching." + ] + }, + { + "name": "Head", + "docs": [ + " Cannot remove the head of the chain." + ] + }, + { + "name": "Founder", + "docs": [ + " Cannot remove the founder." + ] + }, + { + "name": "AlreadyBid", + "docs": [ + " User has already made a bid." + ] + }, + { + "name": "AlreadyCandidate", + "docs": [ + " User is already a candidate." + ] + }, + { + "name": "NotCandidate", + "docs": [ + " User is not a candidate." + ] + }, + { + "name": "MaxMembers", + "docs": [ + " Too many members in the society." + ] + }, + { + "name": "NotFounder", + "docs": [ + " The caller is not the founder." + ] + }, + { + "name": "NotHead", + "docs": [ + " The caller is not the head." + ] + } + ], + "index": 26 + }, + { + "name": "Recovery", + "storage": { + "prefix": "Recovery", + "items": [ + { + "name": "Recoverable", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RecoveryConfig", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of recoverable accounts and their recovery configuration." + ] + }, + { + "name": "ActiveRecoveries", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "ActiveRecovery", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Active recovery attempts.", + "", + " First account is the account to be recovered, and the second account", + " is the user trying to recover the account." + ] + }, + { + "name": "Proxy", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The list of allowed proxy accounts.", + "", + " Map from the user who can access it to the recovered account." + ] + } + ] + }, + "calls": [ + { + "name": "as_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through a recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you want to make a call on-behalf-of.", + " - `call`: The call you want to make with the recovered account.", + "", + " # ", + " - The weight of the `call` + 10,000.", + " - One storage lookup to check account is recovered by `who`. O(1)", + " # " + ] + }, + { + "name": "set_recovered", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow ROOT to bypass the recovery process and set an a rescuer account", + " for a lost account directly.", + "", + " The dispatch origin for this call must be _ROOT_.", + "", + " Parameters:", + " - `lost`: The \"lost account\" to be recovered.", + " - `rescuer`: The \"rescuer account\" which can call as the lost account.", + "", + " # ", + " - One storage write O(1)", + " - One event", + " # " + ] + }, + { + "name": "create_recovery", + "args": [ + { + "name": "friends", + "type": "Vec" + }, + { + "name": "threshold", + "type": "u16" + }, + { + "name": "delay_period", + "type": "BlockNumber" + } + ], + "docs": [ + " Create a recovery configuration for your account. This makes your account recoverable.", + "", + " Payment: `ConfigDepositBase` + `FriendDepositFactor` * #_of_friends balance", + " will be reserved for storing the recovery configuration. This deposit is returned", + " in full when the user calls `remove_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `friends`: A list of friends you trust to vouch for recovery attempts.", + " Should be ordered and contain no duplicate values.", + " - `threshold`: The number of friends that must vouch for a recovery attempt", + " before the account can be recovered. Should be less than or equal to", + " the length of the list of friends.", + " - `delay_period`: The number of blocks after a recovery attempt is initialized", + " that needs to pass before the account can be recovered.", + "", + " # ", + " - Key: F (len of friends)", + " - One storage read to check that account is not already recoverable. O(1).", + " - A check that the friends list is sorted and unique. O(F)", + " - One currency reserve operation. O(X)", + " - One storage write. O(1). Codec O(F).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "initiate_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Initiate the process for recovering a recoverable account.", + "", + " Payment: `RecoveryDeposit` balance will be reserved for initiating the", + " recovery process. This deposit will always be repatriated to the account", + " trying to be recovered. See `close_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `account`: The lost account that you want to recover. This account", + " needs to be recoverable (i.e. have a recovery configuration).", + "", + " # ", + " - One storage read to check that account is recoverable. O(F)", + " - One storage read to check that this recovery process hasn't already started. O(1)", + " - One currency reserve operation. O(X)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "vouch_recovery", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow a \"friend\" of a recoverable account to vouch for an active recovery", + " process for that account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"friend\"", + " for the recoverable account.", + "", + " Parameters:", + " - `lost`: The lost account that you want to recover.", + " - `rescuer`: The account trying to rescue the lost account that you", + " want to vouch for.", + "", + " The combination of these two parameters must point to an active recovery", + " process.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One binary search to confirm caller is a friend. O(logF)", + " - One binary search to confirm caller has not already vouched. O(logV)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + logF + V + logV)", + " # " + ] + }, + { + "name": "claim_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Allow a successful rescuer to claim their recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"rescuer\"", + " who has successfully completed the account recovery process: collected", + " `threshold` or more vouches, waited `delay_period` blocks since initiation.", + "", + " Parameters:", + " - `account`: The lost account that you want to claim has been successfully", + " recovered by you.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + V)", + " # " + ] + }, + { + "name": "close_recovery", + "args": [ + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " As the controller of a recoverable account, close an active recovery", + " process for your account.", + "", + " Payment: By calling this function, the recoverable account will receive", + " the recovery deposit `RecoveryDeposit` placed by the rescuer.", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account with an active recovery process for it.", + "", + " Parameters:", + " - `rescuer`: The account trying to rescue this recoverable account.", + "", + " # ", + " Key: V (len of vouching friends)", + " - One storage read/remove to get the active recovery process. O(1), Codec O(V)", + " - One balance call to repatriate reserved. O(X)", + " - One event.", + "", + " Total Complexity: O(V + X)", + " # " + ] + }, + { + "name": "remove_recovery", + "args": [], + "docs": [ + " Remove the recovery process for your account. Recovered accounts are still accessible.", + "", + " NOTE: The user must make sure to call `close_recovery` on all active", + " recovery attempts before calling this function else it will fail.", + "", + " Payment: By calling this function the recoverable account will unreserve", + " their recovery configuration deposit.", + " (`ConfigDepositBase` + `FriendDepositFactor` * #_of_friends)", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account (i.e. has a recovery configuration).", + "", + " # ", + " Key: F (len of friends)", + " - One storage read to get the prefix iterator for active recoveries. O(1)", + " - One storage read/remove to get the recovery configuration. O(1), Codec O(F)", + " - One balance call to unreserved. O(X)", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "cancel_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Cancel the ability to use `as_recovered` for `account`.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you are able to call on-behalf-of.", + "", + " # ", + " - One storage mutation to check account is recovered by `who`. O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "RecoveryCreated", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been set up for an \\[account\\]." + ] + }, + { + "name": "RecoveryInitiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process has been initiated for lost account by rescuer account.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "RecoveryVouched", + "args": [ + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been vouched for by sender.", + " \\[lost, rescuer, sender\\]" + ] + }, + { + "name": "RecoveryClosed", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been closed.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "AccountRecovered", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Lost account has been successfully recovered by rescuer account.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "RecoveryRemoved", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been removed for an \\[account\\]." + ] + } + ], + "constants": [ + { + "name": "ConfigDepositBase", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a recovery configuration." + ] + }, + { + "name": "FriendDepositFactor", + "type": "BalanceOf", + "value": "0x00203d88792d00000000000000000000", + "docs": [ + " The amount of currency needed per additional user when creating a recovery configuration." + ] + }, + { + "name": "MaxFriends", + "type": "u16", + "value": "0x0900", + "docs": [ + " The maximum amount of friends allowed in a recovery configuration." + ] + }, + { + "name": "RecoveryDeposit", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for starting a recovery." + ] + } + ], + "errors": [ + { + "name": "NotAllowed", + "docs": [ + " User is not allowed to make a call on behalf of this account" + ] + }, + { + "name": "ZeroThreshold", + "docs": [ + " Threshold must be greater than zero" + ] + }, + { + "name": "NotEnoughFriends", + "docs": [ + " Friends list must be greater than zero and threshold" + ] + }, + { + "name": "MaxFriends", + "docs": [ + " Friends list must be less than max friends" + ] + }, + { + "name": "NotSorted", + "docs": [ + " Friends list must be sorted and free of duplicates" + ] + }, + { + "name": "NotRecoverable", + "docs": [ + " This account is not set up for recovery" + ] + }, + { + "name": "AlreadyRecoverable", + "docs": [ + " This account is already set up for recovery" + ] + }, + { + "name": "AlreadyStarted", + "docs": [ + " A recovery process has already started for this account" + ] + }, + { + "name": "NotStarted", + "docs": [ + " A recovery process has not started for this rescuer" + ] + }, + { + "name": "NotFriend", + "docs": [ + " This account is not a friend who can vouch" + ] + }, + { + "name": "DelayPeriod", + "docs": [ + " The friend must wait until the delay period to vouch for this recovery" + ] + }, + { + "name": "AlreadyVouched", + "docs": [ + " This user has already vouched for this recovery" + ] + }, + { + "name": "Threshold", + "docs": [ + " The threshold for recovering this account has not been met" + ] + }, + { + "name": "StillActive", + "docs": [ + " There are still active recovery attempts that need to be closed" + ] + }, + { + "name": "Overflow", + "docs": [ + " There was an overflow in a calculation" + ] + }, + { + "name": "AlreadyProxy", + "docs": [ + " This account is already set up for recovery" + ] + }, + { + "name": "BadState", + "docs": [ + " Some internal state is broken." + ] + } + ], + "index": 27 + }, + { + "name": "Vesting", + "storage": { + "prefix": "Vesting", + "items": [ + { + "name": "Vesting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "VestingInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information regarding the vesting of a given account." + ] + } + ] + }, + "calls": [ + { + "name": "vest", + "args": [], + "docs": [ + " Unlock any vested funds of the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have funds still", + " locked under this pallet.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 2 Reads, 2 Writes", + " - Reads: Vesting Storage, Balances Locks, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, [Sender Account]", + " # " + ] + }, + { + "name": "vest_other", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Unlock any vested funds of a `target` account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account whose vested funds should be unlocked. Must have funds still", + " locked under this pallet.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account", + " - Writes: Vesting Storage, Balances Locks, Target Account", + " # " + ] + }, + { + "name": "vested_transfer", + "args": [ + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Create a vested transfer.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " # " + ] + }, + { + "name": "force_vested_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Force a vested transfer.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `source`: The account whose funds should be transferred.", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 4 Reads, 4 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, Source Account", + " - Writes: Vesting Storage, Balances Locks, Target Account, Source Account", + " # " + ] + } + ], + "events": [ + { + "name": "VestingUpdated", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The amount vested has been updated. This could indicate more funds are available. The", + " balance given is the amount which is left unvested (and thus locked).", + " \\[account, unvested\\]" + ] + }, + { + "name": "VestingCompleted", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has become fully vested. No further vesting can happen." + ] + } + ], + "constants": [ + { + "name": "MinVestedTransfer", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount transferred to call `vested_transfer`." + ] + } + ], + "errors": [ + { + "name": "NotVesting", + "docs": [ + " The account given is not vesting." + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " An existing vesting schedule already exists for this account that cannot be clobbered." + ] + }, + { + "name": "AmountLow", + "docs": [ + " Amount being transferred is too low to create a vesting schedule." + ] + } + ], + "index": 28 + }, + { + "name": "Scheduler", + "storage": { + "prefix": "Scheduler", + "items": [ + { + "name": "Agenda", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Vec>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Items to be executed, indexed by the block number that they should be executed on." + ] + }, + { + "name": "Lookup", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Bytes", + "value": "TaskAddress", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Lookup from identity to the block number and index of the task." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "schedule", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.29 + .126 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda", + " - Will use base weight of 25 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u32" + } + ], + "docs": [ + " Cancel an anonymously scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.15 + 2.869 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_named", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 29.6 + .159 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 35 which should be good for more than 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel_named", + "args": [ + { + "name": "id", + "type": "Bytes" + } + ], + "docs": [ + " Cancel a named scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 24.91 + 2.907 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_after", + "args": [ + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task after a delay.", + "", + " # ", + " Same as [`schedule`].", + " # " + ] + }, + { + "name": "schedule_named_after", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task after a delay.", + "", + " # ", + " Same as [`schedule_named`].", + " # " + ] + } + ], + "events": [ + { + "name": "Scheduled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Scheduled some task. \\[when, index\\]" + ] + }, + { + "name": "Canceled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Canceled some task. \\[when, index\\]" + ] + }, + { + "name": "Dispatched", + "args": [ + "TaskAddress", + "Option", + "DispatchResult" + ], + "docs": [ + " Dispatched some task. \\[task, id, result\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "FailedToSchedule", + "docs": [ + " Failed to schedule a call" + ] + }, + { + "name": "NotFound", + "docs": [ + " Cannot find the scheduled call." + ] + }, + { + "name": "TargetBlockNumberInPast", + "docs": [ + " Given target block number is in the past." + ] + }, + { + "name": "RescheduleNoChange", + "docs": [ + " Reschedule failed because it does not change scheduled time." + ] + } + ], + "index": 29 + }, + { + "name": "Proxy", + "storage": { + "prefix": "Proxy", + "items": [ + { + "name": "Proxies", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The set of account proxies. Maps the account which has delegated to the accounts", + " which are being delegated to, together with the amount held on deposit." + ] + }, + { + "name": "Announcements", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The announcements made by the proxy (key)." + ] + } + ] + }, + "calls": [ + { + "name": "proxy", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorised for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "add_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Register a proxy account for the sender that is able to make calls on its behalf.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to make a proxy.", + " - `proxy_type`: The permissions allowed for this proxy account.", + " - `delay`: The announcement period required of the initial proxy. Will generally be", + " zero.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Unregister a proxy account for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to remove as a proxy.", + " - `proxy_type`: The permissions currently enabled for the removed proxy account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxies", + "args": [], + "docs": [ + " Unregister all proxy accounts for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " WARNING: This may be called on accounts created by `anonymous`, however if done, then", + " the unreserved fees will be inaccessible. **All access to this account will be lost.**", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "anonymous", + "args": [ + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u16" + } + ], + "docs": [ + " Spawn a fresh new account that is guaranteed to be otherwise inaccessible, and", + " initialize it with a proxy of `proxy_type` for `origin` sender.", + "", + " Requires a `Signed` origin.", + "", + " - `proxy_type`: The type of the proxy that the sender will be registered as over the", + " new account. This will almost always be the most permissive `ProxyType` possible to", + " allow for maximum flexibility.", + " - `index`: A disambiguation index, in case this is called multiple times in the same", + " transaction (e.g. with `utility::batch`). Unless you're using `batch` you probably just", + " want to use `0`.", + " - `delay`: The announcement period required of the initial proxy. Will generally be", + " zero.", + "", + " Fails with `Duplicate` if this has already been called in this transaction, from the", + " same sender, with the same parameters.", + "", + " Fails if there are insufficient funds to pay for deposit.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # ", + " TODO: Might be over counting 1 read" + ] + }, + { + "name": "kill_anonymous", + "args": [ + { + "name": "spawner", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "index", + "type": "u16" + }, + { + "name": "height", + "type": "Compact" + }, + { + "name": "ext_index", + "type": "Compact" + } + ], + "docs": [ + " Removes a previously spawned anonymous proxy.", + "", + " WARNING: **All access to this account will be lost.** Any funds held in it will be", + " inaccessible.", + "", + " Requires a `Signed` origin, and the sender account must have been created by a call to", + " `anonymous` with corresponding parameters.", + "", + " - `spawner`: The account that originally called `anonymous` to create this account.", + " - `index`: The disambiguation index originally passed to `anonymous`. Probably `0`.", + " - `proxy_type`: The proxy type originally passed to `anonymous`.", + " - `height`: The height of the chain when the call to `anonymous` was processed.", + " - `ext_index`: The extrinsic index in which the call to `anonymous` was processed.", + "", + " Fails with `NoPermission` in case the caller is not a previously created anonymous", + " account whose `anonymous` call has corresponding parameters.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "announce", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Publish the hash of a proxy-call that will be made in the future.", + "", + " This must be called some number of blocks before the corresponding `proxy` is attempted", + " if the delay associated with the proxy relationship is greater than zero.", + "", + " No more than `MaxPending` announcements may be made at any one time.", + "", + " This will take a deposit of `AnnouncementDepositFactor` as well as", + " `AnnouncementDepositBase` if there are no other pending announcements.", + "", + " The dispatch origin for this call must be _Signed_ and a proxy of `real`.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "remove_announcement", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove a given announcement.", + "", + " May be called by a proxy account to remove a call they previously announced and return", + " the deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "reject_announcement", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove the given announcement of a delegate.", + "", + " May be called by a target (proxied) account to remove a call that one of their delegates", + " (`delegate`) has announced they want to execute. The deposit is returned.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `delegate`: The account that previously announced the call.", + " - `call_hash`: The hash of the call to be made.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "proxy_announced", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorized for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + } + ], + "events": [ + { + "name": "ProxyExecuted", + "args": [ + "DispatchResult" + ], + "docs": [ + " A proxy was executed correctly, with the given \\[result\\]." + ] + }, + { + "name": "AnonymousCreated", + "args": [ + "AccountId", + "AccountId", + "ProxyType", + "u16" + ], + "docs": [ + " Anonymous account has been created by new proxy with given", + " disambiguation index and proxy type. \\[anonymous, who, proxy_type, disambiguation_index\\]" + ] + }, + { + "name": "Announced", + "args": [ + "AccountId", + "AccountId", + "Hash" + ], + "docs": [ + " An announcement was placed to make a call in the future. \\[real, proxy, call_hash\\]" + ] + } + ], + "constants": [ + { + "name": "ProxyDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a proxy.", + "", + " This is held for an additional storage item whose value size is", + " `sizeof(Balance)` bytes and whose key size is `sizeof(AccountId)` bytes." + ] + }, + { + "name": "ProxyDepositFactor", + "type": "BalanceOf", + "value": "0x0060aa7714b400000000000000000000", + "docs": [ + " The amount of currency needed per proxy added.", + "", + " This is held for adding 32 bytes plus an instance of `ProxyType` more into a pre-existing", + " storage value. Thus, when configuring `ProxyDepositFactor` one should take into account", + " `32 + proxy_type.encode().len()` bytes of data." + ] + }, + { + "name": "MaxProxies", + "type": "u16", + "value": "0x2000", + "docs": [ + " The maximum amount of proxies allowed for a single account." + ] + }, + { + "name": "MaxPending", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum amount of time-delayed announcements that are allowed to be pending." + ] + }, + { + "name": "AnnouncementDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating an announcement.", + "", + " This is held when a new storage item holding a `Balance` is created (typically 16 bytes)." + ] + }, + { + "name": "AnnouncementDepositFactor", + "type": "BalanceOf", + "value": "0x00c054ef286801000000000000000000", + "docs": [ + " The amount of currency needed per announcement made.", + "", + " This is held for adding an `AccountId`, `Hash` and `BlockNumber` (typically 68 bytes)", + " into a pre-existing storage value." + ] + } + ], + "errors": [ + { + "name": "TooMany", + "docs": [ + " There are too many proxies registered or too many announcements pending." + ] + }, + { + "name": "NotFound", + "docs": [ + " Proxy registration not found." + ] + }, + { + "name": "NotProxy", + "docs": [ + " Sender is not a proxy of the account to be proxied." + ] + }, + { + "name": "Unproxyable", + "docs": [ + " A call which is incompatible with the proxy type's filter was attempted." + ] + }, + { + "name": "Duplicate", + "docs": [ + " Account is already a proxy." + ] + }, + { + "name": "NoPermission", + "docs": [ + " Call may not be made by proxy because it may escalate its privileges." + ] + }, + { + "name": "Unannounced", + "docs": [ + " Announcement, if made at all, was made too recently." + ] + }, + { + "name": "NoSelfProxy", + "docs": [ + " Cannot add self as proxy." + ] + } + ], + "index": 30 + }, + { + "name": "Multisig", + "storage": { + "prefix": "Multisig", + "items": [ + { + "name": "Multisigs", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "[u8;32]", + "value": "Multisig", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " The set of open multisig operations." + ] + }, + { + "name": "Calls", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "[u8;32]", + "value": "(OpaqueCall,AccountId,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": [ + { + "name": "as_multi_threshold_1", + "args": [ + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Immediately dispatch a multi-signature call using a single approval from the caller.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `other_signatories`: The accounts (other than the sender) who are part of the", + " multi-signature, but do not participate in the approval process.", + " - `call`: The call to be executed.", + "", + " Result is equivalent to the dispatched result.", + "", + " # ", + " O(Z + C) where Z is the length of the call and C its execution weight.", + " -------------------------------", + " - DB Weight: None", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call", + "type": "OpaqueCall" + }, + { + "name": "store_call", + "type": "bool" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " If there are enough, then dispatch the call.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call`: The call to be executed.", + "", + " NOTE: Unless this is the final approval, you will generally want to use", + " `approve_as_multi` instead, since it only requires a hash of the call.", + "", + " Result is equivalent to the dispatched result if `threshold` is exactly `1`. Otherwise", + " on success, result is `Ok` and the result from the interior call, if it was executed,", + " may be found in the deposited `MultisigExecuted` event.", + "", + " # ", + " - `O(S + Z + Call)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One call encode & hash, both of complexity `O(Z)` where `Z` is tx-len.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - The weight of the `call`.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " -------------------------------", + " - DB Weight:", + " - Reads: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Writes: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "approve_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call_hash", + "type": "[u8;32]" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call_hash`: The hash of the call to be executed.", + "", + " NOTE: If this is the final approval, you will want to use `as_multi` instead.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " ----------------------------------", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account]", + " - Write: Multisig Storage, [Caller Account]", + " # " + ] + }, + { + "name": "cancel_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "timepoint", + "type": "Timepoint" + }, + { + "name": "call_hash", + "type": "[u8;32]" + } + ], + "docs": [ + " Cancel a pre-existing, on-going multisig transaction. Any deposit reserved previously", + " for this operation will be unreserved on success.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `timepoint`: The timepoint (block number and transaction index) of the first approval", + " transaction for this dispatch.", + " - `call_hash`: The hash of the call to be executed.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - One event.", + " - I/O: 1 read `O(S)`, one remove.", + " - Storage: removes one item.", + " ----------------------------------", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account], Refund Account, Calls", + " - Write: Multisig Storage, [Caller Account], Refund Account, Calls", + " # " + ] + } + ], + "events": [ + { + "name": "NewMultisig", + "args": [ + "AccountId", + "AccountId", + "CallHash" + ], + "docs": [ + " A new multisig operation has begun. \\[approving, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigApproval", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been approved by someone.", + " \\[approving, timepoint, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigExecuted", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash", + "DispatchResult" + ], + "docs": [ + " A multisig operation has been executed. \\[approving, timepoint, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigCancelled", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been cancelled. \\[cancelling, timepoint, multisig, call_hash\\]" + ] + } + ], + "constants": [ + { + "name": "DepositBase", + "type": "BalanceOf", + "value": "0x00f01c0adbed01000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a multisig execution or to store", + " a dispatch call for later." + ] + }, + { + "name": "DepositFactor", + "type": "BalanceOf", + "value": "0x0000cc7b9fae00000000000000000000", + "docs": [ + " The amount of currency needed per unit threshold when creating a multisig execution." + ] + }, + { + "name": "MaxSignatories", + "type": "u16", + "value": "0x6400", + "docs": [ + " The maximum amount of signatories allowed for a given multisig." + ] + } + ], + "errors": [ + { + "name": "MinimumThreshold", + "docs": [ + " Threshold must be 2 or greater." + ] + }, + { + "name": "AlreadyApproved", + "docs": [ + " Call is already approved by this signatory." + ] + }, + { + "name": "NoApprovalsNeeded", + "docs": [ + " Call doesn't need any (more) approvals." + ] + }, + { + "name": "TooFewSignatories", + "docs": [ + " There are too few signatories in the list." + ] + }, + { + "name": "TooManySignatories", + "docs": [ + " There are too many signatories in the list." + ] + }, + { + "name": "SignatoriesOutOfOrder", + "docs": [ + " The signatories were provided out of order; they should be ordered." + ] + }, + { + "name": "SenderInSignatories", + "docs": [ + " The sender was contained in the other signatories; it shouldn't be." + ] + }, + { + "name": "NotFound", + "docs": [ + " Multisig operation not found when attempting to cancel." + ] + }, + { + "name": "NotOwner", + "docs": [ + " Only the account that originally created the multisig is able to cancel it." + ] + }, + { + "name": "NoTimepoint", + "docs": [ + " No timepoint was given, yet the multisig operation is already underway." + ] + }, + { + "name": "WrongTimepoint", + "docs": [ + " A different timepoint was given to the multisig operation that is underway." + ] + }, + { + "name": "UnexpectedTimepoint", + "docs": [ + " A timepoint was given, yet no multisig operation is underway." + ] + }, + { + "name": "MaxWeightTooLow", + "docs": [ + " The maximum weight information provided was too low." + ] + }, + { + "name": "AlreadyStored", + "docs": [ + " The data to be stored is already stored." + ] + } + ], + "index": 31 + }, + { + "name": "Bounties", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "BountyCount", + "modifier": "Default", + "type": { + "plain": "BountyIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of bounty proposals that have been made." + ] + }, + { + "name": "Bounties", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BountyIndex", + "value": "Bounty", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Bounties that have been made." + ] + }, + { + "name": "BountyDescriptions", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BountyIndex", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The description of each bounty." + ] + }, + { + "name": "BountyApprovals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Bounty indices that have been approved but not yet funded." + ] + } + ] + }, + "calls": [ + { + "name": "propose_bounty", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "description", + "type": "Bytes" + } + ], + "docs": [ + " Propose a new bounty.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `DataDepositPerByte` for each byte in `reason`. It will be unreserved upon approval,", + " or slashed when rejected.", + "", + " - `curator`: The curator account whom will manage this bounty.", + " - `fee`: The curator fee.", + " - `value`: The total payment amount of this bounty, curator fee included.", + " - `description`: The description of this bounty." + ] + }, + { + "name": "approve_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a bounty proposal. At a later time, the bounty will be funded and become active", + " and the original deposit will be returned.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "propose_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "curator", + "type": "LookupSource" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Assign a curator to a funded bounty.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "unassign_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Unassign curator from a bounty.", + "", + " This function can only be called by the `RejectOrigin` a signed origin.", + "", + " If this function is called by the `RejectOrigin`, we assume that the curator is malicious", + " or inactive. As a result, we will slash the curator when possible.", + "", + " If the origin is the curator, we take this as a sign they are unable to do their job and", + " they willingly give up. We could slash them, but for now we allow them to recover their", + " deposit and exit without issue. (We may want to change this if it is abused.)", + "", + " Finally, the origin can be anyone if and only if the curator is \"inactive\". This allows", + " anyone in the community to call out that a curator is not doing their due diligence, and", + " we should pick a new curator. In this case the curator should also be slashed.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "accept_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Accept the curator role for a bounty.", + " A deposit will be reserved from curator and refund upon successful payout.", + "", + " May only be called from the curator.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "award_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Award bounty to a beneficiary account. The beneficiary will be able to claim the funds after a delay.", + "", + " The dispatch origin for this call must be the curator of this bounty.", + "", + " - `bounty_id`: Bounty ID to award.", + " - `beneficiary`: The beneficiary account whom will receive the payout.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "claim_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Claim the payout from an awarded bounty after payout delay.", + "", + " The dispatch origin for this call must be the beneficiary of this bounty.", + "", + " - `bounty_id`: Bounty ID to claim.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "close_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Cancel a proposed or active bounty. All the funds will be sent to treasury and", + " the curator deposit will be unreserved if possible.", + "", + " Only `T::RejectOrigin` is able to cancel a bounty.", + "", + " - `bounty_id`: Bounty ID to cancel.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "extend_bounty_expiry", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Extend the expiry time of an active bounty.", + "", + " The dispatch origin for this call must be the curator of this bounty.", + "", + " - `bounty_id`: Bounty ID to extend.", + " - `remark`: additional information.", + "", + " # ", + " - O(1).", + " # " + ] + } + ], + "events": [ + { + "name": "BountyProposed", + "args": [ + "BountyIndex" + ], + "docs": [ + " New bounty proposal. \\[index\\]" + ] + }, + { + "name": "BountyRejected", + "args": [ + "BountyIndex", + "Balance" + ], + "docs": [ + " A bounty proposal was rejected; funds were slashed. \\[index, bond\\]" + ] + }, + { + "name": "BountyBecameActive", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty proposal is funded and became active. \\[index\\]" + ] + }, + { + "name": "BountyAwarded", + "args": [ + "BountyIndex", + "AccountId" + ], + "docs": [ + " A bounty is awarded to a beneficiary. \\[index, beneficiary\\]" + ] + }, + { + "name": "BountyClaimed", + "args": [ + "BountyIndex", + "Balance", + "AccountId" + ], + "docs": [ + " A bounty is claimed by beneficiary. \\[index, payout, beneficiary\\]" + ] + }, + { + "name": "BountyCanceled", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty is cancelled. \\[index\\]" + ] + }, + { + "name": "BountyExtended", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty expiry is extended. \\[index\\]" + ] + } + ], + "constants": [ + { + "name": "DataDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within bounty description." + ] + }, + { + "name": "BountyDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a bounty proposal." + ] + }, + { + "name": "BountyDepositPayoutDelay", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The delay period for which a bounty beneficiary need to wait before claim the payout." + ] + }, + { + "name": "BountyUpdatePeriod", + "type": "BlockNumber", + "value": "0x00270600", + "docs": [ + " Bounty duration in blocks." + ] + }, + { + "name": "BountyCuratorDeposit", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of the curator fee that will be reserved upfront as deposit for bounty curator." + ] + }, + { + "name": "BountyValueMinimum", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " Minimum value for a bounty." + ] + }, + { + "name": "MaximumReasonLength", + "type": "u32", + "value": "0x00400000", + "docs": [ + " Maximum acceptable reason length." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " No proposal or bounty at that index." + ] + }, + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "UnexpectedStatus", + "docs": [ + " The bounty status is unexpected." + ] + }, + { + "name": "RequireCurator", + "docs": [ + " Require bounty curator." + ] + }, + { + "name": "InvalidValue", + "docs": [ + " Invalid bounty value." + ] + }, + { + "name": "InvalidFee", + "docs": [ + " Invalid bounty fee." + ] + }, + { + "name": "PendingPayout", + "docs": [ + " A bounty payout is pending.", + " To cancel the bounty, you must unassign and slash the curator." + ] + }, + { + "name": "Premature", + "docs": [ + " The bounties cannot be claimed/closed because it's still in the countdown period." + ] + } + ], + "index": 32 + }, + { + "name": "Tips", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "Tips", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Hash", + "value": "OpenTip", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " TipsMap that are not yet completed. Keyed by the hash of `(reason, who)` from the value.", + " This has the insecure enumerable hash function since the key itself is already", + " guaranteed to be a secure hash." + ] + }, + { + "name": "Reasons", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Simple preimage lookup from the reason's hash to the original data. Again, has an", + " insecure enumerable hash since the key is guaranteed to be the result of a secure hash." + ] + } + ] + }, + "calls": [ + { + "name": "report_awesome", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Report something `reason` that deserves a tip and claim any eventual the finder's fee.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `DataDepositPerByte` for each byte in `reason`.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R)` where `R` length of `reason`.", + " - encoding and hashing of 'reason'", + " - DbReads: `Reasons`, `Tips`", + " - DbWrites: `Reasons`, `Tips`", + " # " + ] + }, + { + "name": "retract_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Retract a prior tip-report from `report_awesome`, and cancel the process of tipping.", + "", + " If successful, the original deposit will be unreserved.", + "", + " The dispatch origin for this call must be _Signed_ and the tip identified by `hash`", + " must have been reported by the signing account through `report_awesome` (and not", + " through `tip_new`).", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " Emits `TipRetracted` if successful.", + "", + " # ", + " - Complexity: `O(1)`", + " - Depends on the length of `T::Hash` which is fixed.", + " - DbReads: `Tips`, `origin account`", + " - DbWrites: `Reasons`, `Tips`, `origin account`", + " # " + ] + }, + { + "name": "tip_new", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + }, + { + "name": "tip_value", + "type": "Compact" + } + ], + "docs": [ + " Give a tip for something new; no finder's fee will be taken.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R + T)` where `R` length of `reason`, `T` is the number of tippers.", + " - `O(T)`: decoding `Tipper` vec of length `T`", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - `O(R)`: hashing and encoding of reason of length `R`", + " - DbReads: `Tippers`, `Reasons`", + " - DbWrites: `Reasons`, `Tips`", + " # " + ] + }, + { + "name": "tip", + "args": [ + { + "name": "hash", + "type": "Hash" + }, + { + "name": "tip_value", + "type": "Compact" + } + ], + "docs": [ + " Declare a tip value for an already-open tip.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the hash of the original tip `reason` and the beneficiary", + " account ID.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `TipClosing` if the threshold of tippers has been reached and the countdown period", + " has started.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`, insert tip and check closing,", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + "", + " Actually weight could be lower as it depends on how many tips are in `OpenTip` but it", + " is weighted as if almost full i.e of length `T-1`.", + " - DbReads: `Tippers`, `Tips`", + " - DbWrites: `Tips`", + " # " + ] + }, + { + "name": "close_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Close and payout a tip.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " The tip identified by `hash` must have finished its countdown period.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`.", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - DbReads: `Tips`, `Tippers`, `tip finder`", + " - DbWrites: `Reasons`, `Tips`, `Tippers`, `tip finder`", + " # " + ] + }, + { + "name": "slash_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Remove and slash an already-open tip.", + "", + " May only be called from `T::RejectOrigin`.", + "", + " As a result, the finder is slashed and the deposits are lost.", + "", + " Emits `TipSlashed` if successful.", + "", + " # ", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " # " + ] + } + ], + "events": [ + { + "name": "NewTip", + "args": [ + "Hash" + ], + "docs": [ + " A new tip suggestion has been opened. \\[tip_hash\\]" + ] + }, + { + "name": "TipClosing", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has reached threshold and is closing. \\[tip_hash\\]" + ] + }, + { + "name": "TipClosed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been closed. \\[tip_hash, who, payout\\]" + ] + }, + { + "name": "TipRetracted", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has been retracted. \\[tip_hash\\]" + ] + }, + { + "name": "TipSlashed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been slashed. \\[tip_hash, finder, deposit\\]" + ] + } + ], + "constants": [ + { + "name": "TipCountdown", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The period for which a tip remains open after is has achieved threshold tippers." + ] + }, + { + "name": "TipFindersFee", + "type": "Percent", + "value": "0x14", + "docs": [ + " The amount of the final tip which goes to the original reporter of the tip." + ] + }, + { + "name": "TipReportDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a tip report." + ] + }, + { + "name": "DataDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within the tip report reason." + ] + }, + { + "name": "MaximumReasonLength", + "type": "u32", + "value": "0x00400000", + "docs": [ + " Maximum acceptable reason length." + ] + } + ], + "errors": [ + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "AlreadyKnown", + "docs": [ + " The tip was already found/started." + ] + }, + { + "name": "UnknownTip", + "docs": [ + " The tip hash is unknown." + ] + }, + { + "name": "NotFinder", + "docs": [ + " The account attempting to retract the tip is not the finder of the tip." + ] + }, + { + "name": "StillOpen", + "docs": [ + " The tip cannot be claimed/closed because there are not enough tippers yet." + ] + }, + { + "name": "Premature", + "docs": [ + " The tip cannot be claimed/closed because it's still in the countdown period." + ] + } + ], + "index": 33 + }, + { + "name": "Assets", + "storage": { + "prefix": "Assets", + "items": [ + { + "name": "Asset", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AssetId", + "value": "AssetDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Details of an asset." + ] + }, + { + "name": "Account", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_128Concat", + "key1": "AssetId", + "key2": "AccountId", + "value": "AssetBalance", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00000000000000000000", + "docs": [ + " The number of units of assets held by any given account." + ] + }, + { + "name": "Approvals", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_128Concat", + "key1": "AssetId", + "key2": "AssetApprovalKey", + "value": "AssetApproval", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Approved balance transfers. First balance is the amount approved for transfer. Second", + " is the amount of `T::Currency` reserved for storing this." + ] + }, + { + "name": "Metadata", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AssetId", + "value": "AssetMetadata", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000", + "docs": [ + " Metadata of an asset." + ] + } + ] + }, + "calls": [ + { + "name": "create", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "min_balance", + "type": "TAssetBalance" + } + ], + "docs": [ + " Issue a new class of fungible assets from a public origin.", + "", + " This new asset class has no assets initially and its owner is the origin.", + "", + " The origin must be Signed and the sender must have sufficient funds free.", + "", + " Funds of sender are reserved by `AssetDeposit`.", + "", + " Parameters:", + " - `id`: The identifier of the new asset. This must not be currently in use to identify", + " an existing asset.", + " - `admin`: The admin of this class of assets. The admin is the initial address of each", + " member of the asset class's admin team.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + "", + " Emits `Created` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_create", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "is_sufficient", + "type": "bool" + }, + { + "name": "min_balance", + "type": "Compact" + } + ], + "docs": [ + " Issue a new class of fungible assets from a privileged origin.", + "", + " This new asset class has no assets initially.", + "", + " The origin must conform to `ForceOrigin`.", + "", + " Unlike `create`, no funds are reserved.", + "", + " - `id`: The identifier of the new asset. This must not be currently in use to identify", + " an existing asset.", + " - `owner`: The owner of this class of assets. The owner has full superuser permissions", + " over this asset, but may later change and configure the permissions using `transfer_ownership`", + " and `set_team`.", + " - `max_zombies`: The total number of accounts which may hold assets in this class yet", + " have no existential deposit.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + "", + " Emits `ForceCreated` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "destroy", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "witness", + "type": "AssetDestroyWitness" + } + ], + "docs": [ + " Destroy a class of fungible assets.", + "", + " The origin must conform to `ForceOrigin` or must be Signed and the sender must be the", + " owner of the asset `id`.", + "", + " - `id`: The identifier of the asset to be destroyed. This must identify an existing", + " asset.", + "", + " Emits `Destroyed` event when successful.", + "", + " Weight: `O(c + p + a)` where:", + " - `c = (witness.accounts - witness.sufficients)`", + " - `s = witness.sufficients`", + " - `a = witness.approvals`" + ] + }, + { + "name": "mint", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Mint assets of a particular class.", + "", + " The origin must be Signed and the sender must be the Issuer of the asset `id`.", + "", + " - `id`: The identifier of the asset to have some amount minted.", + " - `beneficiary`: The account to be credited with the minted assets.", + " - `amount`: The amount of the asset to be minted.", + "", + " Emits `Destroyed` event when successful.", + "", + " Weight: `O(1)`", + " Modes: Pre-existing balance of `beneficiary`; Account pre-existence of `beneficiary`." + ] + }, + { + "name": "burn", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Reduce the balance of `who` by as much as possible up to `amount` assets of `id`.", + "", + " Origin must be Signed and the sender should be the Manager of the asset `id`.", + "", + " Bails with `BalanceZero` if the `who` is already dead.", + "", + " - `id`: The identifier of the asset to have some amount burned.", + " - `who`: The account to be debited from.", + " - `amount`: The maximum amount by which `who`'s balance should be reduced.", + "", + " Emits `Burned` with the actual amount burned. If this takes the balance to below the", + " minimum for the asset, then the amount burned is increased to take it to zero.", + "", + " Weight: `O(1)`", + " Modes: Post-existence of `who`; Pre & post Zombie-status of `who`." + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from the sender account to another.", + "", + " Origin must be Signed.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `target`: The account to be credited.", + " - `amount`: The amount by which the sender's balance of assets should be reduced and", + " `target`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the sender balance above zero but below", + " the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `target`; Post-existence of sender; Prior & post zombie-status", + " of sender; Account pre-existence of `target`." + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from the sender account to another, keeping the sender account alive.", + "", + " Origin must be Signed.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `target`: The account to be credited.", + " - `amount`: The amount by which the sender's balance of assets should be reduced and", + " `target`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the sender balance above zero but below", + " the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `target`; Post-existence of sender; Prior & post zombie-status", + " of sender; Account pre-existence of `target`." + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from one account to another.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `source`: The account to be debited.", + " - `dest`: The account to be credited.", + " - `amount`: The amount by which the `source`'s balance of assets should be reduced and", + " `dest`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the `source` balance above zero but", + " below the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `dest`; Post-existence of `source`; Prior & post zombie-status", + " of `source`; Account pre-existence of `dest`." + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Disallow further unprivileged transfers from an account.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `who`: The account to be frozen.", + "", + " Emits `Frozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Allow unprivileged transfers from an account again.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `who`: The account to be unfrozen.", + "", + " Emits `Thawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "freeze_asset", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Disallow further unprivileged transfers for the asset class.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + "", + " Emits `Frozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw_asset", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Allow unprivileged transfers for the asset again.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + "", + " Emits `Thawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "transfer_ownership", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Owner of an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The new Owner of this asset.", + "", + " Emits `OwnerChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_team", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Issuer, Admin and Freezer of an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `issuer`: The new Issuer of this asset.", + " - `admin`: The new Admin of this asset.", + " - `freezer`: The new Freezer of this asset.", + "", + " Emits `TeamChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "name", + "type": "Bytes" + }, + { + "name": "symbol", + "type": "Bytes" + }, + { + "name": "decimals", + "type": "u8" + } + ], + "docs": [ + " Set the metadata for an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " Funds of sender are reserved according to the formula:", + " `MetadataDepositBase + MetadataDepositPerByte * (name.len + symbol.len)` taking into", + " account any already reserved funds.", + "", + " - `id`: The identifier of the asset to update.", + " - `name`: The user friendly name of this asset. Limited in length by `StringLimit`.", + " - `symbol`: The exchange symbol for this asset. Limited in length by `StringLimit`.", + " - `decimals`: The number of decimals this asset uses to represent one unit.", + "", + " Emits `MetadataSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "clear_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " Any deposit is freed for the asset owner.", + "", + " - `id`: The identifier of the asset to clear.", + "", + " Emits `MetadataCleared`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_set_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "name", + "type": "Bytes" + }, + { + "name": "symbol", + "type": "Bytes" + }, + { + "name": "decimals", + "type": "u8" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Force the metadata for an asset to some value.", + "", + " Origin must be ForceOrigin.", + "", + " Any deposit is left alone.", + "", + " - `id`: The identifier of the asset to update.", + " - `name`: The user friendly name of this asset. Limited in length by `StringLimit`.", + " - `symbol`: The exchange symbol for this asset. Limited in length by `StringLimit`.", + " - `decimals`: The number of decimals this asset uses to represent one unit.", + "", + " Emits `MetadataSet`.", + "", + " Weight: `O(N + S)` where N and S are the length of the name and symbol respectively." + ] + }, + { + "name": "force_clear_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset.", + "", + " Origin must be ForceOrigin.", + "", + " Any deposit is returned.", + "", + " - `id`: The identifier of the asset to clear.", + "", + " Emits `MetadataCleared`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_asset_status", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + }, + { + "name": "min_balance", + "type": "Compact" + }, + { + "name": "is_sufficient", + "type": "bool" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Alter the attributes of a given asset.", + "", + " Origin must be `ForceOrigin`.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The new Owner of this asset.", + " - `issuer`: The new Issuer of this asset.", + " - `admin`: The new Admin of this asset.", + " - `freezer`: The new Freezer of this asset.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + " - `is_sufficient`: Whether a non-zero balance of this asset is deposit of sufficient", + " value to account for the state bloat associated with its balance storage. If set to", + " `true`, then non-zero balances may be stored without a `consumer` reference (and thus", + " an ED in the Balances pallet or whatever else is used to control user-account state", + " growth).", + " - `is_frozen`: Whether this asset class is frozen except for permissioned/admin", + " instructions.", + "", + " Emits `AssetStatusChanged` with the identity of the asset.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "approve_transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "delegate", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Approve an amount of asset for transfer by a delegated third-party account.", + "", + " Origin must be Signed.", + "", + " Ensures that `ApprovalDeposit` worth of `Currency` is reserved from signing account", + " for the purpose of holding the approval. If some non-zero amount of assets is already", + " approved from signing account to `delegate`, then it is topped up or unreserved to", + " meet the right value.", + "", + " NOTE: The signing account does not need to own `amount` of assets at the point of", + " making this call.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account to delegate permission to transfer asset.", + " - `amount`: The amount of asset that may be transferred by `delegate`. If there is", + " already an approval in place, then this acts additively.", + "", + " Emits `ApprovedTransfer` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "cancel_approval", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "delegate", + "type": "LookupSource" + } + ], + "docs": [ + " Cancel all of some asset approved for delegated transfer by a third-party account.", + "", + " Origin must be Signed and there must be an approval in place between signer and", + " `delegate`.", + "", + " Unreserves any deposit previously reserved by `approve_transfer` for the approval.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account delegated permission to transfer asset.", + "", + " Emits `ApprovalCancelled` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_cancel_approval", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "delegate", + "type": "LookupSource" + } + ], + "docs": [ + " Cancel all of some asset approved for delegated transfer by a third-party account.", + "", + " Origin must be either ForceOrigin or Signed origin with the signer being the Admin", + " account of the asset `id`.", + "", + " Unreserves any deposit previously reserved by `approve_transfer` for the approval.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account delegated permission to transfer asset.", + "", + " Emits `ApprovalCancelled` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "transfer_approved", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "destination", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Transfer some asset balance from a previously delegated account to some third-party", + " account.", + "", + " Origin must be Signed and there must be an approval in place by the `owner` to the", + " signer.", + "", + " If the entire amount approved for transfer is transferred, then any deposit previously", + " reserved by `approve_transfer` is unreserved.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The account which previously approved for a transfer of at least `amount` and", + " from which the asset balance will be withdrawn.", + " - `destination`: The account to which the asset balance of `amount` will be transferred.", + " - `amount`: The amount of assets to transfer.", + "", + " Emits `TransferredApproved` on success.", + "", + " Weight: `O(1)`" + ] + } + ], + "events": [ + { + "name": "Created", + "args": [ + "AssetId", + "AccountId", + "AccountId" + ], + "docs": [ + " Some asset class was created. \\[asset_id, creator, owner\\]" + ] + }, + { + "name": "Issued", + "args": [ + "AssetId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were issued. \\[asset_id, owner, total_supply\\]" + ] + }, + { + "name": "Transferred", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were transferred. \\[asset_id, from, to, amount\\]" + ] + }, + { + "name": "Burned", + "args": [ + "AssetId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were destroyed. \\[asset_id, owner, balance\\]" + ] + }, + { + "name": "TeamChanged", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " The management team changed \\[asset_id, issuer, admin, freezer\\]" + ] + }, + { + "name": "OwnerChanged", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " The owner changed \\[asset_id, owner\\]" + ] + }, + { + "name": "Frozen", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some account `who` was frozen. \\[asset_id, who\\]" + ] + }, + { + "name": "Thawed", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some account `who` was thawed. \\[asset_id, who\\]" + ] + }, + { + "name": "AssetFrozen", + "args": [ + "AssetId" + ], + "docs": [ + " Some asset `asset_id` was frozen. \\[asset_id\\]" + ] + }, + { + "name": "AssetThawed", + "args": [ + "AssetId" + ], + "docs": [ + " Some asset `asset_id` was thawed. \\[asset_id\\]" + ] + }, + { + "name": "Destroyed", + "args": [ + "AssetId" + ], + "docs": [ + " An asset class was destroyed." + ] + }, + { + "name": "ForceCreated", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some asset class was force-created. \\[asset_id, owner\\]" + ] + }, + { + "name": "MetadataSet", + "args": [ + "AssetId", + "Bytes", + "Bytes", + "u8", + "bool" + ], + "docs": [ + " New metadata has been set for an asset. \\[asset_id, name, symbol, decimals, is_frozen\\]" + ] + }, + { + "name": "MetadataCleared", + "args": [ + "AssetId" + ], + "docs": [ + " Metadata has been cleared for an asset. \\[asset_id\\]" + ] + }, + { + "name": "ApprovedTransfer", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " (Additional) funds have been approved for transfer to a destination account.", + " \\[asset_id, source, delegate, amount\\]" + ] + }, + { + "name": "ApprovalCancelled", + "args": [ + "AssetId", + "AccountId", + "AccountId" + ], + "docs": [ + " An approval for account `delegate` was cancelled by `owner`.", + " \\[id, owner, delegate\\]" + ] + }, + { + "name": "TransferredApproved", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " An `amount` was transferred in its entirety from `owner` to `destination` by", + " the approved `delegate`.", + " \\[id, owner, delegate, destination\\]" + ] + }, + { + "name": "AssetStatusChanged", + "args": [ + "AssetId" + ], + "docs": [ + " An asset has had its attributes changed by the `Force` origin.", + " \\[id\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "BalanceLow", + "docs": [ + " Account balance must be greater than or equal to the transfer amount." + ] + }, + { + "name": "BalanceZero", + "docs": [ + " Balance should be non-zero." + ] + }, + { + "name": "NoPermission", + "docs": [ + " The signing account has no permission to do the operation." + ] + }, + { + "name": "Unknown", + "docs": [ + " The given asset ID is unknown." + ] + }, + { + "name": "Frozen", + "docs": [ + " The origin account is frozen." + ] + }, + { + "name": "InUse", + "docs": [ + " The asset ID is already taken." + ] + }, + { + "name": "BadWitness", + "docs": [ + " Invalid witness data given." + ] + }, + { + "name": "MinBalanceZero", + "docs": [ + " Minimum balance should be non-zero." + ] + }, + { + "name": "Overflow", + "docs": [ + " A mint operation lead to an overflow." + ] + }, + { + "name": "NoProvider", + "docs": [ + " No provider reference exists to allow a non-zero balance of a non-self-sufficient asset." + ] + }, + { + "name": "BadMetadata", + "docs": [ + " Invalid metadata given." + ] + }, + { + "name": "Unapproved", + "docs": [ + " No approval exists that would allow the transfer." + ] + }, + { + "name": "WouldDie", + "docs": [ + " The source account would not survive the transfer and it needs to stay alive." + ] + } + ], + "index": 34 + }, + { + "name": "Mmr", + "storage": { + "prefix": "MerkleMountainRange", + "items": [ + { + "name": "RootHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Latest MMR Root hash." + ] + }, + { + "name": "NumberOfLeaves", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current size of the MMR (number of leaves)." + ] + }, + { + "name": "Nodes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "u64", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Hashes of the nodes in the MMR.", + "", + " Note this collection only contains MMR peaks, the inner nodes (and leaves)", + " are pruned and only stored in the Offchain DB." + ] + } + ] + }, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 35 + }, + { + "name": "Lottery", + "storage": { + "prefix": "Lottery", + "items": [ + { + "name": "LotteryIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [] + }, + { + "name": "Lottery", + "modifier": "Optional", + "type": { + "plain": "LotteryConfig" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the current lottery." + ] + }, + { + "name": "Participants", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(u32,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000", + "docs": [ + " Users who have purchased a ticket. (Lottery Index, Tickets Purchased)" + ] + }, + { + "name": "TicketsCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Total number of tickets sold." + ] + }, + { + "name": "Tickets", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Each ticket's owner.", + "", + " May have residual storage from previous lotteries. Use `TicketsCount` to see which ones", + " are actually valid ticket mappings." + ] + }, + { + "name": "CallIndices", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The calls stored in this pallet to be used in an active lottery if configured", + " by `Config::ValidateCall`." + ] + } + ] + }, + "calls": [ + { + "name": "buy_ticket", + "args": [ + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Buy a ticket to enter the lottery.", + "", + " This extrinsic acts as a passthrough function for `call`. In all", + " situations where `call` alone would succeed, this extrinsic should", + " succeed.", + "", + " If `call` is successful, then we will attempt to purchase a ticket,", + " which may fail silently. To detect success of a ticket purchase, you", + " should listen for the `TicketBought` event.", + "", + " This extrinsic must be called by a signed origin." + ] + }, + { + "name": "set_calls", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Set calls in storage which can be used to purchase a lottery ticket.", + "", + " This function only matters if you use the `ValidateCall` implementation", + " provided by this pallet, which uses storage to determine the valid calls.", + "", + " This extrinsic must be called by the Manager origin." + ] + }, + { + "name": "start_lottery", + "args": [ + { + "name": "price", + "type": "BalanceOf" + }, + { + "name": "length", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "repeat", + "type": "bool" + } + ], + "docs": [ + " Start a lottery using the provided configuration.", + "", + " This extrinsic must be called by the `ManagerOrigin`.", + "", + " Parameters:", + "", + " * `price`: The cost of a single ticket.", + " * `length`: How long the lottery should run for starting at the current block.", + " * `delay`: How long after the lottery end we should wait before picking a winner.", + " * `repeat`: If the lottery should repeat when completed." + ] + }, + { + "name": "stop_repeat", + "args": [], + "docs": [ + " If a lottery is repeating, you can use this to stop the repeat.", + " The lottery will continue to run to completion.", + "", + " This extrinsic must be called by the `ManagerOrigin`." + ] + } + ], + "events": [ + { + "name": "LotteryStarted", + "args": [], + "docs": [ + " A lottery has been started!" + ] + }, + { + "name": "CallsUpdated", + "args": [], + "docs": [ + " A new set of calls have been set!" + ] + }, + { + "name": "Winner", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A winner has been chosen!" + ] + }, + { + "name": "TicketBought", + "args": [ + "AccountId", + "CallIndex" + ], + "docs": [ + " A ticket has been bought!" + ] + } + ], + "constants": [ + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f6c6f74746f", + "docs": [] + }, + { + "name": "MaxCalls", + "type": "u32", + "value": "0x0a000000", + "docs": [] + } + ], + "errors": [ + { + "name": "Overflow", + "docs": [ + " An overflow has occurred." + ] + }, + { + "name": "NotConfigured", + "docs": [ + " A lottery has not been configured." + ] + }, + { + "name": "InProgress", + "docs": [ + " A lottery is already in progress." + ] + }, + { + "name": "AlreadyEnded", + "docs": [ + " A lottery has already ended." + ] + }, + { + "name": "InvalidCall", + "docs": [ + " The call is not valid for an open lottery." + ] + }, + { + "name": "AlreadyParticipating", + "docs": [ + " You are already participating in the lottery with this call." + ] + }, + { + "name": "TooManyCalls", + "docs": [ + " Too many calls for a single lottery." + ] + }, + { + "name": "EncodingFailed", + "docs": [ + " Failed to encode calls" + ] + } + ], + "index": 36 + }, + { + "name": "Gilt", + "storage": { + "prefix": "Gilt", + "items": [ + { + "name": "QueueTotals", + "modifier": "Default", + "type": { + "plain": "Vec<(u32,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The totals of items and balances within each queue. Saves a lot of storage reads in the", + " case of sparsely packed queues.", + "", + " The vector is indexed by duration in `Period`s, offset by one, so information on the queue", + " whose duration is one `Period` would be storage `0`." + ] + }, + { + "name": "Queues", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "u32", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The queues of bids ready to become gilts. Indexed by duration (in `Period`s)." + ] + }, + { + "name": "ActiveTotal", + "modifier": "Default", + "type": { + "plain": "ActiveGiltsTotal" + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Information relating to the gilts currently active." + ] + }, + { + "name": "Active", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "ActiveIndex", + "value": "ActiveGilt", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The currently active gilts, indexed according to the order of creation." + ] + } + ] + }, + "calls": [ + { + "name": "place_bid", + "args": [ + { + "name": "amount", + "type": "Compact" + }, + { + "name": "duration", + "type": "u32" + } + ], + "docs": [ + " Place a bid for a gilt to be issued.", + "", + " Origin must be Signed, and account must have at least `amount` in free balance.", + "", + " - `amount`: The amount of the bid; these funds will be reserved. If the bid is", + " successfully elevated into an issued gilt, then these funds will continue to be", + " reserved until the gilt expires. Must be at least `MinFreeze`.", + " - `duration`: The number of periods for which the funds will be locked if the gilt is", + " issued. It will expire only after this period has elapsed after the point of issuance.", + " Must be greater than 1 and no more than `QueueCount`.", + "", + " Complexities:", + " - `Queues[duration].len()` (just take max)." + ] + }, + { + "name": "retract_bid", + "args": [ + { + "name": "amount", + "type": "Compact" + }, + { + "name": "duration", + "type": "u32" + } + ], + "docs": [ + " Retract a previously placed bid.", + "", + " Origin must be Signed, and the account should have previously issued a still-active bid", + " of `amount` for `duration`.", + "", + " - `amount`: The amount of the previous bid.", + " - `duration`: The duration of the previous bid." + ] + }, + { + "name": "set_target", + "args": [ + { + "name": "target", + "type": "Compact" + } + ], + "docs": [ + " Set target proportion of gilt-funds.", + "", + " Origin must be `AdminOrigin`.", + "", + " - `target`: The target proportion of effective issued funds that should be under gilts", + " at any one time." + ] + }, + { + "name": "thaw", + "args": [ + { + "name": "index", + "type": "Compact" + } + ], + "docs": [ + " Remove an active but expired gilt. Reserved funds under gilt are freed and balance is", + " adjusted to ensure that the funds grow or shrink to maintain the equivalent proportion", + " of effective total issued funds.", + "", + " Origin must be Signed and the account must be the owner of the gilt of the given index.", + "", + " - `index`: The index of the gilt to be thawed." + ] + } + ], + "events": [ + { + "name": "BidPlaced", + "args": [ + "AccountId", + "BalanceOf", + "u32" + ], + "docs": [ + " A bid was successfully placed.", + " \\[ who, amount, duration \\]" + ] + }, + { + "name": "BidRetracted", + "args": [ + "AccountId", + "BalanceOf", + "u32" + ], + "docs": [ + " A bid was successfully removed (before being accepted as a gilt).", + " \\[ who, amount, duration \\]" + ] + }, + { + "name": "GiltIssued", + "args": [ + "ActiveIndex", + "BlockNumber", + "AccountId", + "BalanceOf" + ], + "docs": [ + " A bid was accepted as a gilt. The balance may not be released until expiry.", + " \\[ index, expiry, who, amount \\]" + ] + }, + { + "name": "GiltThawed", + "args": [ + "ActiveIndex", + "AccountId", + "BalanceOf", + "BalanceOf" + ], + "docs": [ + " An expired gilt has been thawed.", + " \\[ index, who, original_amount, additional_amount \\]" + ] + } + ], + "constants": [ + { + "name": "QueueCount", + "type": "u32", + "value": "0x2c010000", + "docs": [ + " Number of duration queues in total. This sets the maximum duration supported, which is", + " this value multiplied by `Period`." + ] + }, + { + "name": "MaxQueueLen", + "type": "u32", + "value": "0xe8030000", + "docs": [ + " Maximum number of items that may be in each duration queue." + ] + }, + { + "name": "FifoQueueLen", + "type": "u32", + "value": "0xf4010000", + "docs": [ + " Portion of the queue which is free from ordering and just a FIFO.", + "", + " Must be no greater than `MaxQueueLen`." + ] + }, + { + "name": "Period", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The base period for the duration queues. This is the common multiple across all", + " supported freezing durations that can be bid upon." + ] + }, + { + "name": "MinFreeze", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount of funds that may be offered to freeze for a gilt. Note that this", + " does not actually limit the amount which may be frozen in a gilt since gilts may be", + " split up in order to satisfy the desired amount of funds under gilts.", + "", + " It should be at least big enough to ensure that there is no possible storage spam attack", + " or queue-filling attack." + ] + }, + { + "name": "IntakePeriod", + "type": "BlockNumber", + "value": "0x0a000000", + "docs": [ + " The number of blocks between consecutive attempts to issue more gilts in an effort to", + " get to the target amount to be frozen.", + "", + " A larger value results in fewer storage hits each block, but a slower period to get to", + " the target." + ] + }, + { + "name": "MaxIntakeBids", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The maximum amount of bids that can be turned into issued gilts each block. A larger", + " value here means less of the block available for transactions should there be a glut of", + " bids to make into gilts to reach the target." + ] + } + ], + "errors": [ + { + "name": "DurationTooSmall", + "docs": [ + " The duration of the bid is less than one." + ] + }, + { + "name": "DurationTooBig", + "docs": [ + " The duration is the bid is greater than the number of queues." + ] + }, + { + "name": "AmountTooSmall", + "docs": [ + " The amount of the bid is less than the minimum allowed." + ] + }, + { + "name": "BidTooLow", + "docs": [ + " The queue for the bid's duration is full and the amount bid is too low to get in through", + " replacing an existing bid." + ] + }, + { + "name": "Unknown", + "docs": [ + " Gilt index is unknown." + ] + }, + { + "name": "NotOwner", + "docs": [ + " Not the owner of the gilt." + ] + }, + { + "name": "NotExpired", + "docs": [ + " Gilt not yet at expiry date." + ] + }, + { + "name": "NotFound", + "docs": [ + " The given bid for retraction is not found." + ] + } + ], + "index": 37 + } + ], + "extrinsic": { + "version": 4, + "signedExtensions": [ + "CheckSpecVersion", + "CheckTxVersion", + "CheckGenesis", + "CheckMortality", + "CheckNonce", + "CheckWeight", + "ChargeTransactionPayment" + ] + } + } + } +} diff --git a/packages/polkadot/tests/meta/v13.hex b/packages/polkadot/tests/meta/v13.hex new file mode 100644 index 00000000..6f640dee --- /dev/null +++ b/packages/polkadot/tests/meta/v13.hex @@ -0,0 +1 @@ +0x6d6574610da01853797374656d011853797374656d401c4163636f756e7401010230543a3a4163636f756e744964944163636f756e74496e666f3c543a3a496e6465782c20543a3a4163636f756e74446174613e004101000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004e8205468652066756c6c206163636f756e7420696e666f726d6174696f6e20666f72206120706172746963756c6172206163636f756e742049442e3845787472696e736963436f756e7400000c753332040004b820546f74616c2065787472696e7369637320636f756e7420666f72207468652063757272656e7420626c6f636b2e2c426c6f636b576569676874010038436f6e73756d6564576569676874600000000000000000000000000000000000000000000000000488205468652063757272656e742077656967687420666f722074686520626c6f636b2e40416c6c45787472696e736963734c656e00000c753332040004410120546f74616c206c656e6774682028696e2062797465732920666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e24426c6f636b4861736801010538543a3a426c6f636b4e756d6265721c543a3a48617368008000000000000000000000000000000000000000000000000000000000000000000498204d6170206f6620626c6f636b206e756d6265727320746f20626c6f636b206861736865732e3445787472696e736963446174610101050c7533321c5665633c75383e000400043d012045787472696e73696373206461746120666f72207468652063757272656e7420626c6f636b20286d61707320616e2065787472696e736963277320696e64657820746f206974732064617461292e184e756d626572010038543a3a426c6f636b4e756d6265721000000000040901205468652063757272656e7420626c6f636b206e756d626572206265696e672070726f6365737365642e205365742062792060657865637574655f626c6f636b602e28506172656e744861736801001c543a3a4861736880000000000000000000000000000000000000000000000000000000000000000004702048617368206f66207468652070726576696f757320626c6f636b2e1844696765737401002c4469676573744f663c543e040004f020446967657374206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e184576656e747301008c5665633c4576656e745265636f72643c543a3a4576656e742c20543a3a486173683e3e040004a0204576656e7473206465706f736974656420666f72207468652063757272656e7420626c6f636b2e284576656e74436f756e740100284576656e74496e646578100000000004b820546865206e756d626572206f66206576656e747320696e2074686520604576656e74733c543e60206c6973742e2c4576656e74546f706963730101021c543a3a48617368845665633c28543a3a426c6f636b4e756d6265722c204576656e74496e646578293e000400282501204d617070696e67206265747765656e206120746f7069632028726570726573656e74656420627920543a3a486173682920616e64206120766563746f72206f6620696e646578657394206f66206576656e747320696e2074686520603c4576656e74733c543e3e60206c6973742e00510120416c6c20746f70696320766563746f727320686176652064657465726d696e69737469632073746f72616765206c6f636174696f6e7320646570656e64696e67206f6e2074686520746f7069632e2054686973450120616c6c6f7773206c696768742d636c69656e747320746f206c6576657261676520746865206368616e67657320747269652073746f7261676520747261636b696e67206d656368616e69736d20616e64e420696e2063617365206f66206368616e67657320666574636820746865206c697374206f66206576656e7473206f6620696e7465726573742e004d01205468652076616c756520686173207468652074797065206028543a3a426c6f636b4e756d6265722c204576656e74496e646578296020626563617573652069662077652075736564206f6e6c79206a7573744d012074686520604576656e74496e64657860207468656e20696e20636173652069662074686520746f70696320686173207468652073616d6520636f6e74656e7473206f6e20746865206e65787420626c6f636b0101206e6f206e6f74696669636174696f6e2077696c6c20626520747269676765726564207468757320746865206576656e74206d69676874206265206c6f73742e484c61737452756e74696d65557067726164650000584c61737452756e74696d6555706772616465496e666f04000455012053746f726573207468652060737065635f76657273696f6e6020616e642060737065635f6e616d6560206f66207768656e20746865206c6173742072756e74696d6520757067726164652068617070656e65642e545570677261646564546f553332526566436f756e74010010626f6f6c0400044d012054727565206966207765206861766520757067726164656420736f207468617420607479706520526566436f756e74602069732060753332602e2046616c7365202864656661756c7429206966206e6f742e605570677261646564546f547269706c65526566436f756e74010010626f6f6c0400085d012054727565206966207765206861766520757067726164656420736f2074686174204163636f756e74496e666f20636f6e7461696e73207468726565207479706573206f662060526566436f756e74602e2046616c736548202864656661756c7429206966206e6f742e38457865637574696f6e50686173650000145068617365040004882054686520657865637574696f6e207068617365206f662074686520626c6f636b2e01282866696c6c5f626c6f636b04185f726174696f1c50657262696c6c040901204120646973706174636820746861742077696c6c2066696c6c2074686520626c6f636b2077656967687420757020746f2074686520676976656e20726174696f2e1872656d61726b041c5f72656d61726b1c5665633c75383e146c204d616b6520736f6d65206f6e2d636861696e2072656d61726b2e002c2023203c7765696768743e24202d20604f28312960302023203c2f7765696768743e387365745f686561705f7061676573041470616765730c75363420fc2053657420746865206e756d626572206f6620706167657320696e2074686520576562417373656d626c7920656e7669726f6e6d656e74277320686561702e002c2023203c7765696768743e24202d20604f283129604c202d20312073746f726167652077726974652e64202d2042617365205765696768743a20312e34303520c2b57360202d203120777269746520746f20484541505f5041474553302023203c2f7765696768743e207365745f636f64650410636f64651c5665633c75383e28682053657420746865206e65772072756e74696d6520636f64652e002c2023203c7765696768743e3501202d20604f2843202b2053296020776865726520604360206c656e677468206f662060636f64656020616e642060536020636f6d706c6578697479206f66206063616e5f7365745f636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e7901202d20312063616c6c20746f206063616e5f7365745f636f6465603a20604f28532960202863616c6c73206073705f696f3a3a6d6973633a3a72756e74696d655f76657273696f6e6020776869636820697320657870656e73697665292e2c202d2031206576656e742e7d012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652c206275742067656e6572616c6c792074686973206973207665727920657870656e736976652e902057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f636f64655f776974686f75745f636865636b730410636f64651c5665633c75383e201d012053657420746865206e65772072756e74696d6520636f646520776974686f757420646f696e6720616e7920636865636b73206f662074686520676976656e2060636f6465602e002c2023203c7765696768743e90202d20604f2843296020776865726520604360206c656e677468206f662060636f64656088202d20312073746f726167652077726974652028636f64656320604f28432960292e2c202d2031206576656e742e75012054686520776569676874206f6620746869732066756e6374696f6e20697320646570656e64656e74206f6e207468652072756e74696d652e2057652077696c6c207472656174207468697320617320612066756c6c20626c6f636b2e302023203c2f7765696768743e5c7365745f6368616e6765735f747269655f636f6e666967044c6368616e6765735f747269655f636f6e666967804f7074696f6e3c4368616e67657354726965436f6e66696775726174696f6e3e28a02053657420746865206e6577206368616e676573207472696520636f6e66696775726174696f6e2e002c2023203c7765696768743e24202d20604f28312960b0202d20312073746f72616765207772697465206f722064656c6574652028636f64656320604f28312960292ed8202d20312063616c6c20746f20606465706f7369745f6c6f67603a20557365732060617070656e6460204150492c20736f204f28312964202d2042617365205765696768743a20372e32313820c2b57334202d204442205765696768743aa820202020202d205772697465733a204368616e67657320547269652c2053797374656d20446967657374302023203c2f7765696768743e2c7365745f73746f7261676504146974656d73345665633c4b657956616c75653e206c2053657420736f6d65206974656d73206f662073746f726167652e002c2023203c7765696768743e94202d20604f2849296020776865726520604960206c656e677468206f6620606974656d73607c202d206049602073746f72616765207772697465732028604f28312960292e74202d2042617365205765696768743a20302e353638202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e306b696c6c5f73746f7261676504106b657973205665633c4b65793e2078204b696c6c20736f6d65206974656d732066726f6d2073746f726167652e002c2023203c7765696768743efc202d20604f28494b296020776865726520604960206c656e677468206f6620606b6579736020616e6420604b60206c656e677468206f66206f6e65206b657964202d206049602073746f726167652064656c6574696f6e732e70202d2042617365205765696768743a202e333738202a206920c2b57368202d205772697465733a204e756d626572206f66206974656d73302023203c2f7765696768743e2c6b696c6c5f70726566697808187072656669780c4b6579205f7375626b6579730c7533322c1501204b696c6c20616c6c2073746f72616765206974656d7320776974682061206b657920746861742073746172747320776974682074686520676976656e207072656669782e003d01202a2a4e4f54453a2a2a2057652072656c79206f6e2074686520526f6f74206f726967696e20746f2070726f7669646520757320746865206e756d626572206f66207375626b65797320756e64657241012074686520707265666978207765206172652072656d6f76696e6720746f2061636375726174656c792063616c63756c6174652074686520776569676874206f6620746869732066756e6374696f6e2e002c2023203c7765696768743edc202d20604f285029602077686572652060506020616d6f756e74206f66206b65797320776974682070726566697820607072656669786064202d206050602073746f726167652064656c6574696f6e732e74202d2042617365205765696768743a20302e383334202a205020c2b57380202d205772697465733a204e756d626572206f66207375626b657973202b2031302023203c2f7765696768743e4472656d61726b5f776974685f6576656e74041872656d61726b1c5665633c75383e18a8204d616b6520736f6d65206f6e2d636861696e2072656d61726b20616e6420656d6974206576656e742e002c2023203c7765696768743eb8202d20604f28622960207768657265206220697320746865206c656e677468206f66207468652072656d61726b2e2c202d2031206576656e742e302023203c2f7765696768743e01184045787472696e7369635375636365737304304469737061746368496e666f04b820416e2065787472696e73696320636f6d706c65746564207375636365737366756c6c792e205c5b696e666f5c5d3c45787472696e7369634661696c6564083444697370617463684572726f72304469737061746368496e666f049420416e2065787472696e736963206661696c65642e205c5b6572726f722c20696e666f5c5d2c436f64655570646174656400045420603a636f6465602077617320757064617465642e284e65774163636f756e7404244163636f756e744964047c2041206e6577205c5b6163636f756e745c5d2077617320637265617465642e344b696c6c65644163636f756e7404244163636f756e744964046c20416e205c5b6163636f756e745c5d20776173207265617065642e2052656d61726b656408244163636f756e744964104861736804d4204f6e206f6e2d636861696e2072656d61726b2068617070656e65642e205c5b6f726967696e2c2072656d61726b5f686173685c5d1830426c6f636b57656967687473506c696d6974733a3a426c6f636b57656967687473850100f2052a0100000000204aa9d1010000405973070000000001c06e96a62e010000010098f73e5d010000010000000000000000405973070000000001c0f6e810a30100000100204aa9d1010000010088526a74000000405973070000000000000004d020426c6f636b20262065787472696e7369637320776569676874733a20626173652076616c75657320616e64206c696d6974732e2c426c6f636b4c656e6774684c6c696d6974733a3a426c6f636b4c656e6774683000003c00000050000000500004a820546865206d6178696d756d206c656e677468206f66206120626c6f636b2028696e206279746573292e38426c6f636b48617368436f756e7438543a3a426c6f636b4e756d6265721060090000045501204d6178696d756d206e756d626572206f6620626c6f636b206e756d62657220746f20626c6f636b2068617368206d617070696e677320746f206b65657020286f6c64657374207072756e6564206669727374292e2044625765696768743c52756e74696d6544625765696768744040787d010000000000e1f505000000000409012054686520776569676874206f662072756e74696d65206461746162617365206f7065726174696f6e73207468652072756e74696d652063616e20696e766f6b652e1c56657273696f6e3852756e74696d6556657273696f6e0503106e6f6465387375627374726174652d6e6f64650a0000000b0100000000000034df6acb689907609b0300000037e397fc7c91f5e40100000040fe3ad401f8959a05000000d2bc9897eed08f1503000000f78b278be53f454c02000000ed99c5acb25eedf502000000cbca25e39f14238702000000687ad44ad37f03c201000000bc9d89904f5b923f0100000068b66ba122c93fa70100000037c8bb1350a9a2a80100000091d5df18b0d2cf5801000000ab3c0572291feb8b01000000020000000484204765742074686520636861696e27732063757272656e742076657273696f6e2e28535335385072656669780c753136082a0014a8205468652064657369676e61746564205353383520707265666978206f66207468697320636861696e2e0039012054686973207265706c6163657320746865202273733538466f726d6174222070726f7065727479206465636c6172656420696e2074686520636861696e20737065632e20526561736f6e20697331012074686174207468652072756e74696d652073686f756c64206b6e6f772061626f7574207468652070726566697820696e206f7264657220746f206d616b6520757365206f662069742061737020616e206964656e746966696572206f662074686520636861696e2e143c496e76616c6964537065634e616d6508150120546865206e616d65206f662073706563696669636174696f6e20646f6573206e6f74206d61746368206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e685370656356657273696f6e4e65656473546f496e637265617365084501205468652073706563696669636174696f6e2076657273696f6e206973206e6f7420616c6c6f77656420746f206465637265617365206265747765656e207468652063757272656e742072756e74696d655420616e6420746865206e65772072756e74696d652e744661696c6564546f4578747261637452756e74696d6556657273696f6e0cf0204661696c656420746f2065787472616374207468652072756e74696d652076657273696f6e2066726f6d20746865206e65772072756e74696d652e000d01204569746865722063616c6c696e672060436f72655f76657273696f6e60206f72206465636f64696e67206052756e74696d6556657273696f6e60206661696c65642e4c4e6f6e44656661756c74436f6d706f7369746504010120537569636964652063616c6c6564207768656e20746865206163636f756e7420686173206e6f6e2d64656661756c7420636f6d706f7369746520646174612e3c4e6f6e5a65726f526566436f756e740439012054686572652069732061206e6f6e2d7a65726f207265666572656e636520636f756e742070726576656e74696e6720746865206163636f756e742066726f6d206265696e67207075726765642e001c5574696c69747900010c146261746368041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e48802053656e642061206261746368206f662064697370617463682063616c6c732e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e006101204966206f726967696e20697320726f6f74207468656e2063616c6c2061726520646973706174636820776974686f757420636865636b696e67206f726967696e2066696c7465722e20285468697320696e636c75646573cc20627970617373696e6720606672616d655f73797374656d3a3a436f6e6669673a3a4261736543616c6c46696c74657260292e002c2023203c7765696768743e0501202d20436f6d706c65786974793a204f284329207768657265204320697320746865206e756d626572206f662063616c6c7320746f20626520626174636865642e302023203c2f7765696768743e00590120546869732077696c6c2072657475726e20604f6b6020696e20616c6c2063697263756d7374616e6365732e20546f2064657465726d696e65207468652073756363657373206f66207468652062617463682c20616e3501206576656e74206973206465706f73697465642e20496620612063616c6c206661696c656420616e64207468652062617463682077617320696e7465727275707465642c207468656e20746865590120604261746368496e74657272757074656460206576656e74206973206465706f73697465642c20616c6f6e67207769746820746865206e756d626572206f66207375636365737366756c2063616c6c73206d616465510120616e6420746865206572726f72206f6620746865206661696c65642063616c6c2e20496620616c6c2077657265207375636365737366756c2c207468656e2074686520604261746368436f6d706c657465646050206576656e74206973206465706f73697465642e3461735f646572697661746976650814696e6465780c7531361063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e34e02053656e6420612063616c6c207468726f75676820616e20696e64657865642070736575646f6e796d206f66207468652073656e6465722e0059012046696c7465722066726f6d206f726967696e206172652070617373656420616c6f6e672e205468652063616c6c2077696c6c2062652064697370617463686564207769746820616e206f726967696e207768696368c020757365207468652073616d652066696c74657220617320746865206f726967696e206f6620746869732063616c6c2e004901204e4f54453a20496620796f75206e65656420746f20656e73757265207468617420616e79206163636f756e742d62617365642066696c746572696e67206973206e6f7420686f6e6f7265642028692e652e6501206265636175736520796f7520657870656374206070726f78796020746f2068617665206265656e2075736564207072696f7220696e207468652063616c6c20737461636b20616e6420796f7520646f206e6f742077616e745501207468652063616c6c207265737472696374696f6e7320746f206170706c7920746f20616e79207375622d6163636f756e7473292c207468656e20757365206061735f6d756c74695f7468726573686f6c645f31608020696e20746865204d756c74697369672070616c6c657420696e73746561642e00f8204e4f54453a205072696f7220746f2076657273696f6e202a31322c2074686973207761732063616c6c6564206061735f6c696d697465645f737562602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e2462617463685f616c6c041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e34f02053656e642061206261746368206f662064697370617463682063616c6c7320616e642061746f6d6963616c6c792065786563757465207468656d2e2501205468652077686f6c65207472616e73616374696f6e2077696c6c20726f6c6c6261636b20616e64206661696c20696620616e79206f66207468652063616c6c73206661696c65642e007c204d61792062652063616c6c65642066726f6d20616e79206f726967696e2e00f0202d206063616c6c73603a205468652063616c6c7320746f20626520646973706174636865642066726f6d207468652073616d65206f726967696e2e006101204966206f726967696e20697320726f6f74207468656e2063616c6c2061726520646973706174636820776974686f757420636865636b696e67206f726967696e2066696c7465722e20285468697320696e636c75646573cc20627970617373696e6720606672616d655f73797374656d3a3a436f6e6669673a3a4261736543616c6c46696c74657260292e002c2023203c7765696768743e0501202d20436f6d706c65786974793a204f284329207768657265204320697320746865206e756d626572206f662063616c6c7320746f20626520626174636865642e302023203c2f7765696768743e0108404261746368496e746572727570746564080c7533323444697370617463684572726f72085901204261746368206f66206469737061746368657320646964206e6f7420636f6d706c6574652066756c6c792e20496e646578206f66206669727374206661696c696e6720646973706174636820676976656e2c206173902077656c6c20617320746865206572726f722e205c5b696e6465782c206572726f725c5d384261746368436f6d706c657465640004cc204261746368206f66206469737061746368657320636f6d706c657465642066756c6c792077697468206e6f206572726f722e0000011042616265011042616265402845706f6368496e64657801000c75363420000000000000000004542043757272656e742065706f636820696e6465782e2c417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e0400046c2043757272656e742065706f636820617574686f7269746965732e2c47656e65736973536c6f74010010536c6f7420000000000000000008f82054686520736c6f74206174207768696368207468652066697273742065706f63682061637475616c6c7920737461727465642e205468697320697320309020756e74696c2074686520666972737420626c6f636b206f662074686520636861696e2e2c43757272656e74536c6f74010010536c6f7420000000000000000004542043757272656e7420736c6f74206e756d6265722e2852616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e65737380000000000000000000000000000000000000000000000000000000000000000028b8205468652065706f63682072616e646f6d6e65737320666f7220746865202a63757272656e742a2065706f63682e002c20232053656375726974790005012054686973204d555354204e4f54206265207573656420666f722067616d626c696e672c2061732069742063616e20626520696e666c75656e6365642062792061f8206d616c6963696f75732076616c696461746f7220696e207468652073686f7274207465726d2e204974204d4159206265207573656420696e206d616e7915012063727970746f677261706869632070726f746f636f6c732c20686f77657665722c20736f206c6f6e67206173206f6e652072656d656d6265727320746861742074686973150120286c696b652065766572797468696e6720656c7365206f6e2d636861696e29206974206973207075626c69632e20466f72206578616d706c652c2069742063616e206265050120757365642077686572652061206e756d626572206973206e656564656420746861742063616e6e6f742068617665206265656e2063686f73656e20627920616e0d01206164766572736172792c20666f7220707572706f7365732073756368206173207075626c69632d636f696e207a65726f2d6b6e6f776c656467652070726f6f66732e6050656e64696e6745706f6368436f6e6669674368616e67650000504e657874436f6e66696744657363726970746f7204000461012050656e64696e672065706f636820636f6e66696775726174696f6e206368616e676520746861742077696c6c206265206170706c696564207768656e20746865206e6578742065706f636820697320656e61637465642e384e65787452616e646f6d6e6573730100587363686e6f72726b656c3a3a52616e646f6d6e657373800000000000000000000000000000000000000000000000000000000000000000045c204e6578742065706f63682072616e646f6d6e6573732e3c4e657874417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e04000460204e6578742065706f636820617574686f7269746965732e305365676d656e74496e64657801000c7533321000000000247c2052616e646f6d6e65737320756e64657220636f6e737472756374696f6e2e00f4205765206d616b6520612074726164656f6666206265747765656e2073746f7261676520616363657373657320616e64206c697374206c656e6774682e01012057652073746f72652074686520756e6465722d636f6e737472756374696f6e2072616e646f6d6e65737320696e207365676d656e7473206f6620757020746f942060554e4445525f434f4e535452554354494f4e5f5345474d454e545f4c454e475448602e00ec204f6e63652061207365676d656e7420726561636865732074686973206c656e6774682c20776520626567696e20746865206e657874206f6e652e090120576520726573657420616c6c207365676d656e747320616e642072657475726e20746f206030602061742074686520626567696e6e696e67206f662065766572791c2065706f63682e44556e646572436f6e737472756374696f6e0101050c7533326c5665633c7363686e6f72726b656c3a3a52616e646f6d6e6573733e0004000415012054574f582d4e4f54453a20605365676d656e74496e6465786020697320616e20696e6372656173696e6720696e74656765722c20736f2074686973206973206f6b61792e2c496e697469616c697a656400003c4d6179626552616e646f6d6e65737304000801012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e292077686963682069732060536f6d65601d01206966207065722d626c6f636b20696e697469616c697a6174696f6e2068617320616c7265616479206265656e2063616c6c656420666f722063757272656e7420626c6f636b2e4c417574686f7256726652616e646f6d6e65737301003c4d6179626552616e646f6d6e65737304000c5d012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e29207468617420696e636c756465732074686520565246206f75747075742067656e6572617465645101206174207468697320626c6f636b2e2054686973206669656c642073686f756c6420616c7761797320626520706f70756c6174656420647572696e6720626c6f636b2070726f63657373696e6720756e6c6573731901207365636f6e6461727920706c61696e20736c6f74732061726520656e61626c65642028776869636820646f6e277420636f6e7461696e206120565246206f7574707574292e2845706f6368537461727401008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d62657229200000000000000000145d012054686520626c6f636b206e756d62657273207768656e20746865206c61737420616e642063757272656e742065706f6368206861766520737461727465642c20726573706563746976656c7920604e2d316020616e641420604e602e4901204e4f54453a20576520747261636b207468697320697320696e206f7264657220746f20616e6e6f746174652074686520626c6f636b206e756d626572207768656e206120676976656e20706f6f6c206f66590120656e74726f7079207761732066697865642028692e652e20697420776173206b6e6f776e20746f20636861696e206f6273657276657273292e2053696e63652065706f6368732061726520646566696e656420696e590120736c6f74732c207768696368206d617920626520736b69707065642c2074686520626c6f636b206e756d62657273206d6179206e6f74206c696e6520757020776974682074686520736c6f74206e756d626572732e204c6174656e657373010038543a3a426c6f636b4e756d626572100000000014d820486f77206c617465207468652063757272656e7420626c6f636b20697320636f6d706172656420746f2069747320706172656e742e001501205468697320656e74727920697320706f70756c617465642061732070617274206f6620626c6f636b20657865637574696f6e20616e6420697320636c65616e65642075701101206f6e20626c6f636b2066696e616c697a6174696f6e2e205175657279696e6720746869732073746f7261676520656e747279206f757473696465206f6620626c6f636bb020657865637574696f6e20636f6e746578742073686f756c6420616c77617973207969656c64207a65726f2e2c45706f6368436f6e6669670000584261626545706f6368436f6e66696775726174696f6e04000485012054686520636f6e66696775726174696f6e20666f72207468652063757272656e742065706f63682e2053686f756c64206e6576657220626520604e6f6e656020617320697420697320696e697469616c697a656420696e2067656e657369732e3c4e65787445706f6368436f6e6669670000584261626545706f6368436f6e66696775726174696f6e0400082d012054686520636f6e66696775726174696f6e20666f7220746865206e6578742065706f63682c20604e6f6e65602069662074686520636f6e6669672077696c6c206e6f74206368616e6765e82028796f752063616e2066616c6c6261636b20746f206045706f6368436f6e6669676020696e737465616420696e20746861742063617365292e010c4c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f667045717569766f636174696f6e50726f6f663c543a3a4865616465723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66200d01205265706f727420617574686f726974792065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c207665726966790901207468652065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66110120616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e63652077696c6c34206265207265706f727465642e110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e48706c616e5f636f6e6669675f6368616e67650418636f6e666967504e657874436f6e66696744657363726970746f7210610120506c616e20616e2065706f636820636f6e666967206368616e67652e205468652065706f636820636f6e666967206368616e6765206973207265636f7264656420616e642077696c6c20626520656e6163746564206f6e550120746865206e6578742063616c6c20746f2060656e6163745f65706f63685f6368616e6765602e2054686520636f6e6669672077696c6c20626520616374697661746564206f6e652065706f63682061667465722e5d01204d756c7469706c652063616c6c7320746f2074686973206d6574686f642077696c6c207265706c61636520616e79206578697374696e6720706c616e6e656420636f6e666967206368616e676520746861742068616458206e6f74206265656e20656e6163746564207965742e00083445706f63684475726174696f6e0c75363420c8000000000000000cec2054686520616d6f756e74206f662074696d652c20696e20736c6f74732c207468617420656163682065706f63682073686f756c64206c6173742e1901204e4f54453a2043757272656e746c79206974206973206e6f7420706f737369626c6520746f206368616e6765207468652065706f6368206475726174696f6e20616674657221012074686520636861696e2068617320737461727465642e20417474656d7074696e6720746f20646f20736f2077696c6c20627269636b20626c6f636b2070726f64756374696f6e2e444578706563746564426c6f636b54696d6524543a3a4d6f6d656e7420b80b00000000000014050120546865206578706563746564206176657261676520626c6f636b2074696d6520617420776869636820424142452073686f756c64206265206372656174696e67110120626c6f636b732e2053696e636520424142452069732070726f626162696c6973746963206974206973206e6f74207472697669616c20746f20666967757265206f75740501207768617420746865206578706563746564206176657261676520626c6f636b2074696d652073686f756c64206265206261736564206f6e2074686520736c6f740901206475726174696f6e20616e642074686520736563757269747920706172616d657465722060636020287768657265206031202d20636020726570726573656e7473a0207468652070726f626162696c697479206f66206120736c6f74206265696e6720656d707479292e0c60496e76616c696445717569766f636174696f6e50726f6f6604350120416e2065717569766f636174696f6e2070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e60496e76616c69644b65794f776e65727368697050726f6f660435012041206b6579206f776e6572736869702070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e584475706c69636174654f6666656e63655265706f7274041901204120676976656e2065717569766f636174696f6e207265706f72742069732076616c69642062757420616c72656164792070726576696f75736c79207265706f727465642e022454696d657374616d70012454696d657374616d70080c4e6f77010024543a3a4d6f6d656e7420000000000000000004902043757272656e742074696d6520666f72207468652063757272656e7420626c6f636b2e24446964557064617465010010626f6f6c040004b420446964207468652074696d657374616d7020676574207570646174656420696e207468697320626c6f636b3f01040c736574040c6e6f7748436f6d706163743c543a3a4d6f6d656e743e3c5820536574207468652063757272656e742074696d652e00590120546869732063616c6c2073686f756c6420626520696e766f6b65642065786163746c79206f6e63652070657220626c6f636b2e2049742077696c6c2070616e6963206174207468652066696e616c697a6174696f6ed82070686173652c20696620746869732063616c6c206861736e2774206265656e20696e766f6b656420627920746861742074696d652e004501205468652074696d657374616d702073686f756c642062652067726561746572207468616e207468652070726576696f7573206f6e652062792074686520616d6f756e74207370656369666965642062794420604d696e696d756d506572696f64602e00d820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060496e686572656e74602e002c2023203c7765696768743e3501202d20604f2831296020284e6f7465207468617420696d706c656d656e746174696f6e73206f6620604f6e54696d657374616d7053657460206d75737420616c736f20626520604f2831296029a101202d20312073746f72616765207265616420616e6420312073746f72616765206d75746174696f6e2028636f64656320604f28312960292e202862656361757365206f6620604469645570646174653a3a74616b656020696e20606f6e5f66696e616c697a656029d8202d2031206576656e742068616e646c657220606f6e5f74696d657374616d705f736574602e204d75737420626520604f283129602e302023203c2f7765696768743e0004344d696e696d756d506572696f6424543a3a4d6f6d656e7420dc0500000000000010690120546865206d696e696d756d20706572696f64206265747765656e20626c6f636b732e204265776172652074686174207468697320697320646966666572656e7420746f20746865202a65787065637465642a20706572696f64690120746861742074686520626c6f636b2070726f64756374696f6e206170706172617475732070726f76696465732e20596f75722063686f73656e20636f6e73656e7375732073797374656d2077696c6c2067656e6572616c6c79650120776f726b2077697468207468697320746f2064657465726d696e6520612073656e7369626c6520626c6f636b2074696d652e20652e672e20466f7220417572612c2069742077696c6c20626520646f75626c6520746869737020706572696f64206f6e2064656661756c742073657474696e67732e000328417574686f72736869700128417574686f72736869700c18556e636c65730100e85665633c556e636c65456e7472794974656d3c543a3a426c6f636b4e756d6265722c20543a3a486173682c20543a3a4163636f756e7449643e3e0400041c20556e636c657318417574686f72000030543a3a4163636f756e7449640400046420417574686f72206f662063757272656e7420626c6f636b2e30446964536574556e636c6573010010626f6f6c040004bc205768657468657220756e636c6573207765726520616c72656164792073657420696e207468697320626c6f636b2e0104287365745f756e636c657304286e65775f756e636c6573385665633c543a3a4865616465723e04642050726f76696465206120736574206f6620756e636c65732e00001c48496e76616c6964556e636c65506172656e74048c2054686520756e636c6520706172656e74206e6f7420696e2074686520636861696e2e40556e636c6573416c7265616479536574048420556e636c657320616c72656164792073657420696e2074686520626c6f636b2e34546f6f4d616e79556e636c6573044420546f6f206d616e7920756e636c65732e3047656e65736973556e636c6504582054686520756e636c652069732067656e657369732e30546f6f48696768556e636c6504802054686520756e636c6520697320746f6f206869676820696e20636861696e2e50556e636c65416c7265616479496e636c75646564047c2054686520756e636c6520697320616c726561647920696e636c756465642e204f6c64556e636c6504b82054686520756e636c652069736e277420726563656e7420656e6f75676820746f20626520696e636c756465642e041c496e6469636573011c496e646963657304204163636f756e74730001023c543a3a4163636f756e74496e6465788828543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20626f6f6c29000400048820546865206c6f6f6b75702066726f6d20696e64657820746f206163636f756e742e011414636c61696d0414696e6465783c543a3a4163636f756e74496e646578489c2041737369676e20616e2070726576696f75736c7920756e61737369676e656420696e6465782e00e0205061796d656e743a20604465706f736974602069732072657365727665642066726f6d207468652073656e646572206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e00f4202d2060696e646578603a2074686520696e64657820746f20626520636c61696d65642e2054686973206d757374206e6f7420626520696e207573652e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e207472616e73666572080c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e6465785061012041737369676e20616e20696e64657820616c7265616479206f776e6564206279207468652073656e64657220746f20616e6f74686572206163636f756e742e205468652062616c616e6365207265736572766174696f6ebc206973206566666563746976656c79207472616e7366657272656420746f20746865206e6577206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002901202d2060696e646578603a2074686520696e64657820746f2062652072652d61737369676e65642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e68202d204f6e65207472616e73666572206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743ae4202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429e8202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e742028726563697069656e7429302023203c2f7765696768743e10667265650414696e6465783c543a3a4163636f756e74496e6465784898204672656520757020616e20696e646578206f776e6564206279207468652073656e6465722e006101205061796d656e743a20416e792070726576696f7573206465706f73697420706c6163656420666f722074686520696e64657820697320756e726573657276656420696e207468652073656e646572206163636f756e742e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206f776e2074686520696e6465782e001101202d2060696e646578603a2074686520696e64657820746f2062652066726565642e2054686973206d757374206265206f776e6564206279207468652073656e6465722e008820456d6974732060496e646578467265656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e64202d204f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e38666f7263655f7472616e736665720c0c6e657730543a3a4163636f756e74496414696e6465783c543a3a4163636f756e74496e64657818667265657a6510626f6f6c54590120466f72636520616e20696e64657820746f20616e206163636f756e742e205468697320646f65736e277420726571756972652061206465706f7369742e2049662074686520696e64657820697320616c7265616479ec2068656c642c207468656e20616e79206465706f736974206973207265696d62757273656420746f206974732063757272656e74206f776e65722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00a8202d2060696e646578603a2074686520696e64657820746f206265202872652d2961737369676e65642e6101202d20606e6577603a20746865206e6577206f776e6572206f662074686520696e6465782e20546869732066756e6374696f6e2069732061206e6f2d6f7020696620697420697320657175616c20746f2073656e6465722e4501202d2060667265657a65603a2069662073657420746f206074727565602c2077696c6c20667265657a652074686520696e64657820736f2069742063616e6e6f74206265207472616e736665727265642e009420456d6974732060496e64657841737369676e656460206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e7c202d20557020746f206f6e652072657365727665206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743af8202020202d2052656164733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229fc202020202d205772697465733a20496e6469636573204163636f756e74732c2053797374656d204163636f756e7420286f726967696e616c206f776e657229302023203c2f7765696768743e18667265657a650414696e6465783c543a3a4163636f756e74496e64657844690120467265657a6520616e20696e64657820736f2069742077696c6c20616c7761797320706f696e7420746f207468652073656e646572206163636f756e742e205468697320636f6e73756d657320746865206465706f7369742e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d7573742068617665206170206e6f6e2d66726f7a656e206163636f756e742060696e646578602e00b0202d2060696e646578603a2074686520696e64657820746f2062652066726f7a656e20696e20706c6163652e008c20456d6974732060496e64657846726f7a656e60206966207375636365737366756c2e002c2023203c7765696768743e28202d20604f283129602e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28312960292e74202d20557020746f206f6e6520736c617368206f7065726174696f6e2e34202d204f6e65206576656e742e50202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d94202d204442205765696768743a203120526561642f577269746520284163636f756e747329302023203c2f7765696768743e010c34496e64657841737369676e656408244163636f756e744964304163636f756e74496e64657804b42041206163636f756e7420696e646578207761732061737369676e65642e205c5b696e6465782c2077686f5c5d28496e646578467265656404304163636f756e74496e64657804e82041206163636f756e7420696e64657820686173206265656e2066726565642075702028756e61737369676e6564292e205c5b696e6465785c5d2c496e64657846726f7a656e08304163636f756e74496e646578244163636f756e7449640429012041206163636f756e7420696e64657820686173206265656e2066726f7a656e20746f206974732063757272656e74206163636f756e742049442e205c5b696e6465782c2077686f5c5d041c4465706f7369743042616c616e63654f663c543e4000407a10f35a0000000000000000000004ac20546865206465706f736974206e656564656420666f7220726573657276696e6720616e20696e6465782e142c4e6f7441737369676e656404902054686520696e64657820776173206e6f7420616c72656164792061737369676e65642e204e6f744f776e657204a82054686520696e6465782069732061737369676e656420746f20616e6f74686572206163636f756e742e14496e55736504742054686520696e64657820776173206e6f7420617661696c61626c652e2c4e6f745472616e7366657204cc2054686520736f7572636520616e642064657374696e6174696f6e206163636f756e747320617265206964656e746963616c2e245065726d616e656e7404d42054686520696e646578206973207065726d616e656e7420616e64206d6179206e6f742062652066726565642f6368616e6765642e052042616c616e636573012042616c616e6365731434546f74616c49737375616e6365010028543a3a42616c616e6365400000000000000000000000000000000004982054686520746f74616c20756e6974732069737375656420696e207468652073797374656d2e1c4163636f756e7401010230543a3a4163636f756e7449645c4163636f756e74446174613c543a3a42616c616e63653e000101000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c6c205468652062616c616e6365206f6620616e206163636f756e742e004101204e4f54453a2054686973206973206f6e6c79207573656420696e207468652063617365207468617420746869732070616c6c6574206973207573656420746f2073746f72652062616c616e6365732e144c6f636b7301010230543a3a4163636f756e744964d05765616b426f756e6465645665633c42616c616e63654c6f636b3c543a3a42616c616e63653e2c20543a3a4d61784c6f636b733e00040008b820416e79206c6971756964697479206c6f636b73206f6e20736f6d65206163636f756e742062616c616e6365732e2501204e4f54453a2053686f756c64206f6e6c79206265206163636573736564207768656e2073657474696e672c206368616e67696e6720616e642066726565696e672061206c6f636b2e20526573657276657301010230543a3a4163636f756e7449642901426f756e6465645665633c52657365727665446174613c543a3a526573657276654964656e7469666965722c20543a3a42616c616e63653e2c20543a3a0a4d617852657365727665733e00040004a4204e616d6564207265736572766573206f6e20736f6d65206163636f756e742062616c616e6365732e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076322e302e3020666f72206e6577206e6574776f726b732e0114207472616e736665720810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e6cd8205472616e7366657220736f6d65206c697175696420667265652062616c616e636520746f20616e6f74686572206163636f756e742e00090120607472616e73666572602077696c6c207365742074686520604672656542616c616e636560206f66207468652073656e64657220616e642072656365697665722e21012049742077696c6c2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d2062792074686520605472616e73666572466565602e1501204966207468652073656e6465722773206163636f756e742069732062656c6f7720746865206578697374656e7469616c206465706f736974206173206120726573756c74b4206f6620746865207472616e736665722c20746865206163636f756e742077696c6c206265207265617065642e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605369676e65646020627920746865207472616e736163746f722e002c2023203c7765696768743e3101202d20446570656e64656e74206f6e20617267756d656e747320627574206e6f7420637269746963616c2c20676976656e2070726f70657220696d706c656d656e746174696f6e7320666f72cc202020696e70757420636f6e6669672074797065732e205365652072656c617465642066756e6374696f6e732062656c6f772e6901202d20497420636f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e642077726974657320696e7465726e616c6c7920616e64206e6f20636f6d706c657820636f6d7075746174696f6e2e004c2052656c617465642066756e6374696f6e733a0051012020202d2060656e737572655f63616e5f77697468647261776020697320616c776179732063616c6c656420696e7465726e616c6c792062757420686173206120626f756e64656420636f6d706c65786974792e2d012020202d205472616e7366657272696e672062616c616e63657320746f206163636f756e7473207468617420646964206e6f74206578697374206265666f72652077696c6c206361757365d420202020202060543a3a4f6e4e65774163636f756e743a3a6f6e5f6e65775f6163636f756e746020746f2062652063616c6c65642e61012020202d2052656d6f76696e6720656e6f7567682066756e64732066726f6d20616e206163636f756e742077696c6c20747269676765722060543a3a4475737452656d6f76616c3a3a6f6e5f756e62616c616e636564602e49012020202d20607472616e736665725f6b6565705f616c6976656020776f726b73207468652073616d652077617920617320607472616e73666572602c206275742068617320616e206164646974696f6e616cf82020202020636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c20746865206f726967696e206163636f756e742e88202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d4501202d2042617365205765696768743a2037332e363420c2b5732c20776f7273742063617365207363656e6172696f20286163636f756e7420637265617465642c206163636f756e742072656d6f76656429dc202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374696e6174696f6e206163636f756e741501202d204f726967696e206163636f756e7420697320616c726561647920696e206d656d6f72792c20736f206e6f204442206f7065726174696f6e7320666f72207468656d2e302023203c2f7765696768743e2c7365745f62616c616e63650c0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365206e65775f667265654c436f6d706163743c543a3a42616c616e63653e306e65775f72657365727665644c436f6d706163743c543a3a42616c616e63653e489420536574207468652062616c616e636573206f66206120676976656e206163636f756e742e00210120546869732077696c6c20616c74657220604672656542616c616e63656020616e642060526573657276656442616c616e63656020696e2073746f726167652e2069742077696c6c090120616c736f2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d202860546f74616c49737375616e636560292e190120496620746865206e65772066726565206f722072657365727665642062616c616e63652069732062656c6f7720746865206578697374656e7469616c206465706f7369742c01012069742077696c6c20726573657420746865206163636f756e74206e6f6e63652028606672616d655f73797374656d3a3a4163636f756e744e6f6e636560292e00b420546865206469737061746368206f726967696e20666f7220746869732063616c6c2069732060726f6f74602e002c2023203c7765696768743e80202d20496e646570656e64656e74206f662074686520617267756d656e74732ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e58202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d3c202d2042617365205765696768743a6820202020202d204372656174696e673a2032372e353620c2b5736420202020202d204b696c6c696e673a2033352e313120c2b57398202d204442205765696768743a203120526561642c203120577269746520746f206077686f60302023203c2f7765696768743e38666f7263655f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e1851012045786163746c7920617320607472616e73666572602c2065786365707420746865206f726967696e206d75737420626520726f6f7420616e642074686520736f75726365206163636f756e74206d61792062652c207370656369666965642e2c2023203c7765696768743e4101202d2053616d65206173207472616e736665722c20627574206164646974696f6e616c207265616420616e6420777269746520626563617573652074686520736f75726365206163636f756e74206973902020206e6f7420617373756d656420746f20626520696e20746865206f7665726c61792e302023203c2f7765696768743e4c7472616e736665725f6b6565705f616c6976650810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e2c51012053616d6520617320746865205b607472616e73666572605d2063616c6c2c206275742077697468206120636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c2074686540206f726967696e206163636f756e742e00bc20393925206f66207468652074696d6520796f752077616e74205b607472616e73666572605d20696e73746561642e00c4205b607472616e73666572605d3a207374727563742e50616c6c65742e68746d6c236d6574686f642e7472616e736665722c2023203c7765696768743ee8202d2043686561706572207468616e207472616e736665722062656361757365206163636f756e742063616e6e6f74206265206b696c6c65642e60202d2042617365205765696768743a2035312e3420c2b5731d01202d204442205765696768743a2031205265616420616e64203120577269746520746f2064657374202873656e64657220697320696e206f7665726c617920616c7265616479292c20233c2f7765696768743e307472616e736665725f616c6c0810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365286b6565705f616c69766510626f6f6c480901205472616e736665722074686520656e74697265207472616e7366657261626c652062616c616e63652066726f6d207468652063616c6c6572206163636f756e742e005d01204e4f54453a20546869732066756e6374696f6e206f6e6c7920617474656d70747320746f207472616e73666572205f7472616e7366657261626c655f2062616c616e6365732e2054686973206d65616e732074686174650120616e79206c6f636b65642c2072657365727665642c206f72206578697374656e7469616c206465706f7369747320287768656e20606b6565705f616c6976656020697320607472756560292c2077696c6c206e6f742062656101207472616e7366657272656420627920746869732066756e6374696f6e2e20546f20656e73757265207468617420746869732066756e6374696f6e20726573756c747320696e2061206b696c6c6564206163636f756e742c490120796f75206d69676874206e65656420746f207072657061726520746865206163636f756e742062792072656d6f76696e6720616e79207265666572656e636520636f756e746572732c2073746f7261676544206465706f736974732c206574632e2e2e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205369676e65642e00a4202d206064657374603a2054686520726563697069656e74206f6620746865207472616e736665722e5d01202d20606b6565705f616c697665603a204120626f6f6c65616e20746f2064657465726d696e652069662074686520607472616e736665725f616c6c60206f7065726174696f6e2073686f756c642073656e6420616c6c51012020206f66207468652066756e647320746865206163636f756e74206861732c2063617573696e67207468652073656e646572206163636f756e7420746f206265206b696c6c6564202866616c7365292c206f725d012020207472616e736665722065766572797468696e6720657863657074206174206c6561737420746865206578697374656e7469616c206465706f7369742c2077686963682077696c6c2067756172616e74656520746fa02020206b656570207468652073656e646572206163636f756e7420616c697665202874727565292e3420202023203c7765696768743e3d01202d204f2831292e204a757374206c696b65207472616e736665722c206275742072656164696e672074686520757365722773207472616e7366657261626c652062616c616e63652066697273742e34202020233c2f7765696768743e01201c456e646f77656408244163636f756e7449641c42616c616e636504250120416e206163636f756e74207761732063726561746564207769746820736f6d6520667265652062616c616e63652e205c5b6163636f756e742c20667265655f62616c616e63655c5d20447573744c6f737408244163636f756e7449641c42616c616e636508410120416e206163636f756e74207761732072656d6f7665642077686f73652062616c616e636520776173206e6f6e2d7a65726f206275742062656c6f77204578697374656e7469616c4465706f7369742cd020726573756c74696e6720696e20616e206f75747269676874206c6f73732e205c5b6163636f756e742c2062616c616e63655c5d205472616e736665720c244163636f756e744964244163636f756e7449641c42616c616e636504a0205472616e73666572207375636365656465642e205c5b66726f6d2c20746f2c2076616c75655c5d2842616c616e63655365740c244163636f756e7449641c42616c616e63651c42616c616e636504cc20412062616c616e6365207761732073657420627920726f6f742e205c5b77686f2c20667265652c2072657365727665645c5d1c4465706f73697408244163636f756e7449641c42616c616e636504210120536f6d6520616d6f756e7420776173206465706f73697465642028652e672e20666f72207472616e73616374696f6e2066656573292e205c5b77686f2c206465706f7369745c5d20526573657276656408244163636f756e7449641c42616c616e636504210120536f6d652062616c616e63652077617320726573657276656420286d6f7665642066726f6d206672656520746f207265736572766564292e205c5b77686f2c2076616c75655c5d28556e726573657276656408244163636f756e7449641c42616c616e636504290120536f6d652062616c616e63652077617320756e726573657276656420286d6f7665642066726f6d20726573657276656420746f2066726565292e205c5b77686f2c2076616c75655c5d4852657365727665526570617472696174656410244163636f756e744964244163636f756e7449641c42616c616e6365185374617475730c510120536f6d652062616c616e636520776173206d6f7665642066726f6d207468652072657365727665206f6620746865206669727374206163636f756e7420746f20746865207365636f6e64206163636f756e742edc2046696e616c20617267756d656e7420696e64696361746573207468652064657374696e6174696f6e2062616c616e636520747970652ea8205c5b66726f6d2c20746f2c2062616c616e63652c2064657374696e6174696f6e5f7374617475735c5d04484578697374656e7469616c4465706f73697428543a3a42616c616e63654000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f206b65657020616e206163636f756e74206f70656e2e203856657374696e6742616c616e6365049c2056657374696e672062616c616e636520746f6f206869676820746f2073656e642076616c7565544c69717569646974795265737472696374696f6e7304c8204163636f756e74206c6971756964697479207265737472696374696f6e732070726576656e74207769746864726177616c4c496e73756666696369656e7442616c616e636504782042616c616e636520746f6f206c6f7720746f2073656e642076616c7565484578697374656e7469616c4465706f73697404ec2056616c756520746f6f206c6f7720746f20637265617465206163636f756e742064756520746f206578697374656e7469616c206465706f736974244b656570416c6976650490205472616e736665722f7061796d656e7420776f756c64206b696c6c206163636f756e745c4578697374696e6756657374696e675363686564756c6504cc20412076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e742c446561644163636f756e74048c2042656e6566696369617279206163636f756e74206d757374207072652d65786973743c546f6f4d616e79526573657276657304b0204e756d626572206f66206e616d656420726573657276657320657863656564204d6178526573657276657306485472616e73616374696f6e5061796d656e7401485472616e73616374696f6e5061796d656e7408444e6578744665654d756c7469706c6965720100284d756c7469706c69657240000064a7b3b6e00d0000000000000000003853746f7261676556657273696f6e01002052656c6561736573040000000008485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e2c576569676874546f466565a45665633c576569676874546f466565436f656666696369656e743c42616c616e63654f663c543e3e3e5c0401000000000000000000000000000000000000000001040d012054686520706f6c796e6f6d69616c2074686174206973206170706c69656420696e206f7264657220746f20646572697665206665652066726f6d207765696768742e000768456c656374696f6e50726f76696465724d756c746950686173650168456c656374696f6e50726f76696465724d756c746950686173652814526f756e6401000c753332100100000018ac20496e7465726e616c20636f756e74657220666f7220746865206e756d626572206f6620726f756e64732e00550120546869732069732075736566756c20666f722064652d6475706c69636174696f6e206f66207472616e73616374696f6e73207375626d697474656420746f2074686520706f6f6c2c20616e642067656e6572616c6c20646961676e6f7374696373206f66207468652070616c6c65742e004d012054686973206973206d6572656c7920696e6372656d656e746564206f6e6365207065722065766572792074696d65207468617420616e20757073747265616d2060656c656374602069732063616c6c65642e3043757272656e74506861736501005450686173653c543a3a426c6f636b4e756d6265723e0400043c2043757272656e742070686173652e38517565756564536f6c7574696f6e00006c5265616479536f6c7574696f6e3c543a3a4163636f756e7449643e0400043d012043757272656e74206265737420736f6c7574696f6e2c207369676e6564206f7220756e7369676e65642c2071756575656420746f2062652072657475726e65642075706f6e2060656c656374602e20536e617073686f7400006c526f756e64536e617073686f743c543a3a4163636f756e7449643e04000c7020536e617073686f742064617461206f662074686520726f756e642e005d01205468697320697320637265617465642061742074686520626567696e6e696e67206f6620746865207369676e656420706861736520616e6420636c65617265642075706f6e2063616c6c696e672060656c656374602e38446573697265645461726765747300000c75333204000ccc2044657369726564206e756d626572206f66207461726765747320746f20656c65637420666f72207468697320726f756e642e00a8204f6e6c7920657869737473207768656e205b60536e617073686f74605d2069732070726573656e742e40536e617073686f744d65746164617461000058536f6c7574696f6e4f72536e617073686f7453697a6504000c9820546865206d65746164617461206f6620746865205b60526f756e64536e617073686f74605d00a8204f6e6c7920657869737473207768656e205b60536e617073686f74605d2069732070726573656e742e645369676e65645375626d697373696f6e4e657874496e64657801000c753332100000000024010120546865206e65787420696e64657820746f2062652061737369676e656420746f20616e20696e636f6d696e67207369676e6564207375626d697373696f6e2e007501204576657279206163636570746564207375626d697373696f6e2069732061737369676e6564206120756e6971756520696e6465783b207468617420696e64657820697320626f756e6420746f207468617420706172746963756c61726501207375626d697373696f6e20666f7220746865206475726174696f6e206f662074686520656c656374696f6e2e204f6e20656c656374696f6e2066696e616c697a6174696f6e2c20746865206e65787420696e6465782069733020726573657420746f20302e0069012057652063616e2774206a7573742075736520605369676e65645375626d697373696f6e496e64696365732e6c656e2829602c206265636175736520746861742773206120626f756e646564207365743b20706173742069747359012063617061636974792c2069742077696c6c2073696d706c792073617475726174652e2057652063616e2774206a7573742069746572617465206f76657220605369676e65645375626d697373696f6e734d6170602cf4206265636175736520697465726174696f6e20697320736c6f772e20496e73746561642c2077652073746f7265207468652076616c756520686572652e5c5369676e65645375626d697373696f6e496e64696365730100585375626d697373696f6e496e64696365734f663c543e0400184d01204120736f727465642c20626f756e64656420736574206f6620602873636f72652c20696e64657829602c20776865726520656163682060696e6465786020706f696e747320746f20612076616c756520696e5420605369676e65645375626d697373696f6e73602e007101205765206e65766572206e65656420746f2070726f63657373206d6f7265207468616e20612073696e676c65207369676e6564207375626d697373696f6e20617420612074696d652e205369676e6564207375626d697373696f6e7375012063616e206265207175697465206c617267652c20736f2077652772652077696c6c696e6720746f207061792074686520636f7374206f66206d756c7469706c6520646174616261736520616363657373657320746f206163636573732101207468656d206f6e6520617420612074696d6520696e7374656164206f662072656164696e6720616e64206465636f64696e6720616c6c206f66207468656d206174206f6e63652e505369676e65645375626d697373696f6e734d61700101050c753332545369676e65645375626d697373696f6e4f663c543e00d10100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000001c7420556e636865636b65642c207369676e656420736f6c7574696f6e732e00690120546f676574686572207769746820605375626d697373696f6e496e6469636573602c20746869732073746f726573206120626f756e64656420736574206f6620605369676e65645375626d697373696f6e7360207768696c65ec20616c6c6f77696e6720757320746f206b656570206f6e6c7920612073696e676c65206f6e6520696e206d656d6f727920617420612074696d652e0069012054776f78206e6f74653a20746865206b6579206f6620746865206d617020697320616e206175746f2d696e6372656d656e74696e6720696e6465782077686963682075736572732063616e6e6f7420696e7370656374206f72f4206166666563743b2077652073686f756c646e2774206e65656420612063727970746f67726170686963616c6c7920736563757265206861736865722e544d696e696d756d556e7472757374656453636f7265000034456c656374696f6e53636f72650400105d0120546865206d696e696d756d2073636f7265207468617420656163682027756e747275737465642720736f6c7574696f6e206d7573742061747461696e20696e206f7264657220746f20626520636f6e7369646572656428206665617369626c652e00b82043616e206265207365742076696120607365745f6d696e696d756d5f756e747275737465645f73636f7265602e01103c7375626d69745f756e7369676e65640820736f6c7574696f6e64526177536f6c7574696f6e3c436f6d706163744f663c543e3e1c7769746e65737358536f6c7574696f6e4f72536e617073686f7453697a6538a8205375626d6974206120736f6c7574696f6e20666f722074686520756e7369676e65642070686173652e00cc20546865206469737061746368206f726967696e20666f20746869732063616c6c206d757374206265205f5f6e6f6e655f5f2e0041012054686973207375626d697373696f6e20697320636865636b6564206f6e2074686520666c792e204d6f72656f7665722c207468697320756e7369676e656420736f6c7574696f6e206973206f6e6c7959012076616c696461746564207768656e207375626d697474656420746f2074686520706f6f6c2066726f6d20746865202a2a6c6f63616c2a2a206e6f64652e204566666563746976656c792c2074686973206d65616e7361012074686174206f6e6c79206163746976652076616c696461746f72732063616e207375626d69742074686973207472616e73616374696f6e207768656e20617574686f72696e67206120626c6f636b202873696d696c61724420746f20616e20696e686572656e74292e005d0120546f2070726576656e7420616e7920696e636f727265637420736f6c7574696f6e2028616e642074687573207761737465642074696d652f776569676874292c2074686973207472616e73616374696f6e2077696c6c51012070616e69632069662074686520736f6c7574696f6e207375626d6974746564206279207468652076616c696461746f7220697320696e76616c696420696e20616e79207761792c206566666563746976656c79a02070757474696e6720746865697220617574686f72696e6720726577617264206174207269736b2e00e4204e6f206465706f736974206f7220726577617264206973206173736f63696174656420776974682074686973207375626d697373696f6e2e6c7365745f6d696e696d756d5f756e747275737465645f73636f726504406d617962655f6e6578745f73636f7265544f7074696f6e3c456c656374696f6e53636f72653e14b4205365742061206e65772076616c756520666f7220604d696e696d756d556e7472757374656453636f7265602e00dc204469737061746368206f726967696e206d75737420626520616c69676e656420776974682060543a3a466f7263654f726967696e602e00f4205468697320636865636b2063616e206265207475726e6564206f66662062792073657474696e67207468652076616c756520746f20604e6f6e65602e747365745f656d657267656e63795f656c656374696f6e5f726573756c740420736f6c7574696f6e6c5265616479536f6c7574696f6e3c543a3a4163636f756e7449643e205d0120536574206120736f6c7574696f6e20696e207468652071756575652c20746f2062652068616e646564206f757420746f2074686520636c69656e74206f6620746869732070616c6c657420696e20746865206e6578748c2063616c6c20746f2060456c656374696f6e50726f76696465723a3a656c656374602e00490120546869732063616e206f6e6c79206265207365742062792060543a3a466f7263654f726967696e602c20616e64206f6e6c79207768656e207468652070686173652069732060456d657267656e6379602e0065012054686520736f6c7574696f6e206973206e6f7420636865636b656420666f7220616e7920666561736962696c69747920616e6420697320617373756d656420746f206265207472757374776f727468792c20617320616e79550120666561736962696c69747920636865636b20697473656c662063616e20696e207072696e6369706c652063617573652074686520656c656374696f6e2070726f6365737320746f206661696c202864756520746f6c206d656d6f72792f77656967687420636f6e73747261696e73292e187375626d69740820736f6c7574696f6e64526177536f6c7574696f6e3c436f6d706163744f663c543e3e586e756d5f7369676e65645f7375626d697373696f6e730c75333234a0205375626d6974206120736f6c7574696f6e20666f7220746865207369676e65642070686173652e00d420546865206469737061746368206f726967696e20666f20746869732063616c6c206d757374206265205f5f7369676e65645f5f2e0061012054686520736f6c7574696f6e20697320706f74656e7469616c6c79207175657565642c206261736564206f6e2074686520636c61696d65642073636f726520616e642070726f6365737365642061742074686520656e6454206f6620746865207369676e65642070686173652e0061012041206465706f73697420697320726573657276656420616e64207265636f7264656420666f722074686520736f6c7574696f6e2e204261736564206f6e20746865206f7574636f6d652c2074686520736f6c7574696f6e1901206d696768742062652072657761726465642c20736c61736865642c206f722067657420616c6c206f7220612070617274206f6620746865206465706f736974206261636b2e002c2023203c7765696768743eb42051756575652073697a65206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e011838536f6c7574696f6e53746f726564083c456c656374696f6e436f6d7075746510626f6f6c18b8204120736f6c7574696f6e207761732073746f72656420776974682074686520676976656e20636f6d707574652e0041012049662074686520736f6c7574696f6e206973207369676e65642c2074686973206d65616e732074686174206974206861736e277420796574206265656e2070726f6365737365642e20496620746865090120736f6c7574696f6e20697320756e7369676e65642c2074686973206d65616e7320746861742069742068617320616c736f206265656e2070726f6365737365642e005501205468652060626f6f6c6020697320607472756560207768656e20612070726576696f757320736f6c7574696f6e2077617320656a656374656420746f206d616b6520726f6f6d20666f722074686973206f6e652e44456c656374696f6e46696e616c697a6564045c4f7074696f6e3c456c656374696f6e436f6d707574653e0859012054686520656c656374696f6e20686173206265656e2066696e616c697a65642c20776974682060536f6d6560206f662074686520676976656e20636f6d7075746174696f6e2c206f7220656c7365206966207468656420656c656374696f6e206661696c65642c20604e6f6e65602e20526577617264656408244163636f756e7449641c42616c616e636504290120416e206163636f756e7420686173206265656e20726577617264656420666f72207468656972207369676e6564207375626d697373696f6e206265696e672066696e616c697a65642e1c536c617368656408244163636f756e7449641c42616c616e636504250120416e206163636f756e7420686173206265656e20736c617368656420666f72207375626d697474696e6720616e20696e76616c6964207369676e6564207375626d697373696f6e2e485369676e6564506861736553746172746564040c75333204c420546865207369676e6564207068617365206f662074686520676976656e20726f756e642068617320737461727465642e50556e7369676e6564506861736553746172746564040c75333204cc2054686520756e7369676e6564207068617365206f662074686520676976656e20726f756e642068617320737461727465642e2834556e7369676e6564506861736538543a3a426c6f636b4e756d62657210320000000480204475726174696f6e206f662074686520756e7369676e65642070686173652e2c5369676e6564506861736538543a3a426c6f636b4e756d62657210320000000478204475726174696f6e206f6620746865207369676e65642070686173652e70536f6c7574696f6e496d70726f76656d656e745468726573686f6c641c50657262696c6c10a0860100084d0120546865206d696e696d756d20616d6f756e74206f6620696d70726f76656d656e7420746f2074686520736f6c7574696f6e2073636f7265207468617420646566696e6573206120736f6c7574696f6e206173642022626574746572222028696e20616e79207068617365292e384f6666636861696e52657065617438543a3a426c6f636b4e756d626572100500000010b42054686520726570656174207468726573686f6c64206f6620746865206f6666636861696e20776f726b65722e00610120466f72206578616d706c652c20696620697420697320352c2074686174206d65616e732074686174206174206c65617374203520626c6f636b732077696c6c20656c61707365206265747765656e20617474656d7074738420746f207375626d69742074686520776f726b6572277320736f6c7574696f6e2e505369676e65644d61785375626d697373696f6e730c753332100a0000001ce4204d6178696d756d206e756d626572206f66207369676e6564207375626d697373696f6e7320746861742063616e206265207175657565642e005501204974206973206265737420746f2061766f69642061646a757374696e67207468697320647572696e6720616e20656c656374696f6e2c20617320697420696d706163747320646f776e73747265616d2064617461650120737472756374757265732e20496e20706172746963756c61722c20605369676e65645375626d697373696f6e496e64696365733c543e6020697320626f756e646564206f6e20746869732076616c75652e20496620796f75f42075706461746520746869732076616c756520647572696e6720616e20656c656374696f6e2c20796f75205f6d7573745f20656e7375726520746861744d0120605369676e65645375626d697373696f6e496e64696365732e6c656e282960206973206c657373207468616e206f7220657175616c20746f20746865206e65772076616c75652e204f74686572776973652cf020617474656d70747320746f207375626d6974206e657720736f6c7574696f6e73206d617920636175736520612072756e74696d652070616e69632e3c5369676e65644d61785765696768741857656967687420c07c907c2d0100000c94204d6178696d756d20776569676874206f662061207369676e656420736f6c7574696f6e2e00fc20546869732073686f756c642070726f6261626c792062652073696d696c617220746f205b60436f6e6669673a3a4d696e65724d6178576569676874605d2e405369676e6564526577617264426173653042616c616e63654f663c543e4000407a10f35a00000000000000000000048820426173652072657761726420666f722061207369676e656420736f6c7574696f6e445369676e65644465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004902042617365206465706f73697420666f722061207369676e656420736f6c7574696f6e2e445369676e65644465706f736974427974653042616c616e63654f663c543e400010a5d4e8000000000000000000000004a0205065722d62797465206465706f73697420666f722061207369676e656420736f6c7574696f6e2e4c5369676e65644465706f7369745765696768743042616c616e63654f663c543e400000000000000000000000000000000004a8205065722d776569676874206465706f73697420666f722061207369676e656420736f6c7574696f6e2e2c6850726544697370617463684561726c795375626d697373696f6e0468205375626d697373696f6e2077617320746f6f206561726c792e6c507265446973706174636857726f6e6757696e6e6572436f756e74048c2057726f6e67206e756d626572206f662077696e6e6572732070726573656e7465642e6450726544697370617463685765616b5375626d697373696f6e0494205375626d697373696f6e2077617320746f6f207765616b2c2073636f72652d776973652e3c5369676e6564517565756546756c6c044d0120546865207175657565207761732066756c6c2c20616e642074686520736f6c7574696f6e20776173206e6f7420626574746572207468616e20616e79206f6620746865206578697374696e67206f6e65732e585369676e656443616e6e6f745061794465706f736974049820546865206f726967696e206661696c656420746f2070617920746865206465706f7369742e505369676e6564496e76616c69645769746e65737304a4205769746e657373206461746120746f20646973706174636861626c6520697320696e76616c69642e4c5369676e6564546f6f4d75636857656967687404bc20546865207369676e6564207375626d697373696f6e20636f6e73756d657320746f6f206d756368207765696768743c4f637743616c6c57726f6e67457261049c204f4357207375626d697474656420736f6c7574696f6e20666f722077726f6e6720726f756e645c4d697373696e67536e617073686f744d6574616461746104ac20536e617073686f74206d657461646174612073686f756c6420657869737420627574206469646e27742e58496e76616c69645375626d697373696f6e496e64657804d4206053656c663a3a696e736572745f7375626d697373696f6e602072657475726e656420616e20696e76616c696420696e6465782e3843616c6c4e6f74416c6c6f776564049c205468652063616c6c206973206e6f7420616c6c6f776564206174207468697320706f696e742e081c5374616b696e67011c5374616b696e679430486973746f7279446570746801000c75333210540000001c8c204e756d626572206f66206572617320746f206b65657020696e20686973746f72792e00390120496e666f726d6174696f6e206973206b65707420666f72206572617320696e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e006101204d757374206265206d6f7265207468616e20746865206e756d626572206f6620657261732064656c617965642062792073657373696f6e206f74686572776973652e20492e652e2061637469766520657261206d757374390120616c7761797320626520696e20686973746f72792e20492e652e20606163746976655f657261203e2063757272656e745f657261202d20686973746f72795f646570746860206d757374206265302067756172616e746565642e3856616c696461746f72436f756e7401000c753332100000000004a82054686520696465616c206e756d626572206f66207374616b696e67207061727469636970616e74732e544d696e696d756d56616c696461746f72436f756e7401000c7533321000000000044101204d696e696d756d206e756d626572206f66207374616b696e67207061727469636970616e7473206265666f726520656d657267656e637920636f6e646974696f6e732061726520696d706f7365642e34496e76756c6e657261626c65730100445665633c543a3a4163636f756e7449643e04000c590120416e792076616c696461746f72732074686174206d6179206e6576657220626520736c6173686564206f7220666f726369626c79206b69636b65642e20497427732061205665632073696e636520746865792772654d01206561737920746f20696e697469616c697a6520616e642074686520706572666f726d616e636520686974206973206d696e696d616c2028776520657870656374206e6f206d6f7265207468616e20666f7572ac20696e76756c6e657261626c65732920616e64207265737472696374656420746f20746573746e6574732e18426f6e64656400010530543a3a4163636f756e74496430543a3a4163636f756e744964000400040101204d61702066726f6d20616c6c206c6f636b65642022737461736822206163636f756e747320746f2074686520636f6e74726f6c6c6572206163636f756e742e404d696e4e6f6d696e61746f72426f6e6401003042616c616e63654f663c543e400000000000000000000000000000000004210120546865206d696e696d756d2061637469766520626f6e6420746f206265636f6d6520616e64206d61696e7461696e2074686520726f6c65206f662061206e6f6d696e61746f722e404d696e56616c696461746f72426f6e6401003042616c616e63654f663c543e400000000000000000000000000000000004210120546865206d696e696d756d2061637469766520626f6e6420746f206265636f6d6520616e64206d61696e7461696e2074686520726f6c65206f6620612076616c696461746f722e184c656467657200010230543a3a4163636f756e744964a45374616b696e674c65646765723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400044501204d61702066726f6d20616c6c2028756e6c6f636b6564292022636f6e74726f6c6c657222206163636f756e747320746f2074686520696e666f20726567617264696e6720746865207374616b696e672e14506179656501010530543a3a4163636f756e7449647c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e00040004e42057686572652074686520726577617264207061796d656e742073686f756c64206265206d6164652e204b657965642062792073746173682e2856616c696461746f727301010530543a3a4163636f756e7449643856616c696461746f725072656673000800000c450120546865206d61702066726f6d202877616e6e616265292076616c696461746f72207374617368206b657920746f2074686520707265666572656e636573206f6620746861742076616c696461746f722e004901205768656e207570646174696e6720746869732073746f72616765206974656d2c20796f75206d75737420616c736f20757064617465207468652060436f756e746572466f7256616c696461746f7273602e50436f756e746572466f7256616c696461746f727301000c7533321000000000042101204120747261636b657220746f206b65657020636f756e74206f6620746865206e756d626572206f66206974656d7320696e20746865206056616c696461746f727360206d61702e484d617856616c696461746f7273436f756e7400000c75333204000c310120546865206d6178696d756d2076616c696461746f7220636f756e74206265666f72652077652073746f7020616c6c6f77696e67206e65772076616c696461746f727320746f206a6f696e2e00d0205768656e20746869732076616c7565206973206e6f74207365742c206e6f206c696d6974732061726520656e666f726365642e284e6f6d696e61746f727300010530543a3a4163636f756e744964644e6f6d696e6174696f6e733c543a3a4163636f756e7449643e0004000c650120546865206d61702066726f6d206e6f6d696e61746f72207374617368206b657920746f2074686520736574206f66207374617368206b657973206f6620616c6c2076616c696461746f727320746f206e6f6d696e6174652e004901205768656e207570646174696e6720746869732073746f72616765206974656d2c20796f75206d75737420616c736f20757064617465207468652060436f756e746572466f724e6f6d696e61746f7273602e50436f756e746572466f724e6f6d696e61746f727301000c7533321000000000042101204120747261636b657220746f206b65657020636f756e74206f6620746865206e756d626572206f66206974656d7320696e2074686520604e6f6d696e61746f727360206d61702e484d61784e6f6d696e61746f7273436f756e7400000c75333204000c310120546865206d6178696d756d206e6f6d696e61746f7220636f756e74206265666f72652077652073746f7020616c6c6f77696e67206e65772076616c696461746f727320746f206a6f696e2e00d0205768656e20746869732076616c7565206973206e6f74207365742c206e6f206c696d6974732061726520656e666f726365642e2843757272656e74457261000020457261496e6465780400105c205468652063757272656e742065726120696e6465782e006501205468697320697320746865206c617465737420706c616e6e6564206572612c20646570656e64696e67206f6e20686f77207468652053657373696f6e2070616c6c657420717565756573207468652076616c696461746f7280207365742c206974206d6967687420626520616374697665206f72206e6f742e24416374697665457261000034416374697665457261496e666f040010d820546865206163746976652065726120696e666f726d6174696f6e2c20697420686f6c647320696e64657820616e642073746172742e0059012054686520616374697665206572612069732074686520657261206265696e672063757272656e746c792072657761726465642e2056616c696461746f7220736574206f66207468697320657261206d757374206265ac20657175616c20746f205b6053657373696f6e496e746572666163653a3a76616c696461746f7273605d2e5445726173537461727453657373696f6e496e64657800010520457261496e6465783053657373696f6e496e646578000400103101205468652073657373696f6e20696e646578206174207768696368207468652065726120737461727420666f7220746865206c6173742060484953544f52595f44455054486020657261732e006101204e6f74653a205468697320747261636b7320746865207374617274696e672073657373696f6e2028692e652e2073657373696f6e20696e646578207768656e20657261207374617274206265696e672061637469766529f020666f7220746865206572617320696e20605b43757272656e74457261202d20484953544f52595f44455054482c2043757272656e744572615d602e2c457261735374616b65727301020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000001878204578706f73757265206f662076616c696461746f72206174206572612e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e48457261735374616b657273436c697070656401020520457261496e64657830543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e050c0000002c9820436c6970706564204578706f73757265206f662076616c696461746f72206174206572612e00590120546869732069732073696d696c617220746f205b60457261735374616b657273605d20627574206e756d626572206f66206e6f6d696e61746f7273206578706f736564206973207265647563656420746f20746865dc2060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732e1d0120284e6f74653a20746865206669656c642060746f74616c6020616e6420606f776e60206f6620746865206578706f737572652072656d61696e7320756e6368616e676564292ef42054686973206973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e005d012054686973206973206b657965642066697374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4101204966207374616b657273206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e20656d707479206578706f737572652069732072657475726e65642e484572617356616c696461746f72507265667301020520457261496e64657830543a3a4163636f756e7449643856616c696461746f725072656673050800001411012053696d696c617220746f2060457261735374616b657273602c207468697320686f6c64732074686520707265666572656e636573206f662076616c696461746f72732e0061012054686973206973206b65796564206669727374206279207468652065726120696e64657820746f20616c6c6f772062756c6b2064656c6574696f6e20616e64207468656e20746865207374617368206163636f756e742e00a82049732069742072656d6f7665642061667465722060484953544f52595f44455054486020657261732e4c4572617356616c696461746f7252657761726400010520457261496e6465783042616c616e63654f663c543e0004000c09012054686520746f74616c2076616c696461746f7220657261207061796f757420666f7220746865206c6173742060484953544f52595f44455054486020657261732e0021012045726173207468617420686176656e27742066696e697368656420796574206f7220686173206265656e2072656d6f76656420646f65736e27742068617665207265776172642e4045726173526577617264506f696e747301010520457261496e64657874457261526577617264506f696e74733c543a3a4163636f756e7449643e0014000000000008ac205265776172647320666f7220746865206c6173742060484953544f52595f44455054486020657261732e250120496620726577617264206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207265776172642069732072657475726e65642e3845726173546f74616c5374616b6501010520457261496e6465783042616c616e63654f663c543e00400000000000000000000000000000000008ec2054686520746f74616c20616d6f756e74207374616b656420666f7220746865206c6173742060484953544f52595f44455054486020657261732e1d0120496620746f74616c206861736e2774206265656e20736574206f7220686173206265656e2072656d6f766564207468656e2030207374616b652069732072657475726e65642e20466f72636545726101001c466f7263696e6704000454204d6f6465206f662065726120666f7263696e672e4c536c6173685265776172644672616374696f6e01001c50657262696c6c10000000000cf8205468652070657263656e74616765206f662074686520736c617368207468617420697320646973747269627574656420746f207265706f72746572732e00e4205468652072657374206f662074686520736c61736865642076616c75652069732068616e646c6564206279207468652060536c617368602e4c43616e63656c6564536c6173685061796f757401003042616c616e63654f663c543e40000000000000000000000000000000000815012054686520616d6f756e74206f662063757272656e637920676976656e20746f207265706f7274657273206f66206120736c617368206576656e7420776869636820776173ec2063616e63656c65642062792065787472616f7264696e6172792063697263756d7374616e6365732028652e672e20676f7665726e616e6365292e40556e6170706c696564536c617368657301010520457261496e646578bc5665633c556e6170706c696564536c6173683c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e00040004c420416c6c20756e6170706c69656420736c61736865732074686174206172652071756575656420666f72206c617465722e28426f6e646564457261730100745665633c28457261496e6465782c2053657373696f6e496e646578293e04001025012041206d617070696e672066726f6d207374696c6c2d626f6e646564206572617320746f207468652066697273742073657373696f6e20696e646578206f662074686174206572612e00c8204d75737420636f6e7461696e7320696e666f726d6174696f6e20666f72206572617320666f72207468652072616e67653abc20605b6163746976655f657261202d20626f756e64696e675f6475726174696f6e3b206163746976655f6572615d604c56616c696461746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449645c2850657262696c6c2c2042616c616e63654f663c543e2905040008450120416c6c20736c617368696e67206576656e7473206f6e2076616c696461746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682070726f706f7274696f6e7020616e6420736c6173682076616c7565206f6620746865206572612e4c4e6f6d696e61746f72536c617368496e45726100020520457261496e64657830543a3a4163636f756e7449643042616c616e63654f663c543e05040004610120416c6c20736c617368696e67206576656e7473206f6e206e6f6d696e61746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682076616c7565206f6620746865206572612e34536c617368696e675370616e7300010530543a3a4163636f756e7449645c736c617368696e673a3a536c617368696e675370616e73000400048c20536c617368696e67207370616e7320666f72207374617368206163636f756e74732e245370616e536c6173680101058c28543a3a4163636f756e7449642c20736c617368696e673a3a5370616e496e6465782988736c617368696e673a3a5370616e5265636f72643c42616c616e63654f663c543e3e00800000000000000000000000000000000000000000000000000000000000000000083d01205265636f72647320696e666f726d6174696f6e2061626f757420746865206d6178696d756d20736c617368206f6620612073746173682077697468696e206120736c617368696e67207370616e2cb82061732077656c6c20617320686f77206d7563682072657761726420686173206265656e2070616964206f75742e584561726c69657374556e6170706c696564536c617368000020457261496e646578040004fc20546865206561726c696573742065726120666f72207768696368207765206861766520612070656e64696e672c20756e6170706c69656420736c6173682e5443757272656e74506c616e6e656453657373696f6e01003053657373696f6e496e64657810000000000ce820546865206c61737420706c616e6e65642073657373696f6e207363686564756c6564206279207468652073657373696f6e2070616c6c65742e0031012054686973206973206261736963616c6c7920696e2073796e632077697468207468652063616c6c20746f205b6053657373696f6e4d616e616765723a3a6e65775f73657373696f6e605d2e3853746f7261676556657273696f6e01002052656c6561736573040610cc2054727565206966206e6574776f726b20686173206265656e20757067726164656420746f20746869732076657273696f6e2e7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e00a020546869732069732073657420746f2076362e302e3020666f72206e6577206e6574776f726b732e384368696c6c5468726573686f6c6400001c50657263656e7404000c810120546865207468726573686f6c6420666f72207768656e2075736572732063616e2073746172742063616c6c696e6720606368696c6c5f6f746865726020666f72206f746865722076616c696461746f7273202f206e6f6d696e61746f72732e6d0120546865207468726573686f6c6420697320636f6d706172656420746f207468652061637475616c206e756d626572206f662076616c696461746f7273202f206e6f6d696e61746f7273202860436f756e74466f722a602920696ee4207468652073797374656d20636f6d706172656420746f2074686520636f6e66696775726564206d61782028604d61782a436f756e7460292e016410626f6e640c28636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e1470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e5865012054616b6520746865206f726967696e206163636f756e74206173206120737461736820616e64206c6f636b207570206076616c756560206f66206974732062616c616e63652e2060636f6e74726f6c6c6572602077696c6c8420626520746865206163636f756e74207468617420636f6e74726f6c732069742e003101206076616c756560206d757374206265206d6f7265207468616e2074686520606d696e696d756d5f62616c616e636560207370656369666965642062792060543a3a43757272656e6379602e00250120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20627920746865207374617368206163636f756e742e004020456d6974732060426f6e646564602e002c2023203c7765696768743ed4202d20496e646570656e64656e74206f662074686520617267756d656e74732e204d6f64657261746520636f6d706c65786974792e20202d204f2831292e68202d20546872656520657874726120444220656e74726965732e005101204e4f54453a2054776f206f66207468652073746f726167652077726974657320286053656c663a3a626f6e646564602c206053656c663a3a7061796565602920617265205f6e657665725f20636c65616e6564410120756e6c6573732074686520606f726967696e602066616c6c732062656c6f77205f6578697374656e7469616c206465706f7369745f20616e6420676574732072656d6f76656420617320647573742e4c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a3101202d20526561643a20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c2043757272656e74204572612c20486973746f72792044657074682c204c6f636b73e0202d2057726974653a20426f6e6465642c2050617965652c205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e28626f6e645f657874726104386d61785f6164646974696f6e616c54436f6d706163743c42616c616e63654f663c543e3e5465012041646420736f6d6520657874726120616d6f756e742074686174206861766520617070656172656420696e207468652073746173682060667265655f62616c616e63656020696e746f207468652062616c616e63652075703420666f72207374616b696e672e00510120557365207468697320696620746865726520617265206164646974696f6e616c2066756e647320696e20796f7572207374617368206163636f756e74207468617420796f75207769736820746f20626f6e642e650120556e6c696b65205b60626f6e64605d206f72205b60756e626f6e64605d20746869732066756e6374696f6e20646f6573206e6f7420696d706f736520616e79206c696d69746174696f6e206f6e2074686520616d6f756e744c20746861742063616e2062652061646465642e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c657220616e64f82069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004020456d6974732060426f6e646564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e20202d204f2831292e40202d204f6e6520444220656e7472792e34202d2d2d2d2d2d2d2d2d2d2d2d2c204442205765696768743a1501202d20526561643a2045726120456c656374696f6e205374617475732c20426f6e6465642c204c65646765722c205b4f726967696e204163636f756e745d2c204c6f636b73a4202d2057726974653a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e18756e626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e8c5501205363686564756c65206120706f7274696f6e206f662074686520737461736820746f20626520756e6c6f636b656420726561647920666f72207472616e73666572206f75742061667465722074686520626f6e64010120706572696f6420656e64732e2049662074686973206c656176657320616e20616d6f756e74206163746976656c7920626f6e646564206c657373207468616e250120543a3a43757272656e63793a3a6d696e696d756d5f62616c616e636528292c207468656e20697420697320696e6372656173656420746f207468652066756c6c20616d6f756e742e004901204f6e63652074686520756e6c6f636b20706572696f6420697320646f6e652c20796f752063616e2063616c6c206077697468647261775f756e626f6e6465646020746f2061637475616c6c79206d6f7665c0207468652066756e6473206f7574206f66206d616e6167656d656e7420726561647920666f72207472616e736665722e003d01204e6f206d6f7265207468616e2061206c696d69746564206e756d626572206f6620756e6c6f636b696e67206368756e6b73202873656520604d41585f554e4c4f434b494e475f4348554e4b5360293d012063616e20636f2d657869737473206174207468652073616d652074696d652e20496e207468617420636173652c205b6043616c6c3a3a77697468647261775f756e626f6e646564605d206e656564fc20746f2062652063616c6c656420666972737420746f2072656d6f766520736f6d65206f6620746865206368756e6b732028696620706f737369626c65292e003d012049662061207573657220656e636f756e74657273207468652060496e73756666696369656e74426f6e6460206572726f72207768656e2063616c6c696e6720746869732065787472696e7369632c1d0120746865792073686f756c642063616c6c20606368696c6c6020666972737420696e206f7264657220746f206672656520757020746865697220626f6e6465642066756e64732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004820456d6974732060556e626f6e646564602e00982053656520616c736f205b6043616c6c3a3a77697468647261775f756e626f6e646564605d2e002c2023203c7765696768743e4101202d20496e646570656e64656e74206f662074686520617267756d656e74732e204c696d697465642062757420706f74656e7469616c6c79206578706c6f697461626c6520636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732e6501202d20456163682063616c6c20287265717569726573207468652072656d61696e646572206f662074686520626f6e6465642062616c616e636520746f2062652061626f766520606d696e696d756d5f62616c616e63656029710120202077696c6c2063617573652061206e657720656e74727920746f20626520696e73657274656420696e746f206120766563746f722028604c65646765722e756e6c6f636b696e676029206b65707420696e2073746f726167652e5101202020546865206f6e6c792077617920746f20636c65616e207468652061666f72656d656e74696f6e65642073746f72616765206974656d20697320616c736f20757365722d636f6e74726f6c6c6564207669615c2020206077697468647261775f756e626f6e646564602e40202d204f6e6520444220656e7472792e2c202d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a1d01202d20526561643a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e744572612c204c6f636b732c2042616c616e63654f662053746173682ca4202d2057726974653a204c6f636b732c204c65646765722c2042616c616e63654f662053746173682c28203c2f7765696768743e4477697468647261775f756e626f6e64656404486e756d5f736c617368696e675f7370616e730c7533327c2d012052656d6f766520616e7920756e6c6f636b6564206368756e6b732066726f6d207468652060756e6c6f636b696e67602071756575652066726f6d206f7572206d616e6167656d656e742e003501205468697320657373656e7469616c6c7920667265657320757020746861742062616c616e636520746f206265207573656420627920746865207374617368206163636f756e7420746f20646f4c2077686174657665722069742077616e74732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e004c20456d697473206057697468647261776e602e006c2053656520616c736f205b6043616c6c3a3a756e626f6e64605d2e002c2023203c7765696768743e5501202d20436f756c6420626520646570656e64656e74206f6e2074686520606f726967696e6020617267756d656e7420616e6420686f77206d7563682060756e6c6f636b696e6760206368756e6b732065786973742e45012020497420696d706c6965732060636f6e736f6c69646174655f756e6c6f636b656460207768696368206c6f6f7073206f76657220604c65646765722e756e6c6f636b696e67602c207768696368206973f42020696e6469726563746c7920757365722d636f6e74726f6c6c65642e20536565205b60756e626f6e64605d20666f72206d6f72652064657461696c2e7901202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732c20796574207468652073697a65206f6620776869636820636f756c64206265206c61726765206261736564206f6e20606c6564676572602ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d090120436f6d706c6578697479204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2072656d6f766520205570646174653a2501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c204c6f636b732c205b4f726967696e204163636f756e745da8202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c656467657218204b696c6c3a4501202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c2043757272656e74204572612c20426f6e6465642c20536c617368696e67205370616e732c205b4f726967696e8c2020204163636f756e745d2c204c6f636b732c2042616c616e63654f662073746173685101202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732cb02020205b4f726967696e204163636f756e745d2c204c6f636b732c2042616c616e63654f662073746173682e74202d2057726974657320456163683a205370616e536c617368202a20530d01204e4f54453a2057656967687420616e6e6f746174696f6e20697320746865206b696c6c207363656e6172696f2c20776520726566756e64206f74686572776973652e302023203c2f7765696768743e2076616c6964617465041470726566733856616c696461746f72507265667344e8204465636c617265207468652064657369726520746f2076616c696461746520666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e30202d2d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a90202d20526561643a2045726120456c656374696f6e205374617475732c204c656467657280202d2057726974653a204e6f6d696e61746f72732c2056616c696461746f7273302023203c2f7765696768743e206e6f6d696e617465041c74617267657473a05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e4c1101204465636c617265207468652064657369726520746f206e6f6d696e6174652060746172676574736020666f7220746865206f726967696e20636f6e74726f6c6c65722e00510120456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e20546869732063616e206f6e6c792062652063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e3101202d20546865207472616e73616374696f6e277320636f6d706c65786974792069732070726f706f7274696f6e616c20746f207468652073697a65206f662060746172676574736020284e2901012077686963682069732063617070656420617420436f6d7061637441737369676e6d656e74733a3a4c494d495420284d41585f4e4f4d494e4154494f4e53292ed8202d20426f74682074686520726561647320616e642077726974657320666f6c6c6f7720612073696d696c6172207061747465726e2e28202d2d2d2d2d2d2d2d2d34205765696768743a204f284e2984207768657265204e20697320746865206e756d626572206f6620746172676574732c204442205765696768743ac8202d2052656164733a2045726120456c656374696f6e205374617475732c204c65646765722c2043757272656e742045726184202d205772697465733a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e146368696c6c0044c8204465636c617265206e6f2064657369726520746f206569746865722076616c6964617465206f72206e6f6d696e6174652e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e0d0120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e54202d20436f6e7461696e73206f6e6520726561642ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e24202d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743a88202d20526561643a20457261456c656374696f6e5374617475732c204c656467657280202d2057726974653a2056616c696461746f72732c204e6f6d696e61746f7273302023203c2f7765696768743e247365745f7061796565041470617965657c52657761726444657374696e6174696f6e3c543a3a4163636f756e7449643e40b8202852652d2973657420746865207061796d656e742074617267657420666f72206120636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e28202d2d2d2d2d2d2d2d2d3c202d205765696768743a204f28312934202d204442205765696768743a4c20202020202d20526561643a204c65646765724c20202020202d2057726974653a205061796565302023203c2f7765696768743e387365745f636f6e74726f6c6c65720428636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654090202852652d297365742074686520636f6e74726f6c6c6572206f6620612073746173682e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e2c202d2d2d2d2d2d2d2d2d2d34205765696768743a204f2831292c204442205765696768743af4202d20526561643a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572f8202d2057726974653a20426f6e6465642c204c6564676572204e657720436f6e74726f6c6c65722c204c6564676572204f6c6420436f6e74726f6c6c6572302023203c2f7765696768743e4c7365745f76616c696461746f725f636f756e74040c6e657730436f6d706163743c7533323e209420536574732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e34205765696768743a204f2831295c2057726974653a2056616c696461746f7220436f756e74302023203c2f7765696768743e60696e6372656173655f76616c696461746f725f636f756e7404286164646974696f6e616c30436f6d706163743c7533323e1cac20496e6372656d656e74732074686520696465616c206e756d626572206f662076616c696461746f72732e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e842053616d65206173205b607365745f76616c696461746f725f636f756e74605d2e302023203c2f7765696768743e547363616c655f76616c696461746f725f636f756e740418666163746f721c50657263656e741cd4205363616c652075702074686520696465616c206e756d626572206f662076616c696461746f7273206279206120666163746f722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e842053616d65206173205b607365745f76616c696461746f725f636f756e74605d2e302023203c2f7765696768743e34666f7263655f6e6f5f65726173003cb020466f72636520746865726520746f206265206e6f206e6577206572617320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e00282023205761726e696e67001d012054686520656c656374696f6e2070726f6365737320737461727473206d756c7469706c6520626c6f636b73206265666f72652074686520656e64206f6620746865206572612e3d0120546875732074686520656c656374696f6e2070726f63657373206d6179206265206f6e676f696e67207768656e20746869732069732063616c6c65642e20496e2074686973206361736520746865e020656c656374696f6e2077696c6c20636f6e74696e756520756e74696c20746865206e65787420657261206973207472696767657265642e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e3c202d205765696768743a204f28312948202d2057726974653a20466f726365457261302023203c2f7765696768743e34666f7263655f6e65775f65726100404d0120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f6620746865206e6578742073657373696f6e2e20416674657220746869732c2069742077696c6c206265a020726573657420746f206e6f726d616c20286e6f6e2d666f7263656429206265686176696f75722e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e00282023205761726e696e67001d012054686520656c656374696f6e2070726f6365737320737461727473206d756c7469706c6520626c6f636b73206265666f72652074686520656e64206f6620746865206572612e4d0120496620746869732069732063616c6c6564206a757374206265666f72652061206e657720657261206973207472696767657265642c2074686520656c656374696f6e2070726f63657373206d6179206e6f7490206861766520656e6f75676820626c6f636b7320746f20676574206120726573756c742e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e3c202d205765696768743a204f28312944202d20577269746520466f726365457261302023203c2f7765696768743e447365745f696e76756c6e657261626c65730434696e76756c6e657261626c6573445665633c543a3a4163636f756e7449643e20cc20536574207468652076616c696461746f72732077686f2063616e6e6f7420626520736c61736865642028696620616e79292e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743e1c202d204f2856295c202d2057726974653a20496e76756c6e657261626c6573302023203c2f7765696768743e34666f7263655f756e7374616b650814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c753332280d0120466f72636520612063757272656e74207374616b657220746f206265636f6d6520636f6d706c6574656c7920756e7374616b65642c20696d6d6564696174656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e002c2023203c7765696768743eec204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e7320746f2062652072656d6f766564b82052656164733a20426f6e6465642c20536c617368696e67205370616e732c204163636f756e742c204c6f636b738501205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c204163636f756e742c204c6f636b736c2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e50666f7263655f6e65775f6572615f616c776179730038050120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f662073657373696f6e7320696e646566696e6974656c792e008820546865206469737061746368206f726967696e206d75737420626520526f6f742e00282023205761726e696e67001d012054686520656c656374696f6e2070726f6365737320737461727473206d756c7469706c6520626c6f636b73206265666f72652074686520656e64206f6620746865206572612e4d0120496620746869732069732063616c6c6564206a757374206265666f72652061206e657720657261206973207472696767657265642c2074686520656c656374696f6e2070726f63657373206d6179206e6f7490206861766520656e6f75676820626c6f636b7320746f20676574206120726573756c742e002c2023203c7765696768743e3c202d205765696768743a204f28312948202d2057726974653a20466f726365457261302023203c2f7765696768743e5463616e63656c5f64656665727265645f736c617368080c65726120457261496e64657834736c6173685f696e6469636573205665633c7533323e34982043616e63656c20656e6163746d656e74206f66206120646566657272656420736c6173682e00b42043616e2062652063616c6c6564206279207468652060543a3a536c61736843616e63656c4f726967696e602e00050120506172616d65746572733a2065726120616e6420696e6469636573206f662074686520736c617368657320666f7220746861742065726120746f206b696c6c2e002c2023203c7765696768743e5420436f6d706c65786974793a204f2855202b205329b82077697468205520756e6170706c69656420736c6173686573207765696768746564207769746820553d31303030d420616e64205320697320746865206e756d626572206f6620736c61736820696e646963657320746f2062652063616e63656c65642e68202d20526561643a20556e6170706c69656420536c61736865736c202d2057726974653a20556e6170706c69656420536c6173686573302023203c2f7765696768743e387061796f75745f7374616b657273083c76616c696461746f725f737461736830543a3a4163636f756e7449640c65726120457261496e64657870110120506179206f757420616c6c20746865207374616b65727320626568696e6420612073696e676c652076616c696461746f7220666f7220612073696e676c65206572612e004d01202d206076616c696461746f725f73746173686020697320746865207374617368206163636f756e74206f66207468652076616c696461746f722e205468656972206e6f6d696e61746f72732c20757020746f290120202060543a3a4d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602c2077696c6c20616c736f207265636569766520746865697220726577617264732e3501202d206065726160206d617920626520616e7920657261206265747765656e20605b63757272656e745f657261202d20686973746f72795f64657074683b2063757272656e745f6572615d602e00590120546865206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e20416e79206163636f756e742063616e2063616c6c20746869732066756e6374696f6e2c206576656e20696678206974206973206e6f74206f6e65206f6620746865207374616b6572732e00010120546869732063616e206f6e6c792062652063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743e0101202d2054696d6520636f6d706c65786974793a206174206d6f7374204f284d61784e6f6d696e61746f72526577617264656450657256616c696461746f72292ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e30202d2d2d2d2d2d2d2d2d2d2d1d01204e20697320746865204e756d626572206f66207061796f75747320666f72207468652076616c696461746f722028696e636c7564696e67207468652076616c696461746f722920205765696768743a88202d205265776172642044657374696e6174696f6e205374616b65643a204f284e29c4202d205265776172642044657374696e6174696f6e20436f6e74726f6c6c657220284372656174696e67293a204f284e292c204442205765696768743a2901202d20526561643a20457261456c656374696f6e5374617475732c2043757272656e744572612c20486973746f727944657074682c204572617356616c696461746f725265776172642c2d01202020202020202020457261735374616b657273436c69707065642c2045726173526577617264506f696e74732c204572617356616c696461746f725072656673202838206974656d73291101202d205265616420456163683a20426f6e6465642c204c65646765722c2050617965652c204c6f636b732c2053797374656d204163636f756e74202835206974656d7329d8202d20577269746520456163683a2053797374656d204163636f756e742c204c6f636b732c204c6564676572202833206974656d73290051012020204e4f54453a20776569676874732061726520617373756d696e672074686174207061796f75747320617265206d61646520746f20616c697665207374617368206163636f756e7420285374616b6564292e5901202020506179696e67206576656e2061206465616420636f6e74726f6c6c65722069732063686561706572207765696768742d776973652e20576520646f6e277420646f20616e7920726566756e647320686572652e302023203c2f7765696768743e187265626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e38e0205265626f6e64206120706f7274696f6e206f6620746865207374617368207363686564756c656420746f20626520756e6c6f636b65642e00550120546865206469737061746368206f726967696e206d757374206265207369676e65642062792074686520636f6e74726f6c6c65722c20616e642069742063616e206265206f6e6c792063616c6c6564207768656e8c205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e002c2023203c7765696768743ed4202d2054696d6520636f6d706c65786974793a204f284c292c207768657265204c20697320756e6c6f636b696e67206368756e6b7394202d20426f756e64656420627920604d41585f554e4c4f434b494e475f4348554e4b53602ef4202d2053746f72616765206368616e6765733a2043616e277420696e6372656173652073746f726167652c206f6e6c792064656372656173652069742e40202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a010120202020202d2052656164733a20457261456c656374696f6e5374617475732c204c65646765722c204c6f636b732c205b4f726967696e204163636f756e745db820202020202d205772697465733a205b4f726967696e204163636f756e745d2c204c6f636b732c204c6564676572302023203c2f7765696768743e447365745f686973746f72795f646570746808446e65775f686973746f72795f646570746844436f6d706163743c457261496e6465783e485f6572615f6974656d735f64656c6574656430436f6d706163743c7533323e543101205365742060486973746f72794465707468602076616c75652e20546869732066756e6374696f6e2077696c6c2064656c65746520616e7920686973746f727920696e666f726d6174696f6e80207768656e2060486973746f727944657074686020697320726564756365642e003020506172616d65746572733a1101202d20606e65775f686973746f72795f6465707468603a20546865206e657720686973746f727920646570746820796f7520776f756c64206c696b6520746f207365742e4901202d20606572615f6974656d735f64656c65746564603a20546865206e756d626572206f66206974656d7320746861742077696c6c2062652064656c6574656420627920746869732064697370617463682e450120202020546869732073686f756c64207265706f727420616c6c207468652073746f72616765206974656d7320746861742077696c6c2062652064656c6574656420627920636c656172696e67206f6c6445012020202065726120686973746f72792e204e656564656420746f207265706f727420616e2061636375726174652077656967687420666f72207468652064697370617463682e2054727573746564206279a02020202060526f6f746020746f207265706f727420616e206163637572617465206e756d6265722e0054204f726967696e206d75737420626520726f6f742e002c2023203c7765696768743ee0202d20453a204e756d626572206f6620686973746f7279206465707468732072656d6f7665642c20692e652e203130202d3e2037203d20333c202d205765696768743a204f28452934202d204442205765696768743aa020202020202d2052656164733a2043757272656e74204572612c20486973746f72792044657074687020202020202d205772697465733a20486973746f7279204465707468310120202020202d20436c6561722050726566697820456163683a20457261205374616b6572732c204572615374616b657273436c69707065642c204572617356616c696461746f725072656673810120202020202d2057726974657320456163683a204572617356616c696461746f725265776172642c2045726173526577617264506f696e74732c2045726173546f74616c5374616b652c2045726173537461727453657373696f6e496e646578302023203c2f7765696768743e28726561705f73746173680814737461736830543a3a4163636f756e744964486e756d5f736c617368696e675f7370616e730c7533323c61012052656d6f766520616c6c20646174612073747275637475726520636f6e6365726e696e672061207374616b65722f7374617368206f6e6365206974732062616c616e636520697320617420746865206d696e696d756d2e6101205468697320697320657373656e7469616c6c79206571756976616c656e7420746f206077697468647261775f756e626f6e64656460206578636570742069742063616e2062652063616c6c656420627920616e796f6e65f820616e6420746865207461726765742060737461736860206d7573742068617665206e6f2066756e6473206c656674206265796f6e64207468652045442e009020546869732063616e2062652063616c6c65642066726f6d20616e79206f726967696e2e000101202d20607374617368603a20546865207374617368206163636f756e7420746f20726561702e204974732062616c616e6365206d757374206265207a65726f2e002c2023203c7765696768743e250120436f6d706c65786974793a204f285329207768657265205320697320746865206e756d626572206f6620736c617368696e67207370616e73206f6e20746865206163636f756e742e2c204442205765696768743ad8202d2052656164733a205374617368204163636f756e742c20426f6e6465642c20536c617368696e67205370616e732c204c6f636b73a501202d205772697465733a20426f6e6465642c20536c617368696e67205370616e73202869662053203e2030292c204c65646765722c2050617965652c2056616c696461746f72732c204e6f6d696e61746f72732c205374617368204163636f756e742c204c6f636b7374202d2057726974657320456163683a205370616e536c617368202a2053302023203c2f7765696768743e106b69636b040c77686fa05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e34e42052656d6f76652074686520676976656e206e6f6d696e6174696f6e732066726f6d207468652063616c6c696e672076616c696461746f722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e490120416e642c2069742063616e206265206f6e6c792063616c6c6564207768656e205b60457261456c656374696f6e537461747573605d2069732060436c6f736564602e2054686520636f6e74726f6c6c657298206163636f756e742073686f756c6420726570726573656e7420612076616c696461746f722e005101202d206077686f603a2041206c697374206f66206e6f6d696e61746f72207374617368206163636f756e74732077686f20617265206e6f6d696e6174696e6720746869732076616c696461746f72207768696368c420202073686f756c64206e6f206c6f6e676572206265206e6f6d696e6174696e6720746869732076616c696461746f722e005901204e6f74653a204d616b696e6720746869732063616c6c206f6e6c79206d616b65732073656e736520696620796f7520666972737420736574207468652076616c696461746f7220707265666572656e63657320746f7c20626c6f636b20616e792066757274686572206e6f6d696e6174696f6e732e487365745f7374616b696e675f6c696d69747314486d696e5f6e6f6d696e61746f725f626f6e643042616c616e63654f663c543e486d696e5f76616c696461746f725f626f6e643042616c616e63654f663c543e4c6d61785f6e6f6d696e61746f725f636f756e742c4f7074696f6e3c7533323e4c6d61785f76616c696461746f725f636f756e742c4f7074696f6e3c7533323e247468726573686f6c643c4f7074696f6e3c50657263656e743e34bc205570646174652074686520766172696f7573207374616b696e67206c696d69747320746869732070616c6c65742e002901202a20606d696e5f6e6f6d696e61746f725f626f6e64603a20546865206d696e696d756d2061637469766520626f6e64206e656564656420746f2062652061206e6f6d696e61746f722e2901202a20606d696e5f76616c696461746f725f626f6e64603a20546865206d696e696d756d2061637469766520626f6e64206e656564656420746f20626520612076616c696461746f722e4501202a20606d61785f6e6f6d696e61746f725f636f756e74603a20546865206d6178206e756d626572206f662075736572732077686f2063616e2062652061206e6f6d696e61746f72206174206f6e63652eb02020205768656e2073657420746f20604e6f6e65602c206e6f206c696d697420697320656e666f726365642e4501202a20606d61785f76616c696461746f725f636f756e74603a20546865206d6178206e756d626572206f662075736572732077686f2063616e20626520612076616c696461746f72206174206f6e63652eb02020205768656e2073657420746f20604e6f6e65602c206e6f206c696d697420697320656e666f726365642e00ac204f726967696e206d75737420626520526f6f7420746f2063616c6c20746869732066756e6374696f6e2e003901204e4f54453a204578697374696e67206e6f6d696e61746f727320616e642076616c696461746f72732077696c6c206e6f742062652061666665637465642062792074686973207570646174652e150120746f206b69636b2070656f706c6520756e64657220746865206e6577206c696d6974732c20606368696c6c5f6f74686572602073686f756c642062652063616c6c65642e2c6368696c6c5f6f746865720428636f6e74726f6c6c657230543a3a4163636f756e744964584501204465636c61726520612060636f6e74726f6c6c65726020746f2073746f702070617274696369706174696e672061732065697468657220612076616c696461746f72206f72206e6f6d696e61746f722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00450120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2c206275742063616e2062652063616c6c656420627920616e796f6e652e005d01204966207468652063616c6c6572206973207468652073616d652061732074686520636f6e74726f6c6c6572206265696e672074617267657465642c207468656e206e6f206675727468657220636865636b7320617265dc20656e666f726365642c20616e6420746869732066756e6374696f6e2062656861766573206a757374206c696b6520606368696c6c602e006101204966207468652063616c6c657220697320646966666572656e74207468616e2074686520636f6e74726f6c6c6572206265696e672074617267657465642c2074686520666f6c6c6f77696e6720636f6e646974696f6e7334206d757374206265206d65743a4101202a204120604368696c6c5468726573686f6c6460206d7573742062652073657420616e6420636865636b656420776869636820646566696e657320686f7720636c6f736520746f20746865206d617859012020206e6f6d696e61746f7273206f722076616c696461746f7273207765206d757374207265616368206265666f72652075736572732063616e207374617274206368696c6c696e67206f6e652d616e6f746865722e5d01202a204120604d61784e6f6d696e61746f72436f756e746020616e6420604d617856616c696461746f72436f756e7460206d75737420626520736574207768696368206973207573656420746f2064657465726d696e6594202020686f7720636c6f73652077652061726520746f20746865207468726573686f6c642e6101202a204120604d696e4e6f6d696e61746f72426f6e646020616e6420604d696e56616c696461746f72426f6e6460206d7573742062652073657420616e6420636865636b65642c2077686963682064657465726d696e6573550120202069662074686973206973206120706572736f6e20746861742073686f756c64206265206368696c6c6564206265636175736520746865792068617665206e6f74206d657420746865207468726573686f6c6444202020626f6e642072657175697265642e00590120546869732063616e2062652068656c7066756c20696620626f6e6420726571756972656d656e74732061726520757064617465642c20616e64207765206e65656420746f2072656d6f7665206f6c642075736572739c2077686f20646f206e6f74207361746973667920746865736520726571756972656d656e74732e000128244572615061796f75740c20457261496e6465781c42616c616e63651c42616c616e63650c59012054686520657261207061796f757420686173206265656e207365743b207468652066697273742062616c616e6365206973207468652076616c696461746f722d7061796f75743b20746865207365636f6e64206973c4207468652072656d61696e6465722066726f6d20746865206d6178696d756d20616d6f756e74206f66207265776172642eac205c5b6572615f696e6465782c2076616c696461746f725f7061796f75742c2072656d61696e6465725c5d1852657761726408244163636f756e7449641c42616c616e636504fc20546865207374616b657220686173206265656e207265776172646564206279207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d14536c61736808244163636f756e7449641c42616c616e6365082501204f6e652076616c696461746f722028616e6420697473206e6f6d696e61746f72732920686173206265656e20736c61736865642062792074686520676976656e20616d6f756e742e58205c5b76616c696461746f722c20616d6f756e745c5d684f6c64536c617368696e675265706f7274446973636172646564043053657373696f6e496e646578081d0120416e206f6c6420736c617368696e67207265706f72742066726f6d2061207072696f72206572612077617320646973636172646564206265636175736520697420636f756c6490206e6f742062652070726f6365737365642e205c5b73657373696f6e5f696e6465785c5d3c5374616b696e67456c656374696f6e0004882041206e657720736574206f66207374616b6572732077617320656c65637465642e18426f6e64656408244163636f756e7449641c42616c616e636510d420416e206163636f756e742068617320626f6e646564207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d005101204e4f54453a2054686973206576656e74206973206f6e6c7920656d6974746564207768656e2066756e64732061726520626f6e64656420766961206120646973706174636861626c652e204e6f7461626c792c25012069742077696c6c206e6f7420626520656d697474656420666f72207374616b696e672072657761726473207768656e20746865792061726520616464656420746f207374616b652e20556e626f6e64656408244163636f756e7449641c42616c616e636504dc20416e206163636f756e742068617320756e626f6e646564207468697320616d6f756e742e205c5b73746173682c20616d6f756e745c5d2457697468647261776e08244163636f756e7449641c42616c616e6365085d0120416e206163636f756e74206861732063616c6c6564206077697468647261775f756e626f6e6465646020616e642072656d6f76656420756e626f6e64696e67206368756e6b7320776f727468206042616c616e636560b02066726f6d2074686520756e6c6f636b696e672071756575652e205c5b73746173682c20616d6f756e745c5d184b69636b656408244163636f756e744964244163636f756e744964040d012041206e6f6d696e61746f7220686173206265656e206b69636b65642066726f6d20612076616c696461746f722e205c5b6e6f6d696e61746f722c2073746173685c5d545374616b696e67456c656374696f6e4661696c65640004b02054686520656c656374696f6e206661696c65642e204e6f206e65772065726120697320706c616e6e65642e143853657373696f6e735065724572613053657373696f6e496e64657810060000000470204e756d626572206f662073657373696f6e7320706572206572612e3c426f6e64696e674475726174696f6e20457261496e64657810a002000004e4204e756d626572206f6620657261732074686174207374616b65642066756e6473206d7573742072656d61696e20626f6e64656420666f722e48536c61736844656665724475726174696f6e20457261496e64657810a8000000100101204e756d626572206f662065726173207468617420736c6173686573206172652064656665727265642062792c20616674657220636f6d7075746174696f6e2e000d0120546869732073686f756c64206265206c657373207468616e2074686520626f6e64696e67206475726174696f6e2e2053657420746f203020696620736c617368657315012073686f756c64206265206170706c69656420696d6d6564696174656c792c20776974686f7574206f70706f7274756e69747920666f7220696e74657276656e74696f6e2e804d61784e6f6d696e61746f72526577617264656450657256616c696461746f720c753332100001000010f820546865206d6178696d756d206e756d626572206f66206e6f6d696e61746f727320726577617264656420666f7220656163682076616c696461746f722e00690120466f7220656163682076616c696461746f72206f6e6c79207468652060244d61784e6f6d696e61746f72526577617264656450657256616c696461746f72602062696767657374207374616b6572732063616e20636c61696d2101207468656972207265776172642e2054686973207573656420746f206c696d69742074686520692f6f20636f737420666f7220746865206e6f6d696e61746f72207061796f75742e384d61784e6f6d696e6174696f6e730c7533321010000000005c344e6f74436f6e74726f6c6c65720468204e6f74206120636f6e74726f6c6c6572206163636f756e742e204e6f7453746173680454204e6f742061207374617368206163636f756e742e34416c7265616479426f6e646564046420537461736820697320616c726561647920626f6e6465642e34416c7265616479506169726564047820436f6e74726f6c6c657220697320616c7265616479207061697265642e30456d70747954617267657473046420546172676574732063616e6e6f7420626520656d7074792e384475706c6963617465496e6465780444204475706c696361746520696e6465782e44496e76616c6964536c617368496e646578048820536c617368207265636f726420696e646578206f7574206f6620626f756e64732e40496e73756666696369656e74426f6e6404d02043616e206e6f7420626f6e6420776974682076616c7565206c657373207468616e206d696e696d756d2072657175697265642e304e6f4d6f72654368756e6b7304942043616e206e6f74207363686564756c65206d6f726520756e6c6f636b206368756e6b732e344e6f556e6c6f636b4368756e6b04a42043616e206e6f74207265626f6e6420776974686f757420756e6c6f636b696e67206368756e6b732e3046756e64656454617267657404cc20417474656d7074696e6720746f2074617267657420612073746173682074686174207374696c6c206861732066756e64732e48496e76616c6964457261546f526577617264045c20496e76616c69642065726120746f207265776172642e68496e76616c69644e756d6265724f664e6f6d696e6174696f6e73047c20496e76616c6964206e756d626572206f66206e6f6d696e6174696f6e732e484e6f74536f72746564416e64556e697175650484204974656d7320617265206e6f7420736f7274656420616e6420756e697175652e38416c7265616479436c61696d6564040d01205265776172647320666f72207468697320657261206861766520616c7265616479206265656e20636c61696d656420666f7220746869732076616c696461746f722e54496e636f7272656374486973746f7279446570746804c420496e636f72726563742070726576696f757320686973746f727920646570746820696e7075742070726f76696465642e58496e636f7272656374536c617368696e675370616e7304b420496e636f7272656374206e756d626572206f6620736c617368696e67207370616e732070726f76696465642e204261645374617465043d0120496e7465726e616c20737461746520686173206265636f6d6520736f6d65686f7720636f7272757074656420616e6420746865206f7065726174696f6e2063616e6e6f7420636f6e74696e75652e38546f6f4d616e7954617267657473049820546f6f206d616e79206e6f6d696e6174696f6e207461726765747320737570706c6965642e244261645461726765740441012041206e6f6d696e6174696f6e207461726765742077617320737570706c69656420746861742077617320626c6f636b6564206f72206f7468657277697365206e6f7420612076616c696461746f722e4043616e6e6f744368696c6c4f746865720459012054686520757365722068617320656e6f75676820626f6e6420616e6420746875732063616e6e6f74206265206368696c6c656420666f72636566756c6c7920627920616e2065787465726e616c20706572736f6e2e44546f6f4d616e794e6f6d696e61746f72730875012054686572652061726520746f6f206d616e79206e6f6d696e61746f727320696e207468652073797374656d2e20476f7665726e616e6365206e6565647320746f2061646a75737420746865207374616b696e672073657474696e67739420746f206b656570207468696e6773207361666520666f72207468652072756e74696d652e44546f6f4d616e7956616c696461746f72730875012054686572652061726520746f6f206d616e792076616c696461746f727320696e207468652073797374656d2e20476f7665726e616e6365206e6565647320746f2061646a75737420746865207374616b696e672073657474696e67739420746f206b656570207468696e6773207361666520666f72207468652072756e74696d652e091c53657373696f6e011c53657373696f6e1c2856616c696461746f727301004c5665633c543a3a56616c696461746f7249643e0400047c205468652063757272656e7420736574206f662076616c696461746f72732e3043757272656e74496e64657801003053657373696f6e496e646578100000000004782043757272656e7420696e646578206f66207468652073657373696f6e2e345175657565644368616e676564010010626f6f6c040008390120547275652069662074686520756e6465726c79696e672065636f6e6f6d6963206964656e746974696573206f7220776569676874696e6720626568696e64207468652076616c696461746f7273a420686173206368616e67656420696e20746865207175657565642076616c696461746f72207365742e285175657565644b6579730100785665633c28543a3a56616c696461746f7249642c20543a3a4b657973293e0400083d012054686520717565756564206b65797320666f7220746865206e6578742073657373696f6e2e205768656e20746865206e6578742073657373696f6e20626567696e732c207468657365206b657973e02077696c6c206265207573656420746f2064657465726d696e65207468652076616c696461746f7227732073657373696f6e206b6579732e4844697361626c656456616c696461746f72730100205665633c7533323e04000c8020496e6469636573206f662064697361626c65642076616c696461746f72732e003501205468652073657420697320636c6561726564207768656e20606f6e5f73657373696f6e5f656e64696e67602072657475726e732061206e657720736574206f66206964656e7469746965732e204e6578744b65797300010538543a3a56616c696461746f7249641c543a3a4b657973000400049c20546865206e6578742073657373696f6e206b65797320666f7220612076616c696461746f722e204b65794f776e657200010550284b65795479706549642c205665633c75383e2938543a3a56616c696461746f72496400040004090120546865206f776e6572206f662061206b65792e20546865206b65792069732074686520604b657954797065496460202b2074686520656e636f646564206b65792e0108207365745f6b65797308106b6579731c543a3a4b6579731470726f6f661c5665633c75383e38e82053657473207468652073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c657220746f20606b657973602e210120416c6c6f777320616e206163636f756e7420746f20736574206974732073657373696f6e206b6579207072696f7220746f206265636f6d696e6720612076616c696461746f722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a20606f726967696e206163636f756e74602c2060543a3a56616c696461746f7249644f66602c20604e6578744b65797360a4202d2044625772697465733a20606f726967696e206163636f756e74602c20604e6578744b6579736084202d204462526561647320706572206b65792069643a20604b65794f776e65726088202d20446257726974657320706572206b65792069643a20604b65794f776e657260302023203c2f7765696768743e2870757267655f6b6579730030cc2052656d6f76657320616e792073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c65722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743eb4202d20436f6d706c65786974793a20604f2831296020696e206e756d626572206f66206b65792074797065732e590120202041637475616c20636f737420646570656e6473206f6e20746865206e756d626572206f66206c656e677468206f662060543a3a4b6579733a3a6b65795f6964732829602077686963682069732066697865642ef0202d20446252656164733a2060543a3a56616c696461746f7249644f66602c20604e6578744b657973602c20606f726967696e206163636f756e7460a4202d2044625772697465733a20604e6578744b657973602c20606f726967696e206163636f756e746088202d20446257726974657320706572206b65792069643a20604b65794f776e657260302023203c2f7765696768743e0104284e657753657373696f6e043053657373696f6e496e646578086501204e65772073657373696f6e206861732068617070656e65642e204e6f746520746861742074686520617267756d656e7420697320746865205c5b73657373696f6e5f696e6465785c5d2c206e6f742074686520626c6f636b88206e756d626572206173207468652074797065206d6967687420737567676573742e001430496e76616c696450726f6f66046420496e76616c6964206f776e6572736869702070726f6f662e5c4e6f4173736f63696174656456616c696461746f72496404a0204e6f206173736f6369617465642076616c696461746f7220494420666f72206163636f756e742e344475706c6963617465644b657904682052656769737465726564206475706c6963617465206b65792e184e6f4b65797304a8204e6f206b65797320617265206173736f63696174656420776974682074686973206163636f756e742e244e6f4163636f756e74041d01204b65792073657474696e67206163636f756e74206973206e6f74206c6976652c20736f206974277320696d706f737369626c6520746f206173736f6369617465206b6579732e0a2444656d6f6372616379012444656d6f6372616379383c5075626c696350726f70436f756e7401002450726f70496e646578100000000004f420546865206e756d626572206f6620287075626c6963292070726f706f73616c7320746861742068617665206265656e206d61646520736f206661722e2c5075626c696350726f707301009c5665633c2850726f70496e6465782c20543a3a486173682c20543a3a4163636f756e744964293e040004210120546865207075626c69632070726f706f73616c732e20556e736f727465642e20546865207365636f6e64206974656d206973207468652070726f706f73616c277320686173682e244465706f7369744f660001052450726f70496e64657884285665633c543a3a4163636f756e7449643e2c2042616c616e63654f663c543e290004000c842054686f73652077686f2068617665206c6f636b65642061206465706f7369742e00d82054574f582d4e4f54453a20536166652c20617320696e6372656173696e6720696e7465676572206b6579732061726520736166652e24507265696d616765730001061c543a3a48617368e8507265696d6167655374617475733c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e000400086101204d6170206f662068617368657320746f207468652070726f706f73616c20707265696d6167652c20616c6f6e6720776974682077686f207265676973746572656420697420616e64207468656972206465706f7369742ee42054686520626c6f636b206e756d6265722069732074686520626c6f636b20617420776869636820697420776173206465706f73697465642e3c5265666572656e64756d436f756e7401003c5265666572656e64756d496e646578100000000004310120546865206e6578742066726565207265666572656e64756d20696e6465782c20616b6120746865206e756d626572206f66207265666572656e6461207374617274656420736f206661722e344c6f77657374556e62616b656401003c5265666572656e64756d496e646578100000000008250120546865206c6f77657374207265666572656e64756d20696e64657820726570726573656e74696e6720616e20756e62616b6564207265666572656e64756d2e20457175616c20746fdc20605265666572656e64756d436f756e74602069662074686572652069736e2774206120756e62616b6564207265666572656e64756d2e405265666572656e64756d496e666f4f660001053c5265666572656e64756d496e646578d45265666572656e64756d496e666f3c543a3a426c6f636b4e756d6265722c20543a3a486173682c2042616c616e63654f663c543e3e0004000cb420496e666f726d6174696f6e20636f6e6365726e696e6720616e7920676976656e207265666572656e64756d2e0009012054574f582d4e4f54453a205341464520617320696e646578657320617265206e6f7420756e64657220616e2061747461636b6572e280997320636f6e74726f6c2e20566f74696e674f6601010530543a3a4163636f756e744964c8566f74696e673c42616c616e63654f663c543e2c20543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00d8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000105d0120416c6c20766f74657320666f72206120706172746963756c617220766f7465722e2057652073746f7265207468652062616c616e636520666f7220746865206e756d626572206f6620766f74657320746861742077655d012068617665207265636f726465642e20546865207365636f6e64206974656d2069732074686520746f74616c20616d6f756e74206f662064656c65676174696f6e732c20746861742077696c6c2062652061646465642e00e82054574f582d4e4f54453a205341464520617320604163636f756e7449646073206172652063727970746f2068617368657320616e797761792e144c6f636b7300010530543a3a4163636f756e74496438543a3a426c6f636b4e756d626572000400105d01204163636f756e747320666f7220776869636820746865726520617265206c6f636b7320696e20616374696f6e207768696368206d61792062652072656d6f76656420617420736f6d6520706f696e7420696e207468655101206675747572652e205468652076616c75652069732074686520626c6f636b206e756d62657220617420776869636820746865206c6f636b206578706972657320616e64206d61792062652072656d6f7665642e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e544c6173745461626c656457617345787465726e616c010010626f6f6c0400085901205472756520696620746865206c617374207265666572656e64756d207461626c656420776173207375626d69747465642065787465726e616c6c792e2046616c7365206966206974207761732061207075626c6963282070726f706f73616c2e304e65787445787465726e616c00006028543a3a486173682c20566f74655468726573686f6c6429040010590120546865207265666572656e64756d20746f206265207461626c6564207768656e6576657220697420776f756c642062652076616c696420746f207461626c6520616e2065787465726e616c2070726f706f73616c2e550120546869732068617070656e73207768656e2061207265666572656e64756d206e6565647320746f206265207461626c656420616e64206f6e65206f662074776f20636f6e646974696f6e7320617265206d65743aa4202d20604c6173745461626c656457617345787465726e616c60206973206066616c7365603b206f7268202d20605075626c696350726f70736020697320656d7074792e24426c61636b6c6973740001061c543a3a486173688c28543a3a426c6f636b4e756d6265722c205665633c543a3a4163636f756e7449643e290004000851012041207265636f7264206f662077686f207665746f656420776861742e204d6170732070726f706f73616c206861736820746f206120706f737369626c65206578697374656e7420626c6f636b206e756d626572e82028756e74696c207768656e206974206d6179206e6f742062652072657375626d69747465642920616e642077686f207665746f65642069742e3443616e63656c6c6174696f6e730101061c543a3a4861736810626f6f6c000400042901205265636f7264206f6620616c6c2070726f706f73616c7320746861742068617665206265656e207375626a65637420746f20656d657267656e63792063616e63656c6c6174696f6e2e3853746f7261676556657273696f6e00002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e01641c70726f706f7365083470726f706f73616c5f686173681c543a3a486173681476616c756554436f6d706163743c42616c616e63654f663c543e3e2ca02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e00190120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573748420686176652066756e647320746f20636f76657220746865206465706f7369742e00d8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20707265696d6167652e1901202d206076616c7565603a2054686520616d6f756e74206f66206465706f73697420286d757374206265206174206c6561737420604d696e696d756d4465706f73697460292e004820456d697473206050726f706f736564602e003c205765696768743a20604f28702960187365636f6e64082070726f706f73616c48436f6d706163743c50726f70496e6465783e4c7365636f6e64735f75707065725f626f756e6430436f6d706163743c7533323e28b8205369676e616c732061677265656d656e742077697468206120706172746963756c61722070726f706f73616c2e00050120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e6465721501206d75737420686176652066756e647320746f20636f76657220746865206465706f7369742c20657175616c20746f20746865206f726967696e616c206465706f7369742e00cc202d206070726f706f73616c603a2054686520696e646578206f66207468652070726f706f73616c20746f207365636f6e642e4501202d20607365636f6e64735f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e207468652063757272656e74206e756d626572206f66207365636f6e6473206f6e2074686973290120202070726f706f73616c2e2045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e002101205765696768743a20604f28532960207768657265205320697320746865206e756d626572206f66207365636f6e647320612070726f706f73616c20616c7265616479206861732e10766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f7465644163636f756e74566f74653c42616c616e63654f663c543e3e24350120566f746520696e2061207265666572656e64756d2e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374207468652070726f706f73616c3bbc206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00e0202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f20766f746520666f722e88202d2060766f7465603a2054686520766f746520636f6e66696775726174696f6e2e003101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722068617320766f746564206f6e2e40656d657267656e63795f63616e63656c04247265665f696e6465783c5265666572656e64756d496e646578205101205363686564756c6520616e20656d657267656e63792063616e63656c6c6174696f6e206f662061207265666572656e64756d2e2043616e6e6f742068617070656e20747769636520746f207468652073616d6530207265666572656e64756d2e00fc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206043616e63656c6c6174696f6e4f726967696e602e00d4202d607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e0040205765696768743a20604f283129602e4065787465726e616c5f70726f706f7365043470726f706f73616c5f686173681c543a3a48617368243101205363686564756c652061207265666572656e64756d20746f206265207461626c6564206f6e6365206974206973206c6567616c20746f207363686564756c6520616e2065787465726e616c30207265666572656e64756d2e00ec20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206045787465726e616c4f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e001901205765696768743a20604f2856296020776974682056206e756d626572206f66207665746f65727320696e2074686520626c61636b6c697374206f662070726f706f73616c2ebc2020204465636f64696e6720766563206f66206c656e67746820562e2043686172676564206173206d6178696d756d6465787465726e616c5f70726f706f73655f6d616a6f72697479043470726f706f73616c5f686173681c543a3a486173682c5901205363686564756c652061206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f207363686564756c656020616e2065787465726e616c207265666572656e64756d2e00f020546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c4d616a6f726974794f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e003c205765696768743a20604f283129606065787465726e616c5f70726f706f73655f64656661756c74043470726f706f73616c5f686173681c543a3a486173682c4901205363686564756c652061206e656761746976652d7475726e6f75742d62696173207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f84207363686564756c6520616e2065787465726e616c207265666572656e64756d2e00ec20546865206469737061746368206f6620746869732063616c6c206d757374206265206045787465726e616c44656661756c744f726967696e602e00d8202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e003c205765696768743a20604f2831296028666173745f747261636b0c3470726f706f73616c5f686173681c543a3a4861736834766f74696e675f706572696f6438543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d6265723c5101205363686564756c65207468652063757272656e746c792065787465726e616c6c792d70726f706f736564206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564650120696d6d6564696174656c792e204966207468657265206973206e6f2065787465726e616c6c792d70726f706f736564207265666572656e64756d2063757272656e746c792c206f72206966207468657265206973206f6e65ec20627574206974206973206e6f742061206d616a6f726974792d63617272696573207265666572656e64756d207468656e206974206661696c732e00d420546865206469737061746368206f6620746869732063616c6c206d757374206265206046617374547261636b4f726967696e602e00f8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652063757272656e742065787465726e616c2070726f706f73616c2e6101202d2060766f74696e675f706572696f64603a2054686520706572696f64207468617420697320616c6c6f77656420666f7220766f74696e67206f6e20746869732070726f706f73616c2e20496e6372656173656420746f982020206046617374547261636b566f74696e67506572696f646020696620746f6f206c6f772e5501202d206064656c6179603a20546865206e756d626572206f6620626c6f636b20616674657220766f74696e672068617320656e64656420696e20617070726f76616c20616e6420746869732073686f756c64206265bc202020656e61637465642e205468697320646f65736e277420686176652061206d696e696d756d20616d6f756e742e004420456d697473206053746172746564602e003c205765696768743a20604f28312960347665746f5f65787465726e616c043470726f706f73616c5f686173681c543a3a4861736824bc205665746f20616e6420626c61636b6c697374207468652065787465726e616c2070726f706f73616c20686173682e00dc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520605665746f4f726967696e602e003101202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f66207468652070726f706f73616c20746f207665746f20616e6420626c61636b6c6973742e004020456d69747320605665746f6564602e000101205765696768743a20604f2856202b206c6f6728562929602077686572652056206973206e756d626572206f6620606578697374696e67207665746f657273604463616e63656c5f7265666572656e64756d04247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e1c542052656d6f76652061207265666572656e64756d2e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00d8202d20607265665f696e646578603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e00482023205765696768743a20604f283129602e3463616e63656c5f717565756564041477686963683c5265666572656e64756d496e6465781ca02043616e63656c20612070726f706f73616c2071756575656420666f7220656e6163746d656e742e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e00c8202d20607768696368603a2054686520696e646578206f6620746865207265666572656e64756d20746f2063616e63656c2e004d01205765696768743a20604f284429602077686572652060446020697320746865206974656d7320696e207468652064697370617463682071756575652e205765696768746564206173206044203d203130602e2064656c65676174650c08746f30543a3a4163636f756e74496428636f6e76696374696f6e28436f6e76696374696f6e1c62616c616e63653042616c616e63654f663c543e503d012044656c65676174652074686520766f74696e6720706f77657220287769746820736f6d6520676976656e20636f6e76696374696f6e29206f66207468652073656e64696e67206163636f756e742e005901205468652062616c616e63652064656c656761746564206973206c6f636b656420666f72206173206c6f6e6720617320697427732064656c6567617465642c20616e64207468657265616674657220666f7220746865cc2074696d6520617070726f70726961746520666f722074686520636f6e76696374696f6e2773206c6f636b20706572696f642e00610120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e696e67206163636f756e74206d757374206569746865723a782020202d2062652064656c65676174696e6720616c72656164793b206f725d012020202d2068617665206e6f20766f74696e67206163746976697479202869662074686572652069732c207468656e2069742077696c6c206e65656420746f2062652072656d6f7665642f636f6e736f6c6964617465649820202020207468726f7567682060726561705f766f746560206f722060756e766f746560292e004901202d2060746f603a20546865206163636f756e742077686f736520766f74696e6720746865206074617267657460206163636f756e74277320766f74696e6720706f7765722077696c6c20666f6c6c6f772e5901202d2060636f6e76696374696f6e603a2054686520636f6e76696374696f6e20746861742077696c6c20626520617474616368656420746f207468652064656c65676174656420766f7465732e205768656e2074686545012020206163636f756e7420697320756e64656c6567617465642c207468652066756e64732077696c6c206265206c6f636b656420666f722074686520636f72726573706f6e64696e6720706572696f642e5501202d206062616c616e6365603a2054686520616d6f756e74206f6620746865206163636f756e7427732062616c616e636520746f206265207573656420696e2064656c65676174696e672e2054686973206d757374c82020206e6f74206265206d6f7265207468616e20746865206163636f756e7427732063757272656e742062616c616e63652e004c20456d697473206044656c656761746564602e004101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732e28756e64656c65676174650030d020556e64656c65676174652074686520766f74696e6720706f776572206f66207468652073656e64696e67206163636f756e742e00610120546f6b656e73206d617920626520756e6c6f636b656420666f6c6c6f77696e67206f6e636520616e20616d6f756e74206f662074696d6520636f6e73697374656e74207769746820746865206c6f636b20706572696f64e0206f662074686520636f6e76696374696f6e2077697468207768696368207468652064656c65676174696f6e20776173206973737565642e00490120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265582063757272656e746c792064656c65676174696e672e005420456d6974732060556e64656c656761746564602e004101205765696768743a20604f28522960207768657265205220697320746865206e756d626572206f66207265666572656e64756d732074686520766f7465722064656c65676174696e6720746f20686173cc202020766f746564206f6e2e205765696768742069732063686172676564206173206966206d6178696d756d20766f7465732e58636c6561725f7075626c69635f70726f706f73616c7300147420436c6561727320616c6c207075626c69632070726f706f73616c732e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f526f6f745f2e0040205765696768743a20604f283129602e346e6f74655f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e2861012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e205468697320646f65736e27742072657175697265207468652070726f706f73616c20746f206265250120696e207468652064697370617463682071756575652062757420646f657320726571756972652061206465706f7369742c2072657475726e6564206f6e636520656e61637465642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e005101205765696768743a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e646e6f74655f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e040d012053616d6520617320606e6f74655f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e586e6f74655f696d6d696e656e745f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e3045012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e2054686973207265717569726573207468652070726f706f73616c20746f206265410120696e207468652064697370617463682071756575652e204e6f206465706f736974206973206e65656465642e205768656e20746869732063616c6c206973207375636365737366756c2c20692e652e39012074686520707265696d61676520686173206e6f74206265656e2075706c6f61646564206265666f726520616e64206d61746368657320736f6d6520696d6d696e656e742070726f706f73616c2c40206e6f2066656520697320706169642e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00c8202d2060656e636f6465645f70726f706f73616c603a2054686520707265696d616765206f6620612070726f706f73616c2e005c20456d6974732060507265696d6167654e6f746564602e005101205765696768743a20604f28452960207769746820452073697a65206f662060656e636f6465645f70726f706f73616c60202870726f7465637465642062792061207265717569726564206465706f736974292e886e6f74655f696d6d696e656e745f707265696d6167655f6f7065726174696f6e616c0440656e636f6465645f70726f706f73616c1c5665633c75383e0431012053616d6520617320606e6f74655f696d6d696e656e745f707265696d6167656020627574206f726967696e20697320604f7065726174696f6e616c507265696d6167654f726967696e602e34726561705f707265696d616765083470726f706f73616c5f686173681c543a3a486173686070726f706f73616c5f6c656e5f75707065725f626f756e6430436f6d706163743c7533323e3cf42052656d6f766520616e20657870697265642070726f706f73616c20707265696d61676520616e6420636f6c6c65637420746865206465706f7369742e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00d0202d206070726f706f73616c5f68617368603a2054686520707265696d6167652068617368206f6620612070726f706f73616c2e2d01202d206070726f706f73616c5f6c656e6774685f75707065725f626f756e64603a20616e20757070657220626f756e64206f6e206c656e677468206f66207468652070726f706f73616c2e010120202045787472696e736963206973207765696768746564206163636f7264696e6720746f20746869732076616c75652077697468206e6f20726566756e642e00510120546869732077696c6c206f6e6c7920776f726b2061667465722060566f74696e67506572696f646020626c6f636b732066726f6d207468652074696d6520746861742074686520707265696d616765207761735d01206e6f7465642c2069662069742773207468652073616d65206163636f756e7420646f696e672069742e2049662069742773206120646966666572656e74206163636f756e742c207468656e206974276c6c206f6e6c79b020776f726b20616e206164646974696f6e616c2060456e6163746d656e74506572696f6460206c617465722e006020456d6974732060507265696d616765526561706564602e00b8205765696768743a20604f284429602077686572652044206973206c656e677468206f662070726f706f73616c2e18756e6c6f636b041874617267657430543a3a4163636f756e7449641ca420556e6c6f636b20746f6b656e732074686174206861766520616e2065787069726564206c6f636b2e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e00bc202d2060746172676574603a20546865206163636f756e7420746f2072656d6f766520746865206c6f636b206f6e2e00c0205765696768743a20604f2852296020776974682052206e756d626572206f6620766f7465206f66207461726765742e2c72656d6f76655f766f74650414696e6465783c5265666572656e64756d496e6465786c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e00102049663a8c202d20746865207265666572656e64756d207761732063616e63656c6c65642c206f7280202d20746865207265666572656e64756d206973206f6e676f696e672c206f7294202d20746865207265666572656e64756d2068617320656e6465642073756368207468617401012020202d2074686520766f7465206f6620746865206163636f756e742077617320696e206f70706f736974696f6e20746f2074686520726573756c743b206f72d82020202d20746865726520776173206e6f20636f6e76696374696f6e20746f20746865206163636f756e74277320766f74653b206f72882020202d20746865206163636f756e74206d61646520612073706c697420766f74656101202e2e2e7468656e2074686520766f74652069732072656d6f76656420636c65616e6c7920616e64206120666f6c6c6f77696e672063616c6c20746f2060756e6c6f636b60206d617920726573756c7420696e206d6f72655c2066756e6473206265696e6720617661696c61626c652e00ac2049662c20686f77657665722c20746865207265666572656e64756d2068617320656e64656420616e643af0202d2069742066696e697368656420636f72726573706f6e64696e6720746f2074686520766f7465206f6620746865206163636f756e742c20616e64e0202d20746865206163636f756e74206d6164652061207374616e6461726420766f7465207769746820636f6e76696374696f6e2c20616e64c0202d20746865206c6f636b20706572696f64206f662074686520636f6e76696374696f6e206973206e6f74206f7665725d01202e2e2e7468656e20746865206c6f636b2077696c6c206265206167677265676174656420696e746f20746865206f766572616c6c206163636f756e742773206c6f636b2c207768696368206d617920696e766f6c76655d01202a6f7665726c6f636b696e672a20287768657265207468652074776f206c6f636b732061726520636f6d62696e656420696e746f20612073696e676c65206c6f636b207468617420697320746865206d6178696d756de8206f6620626f74682074686520616d6f756e74206c6f636b656420616e64207468652074696d65206973206974206c6f636b656420666f72292e004d0120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2c20616e6420746865207369676e6572206d7573742068617665206120766f74658c207265676973746572656420666f72207265666572656e64756d2060696e646578602e00f8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e005901205765696768743a20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652e4472656d6f76655f6f746865725f766f7465081874617267657430543a3a4163636f756e74496414696e6465783c5265666572656e64756d496e6465783c802052656d6f7665206120766f746520666f722061207265666572656e64756d2e0051012049662074686520607461726765746020697320657175616c20746f20746865207369676e65722c207468656e20746869732066756e6374696f6e2069732065786163746c79206571756976616c656e7420746f3101206072656d6f76655f766f7465602e204966206e6f7420657175616c20746f20746865207369676e65722c207468656e2074686520766f7465206d757374206861766520657870697265642c590120656974686572206265636175736520746865207265666572656e64756d207761732063616e63656c6c65642c20626563617573652074686520766f746572206c6f737420746865207265666572656e64756d206f729c20626563617573652074686520636f6e76696374696f6e20706572696f64206973206f7665722e00cc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265205f5369676e65645f2e005101202d2060746172676574603a20546865206163636f756e74206f662074686520766f746520746f2062652072656d6f7665643b2074686973206163636f756e74206d757374206861766520766f74656420666f72582020207265666572656e64756d2060696e646578602ef8202d2060696e646578603a2054686520696e646578206f66207265666572656e64756d206f662074686520766f746520746f2062652072656d6f7665642e005901205765696768743a20604f2852202b206c6f6720522960207768657265205220697320746865206e756d626572206f66207265666572656e646120746861742060746172676574602068617320766f746564206f6e2edc2020205765696768742069732063616c63756c6174656420666f7220746865206d6178696d756d206e756d626572206f6620766f74652e38656e6163745f70726f706f73616c083470726f706f73616c5f686173681c543a3a4861736814696e6465783c5265666572656e64756d496e64657804510120456e61637420612070726f706f73616c2066726f6d2061207265666572656e64756d2e20466f72206e6f77207765206a757374206d616b65207468652077656967687420626520746865206d6178696d756d2e24626c61636b6c697374083470726f706f73616c5f686173681c543a3a486173683c6d617962655f7265665f696e6465785c4f7074696f6e3c5265666572656e64756d496e6465783e3c4901205065726d616e656e746c7920706c61636520612070726f706f73616c20696e746f2074686520626c61636b6c6973742e20546869732070726576656e74732069742066726f6d2065766572206265696e67402070726f706f73656420616761696e2e0055012049662063616c6c6564206f6e206120717565756564207075626c6963206f722065787465726e616c2070726f706f73616c2c207468656e20746869732077696c6c20726573756c7420696e206974206265696e6755012072656d6f7665642e2049662074686520607265665f696e6465786020737570706c69656420697320616e20616374697665207265666572656e64756d2077697468207468652070726f706f73616c20686173682c6c207468656e2069742077696c6c2062652063616e63656c6c65642e00f020546865206469737061746368206f726967696e206f6620746869732063616c6c206d7573742062652060426c61636b6c6973744f726967696e602e00fc202d206070726f706f73616c5f68617368603a205468652070726f706f73616c206861736820746f20626c61636b6c697374207065726d616e656e746c792e4901202d20607265665f696e646578603a20416e206f6e676f696e67207265666572656e64756d2077686f73652068617368206973206070726f706f73616c5f68617368602c2077686963682077696c6c2062652c2063616e63656c6c65642e004501205765696768743a20604f28702960202874686f756768206173207468697320697320616e20686967682d70726976696c6567652064697370617463682c20776520617373756d6520697420686173206154202020726561736f6e61626c652076616c7565292e3c63616e63656c5f70726f706f73616c042870726f705f696e64657848436f6d706163743c50726f70496e6465783e1c4c2052656d6f766520612070726f706f73616c2e00050120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265206043616e63656c50726f706f73616c4f726967696e602e00d4202d206070726f705f696e646578603a2054686520696e646578206f66207468652070726f706f73616c20746f2063616e63656c2e00e8205765696768743a20604f28702960207768657265206070203d205075626c696350726f70733a3a3c543e3a3a6465636f64655f6c656e28296001482050726f706f736564082450726f70496e6465781c42616c616e63650431012041206d6f74696f6e20686173206265656e2070726f706f7365642062792061207075626c6963206163636f756e742e205c5b70726f706f73616c5f696e6465782c206465706f7369745c5d185461626c65640c2450726f70496e6465781c42616c616e6365385665633c4163636f756e7449643e047d012041207075626c69632070726f706f73616c20686173206265656e207461626c656420666f72207265666572656e64756d20766f74652e205c5b70726f706f73616c5f696e6465782c206465706f7369742c206465706f7369746f72735c5d3845787465726e616c5461626c656400049820416e2065787465726e616c2070726f706f73616c20686173206265656e207461626c65642e1c53746172746564083c5265666572656e64756d496e64657834566f74655468726573686f6c6404c42041207265666572656e64756d2068617320626567756e2e205c5b7265665f696e6465782c207468726573686f6c645c5d18506173736564043c5265666572656e64756d496e64657804e820412070726f706f73616c20686173206265656e20617070726f766564206279207265666572656e64756d2e205c5b7265665f696e6465785c5d244e6f74506173736564043c5265666572656e64756d496e64657804e820412070726f706f73616c20686173206265656e2072656a6563746564206279207265666572656e64756d2e205c5b7265665f696e6465785c5d2443616e63656c6c6564043c5265666572656e64756d496e64657804bc2041207265666572656e64756d20686173206265656e2063616e63656c6c65642e205c5b7265665f696e6465785c5d204578656375746564083c5265666572656e64756d496e64657810626f6f6c04c820412070726f706f73616c20686173206265656e20656e61637465642e205c5b7265665f696e6465782c2069735f6f6b5c5d2444656c65676174656408244163636f756e744964244163636f756e74496404210120416e206163636f756e74206861732064656c65676174656420746865697220766f746520746f20616e6f74686572206163636f756e742e205c5b77686f2c207461726765745c5d2c556e64656c65676174656404244163636f756e74496404f820416e205c5b6163636f756e745c5d206861732063616e63656c6c656420612070726576696f75732064656c65676174696f6e206f7065726174696f6e2e185665746f65640c244163636f756e74496410486173682c426c6f636b4e756d62657204110120416e2065787465726e616c2070726f706f73616c20686173206265656e207665746f65642e205c5b77686f2c2070726f706f73616c5f686173682c20756e74696c5c5d34507265696d6167654e6f7465640c1048617368244163636f756e7449641c42616c616e636504610120412070726f706f73616c277320707265696d61676520776173206e6f7465642c20616e6420746865206465706f7369742074616b656e2e205c5b70726f706f73616c5f686173682c2077686f2c206465706f7369745c5d30507265696d616765557365640c1048617368244163636f756e7449641c42616c616e636508150120412070726f706f73616c20707265696d616765207761732072656d6f76656420616e6420757365642028746865206465706f736974207761732072657475726e6564292e94205c5b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369745c5d3c507265696d616765496e76616c69640810486173683c5265666572656e64756d496e646578080d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d6167652077617320696e76616c69642e74205c5b70726f706f73616c5f686173682c207265665f696e6465785c5d3c507265696d6167654d697373696e670810486173683c5265666572656e64756d496e646578080d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d61676520776173206d697373696e672e74205c5b70726f706f73616c5f686173682c207265665f696e6465785c5d38507265696d616765526561706564101048617368244163636f756e7449641c42616c616e6365244163636f756e744964082d012041207265676973746572656420707265696d616765207761732072656d6f76656420616e6420746865206465706f73697420636f6c6c656374656420627920746865207265617065722eb4205c5b70726f706f73616c5f686173682c2070726f76696465722c206465706f7369742c207265617065725c5d20556e6c6f636b656404244163636f756e74496404bc20416e205c5b6163636f756e745c5d20686173206265656e20756e6c6f636b6564207375636365737366756c6c792e2c426c61636b6c697374656404104861736804d820412070726f706f73616c205c5b686173685c5d20686173206265656e20626c61636b6c6973746564207065726d616e656e746c792e203c456e6163746d656e74506572696f6438543a3a426c6f636b4e756d62657210002f0d0014710120546865206d696e696d756d20706572696f64206f66206c6f636b696e6720616e642074686520706572696f64206265747765656e20612070726f706f73616c206265696e6720617070726f76656420616e6420656e61637465642e0031012049742073686f756c642067656e6572616c6c792062652061206c6974746c65206d6f7265207468616e2074686520756e7374616b6520706572696f6420746f20656e737572652074686174690120766f74696e67207374616b657273206861766520616e206f70706f7274756e69747920746f2072656d6f7665207468656d73656c7665732066726f6d207468652073797374656d20696e2074686520636173652077686572659c207468657920617265206f6e20746865206c6f73696e672073696465206f66206120766f74652e304c61756e6368506572696f6438543a3a426c6f636b4e756d62657210004e0c0004e420486f77206f6674656e2028696e20626c6f636b7329206e6577207075626c6963207265666572656e646120617265206c61756e636865642e30566f74696e67506572696f6438543a3a426c6f636b4e756d62657210004e0c0004b820486f77206f6674656e2028696e20626c6f636b732920746f20636865636b20666f72206e657720766f7465732e384d696e696d756d4465706f7369743042616c616e63654f663c543e400000c16ff2862300000000000000000004350120546865206d696e696d756d20616d6f756e7420746f20626520757365642061732061206465706f73697420666f722061207075626c6963207265666572656e64756d2070726f706f73616c2e5446617374547261636b566f74696e67506572696f6438543a3a426c6f636b4e756d626572108051010004ec204d696e696d756d20766f74696e6720706572696f6420616c6c6f77656420666f72206120666173742d747261636b207265666572656e64756d2e34436f6f6c6f6666506572696f6438543a3a426c6f636b4e756d62657210004e0c0004610120506572696f6420696e20626c6f636b7320776865726520616e2065787465726e616c2070726f706f73616c206d6179206e6f742062652072652d7375626d6974746564206166746572206265696e67207665746f65642e4c507265696d616765427974654465706f7369743042616c616e63654f663c543e400010a5d4e800000000000000000000000429012054686520616d6f756e74206f662062616c616e63652074686174206d757374206265206465706f7369746564207065722062797465206f6620707265696d6167652073746f7265642e204d6178566f7465730c753332106400000010b020546865206d6178696d756d206e756d626572206f6620766f74657320666f7220616e206163636f756e742e00d420416c736f207573656420746f20636f6d70757465207765696768742c20616e206f7665726c79206269672076616c75652063616e1501206c65616420746f2065787472696e7369632077697468207665727920626967207765696768743a20736565206064656c65676174656020666f7220696e7374616e63652e842056616c75654c6f7704382056616c756520746f6f206c6f773c50726f706f73616c4d697373696e6704602050726f706f73616c20646f6573206e6f7420657869737420426164496e646578043820556e6b6e6f776e20696e6465783c416c726561647943616e63656c656404982043616e6e6f742063616e63656c207468652073616d652070726f706f73616c207477696365444475706c696361746550726f706f73616c04582050726f706f73616c20616c7265616479206d6164654c50726f706f73616c426c61636b6c6973746564046c2050726f706f73616c207374696c6c20626c61636b6c6973746564444e6f7453696d706c654d616a6f7269747904ac204e6578742065787465726e616c2070726f706f73616c206e6f742073696d706c65206d616a6f726974792c496e76616c696448617368043420496e76616c69642068617368284e6f50726f706f73616c0454204e6f2065787465726e616c2070726f706f73616c34416c72656164795665746f6564049c204964656e74697479206d6179206e6f74207665746f20612070726f706f73616c207477696365304e6f7444656c6567617465640438204e6f742064656c656761746564444475706c6963617465507265696d616765045c20507265696d61676520616c7265616479206e6f7465642c4e6f74496d6d696e656e740434204e6f7420696d6d696e656e7420546f6f4561726c79042820546f6f206561726c7920496d6d696e656e74042420496d6d696e656e743c507265696d6167654d697373696e67044c20507265696d616765206e6f7420666f756e64445265666572656e64756d496e76616c6964048820566f746520676976656e20666f7220696e76616c6964207265666572656e64756d3c507265696d616765496e76616c6964044420496e76616c696420707265696d6167652c4e6f6e6557616974696e670454204e6f2070726f706f73616c732077616974696e67244e6f744c6f636b656404a42054686520746172676574206163636f756e7420646f6573206e6f7420686176652061206c6f636b2e284e6f744578706972656404f020546865206c6f636b206f6e20746865206163636f756e7420746f20626520756e6c6f636b656420686173206e6f742079657420657870697265642e204e6f74566f74657204c82054686520676976656e206163636f756e7420646964206e6f7420766f7465206f6e20746865207265666572656e64756d2e304e6f5065726d697373696f6e04cc20546865206163746f7220686173206e6f207065726d697373696f6e20746f20636f6e647563742074686520616374696f6e2e44416c726561647944656c65676174696e67048c20546865206163636f756e7420697320616c72656164792064656c65676174696e672e44496e73756666696369656e7446756e647304010120546f6f206869676820612062616c616e6365207761732070726f7669646564207468617420746865206163636f756e742063616e6e6f74206166666f72642e344e6f7444656c65676174696e6704a420546865206163636f756e74206973206e6f742063757272656e746c792064656c65676174696e672e28566f746573457869737408590120546865206163636f756e742063757272656e746c792068617320766f74657320617474616368656420746f20697420616e6420746865206f7065726174696f6e2063616e6e6f74207375636365656420756e74696cec207468657365206172652072656d6f7665642c20656974686572207468726f7567682060756e766f746560206f722060726561705f766f7465602e44496e7374616e744e6f74416c6c6f77656404dc2054686520696e7374616e74207265666572656e64756d206f726967696e2069732063757272656e746c7920646973616c6c6f7765642e204e6f6e73656e736504982044656c65676174696f6e20746f206f6e6573656c66206d616b6573206e6f2073656e73652e3c57726f6e675570706572426f756e64045420496e76616c696420757070657220626f756e642e3c4d6178566f746573526561636865640484204d6178696d756d206e756d626572206f6620766f74657320726561636865642e38496e76616c69645769746e6573730490205468652070726f7669646564207769746e65737320646174612069732077726f6e672e40546f6f4d616e7950726f706f73616c730494204d6178696d756d206e756d626572206f662070726f706f73616c7320726561636865642e0b1c436f756e63696c014c496e7374616e636531436f6c6c656374697665182450726f706f73616c73010090426f756e6465645665633c543a3a486173682c20543a3a4d617850726f706f73616c733e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368683c5420617320436f6e6669673c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e744964040004650120546865207072696d65206d656d62657220746861742068656c70732064657465726d696e65207468652064656661756c7420766f7465206265686176696f7220696e2063617365206f6620616273656e746174696f6e732e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c38f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e004d01205472616e73616374696f6e20666565732077696c6c2062652077616976656420696620746865206d656d62657220697320766f74696e67206f6e20616e7920706172746963756c61722070726f706f73616c690120666f72207468652066697273742074696d6520616e64207468652063616c6c206973207375636365737366756c2e2053756273657175656e7420766f7465206368616e6765732077696c6c206368617267652061206665652e2c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e78510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e0065012049662074686520636c6f7365206f7065726174696f6e20636f6d706c65746573207375636365737366756c6c79207769746820646973617070726f76616c2c20746865207472616e73616374696f6e206665652077696c6c6101206265207761697665642e204f746865727769736520657865637574696f6e206f662074686520617070726f766564206f7065726174696f6e2077696c6c206265206368617267656420746f207468652063616c6c65722e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed8205c5b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645c5d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292eac205c5b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5c5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e6c205c5b70726f706f73616c5f686173682c207965732c206e6f5c5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e0c48546563686e6963616c436f6d6d6974746565014c496e7374616e636532436f6c6c656374697665182450726f706f73616c73010090426f756e6465645665633c543a3a486173682c20543a3a4d617850726f706f73616c733e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001061c543a3a48617368683c5420617320436f6e6669673c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001061c543a3a486173688c566f7465733c543a3a4163636f756e7449642c20543a3a426c6f636b4e756d6265723e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e145072696d65000030543a3a4163636f756e744964040004650120546865207072696d65206d656d62657220746861742068656c70732064657465726d696e65207468652064656661756c7420766f7465206265686176696f7220696e2063617365206f6620616273656e746174696f6e732e01182c7365745f6d656d626572730c2c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e147072696d65504f7074696f6e3c543a3a4163636f756e7449643e246f6c645f636f756e742c4d656d626572436f756e746084205365742074686520636f6c6c6563746976652773206d656d626572736869702e004901202d20606e65775f6d656d62657273603a20546865206e6577206d656d626572206c6973742e204265206e69636520746f2074686520636861696e20616e642070726f7669646520697420736f727465642ee4202d20607072696d65603a20546865207072696d65206d656d6265722077686f736520766f74652073657473207468652064656661756c742e3901202d20606f6c645f636f756e74603a2054686520757070657220626f756e6420666f72207468652070726576696f7573206e756d626572206f66206d656d6265727320696e2073746f726167652eac202020202020202020202020202020205573656420666f722077656967687420657374696d6174696f6e2e005820526571756972657320726f6f74206f726967696e2e005501204e4f54453a20446f6573206e6f7420656e666f7263652074686520657870656374656420604d61784d656d6265727360206c696d6974206f6e2074686520616d6f756e74206f66206d656d626572732c206275742501202020202020207468652077656967687420657374696d6174696f6e732072656c79206f6e20697420746f20657374696d61746520646973706174636861626c65207765696768742e002c2023203c7765696768743e282023232057656967687454202d20604f284d50202b204e29602077686572653ae42020202d20604d60206f6c642d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429e42020202d20604e60206e65772d6d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e646564299c2020202d206050602070726f706f73616c732d636f756e742028636f64652d626f756e6465642918202d2044423a75012020202d20312073746f72616765206d75746174696f6e2028636f64656320604f284d296020726561642c20604f284e29602077726974652920666f722072656164696e6720616e642077726974696e6720746865206d656d62657273f02020202d20312073746f7261676520726561642028636f64656320604f285029602920666f722072656164696e67207468652070726f706f73616c7349012020202d206050602073746f72616765206d75746174696f6e732028636f64656320604f284d29602920666f72207570646174696e672074686520766f74657320666f7220656163682070726f706f73616c61012020202d20312073746f726167652077726974652028636f64656320604f283129602920666f722064656c6574696e6720746865206f6c6420607072696d656020616e642073657474696e6720746865206e6577206f6e65302023203c2f7765696768743e1c65786563757465082070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e28f420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e002c2023203c7765696768743e28202323205765696768748501202d20604f284d202b2050296020776865726520604d60206d656d626572732d636f756e742028636f64652d626f756e6465642920616e642060506020636f6d706c6578697479206f66206469737061746368696e67206070726f706f73616c60d8202d2044423a203120726561642028636f64656320604f284d296029202b20444220616363657373206f66206070726f706f73616c6028202d2031206576656e74302023203c2f7765696768743e1c70726f706f73650c247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c7c426f783c3c5420617320436f6e6669673c493e3e3a3a50726f706f73616c3e306c656e6774685f626f756e6430436f6d706163743c7533323e6cfc204164642061206e65772070726f706f73616c20746f2065697468657220626520766f746564206f6e206f72206578656375746564206469726563746c792e0088205265717569726573207468652073656e64657220746f206265206d656d6265722e00450120607468726573686f6c64602064657465726d696e65732077686574686572206070726f706f73616c60206973206578656375746564206469726563746c792028607468726573686f6c64203c2032602958206f722070757420757020666f7220766f74696e672e002c2023203c7765696768743e2820232320576569676874b0202d20604f2842202b204d202b2050312960206f7220604f2842202b204d202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429c82020202d206272616e6368696e6720697320696e666c75656e63656420627920607468726573686f6c64602077686572653af820202020202d20605031602069732070726f706f73616c20657865637574696f6e20636f6d706c65786974792028607468726573686f6c64203c20326029010120202020202d20605032602069732070726f706f73616c732d636f756e742028636f64652d626f756e646564292028607468726573686f6c64203e3d2032602918202d2044423ab82020202d20312073746f726167652072656164206069735f6d656d626572602028636f64656320604f284d296029f42020202d20312073746f726167652072656164206050726f706f73616c4f663a3a636f6e7461696e735f6b6579602028636f64656320604f2831296029ac2020202d20444220616363657373657320696e666c75656e63656420627920607468726573686f6c64603a0d0120202020202d204549544845522073746f7261676520616363657373657320646f6e65206279206070726f706f73616c602028607468726573686f6c64203c20326029bc20202020202d204f522070726f706f73616c20696e73657274696f6e2028607468726573686f6c64203c3d20326029dc202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c73602028636f64656320604f285032296029e8202020202020202d20312073746f72616765206d75746174696f6e206050726f706f73616c436f756e74602028636f64656320604f2831296029d0202020202020202d20312073746f72616765207772697465206050726f706f73616c4f66602028636f64656320604f2842296029c0202020202020202d20312073746f726167652077726974652060566f74696e67602028636f64656320604f284d296029302020202d2031206576656e74302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c38f42041646420616e20617965206f72206e617920766f746520666f72207468652073656e64657220746f2074686520676976656e2070726f706f73616c2e0090205265717569726573207468652073656e64657220746f2062652061206d656d6265722e004d01205472616e73616374696f6e20666565732077696c6c2062652077616976656420696620746865206d656d62657220697320766f74696e67206f6e20616e7920706172746963756c61722070726f706f73616c690120666f72207468652066697273742074696d6520616e64207468652063616c6c206973207375636365737366756c2e2053756273657175656e7420766f7465206368616e6765732077696c6c206368617267652061206665652e2c2023203c7765696768743e28202323205765696768740d01202d20604f284d296020776865726520604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e6465642918202d2044423ab02020202d20312073746f72616765207265616420604d656d62657273602028636f64656320604f284d296029bc2020202d20312073746f72616765206d75746174696f6e2060566f74696e67602028636f64656320604f284d29602928202d2031206576656e74302023203c2f7765696768743e14636c6f7365103470726f706f73616c5f686173681c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e5470726f706f73616c5f7765696768745f626f756e643c436f6d706163743c5765696768743e306c656e6774685f626f756e6430436f6d706163743c7533323e78510120436c6f7365206120766f746520746861742069732065697468657220617070726f7665642c20646973617070726f766564206f722077686f736520766f74696e6720706572696f642068617320656e6465642e005901204d61792062652063616c6c656420627920616e79207369676e6564206163636f756e7420696e206f7264657220746f2066696e69736820766f74696e6720616e6420636c6f7365207468652070726f706f73616c2e004d012049662063616c6c6564206265666f72652074686520656e64206f662074686520766f74696e6720706572696f642069742077696c6c206f6e6c7920636c6f73652074686520766f7465206966206974206973c02068617320656e6f75676820766f74657320746f20626520617070726f766564206f7220646973617070726f7665642e004d012049662063616c6c65642061667465722074686520656e64206f662074686520766f74696e6720706572696f642061627374656e74696f6e732061726520636f756e7465642061732072656a656374696f6e73290120756e6c6573732074686572652069732061207072696d65206d656d6265722073657420616e6420746865207072696d65206d656d626572206361737420616e20617070726f76616c2e0065012049662074686520636c6f7365206f7065726174696f6e20636f6d706c65746573207375636365737366756c6c79207769746820646973617070726f76616c2c20746865207472616e73616374696f6e206665652077696c6c6101206265207761697665642e204f746865727769736520657865637574696f6e206f662074686520617070726f766564206f7065726174696f6e2077696c6c206265206368617267656420746f207468652063616c6c65722e008d01202b206070726f706f73616c5f7765696768745f626f756e64603a20546865206d6178696d756d20616d6f756e74206f662077656967687420636f6e73756d656420627920657865637574696e672074686520636c6f7365642070726f706f73616c2e6501202b20606c656e6774685f626f756e64603a2054686520757070657220626f756e6420666f7220746865206c656e677468206f66207468652070726f706f73616c20696e2073746f726167652e20436865636b6564207669618101202020202020202020202020202020202020206073746f726167653a3a726561646020736f206974206973206073697a655f6f663a3a3c7533323e2829203d3d203460206c6172676572207468616e207468652070757265206c656e6774682e002c2023203c7765696768743e282023232057656967687478202d20604f2842202b204d202b205031202b20503229602077686572653ae42020202d20604260206973206070726f706f73616c602073697a6520696e20627974657320286c656e6774682d6665652d626f756e64656429e02020202d20604d60206973206d656d626572732d636f756e742028636f64652d20616e6420676f7665726e616e63652d626f756e64656429cc2020202d20605031602069732074686520636f6d706c6578697479206f66206070726f706f73616c6020707265696d6167652ea82020202d20605032602069732070726f706f73616c2d636f756e742028636f64652d626f756e6465642918202d2044423a110120202d20322073746f726167652072656164732028604d656d62657273603a20636f64656320604f284d29602c20605072696d65603a20636f64656320604f2831296029810120202d2033206d75746174696f6e73202860566f74696e67603a20636f64656320604f284d29602c206050726f706f73616c4f66603a20636f64656320604f284229602c206050726f706f73616c73603a20636f64656320604f285032296029e020202d20616e79206d75746174696f6e7320646f6e65207768696c6520657865637574696e67206070726f706f73616c602028605031602944202d20757020746f2033206576656e7473302023203c2f7765696768743e4c646973617070726f76655f70726f706f73616c043470726f706f73616c5f686173681c543a3a4861736834790120446973617070726f766520612070726f706f73616c2c20636c6f73652c20616e642072656d6f76652069742066726f6d207468652073797374656d2c207265676172646c657373206f66206974732063757272656e742073746174652e008c204d7573742062652063616c6c65642062792074686520526f6f74206f726967696e2e003020506172616d65746572733a2101202a206070726f706f73616c5f68617368603a205468652068617368206f66207468652070726f706f73616c20746861742073686f756c6420626520646973617070726f7665642e002c2023203c7765696768743ee020436f6d706c65786974793a204f285029207768657265205020697320746865206e756d626572206f66206d61782070726f706f73616c732c204442205765696768743a4c202a2052656164733a2050726f706f73616c73a0202a205772697465733a20566f74696e672c2050726f706f73616c732c2050726f706f73616c4f66302023203c2f7765696768743e011c2050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e740c4d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292ed8205c5b6163636f756e742c2070726f706f73616c5f696e6465782c2070726f706f73616c5f686173682c207468726573686f6c645c5d14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740c09012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292eac205c5b6163636f756e742c2070726f706f73616c5f686173682c20766f7465642c207965732c206e6f5c5d20417070726f76656404104861736808c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d2c446973617070726f76656404104861736808d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e48205c5b70726f706f73616c5f686173685c5d204578656375746564081048617368384469737061746368526573756c740825012041206d6f74696f6e207761732065786563757465643b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d384d656d6265724578656375746564081048617368384469737061746368526573756c74084d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b20726573756c742077696c6c20626520604f6b602069662069742072657475726e656420776974686f7574206572726f722e68205c5b70726f706f73616c5f686173682c20726573756c745c5d18436c6f7365640c10486173682c4d656d626572436f756e742c4d656d626572436f756e7408590120412070726f706f73616c2077617320636c6f736564206265636175736520697473207468726573686f6c64207761732072656163686564206f7220616674657220697473206475726174696f6e207761732075702e6c205c5b70726f706f73616c5f686173682c207965732c206e6f5c5d0028244e6f744d656d6265720460204163636f756e74206973206e6f742061206d656d626572444475706c696361746550726f706f73616c0480204475706c69636174652070726f706f73616c73206e6f7420616c6c6f7765643c50726f706f73616c4d697373696e6704502050726f706f73616c206d7573742065786973742857726f6e67496e6465780444204d69736d61746368656420696e646578344475706c6963617465566f7465045c204475706c696361746520766f74652069676e6f72656448416c7265616479496e697469616c697a65640484204d656d626572732061726520616c726561647920696e697469616c697a65642120546f6f4561726c790405012054686520636c6f73652063616c6c20776173206d61646520746f6f206561726c792c206265666f72652074686520656e64206f662074686520766f74696e672e40546f6f4d616e7950726f706f73616c730401012054686572652063616e206f6e6c792062652061206d6178696d756d206f6620604d617850726f706f73616c7360206163746976652070726f706f73616c732e4c57726f6e6750726f706f73616c57656967687404d42054686520676976656e2077656967687420626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e4c57726f6e6750726f706f73616c4c656e67746804d42054686520676976656e206c656e67746820626f756e6420666f72207468652070726f706f73616c2077617320746f6f206c6f772e0d24456c656374696f6e730124456c656374696f6e73141c4d656d626572730100ac5665633c53656174486f6c6465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e04000c74205468652063757272656e7420656c6563746564206d656d626572732e00b820496e76617269616e743a20416c7761797320736f72746564206261736564206f6e206163636f756e742069642e2452756e6e65727355700100ac5665633c53656174486f6c6465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e04001084205468652063757272656e742072657365727665642072756e6e6572732d75702e00590120496e76617269616e743a20416c7761797320736f72746564206261736564206f6e2072616e6b2028776f72736520746f2062657374292e2055706f6e2072656d6f76616c206f662061206d656d6265722c20746865bc206c6173742028692e652e205f626573745f292072756e6e65722d75702077696c6c206265207265706c616365642e2843616e646964617465730100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e0400185901205468652070726573656e742063616e646964617465206c6973742e20412063757272656e74206d656d626572206f722072756e6e65722d75702063616e206e6576657220656e746572207468697320766563746f72d020616e6420697320616c7761797320696d706c696369746c7920617373756d656420746f20626520612063616e6469646174652e007c205365636f6e6420656c656d656e7420697320746865206465706f7369742e00b820496e76617269616e743a20416c7761797320736f72746564206261736564206f6e206163636f756e742069642e38456c656374696f6e526f756e647301000c75333210000000000441012054686520746f74616c206e756d626572206f6620766f746520726f756e6473207468617420686176652068617070656e65642c206578636c7564696e6720746865207570636f6d696e67206f6e652e18566f74696e6701010530543a3a4163636f756e74496484566f7465723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e00840000000000000000000000000000000000000000000000000000000000000000000cb820566f74657320616e64206c6f636b6564207374616b65206f66206120706172746963756c617220766f7465722e00c42054574f582d4e4f54453a205341464520617320604163636f756e7449646020697320612063727970746f20686173682e011810766f74650814766f746573445665633c543a3a4163636f756e7449643e1476616c756554436f6d706163743c42616c616e63654f663c543e3e5c5d0120566f746520666f72206120736574206f662063616e6469646174657320666f7220746865207570636f6d696e6720726f756e64206f6620656c656374696f6e2e20546869732063616e2062652063616c6c656420746fe4207365742074686520696e697469616c20766f7465732c206f722075706461746520616c7265616479206578697374696e6720766f7465732e0061012055706f6e20696e697469616c20766f74696e672c206076616c75656020756e697473206f66206077686f6027732062616c616e6365206973206c6f636b656420616e642061206465706f73697420616d6f756e7420697351012072657365727665642e20546865206465706f736974206973206261736564206f6e20746865206e756d626572206f6620766f74657320616e642063616e2062652075706461746564206f7665722074696d652e0050205468652060766f746573602073686f756c643a482020202d206e6f7420626520656d7074792e59012020202d206265206c657373207468616e20746865206e756d626572206f6620706f737369626c652063616e646964617465732e204e6f7465207468617420616c6c2063757272656e74206d656d6265727320616e641501202020202072756e6e6572732d75702061726520616c736f206175746f6d61746963616c6c792063616e6469646174657320666f7220746865206e65787420726f756e642e005101204966206076616c756560206973206d6f7265207468616e206077686f60277320746f74616c2062616c616e63652c207468656e20746865206d6178696d756d206f66207468652074776f20697320757365642e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642e003020232323205761726e696e670059012049742069732074686520726573706f6e736962696c697479206f66207468652063616c6c657220746f202a2a4e4f542a2a20706c61636520616c6c206f662074686569722062616c616e636520696e746f20746865ac206c6f636b20616e64206b65657020736f6d6520666f722066757274686572206f7065726174696f6e732e002c2023203c7765696768743e550120576520617373756d6520746865206d6178696d756d2077656967687420616d6f6e6720616c6c20332063617365733a20766f74655f657175616c2c20766f74655f6d6f726520616e6420766f74655f6c6573732e302023203c2f7765696768743e3072656d6f76655f766f7465720014702052656d6f766520606f726967696e60206173206120766f7465722e00bc20546869732072656d6f76657320746865206c6f636b20616e642072657475726e7320746865206465706f7369742e00010120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e656420616e64206265206120766f7465722e407375626d69745f63616e646964616379043c63616e6469646174655f636f756e7430436f6d706163743c7533323e3c1501205375626d6974206f6e6573656c6620666f722063616e6469646163792e204120666978656420616d6f756e74206f66206465706f736974206973207265636f726465642e00610120416c6c2063616e64696461746573206172652077697065642061742074686520656e64206f6620746865207465726d2e205468657920656974686572206265636f6d652061206d656d6265722f72756e6e65722d75702cd0206f72206c65617665207468652073797374656d207768696c65207468656972206465706f73697420697320736c61736865642e00c420546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642e003020232323205761726e696e67006101204576656e20696620612063616e64696461746520656e6473207570206265696e672061206d656d6265722c2074686579206d7573742063616c6c205b6043616c6c3a3a72656e6f756e63655f63616e646964616379605d5d0120746f20676574207468656972206465706f736974206261636b2e204c6f73696e67207468652073706f7420696e20616e20656c656374696f6e2077696c6c20616c77617973206c65616420746f206120736c6173682e002c2023203c7765696768743e0d0120546865206e756d626572206f662063757272656e742063616e64696461746573206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e4872656e6f756e63655f63616e646964616379042872656e6f756e63696e672852656e6f756e63696e674451012052656e6f756e6365206f6e65277320696e74656e74696f6e20746f20626520612063616e64696461746520666f7220746865206e65787420656c656374696f6e20726f756e642e203320706f74656e7469616c40206f7574636f6d65732065786973743a004d01202d20606f726967696e6020697320612063616e64696461746520616e64206e6f7420656c656374656420696e20616e79207365742e20496e207468697320636173652c20746865206465706f736974206973f4202020756e72657365727665642c2072657475726e656420616e64206f726967696e2069732072656d6f76656420617320612063616e6469646174652e6501202d20606f726967696e6020697320612063757272656e742072756e6e65722d75702e20496e207468697320636173652c20746865206465706f73697420697320756e72657365727665642c2072657475726e656420616e64902020206f726967696e2069732072656d6f76656420617320612072756e6e65722d75702e5901202d20606f726967696e6020697320612063757272656e74206d656d6265722e20496e207468697320636173652c20746865206465706f73697420697320756e726573657276656420616e64206f726967696e206973590120202072656d6f7665642061732061206d656d6265722c20636f6e73657175656e746c79206e6f74206265696e6720612063616e64696461746520666f7220746865206e65787420726f756e6420616e796d6f72652e550120202053696d696c617220746f205b6072656d6f76655f6d656d62657273605d2c206966207265706c6163656d656e742072756e6e657273206578697374732c20746865792061726520696d6d6564696174656c794d01202020757365642e20496620746865207072696d652069732072656e6f756e63696e672c207468656e206e6f207072696d652077696c6c20657869737420756e74696c20746865206e65787420726f756e642e00490120546865206469737061746368206f726967696e206f6620746869732063616c6c206d757374206265207369676e65642c20616e642068617665206f6e65206f66207468652061626f766520726f6c65732e002c2023203c7765696768743ee4205468652074797065206f662072656e6f756e63696e67206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e3472656d6f76655f6d656d626572080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653c6861735f7265706c6163656d656e7410626f6f6c385d012052656d6f7665206120706172746963756c6172206d656d6265722066726f6d20746865207365742e20546869732069732065666665637469766520696d6d6564696174656c7920616e642074686520626f6e64206f668020746865206f7574676f696e67206d656d62657220697320736c61736865642e00590120496620612072756e6e65722d757020697320617661696c61626c652c207468656e2074686520626573742072756e6e65722d75702077696c6c2062652072656d6f76656420616e64207265706c61636573207468650101206f7574676f696e67206d656d6265722e204f74686572776973652c2061206e65772070687261676d656e20656c656374696f6e20697320737461727465642e00bc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520726f6f742e004501204e6f74652074686174207468697320646f6573206e6f7420616666656374207468652064657369676e6174656420626c6f636b206e756d626572206f6620746865206e65787420656c656374696f6e2e002c2023203c7765696768743e550120496620776520686176652061207265706c6163656d656e742c20776520757365206120736d616c6c207765696768742e20456c73652c2073696e63652074686973206973206120726f6f742063616c6c20616e64d42077696c6c20676f20696e746f2070687261676d656e2c20776520617373756d652066756c6c20626c6f636b20666f72206e6f772e302023203c2f7765696768743e50636c65616e5f646566756e63745f766f74657273082c5f6e756d5f766f746572730c753332305f6e756d5f646566756e63740c75333228490120436c65616e20616c6c20766f746572732077686f2061726520646566756e63742028692e652e207468657920646f206e6f7420736572766520616e7920707572706f736520617420616c6c292e20546865b0206465706f736974206f66207468652072656d6f76656420766f74657273206172652072657475726e65642e000501205468697320697320616e20726f6f742066756e6374696f6e20746f2062652075736564206f6e6c7920666f7220636c65616e696e67207468652073746174652e00bc20546865206469737061746368206f726967696e206f6620746869732063616c6c206d75737420626520726f6f742e002c2023203c7765696768743e61012054686520746f74616c206e756d626572206f6620766f7465727320616e642074686f736520746861742061726520646566756e6374206d7573742062652070726f7669646564206173207769746e65737320646174612e302023203c2f7765696768743e011c1c4e65775465726d04645665633c284163636f756e7449642c2042616c616e6365293e1459012041206e6577207465726d2077697468205c5b6e65775f6d656d626572735c5d2e205468697320696e64696361746573207468617420656e6f7567682063616e64696461746573206578697374656420746f2072756e59012074686520656c656374696f6e2c206e6f74207468617420656e6f756768206861766520686173206265656e20656c65637465642e2054686520696e6e65722076616c7565206d757374206265206578616d696e6564490120666f72207468697320707572706f73652e204120604e65775465726d285c5b5c5d296020696e64696361746573207468617420736f6d652063616e6469646174657320676f7420746865697220626f6e64590120736c617368656420616e64206e6f6e65207765726520656c65637465642c207768696c73742060456d7074795465726d60206d65616e732074686174206e6f2063616e64696461746573206578697374656420746f3020626567696e20776974682e24456d7074795465726d00083501204e6f20286f72206e6f7420656e6f756768292063616e64696461746573206578697374656420666f72207468697320726f756e642e205468697320697320646966666572656e742066726f6dcc20604e65775465726d285c5b5c5d29602e2053656520746865206465736372697074696f6e206f6620604e65775465726d602e34456c656374696f6e4572726f720004e820496e7465726e616c206572726f722068617070656e6564207768696c6520747279696e6720746f20706572666f726d20656c656374696f6e2e304d656d6265724b69636b656404244163636f756e7449640855012041205c5b6d656d6265725c5d20686173206265656e2072656d6f7665642e20546869732073686f756c6420616c7761797320626520666f6c6c6f7765642062792065697468657220604e65775465726d60206f72342060456d7074795465726d602e2452656e6f756e63656404244163636f756e744964049c20536f6d656f6e65206861732072656e6f756e6365642074686569722063616e6469646163792e4043616e646964617465536c617368656408244163636f756e7449641c42616c616e6365105d012041205c5b63616e6469646174655c5d2077617320736c6173686564206279205c5b616d6f756e745c5d2064756520746f206661696c696e6720746f206f627461696e20612073656174206173206d656d626572206f722c2072756e6e65722d75702e00e8204e6f74652074686174206f6c64206d656d6265727320616e642072756e6e6572732d75702061726520616c736f2063616e646964617465732e4453656174486f6c646572536c617368656408244163636f756e7449641c42616c616e63650459012041205c5b7365617420686f6c6465725c5d2077617320736c6173686564206279205c5b616d6f756e745c5d206279206265696e6720666f72636566756c6c792072656d6f7665642066726f6d20746865207365742e1c2050616c6c65744964384c6f636b4964656e74696669657220706872656c65637404d0204964656e74696669657220666f722074686520656c656374696f6e732d70687261676d656e2070616c6c65742773206c6f636b3443616e646964616379426f6e643042616c616e63654f663c543e400080c6a47e8d0300000000000000000004050120486f77206d7563682073686f756c64206265206c6f636b656420757020696e206f7264657220746f207375626d6974206f6e6527732063616e6469646163792e38566f74696e67426f6e64426173653042616c616e63654f663c543e4000f0436de36a0100000000000000000010942042617365206465706f736974206173736f636961746564207769746820766f74696e672e00550120546869732073686f756c642062652073656e7369626c79206869676820746f2065636f6e6f6d6963616c6c7920656e73757265207468652070616c6c65742063616e6e6f742062652061747461636b656420627994206372656174696e67206120676967616e746963206e756d626572206f6620766f7465732e40566f74696e67426f6e64466163746f723042616c616e63654f663c543e400000cc7b9fae000000000000000000000411012054686520616d6f756e74206f6620626f6e642074686174206e65656420746f206265206c6f636b656420666f72206561636820766f746520283332206279746573292e38446573697265644d656d626572730c753332100d0000000470204e756d626572206f66206d656d6265727320746f20656c6563742e404465736972656452756e6e65727355700c75333210070000000478204e756d626572206f662072756e6e6572735f757020746f206b6565702e305465726d4475726174696f6e38543a3a426c6f636b4e756d62657210801303000c510120486f77206c6f6e6720656163682073656174206973206b6570742e205468697320646566696e657320746865206e65787420626c6f636b206e756d62657220617420776869636820616e20656c656374696f6e5d0120726f756e642077696c6c2068617070656e2e2049662073657420746f207a65726f2c206e6f20656c656374696f6e732061726520657665722074726967676572656420616e6420746865206d6f64756c652077696c6c5020626520696e2070617373697665206d6f64652e4430556e61626c65546f566f746504c42043616e6e6f7420766f7465207768656e206e6f2063616e64696461746573206f72206d656d626572732065786973742e1c4e6f566f7465730498204d75737420766f746520666f72206174206c65617374206f6e652063616e6469646174652e30546f6f4d616e79566f74657304882043616e6e6f7420766f7465206d6f7265207468616e2063616e646964617465732e504d6178696d756d566f7465734578636565646564049c2043616e6e6f7420766f7465206d6f7265207468616e206d6178696d756d20616c6c6f7765642e284c6f7742616c616e636504c82043616e6e6f7420766f74652077697468207374616b65206c657373207468616e206d696e696d756d2062616c616e63652e3c556e61626c65546f506179426f6e64047c20566f7465722063616e206e6f742070617920766f74696e6720626f6e642e2c4d7573744265566f7465720444204d757374206265206120766f7465722e285265706f727453656c6604502043616e6e6f74207265706f72742073656c662e4c4475706c69636174656443616e6469646174650484204475706c6963617465642063616e646964617465207375626d697373696f6e2e304d656d6265725375626d6974048c204d656d6265722063616e6e6f742072652d7375626d69742063616e6469646163792e3852756e6e657255705375626d6974048c2052756e6e65722063616e6e6f742072652d7375626d69742063616e6469646163792e68496e73756666696369656e7443616e64696461746546756e647304982043616e64696461746520646f6573206e6f74206861766520656e6f7567682066756e64732e244e6f744d656d6265720438204e6f742061206d656d6265722e48496e76616c69645769746e6573734461746104e4205468652070726f766964656420636f756e74206f66206e756d626572206f662063616e6469646174657320697320696e636f72726563742e40496e76616c6964566f7465436f756e7404d0205468652070726f766964656420636f756e74206f66206e756d626572206f6620766f74657320697320696e636f72726563742e44496e76616c696452656e6f756e63696e67040101205468652072656e6f756e63696e67206f726967696e2070726573656e74656420612077726f6e67206052656e6f756e63696e676020706172616d657465722e48496e76616c69645265706c6163656d656e740401012050726564696374696f6e20726567617264696e67207265706c6163656d656e74206166746572206d656d6265722072656d6f76616c2069732077726f6e672e0e4c546563686e6963616c4d656d62657273686970014c496e7374616e6365314d656d62657273686970081c4d656d626572730100445665633c543a3a4163636f756e7449643e040004c8205468652063757272656e74206d656d626572736869702c2073746f72656420617320616e206f726465726564205665632e145072696d65000030543a3a4163636f756e744964040004a4205468652063757272656e74207072696d65206d656d6265722c206966206f6e65206578697374732e011c286164645f6d656d626572040c77686f30543a3a4163636f756e7449640c7c204164642061206d656d626572206077686f6020746f20746865207365742e00a0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a4164644f726967696e602e3472656d6f76655f6d656d626572040c77686f30543a3a4163636f756e7449640c902052656d6f76652061206d656d626572206077686f602066726f6d20746865207365742e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656d6f76654f726967696e602e2c737761705f6d656d626572081872656d6f766530543a3a4163636f756e7449640c61646430543a3a4163636f756e74496414c02053776170206f7574206f6e65206d656d626572206072656d6f76656020666f7220616e6f746865722060616464602e00a4204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a537761704f726967696e602e001101205072696d65206d656d62657273686970206973202a6e6f742a207061737365642066726f6d206072656d6f76656020746f2060616464602c20696620657874616e742e3472657365745f6d656d62657273041c6d656d62657273445665633c543a3a4163636f756e7449643e105901204368616e676520746865206d656d6265727368697020746f2061206e6577207365742c20646973726567617264696e6720746865206578697374696e67206d656d626572736869702e204265206e69636520616e646c207061737320606d656d6265727360207072652d736f727465642e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52657365744f726967696e602e286368616e67655f6b6579040c6e657730543a3a4163636f756e74496414d82053776170206f7574207468652073656e64696e67206d656d62657220666f7220736f6d65206f74686572206b657920606e6577602e00f4204d6179206f6e6c792062652063616c6c65642066726f6d20605369676e656460206f726967696e206f6620612063757272656e74206d656d6265722e002101205072696d65206d656d62657273686970206973207061737365642066726f6d20746865206f726967696e206163636f756e7420746f20606e6577602c20696620657874616e742e247365745f7072696d65040c77686f30543a3a4163636f756e7449640cc02053657420746865207072696d65206d656d6265722e204d75737420626520612063757272656e74206d656d6265722e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e2c636c6561725f7072696d65000c982052656d6f766520746865207072696d65206d656d626572206966206974206578697374732e00a8204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a5072696d654f726967696e602e01182c4d656d62657241646465640004e42054686520676976656e206d656d626572207761732061646465643b2073656520746865207472616e73616374696f6e20666f722077686f2e344d656d62657252656d6f7665640004ec2054686520676976656e206d656d626572207761732072656d6f7665643b2073656520746865207472616e73616374696f6e20666f722077686f2e384d656d62657273537761707065640004dc2054776f206d656d62657273207765726520737761707065643b2073656520746865207472616e73616374696f6e20666f722077686f2e304d656d6265727352657365740004190120546865206d656d62657273686970207761732072657365743b2073656520746865207472616e73616374696f6e20666f722077686f20746865206e6577207365742069732e284b65794368616e676564000488204f6e65206f6620746865206d656d6265727327206b657973206368616e6765642e1444756d6d7904bc73705f7374643a3a6d61726b65723a3a5068616e746f6d446174613c284163636f756e7449642c204576656e74293e0470205068616e746f6d206d656d6265722c206e6576657220757365642e000834416c72656164794d656d626572044820416c72656164792061206d656d6265722e244e6f744d656d6265720438204e6f742061206d656d6265722e0f1c4772616e647061011c4772616e6470611814537461746501006c53746f72656453746174653c543a3a426c6f636b4e756d6265723e04000490205374617465206f66207468652063757272656e7420617574686f72697479207365742e3450656e64696e674368616e676500008c53746f72656450656e64696e674368616e67653c543a3a426c6f636b4e756d6265723e040004c42050656e64696e67206368616e67653a20287369676e616c65642061742c207363686564756c6564206368616e6765292e284e657874466f72636564000038543a3a426c6f636b4e756d626572040004bc206e65787420626c6f636b206e756d6265722077686572652077652063616e20666f7263652061206368616e67652e1c5374616c6c656400008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d626572290400049020607472756560206966207765206172652063757272656e746c79207374616c6c65642e3043757272656e7453657449640100145365744964200000000000000000085d0120546865206e756d626572206f66206368616e6765732028626f746820696e207465726d73206f66206b65797320616e6420756e6465726c79696e672065636f6e6f6d696320726573706f6e736962696c697469657329c420696e20746865202273657422206f66204772616e6470612076616c696461746f72732066726f6d2067656e657369732e30536574496453657373696f6e0001051453657449643053657373696f6e496e6465780004001059012041206d617070696e672066726f6d206772616e6470612073657420494420746f2074686520696e646578206f6620746865202a6d6f737420726563656e742a2073657373696f6e20666f722077686963682069747368206d656d62657273207765726520726573706f6e7369626c652e00b82054574f582d4e4f54453a2060536574496460206973206e6f7420756e646572207573657220636f6e74726f6c2e010c4c7265706f72745f65717569766f636174696f6e084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66100d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e707265706f72745f65717569766f636174696f6e5f756e7369676e6564084865717569766f636174696f6e5f70726f6f66a845717569766f636174696f6e50726f6f663c543a3a486173682c20543a3a426c6f636b4e756d6265723e3c6b65795f6f776e65725f70726f6f6640543a3a4b65794f776e657250726f6f66240d01205265706f727420766f7465722065717569766f636174696f6e2f6d69736265686176696f722e2054686973206d6574686f642077696c6c2076657269667920746865f82065717569766f636174696f6e2070726f6f6620616e642076616c69646174652074686520676976656e206b6579206f776e6572736869702070726f6f66fc20616761696e73742074686520657874726163746564206f6666656e6465722e20496620626f7468206172652076616c69642c20746865206f6666656e6365482077696c6c206265207265706f727465642e00110120546869732065787472696e736963206d7573742062652063616c6c656420756e7369676e656420616e642069742069732065787065637465642074686174206f6e6c79190120626c6f636b20617574686f72732077696c6c2063616c6c206974202876616c69646174656420696e206056616c6964617465556e7369676e656460292c206173207375636819012069662074686520626c6f636b20617574686f7220697320646566696e65642069742077696c6c20626520646566696e6564206173207468652065717569766f636174696f6e28207265706f727465722e306e6f74655f7374616c6c6564081464656c617938543a3a426c6f636b4e756d6265726c626573745f66696e616c697a65645f626c6f636b5f6e756d62657238543a3a426c6f636b4e756d6265721c1d01204e6f74652074686174207468652063757272656e7420617574686f7269747920736574206f6620746865204752414e4450412066696e616c69747920676164676574206861732901207374616c6c65642e20546869732077696c6c2074726967676572206120666f7263656420617574686f7269747920736574206368616e67652061742074686520626567696e6e696e672101206f6620746865206e6578742073657373696f6e2c20746f20626520656e6163746564206064656c61796020626c6f636b7320616674657220746861742e205468652064656c617915012073686f756c64206265206869676820656e6f75676820746f20736166656c7920617373756d6520746861742074686520626c6f636b207369676e616c6c696e6720746865290120666f72636564206368616e67652077696c6c206e6f742062652072652d6f726765642028652e672e203130303020626c6f636b73292e20546865204752414e44504120766f7465727329012077696c6c20737461727420746865206e657720617574686f7269747920736574207573696e672074686520676976656e2066696e616c697a656420626c6f636b20617320626173652e5c204f6e6c792063616c6c61626c6520627920726f6f742e010c384e6577417574686f7269746965730434417574686f726974794c69737404d8204e657720617574686f726974792073657420686173206265656e206170706c6965642e205c5b617574686f726974795f7365745c5d1850617573656400049c2043757272656e7420617574686f726974792073657420686173206265656e207061757365642e1c526573756d65640004a02043757272656e7420617574686f726974792073657420686173206265656e20726573756d65642e001c2c50617573654661696c656408090120417474656d707420746f207369676e616c204752414e445041207061757365207768656e2074686520617574686f72697479207365742069736e2774206c697665a8202865697468657220706175736564206f7220616c72656164792070656e64696e67207061757365292e30526573756d654661696c656408150120417474656d707420746f207369676e616c204752414e44504120726573756d65207768656e2074686520617574686f72697479207365742069736e277420706175736564a42028656974686572206c697665206f7220616c72656164792070656e64696e6720726573756d65292e344368616e676550656e64696e6704ec20417474656d707420746f207369676e616c204752414e445041206368616e67652077697468206f6e6520616c72656164792070656e64696e672e1c546f6f536f6f6e04c02043616e6e6f74207369676e616c20666f72636564206368616e676520736f20736f6f6e206166746572206c6173742e60496e76616c69644b65794f776e65727368697050726f6f660435012041206b6579206f776e6572736869702070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e60496e76616c696445717569766f636174696f6e50726f6f6604350120416e2065717569766f636174696f6e2070726f6f662070726f76696465642061732070617274206f6620616e2065717569766f636174696f6e207265706f727420697320696e76616c69642e584475706c69636174654f6666656e63655265706f7274041901204120676976656e2065717569766f636174696f6e207265706f72742069732076616c69642062757420616c72656164792070726576696f75736c79207265706f727465642e10205472656173757279012054726561737572790c3450726f706f73616c436f756e7401003450726f706f73616c496e646578100000000004a4204e756d626572206f662070726f706f73616c7320746861742068617665206265656e206d6164652e2450726f706f73616c730001053450726f706f73616c496e6465789c50726f706f73616c3c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e000400047c2050726f706f73616c7320746861742068617665206265656e206d6164652e24417070726f76616c730100a8426f756e6465645665633c50726f706f73616c496e6465782c20543a3a4d6178417070726f76616c733e040004f82050726f706f73616c20696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f742079657420617761726465642e010c3470726f706f73655f7370656e64081476616c756560436f6d706163743c42616c616e63654f663c542c20493e3e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365242d012050757420666f727761726420612073756767657374696f6e20666f72207370656e64696e672e2041206465706f7369742070726f706f7274696f6e616c20746f207468652076616c7565350120697320726573657276656420616e6420736c6173686564206966207468652070726f706f73616c2069732072656a65637465642e2049742069732072657475726e6564206f6e636520746865542070726f706f73616c20697320617761726465642e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129b4202d20446252656164733a206050726f706f73616c436f756e74602c20606f726967696e206163636f756e7460ec202d2044625772697465733a206050726f706f73616c436f756e74602c206050726f706f73616c73602c20606f726967696e206163636f756e7460302023203c2f7765696768743e3c72656a6563745f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e24fc2052656a65637420612070726f706f736564207370656e642e20546865206f726967696e616c206465706f7369742077696c6c20626520736c61736865642e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656a6563744f726967696e602e002c2023203c7765696768743e4c202d20436f6d706c65786974793a204f283129d0202d20446252656164733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460d4202d2044625772697465733a206050726f706f73616c73602c206072656a65637465642070726f706f736572206163636f756e7460302023203c2f7765696768743e40617070726f76655f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e285d0120417070726f766520612070726f706f73616c2e2041742061206c617465722074696d652c207468652070726f706f73616c2077696c6c20626520616c6c6f636174656420746f207468652062656e6566696369617279ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e50202d20436f6d706c65786974793a204f2831292e90202d20446252656164733a206050726f706f73616c73602c2060417070726f76616c73605c202d20446257726974653a2060417070726f76616c7360302023203c2f7765696768743e011c2050726f706f736564043450726f706f73616c496e6465780484204e65772070726f706f73616c2e205c5b70726f706f73616c5f696e6465785c5d205370656e64696e67041c42616c616e6365043d01205765206861766520656e6465642061207370656e6420706572696f6420616e642077696c6c206e6f7720616c6c6f636174652066756e64732e205c5b6275646765745f72656d61696e696e675c5d1c417761726465640c3450726f706f73616c496e6465781c42616c616e6365244163636f756e744964041d0120536f6d652066756e64732068617665206265656e20616c6c6f63617465642e205c5b70726f706f73616c5f696e6465782c2061776172642c2062656e65666963696172795c5d2052656a6563746564083450726f706f73616c496e6465781c42616c616e636504250120412070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e205c5b70726f706f73616c5f696e6465782c20736c61736865645c5d144275726e74041c42616c616e636504b020536f6d65206f66206f75722066756e64732068617665206265656e206275726e742e205c5b6275726e5c5d20526f6c6c6f766572041c42616c616e6365083101205370656e64696e67206861732066696e69736865643b20746869732069732074686520616d6f756e74207468617420726f6c6c73206f76657220756e74696c206e657874207370656e642e54205c5b6275646765745f72656d61696e696e675c5d1c4465706f736974041c42616c616e636504b020536f6d652066756e64732068617665206265656e206465706f73697465642e205c5b6465706f7369745c5d143050726f706f73616c426f6e641c5065726d696c6c1050c30000085501204672616374696f6e206f6620612070726f706f73616c27732076616c756520746861742073686f756c6420626520626f6e64656420696e206f7264657220746f20706c616365207468652070726f706f73616c2e110120416e2061636365707465642070726f706f73616c2067657473207468657365206261636b2e20412072656a65637465642070726f706f73616c20646f6573206e6f742e4c50726f706f73616c426f6e644d696e696d756d3c42616c616e63654f663c542c20493e4000407a10f35a00000000000000000000044901204d696e696d756d20616d6f756e74206f662066756e647320746861742073686f756c6420626520706c6163656420696e2061206465706f73697420666f72206d616b696e6720612070726f706f73616c2e2c5370656e64506572696f6438543a3a426c6f636b4e756d6265721080700000048820506572696f64206265747765656e2073756363657373697665207370656e64732e104275726e1c5065726d696c6c1020a107000411012050657263656e74616765206f662073706172652066756e64732028696620616e7929207468617420617265206275726e7420706572207370656e6420706572696f642e2050616c6c657449642050616c6c657449642070792f7472737279041901205468652074726561737572792773206d6f64756c652069642c207573656420666f72206465726976696e672069747320736f7665726569676e206163636f756e742049442e0c70496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e30496e76616c6964496e6465780494204e6f2070726f706f73616c206f7220626f756e7479206174207468617420696e6465782e40546f6f4d616e79417070726f76616c73048420546f6f206d616e7920617070726f76616c7320696e207468652071756575652e1124436f6e7472616374730124436f6e74726163747314305072697374696e65436f64650001062c436f6465486173683c543e1c5665633c75383e0004000465012041206d617070696e672066726f6d20616e206f726967696e616c20636f6465206861736820746f20746865206f726967696e616c20636f64652c20756e746f756368656420627920696e737472756d656e746174696f6e2e2c436f646553746f726167650001062c436f6465486173683c543e4c5072656661625761736d4d6f64756c653c543e0004000465012041206d617070696e67206265747765656e20616e206f726967696e616c20636f6465206861736820616e6420696e737472756d656e746564207761736d20636f64652c20726561647920666f7220657865637574696f6e2e384163636f756e74436f756e74657201000c753634200000000000000000045420546865207375627472696520636f756e7465722e38436f6e7472616374496e666f4f6600010530543a3a4163636f756e7449643c436f6e7472616374496e666f3c543e0004000ca82054686520636f6465206173736f6369617465642077697468206120676976656e206163636f756e742e00d02054574f582d4e4f54453a20534146452073696e636520604163636f756e7449646020697320612073656375726520686173682e3444656c6574696f6e51756575650100505665633c44656c65746564436f6e74726163743e040010c8204576696374656420636f6e7472616374732074686174206177616974206368696c6420747269652064656c6574696f6e2e004901204368696c6420747269652064656c6574696f6e2069732061206865617679206f7065726174696f6e20646570656e64696e67206f6e2074686520616d6f756e74206f662073746f72616765206974656d7359012073746f72656420696e207361696420747269652e205468657265666f72652074686973206f7065726174696f6e20697320706572666f726d6564206c617a696c7920696e20606f6e5f696e697469616c697a65602e01101063616c6c1010646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e10646174611c5665633c75383e1c0901204d616b657320612063616c6c20746f20616e206163636f756e742c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e002901202a20496620746865206163636f756e74206973206120736d6172742d636f6e7472616374206163636f756e742c20746865206173736f63696174656420636f64652077696c6c206265b020657865637574656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e1901202a20496620746865206163636f756e74206973206120726567756c6172206163636f756e742c20616e792076616c75652077696c6c206265207472616e736665727265642e4901202a204966206e6f206163636f756e742065786973747320616e64207468652063616c6c2076616c7565206973206e6f74206c657373207468616e20606578697374656e7469616c5f6465706f736974602c1501206120726567756c6172206163636f756e742077696c6c206265206372656174656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e54696e7374616e74696174655f776974685f636f64651424656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e10636f64651c5665633c75383e10646174611c5665633c75383e1073616c741c5665633c75383e54350120496e7374616e7469617465732061206e657720636f6e74726163742066726f6d2074686520737570706c6965642060636f646560206f7074696f6e616c6c79207472616e7366657272696e673820736f6d652062616c616e63652e000501205468697320697320746865206f6e6c792066756e6374696f6e20746861742063616e206465706c6f79206e657720636f646520746f2074686520636861696e2e0034202320506172616d6574657273006101202a2060656e646f776d656e74603a205468652062616c616e636520746f207472616e736665722066726f6d2074686520606f726967696e6020746f20746865206e65776c79206372656174656420636f6e74726163742e1901202a20606761735f6c696d6974603a2054686520676173206c696d697420656e666f72636564207768656e20657865637574696e672074686520636f6e7374727563746f722ed0202a2060636f6465603a2054686520636f6e747261637420636f646520746f206465706c6f7920696e207261772062797465732ef8202a206064617461603a2054686520696e707574206461746120746f207061737320746f2074686520636f6e747261637420636f6e7374727563746f722e3501202a206073616c74603a205573656420666f722074686520616464726573732064657269766174696f6e2e20536565205b6050616c6c65743a3a636f6e74726163745f61646472657373605d2e009820496e7374616e74696174696f6e20697320657865637574656420617320666f6c6c6f77733a007501202d2054686520737570706c6965642060636f64656020697320696e737472756d656e7465642c206465706c6f7965642c20616e6420612060636f64655f6861736860206973206372656174656420666f72207468617420636f64652e5d01202d204966207468652060636f64655f686173686020616c726561647920657869737473206f6e2074686520636861696e2074686520756e6465726c79696e672060636f6465602077696c6c206265207368617265642e4d01202d205468652064657374696e6174696f6e206164647265737320697320636f6d7075746564206261736564206f6e207468652073656e6465722c20636f64655f6861736820616e64207468652073616c742e0501202d2054686520736d6172742d636f6e7472616374206163636f756e7420697320637265617465642061742074686520636f6d707574656420616464726573732ed4202d205468652060656e646f776d656e7460206973207472616e7366657272656420746f20746865206e6577206163636f756e742e4501202d2054686520606465706c6f79602066756e6374696f6e20697320657865637574656420696e2074686520636f6e74657874206f6620746865206e65776c792d63726561746564206163636f756e742e2c696e7374616e74696174651424656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d69743c436f6d706163743c5765696768743e24636f64655f686173682c436f6465486173683c543e10646174611c5665633c75383e1073616c741c5665633c75383e14010120496e7374616e746961746573206120636f6e74726163742066726f6d20612070726576696f75736c79206465706c6f796564207761736d2062696e6172792e00390120546869732066756e6374696f6e206973206964656e746963616c20746f205b6053656c663a3a696e7374616e74696174655f776974685f636f6465605d2062757420776974686f7574207468654d0120636f6465206465706c6f796d656e7420737465702e20496e73746561642c207468652060636f64655f6861736860206f6620616e206f6e2d636861696e206465706c6f796564207761736d2062696e61727948206d75737420626520737570706c6965642e3c636c61696d5f73757263686172676508106465737430543a3a4163636f756e744964286175785f73656e646572504f7074696f6e3c543a3a4163636f756e7449643e244d0120416c6c6f777320626c6f636b2070726f64756365727320746f20636c61696d206120736d616c6c2072657761726420666f72206576696374696e67206120636f6e74726163742e204966206120626c6f636b39012070726f6475636572206661696c7320746f20646f20736f2c206120726567756c61722075736572732077696c6c20626520616c6c6f77656420746f20636c61696d20746865207265776172642e004d0120496e2063617365206f662061207375636365737366756c206576696374696f6e206e6f20666565732061726520636861726765642066726f6d207468652073656e6465722e20486f77657665722c20746865450120726577617264206973206361707065642062792074686520746f74616c20616d6f756e74206f662072656e7420746861742077617320706169642062792074686520636f6e7472616374207768696c65382069742077617320616c6976652e00550120496620636f6e7472616374206973206e6f742065766963746564206173206120726573756c74206f6620746869732063616c6c2c205b604572726f723a3a436f6e74726163744e6f74457669637461626c65605dec2069732072657475726e656420616e64207468652073656e646572206973206e6f7420656c696769626c6520666f7220746865207265776172642e012030496e7374616e74696174656408244163636f756e744964244163636f756e74496404390120436f6e7472616374206465706c6f7965642062792061646472657373206174207468652073706563696669656420616464726573732e205c5b6465706c6f7965722c20636f6e74726163745c5d1c4576696374656404244163636f756e74496404190120436f6e747261637420686173206265656e206576696374656420616e64206973206e6f7720696e20746f6d6273746f6e652073746174652e205c5b636f6e74726163745c5d285465726d696e6174656408244163636f756e744964244163636f756e74496430e820436f6e747261637420686173206265656e207465726d696e6174656420776974686f7574206c656176696e67206120746f6d6273746f6e652e68205c5b636f6e74726163742c2062656e65666963696172795c5d0024202320506172616d7300c0202d2060636f6e7472616374603a2054686520636f6e7472616374207468617420776173207465726d696e617465642e3101202d206062656e6566696369617279603a20546865206163636f756e7420746861742072656365697665642074686520636f6e7472616374732072656d61696e696e672062616c616e63652e001c2023204e6f7465002d0120546865206f6e6c792077617920666f72206120636f6e747261637420746f2062652072656d6f76656420776974686f7574206120746f6d6273746f6e6520616e6420656d697474696e67ac2074686973206576656e742069732062792063616c6c696e6720607365616c5f7465726d696e617465602e20526573746f72656410244163636f756e744964244163636f756e74496410486173681c42616c616e636524bc20526573746f726174696f6e206f66206120636f6e747261637420686173206265656e207375636365737366756c2eb8205c5b726573746f7265722c20646573742c20636f64655f686173682c2072656e745f616c6c6f77616e63655c5d0024202320506172616d7300d0202d2060726573746f726572603a204163636f756e74204944206f662074686520726573746f72696e6720636f6e74726163742ebc202d206064657374603a204163636f756e74204944206f662074686520726573746f72656420636f6e74726163742ecc202d2060636f64655f68617368603a20436f64652068617368206f662074686520726573746f72656420636f6e74726163742ef4202d206072656e745f616c6c6f77616e6365603a2052656e7420616c6c6f77616e6365206f662074686520726573746f72656420636f6e74726163742e28436f646553746f72656404104861736804f020436f646520776974682074686520737065636966696564206861736820686173206265656e2073746f7265642e205c5b636f64655f686173685c5d3c5363686564756c6555706461746564040c75333218c020547269676765726564207768656e207468652063757272656e74207363686564756c6520697320757064617465642e30205c5b76657273696f6e5c5d0024202320506172616d7300d0202d206076657273696f6e603a205468652076657273696f6e206f6620746865206e65776c7920736574207363686564756c652e3c436f6e7472616374456d697474656408244163636f756e7449641c5665633c75383e20a0204120637573746f6d206576656e7420656d69747465642062792074686520636f6e74726163742e4c205c5b636f6e74726163742c20646174615c5d0024202320506172616d7300cc202d2060636f6e7472616374603a2054686520636f6e7472616374207468617420656d697474656420746865206576656e742e3101202d206064617461603a204461746120737570706c6965642062792074686520636f6e74726163742e204d657461646174612067656e65726174656420647572696e6720636f6e7472616374b82020202020202020202020636f6d70696c6174696f6e206973206e656564656420746f206465636f64652069742e2c436f646552656d6f76656404104861736810b0204120636f6465207769746820746865207370656369666965642068617368207761732072656d6f7665642e38205c5b636f64655f686173685c5d00550120546869732068617070656e73207768656e20746865206c61737420636f6e747261637420746861742075736573207468697320636f64652068617368207761732072656d6f766564206f7220657669637465642e28205363686564756c652c5363686564756c653c543ed1090400000000020000000100008000000010000000001000000001000020000000200000000040000000000200020000008e0f0000b04602009a8c0300a9720000767600005e380000ea5e00000753000097000000579e030088130500b60000007a170000c11100005721000099370000483a0000d0110000d8d12c08bc4300005c430000bb2e0000a942000000260000b72300009c370000ad540000de540000ca5400000354000018550000e553000011550000c053000007540000da540000a0530000e85300008d5400004a690000bd680000a56a000096670000b053000013540000055400006a5500009255000060550000f455000033550000cae32900000000007a332a00000000004041290000000000a6fb5d000000000060c02a0000000000e6d6290000000000065329000000000062002a0000000000d425290000000000b0522a00000000005cb3540000000000b41c1600000000008057640000000000000100000000000008f6380000000000710200000000000078d68a210000000098d6de2a000000007c75640900000000466d6f000000000070baac0000000000ec73de07000000007406000000000000922c190000000000fc9f1d00000000008618ee0900000000450200000000000082dc6108000000003e573102000000002704000000000000cc94430b000000009406e1100000000096fa930800000000dc010000000000009c020000000000001843c12400000000f001000000000000b80200000000000094070000000000008a9b2a0000000000561200000000000046432b0000000000ab0c000000000000c08c260000000000b005000000000000acd2260000000000b005000000000000046820436f7374207363686564756c6520616e64206c696d6974732e4c5369676e6564436c61696d48616e646963617038543a3a426c6f636b4e756d626572100200000010e0204e756d626572206f6620626c6f636b2064656c617920616e2065787472696e73696320636c61696d20737572636861726765206861732e000d01205768656e20636c61696d207375726368617267652069732063616c6c656420627920616e2065787472696e736963207468652072656e7420697320636865636b65646820666f722063757272656e745f626c6f636b202d2064656c617940546f6d6273746f6e654465706f7369743042616c616e63654f663c543e4000f0e8857a9c0200000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f2067656e6572617465206120746f6d6273746f6e652e484465706f736974506572436f6e74726163743042616c616e63654f663c543e4000f0e8857a9c02000000000000000000202101205468652062616c616e636520657665727920636f6e7472616374206e6565647320746f206465706f73697420746f207374617920616c69766520696e646566696e6974656c792e005101205468697320697320646966666572656e742066726f6d20746865205b6053656c663a3a546f6d6273746f6e654465706f736974605d20626563617573652074686973206f6e6c79206e6565647320746f2062654501206465706f7369746564207768696c652074686520636f6e747261637420697320616c6976652e20436f73747320666f72206164646974696f6e616c2073746f726167652061726520616464656420746f402074686973206261736520636f73742e006d01205468697320697320612073696d706c652077617920746f20656e73757265207468617420636f6e747261637473207769746820656d7074792073746f72616765206576656e7475616c6c79206765742064656c657465642062797101206d616b696e67207468656d207061792072656e742e2054686973206372656174657320616e20696e63656e7469766520746f2072656d6f7665207468656d206561726c7920696e206f7264657220746f20736176652072656e742e544465706f73697450657253746f72616765427974653042616c616e63654f663c543e400060defb740500000000000000000000185501205468652062616c616e6365206120636f6e7472616374206e6565647320746f206465706f736974207065722073746f72616765206279746520746f207374617920616c69766520696e646566696e6974656c792e006901204c6574277320737570706f736520746865206465706f73697420697320312c303030204255202862616c616e636520756e697473292f6279746520616e64207468652072656e7420697320312042552f627974652f6461792c5901207468656e206120636f6e7472616374207769746820312c3030302c3030302042552074686174207573657320312c303030206279746573206f662073746f7261676520776f756c6420706179206e6f2072656e742e4d0120427574206966207468652062616c616e6365207265647563656420746f203530302c30303020425520616e64207468652073746f7261676520737461796564207468652073616d6520617420312c3030302c78207468656e20697420776f756c6420706179203530302042552f6461792e544465706f73697450657253746f726167654974656d3042616c616e63654f663c543e4000f0ab75a40d000000000000000000000c5501205468652062616c616e6365206120636f6e7472616374206e6565647320746f206465706f736974207065722073746f72616765206974656d20746f207374617920616c69766520696e646566696e6974656c792e00310120497420776f726b73207468652073616d65206173205b6053656c663a3a4465706f73697450657253746f7261676542797465605d2062757420666f722073746f72616765206974656d732e3052656e744672616374696f6e1c50657262696c6c1085040000140d0120546865206672616374696f6e206f6620746865206465706f73697420746861742073686f756c6420626520757365642061732072656e742070657220626c6f636b2e005101205768656e206120636f6e7472616374206861736e277420656e6f7567682062616c616e6365206465706f736974656420746f207374617920616c69766520696e646566696e6974656c79206974206e65656473450120746f207061792070657220626c6f636b20666f72207468652073746f7261676520697420636f6e73756d65732074686174206973206e6f7420636f766572656420627920746865206465706f7369742e590120546869732064657465726d696e657320686f77206869676820746869732072656e74207061796d656e742069732070657220626c6f636b2061732061206672616374696f6e206f6620746865206465706f7369742e3c5375726368617267655265776172643042616c616e63654f663c543e40005cb2ec22000000000000000000000008e4205265776172642074686174206973207265636569766564206279207468652070617274792077686f736520746f75636820686173206c65646820746f2072656d6f76616c206f66206120636f6e74726163742e4844656c6574696f6e517565756544657074680c753332101a04000004f420546865206d6178696d756d206e756d626572206f6620747269657320746861742063616e2062652071756575656420666f722064656c6574696f6e2e4c44656c6574696f6e5765696768744c696d6974185765696768742000d0ed902e000000044d0120546865206d6178696d756d20616d6f756e74206f662077656967687420746861742063616e20626520636f6e73756d65642070657220626c6f636b20666f72206c617a7920747269652072656d6f76616c2e8858496e76616c69645363686564756c6556657273696f6e0405012041206e6577207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652063757272656e74206f6e652e54496e76616c6964537572636861726765436c61696d04550120416e206f726967696e206d757374206265207369676e6564206f7220696e686572656e7420616e6420617578696c696172792073656e646572206f6e6c792070726f7669646564206f6e20696e686572656e742e54496e76616c6964536f75726365436f6e747261637404dc2043616e6e6f7420726573746f72652066726f6d206e6f6e6578697374696e67206f7220746f6d6273746f6e6520636f6e74726163742e68496e76616c696444657374696e6174696f6e436f6e747261637404c42043616e6e6f7420726573746f726520746f206e6f6e6578697374696e67206f7220616c69766520636f6e74726163742e40496e76616c6964546f6d6273746f6e65046020546f6d6273746f6e657320646f6e2774206d617463682e54496e76616c6964436f6e74726163744f726967696e04bc20416e206f726967696e20547269654964207772697474656e20696e207468652063757272656e7420626c6f636b2e204f75744f6647617304bc2054686520657865637574656420636f6e7472616374206578686175737465642069747320676173206c696d69742e504f7574707574427566666572546f6f536d616c6c04050120546865206f75747075742062756666657220737570706c69656420746f206120636f6e7472616374204150492063616c6c2077617320746f6f20736d616c6c2e6442656c6f7753756273697374656e63655468726573686f6c6410210120506572666f726d696e672074686520726571756573746564207472616e7366657220776f756c6420686176652062726f756768742074686520636f6e74726163742062656c6f773d01207468652073756273697374656e6365207468726573686f6c642e204e6f207472616e7366657220697320616c6c6f77656420746f20646f207468697320696e206f7264657220746f20616c6c6f77450120666f72206120746f6d6273746f6e6520746f20626520637265617465642e2055736520607365616c5f7465726d696e6174656020746f2072656d6f7665206120636f6e747261637420776974686f757470206c656176696e67206120746f6d6273746f6e6520626568696e642e504e6577436f6e74726163744e6f7446756e64656408390120546865206e65776c79206372656174656420636f6e74726163742069732062656c6f77207468652073756273697374656e6365207468726573686f6c6420616674657220657865637574696e6721012069747320636f6e74727563746f722e204e6f20636f6e7472616374732061726520616c6c6f77656420746f2065786973742062656c6f772074686174207468726573686f6c642e385472616e736665724661696c65640c250120506572666f726d696e672074686520726571756573746564207472616e73666572206661696c656420666f72206120726561736f6e206f726967696e6174696e6720696e2074686531012063686f73656e2063757272656e637920696d706c656d656e746174696f6e206f66207468652072756e74696d652e204d6f73742070726f6261626c79207468652062616c616e63652069738c20746f6f206c6f77206f72206c6f636b732061726520706c61636564206f6e2069742e4c4d617843616c6c44657074685265616368656408250120506572666f726d696e6720612063616c6c207761732064656e6965642062656361757365207468652063616c6c696e67206465707468207265616368656420746865206c696d697498206f6620776861742069732073706563696669656420696e20746865207363686564756c652e40436f6e74726163744e6f74466f756e6404c0204e6f20636f6e74726163742077617320666f756e64206174207468652073706563696669656420616464726573732e4c436f6e74726163744973546f6d6273746f6e6510b0204120746f6d6273746f6e65206578697374206174207468652073706563696669656420616464726573732e00410120546f6d6273746f6e652063616e6e6f742062652063616c6c65642e20416e796f6e652063616e2075736520607365616c5f726573746f72655f746f6020696e206f7264657220746f20726576697665582074686520636f6e74726163742c2074686f7567682e2c52656e744e6f7450616964182501205468652063616c6c656420636f6e747261637420646f6573206e6f74206861766520656e6f7567682062616c616e636520746f2070617920666f72206974732073746f726167652e0039012054686520636f6e74726163742072616e206f7574206f662062616c616e636520616e64206973207468657265666f726520656c696769626c6520666f72206576696374696f6e20696e746f20612d0120746f6d6273746f6e652e20416e796f6e652063616e2065766963742074686520636f6e7472616374206279207375626d697474696e6720612060636c61696d5f737572636861726765602d012065787472696e7369632e20416c7465726e61746976656c792c206120706c61696e2062616c616e6365207472616e736665722063616e206265207573656420696e206f7264657220746ff420696e6372656173652074686520636f6e7472616374732066756e647320736f20746861742069742063616e2062652063616c6c656420616761696e2e30436f6465546f6f4c617267650841012054686520636f646520737570706c69656420746f2060696e7374616e74696174655f776974685f636f646560206578636565647320746865206c696d69742073706563696669656420696e20746865482063757272656e74207363686564756c652e30436f64654e6f74466f756e6404c8204e6f20636f646520636f756c6420626520666f756e642061742074686520737570706c69656420636f646520686173682e2c4f75744f66426f756e6473042901204120627566666572206f757473696465206f662073616e64626f78206d656d6f7279207761732070617373656420746f206120636f6e7472616374204150492066756e6374696f6e2e384465636f64696e674661696c6564042d0120496e7075742070617373656420746f206120636f6e7472616374204150492066756e6374696f6e206661696c656420746f206465636f646520617320657870656374656420747970652e3c436f6e747261637454726170706564048c20436f6e7472616374207472617070656420647572696e6720657865637574696f6e2e3456616c7565546f6f4c6172676504d0205468652073697a6520646566696e656420696e2060543a3a4d617856616c756553697a6560207761732065786365656465642e605465726d696e617465645768696c655265656e7472616e74081d01205465726d696e6174696f6e206f66206120636f6e7472616374206973206e6f7420616c6c6f776564207768696c652074686520636f6e747261637420697320616c72656164793501206f6e207468652063616c6c20737461636b2e2043616e2062652074726967676572656420627920607365616c5f7465726d696e61746560206f7220607365616c5f726573746f72655f746f2e38496e707574466f7277617264656404450120607365616c5f63616c6c6020666f72776172646564207468697320636f6e74726163747320696e7075742e204974207468657265666f7265206973206e6f206c6f6e67657220617661696c61626c652e5052616e646f6d5375626a656374546f6f4c6f6e6704dc20546865207375626a6563742070617373656420746f20607365616c5f72616e646f6d60206578636565647320746865206c696d69742e34546f6f4d616e79546f706963730421012054686520616d6f756e74206f6620746f706963732070617373656420746f20607365616c5f6465706f7369745f6576656e747360206578636565647320746865206c696d69742e3c4475706c6963617465546f706963730431012054686520746f706963732070617373656420746f20607365616c5f6465706f7369745f6576656e74736020636f6e7461696e73206174206c65617374206f6e65206475706c69636174652e404e6f436861696e457874656e73696f6e0c49012054686520636861696e20646f6573206e6f742070726f76696465206120636861696e20657874656e73696f6e2e2043616c6c696e672074686520636861696e20657874656e73696f6e20726573756c7473510120696e2074686973206572726f722e204e6f74652074686174207468697320757375616c6c79202073686f756c646e27742068617070656e206173206465706c6f79696e67207375636820636f6e747261637473342069732072656a65637465642e4444656c6574696f6e517565756546756c6c1405012052656d6f76616c206f66206120636f6e7472616374206661696c65642062656361757365207468652064656c6574696f6e2071756575652069732066756c6c2e00550120546869732063616e2068617070656e207768656e206569746865722063616c6c696e67205b6050616c6c65743a3a636c61696d5f737572636861726765605d206f7220607365616c5f7465726d696e617465602e5101205468652071756575652069732066696c6c65642062792064656c6574696e6720636f6e74726163747320616e6420656d7074696564206279206120666978656420616d6f756e74206561636820626c6f636b2e250120547279696e6720616761696e20647572696e6720616e6f7468657220626c6f636b20697320746865206f6e6c792077617920746f207265736f6c766520746869732069737375652e50436f6e74726163744e6f74457669637461626c65102d01204120636f6e747261637420636f756c64206e6f74206265206576696374656420626563617573652069742068617320656e6f7567682062616c616e636520746f207061792072656e742e00250120546869732063616e2062652072657475726e65642066726f6d205b6050616c6c65743a3a636c61696d5f737572636861726765605d20626563617573652074686520746172676574c420636f6e74726163742068617320656e6f7567682062616c616e636520746f2070617920666f72206974732072656e742e4053746f7261676545786861757374656410350120412073746f72616765206d6f64696669636174696f6e20657868617573746564207468652033326269742074797065207468617420686f6c6473207468652073746f726167652073697a652e00350120546869732063616e206569746865722068617070656e207768656e2074686520616363756d756c617465642073746f7261676520696e20627974657320697320746f6f206c61726765206f72ac207768656e206e756d626572206f662073746f72616765206974656d7320697320746f6f206c617267652e444475706c6963617465436f6e747261637404cc204120636f6e74726163742077697468207468652073616d65204163636f756e74496420616c7265616479206578697374732e5c5465726d696e61746564496e436f6e7374727563746f720cbc204120636f6e74726163742073656c66206465737472756374656420696e2069747320636f6e7374727563746f722e00290120546869732063616e2062652074726967676572656420627920612063616c6c20746f20607365616c5f7465726d696e61746560206f7220607365616c5f726573746f72655f746f602e5c44656275674d657373616765496e76616c69645554463804410120546865206465627567206d6573736167652073706563696669656420746f20607365616c5f64656275675f6d6573736167656020646f657320636f6e7461696e20696e76616c6964205554462d382e405265656e7472616e636544656e69656404110120412063616c6c20747269656420746f20696e766f6b65206120636f6e7472616374207468617420697320666c6167676564206173206e6f6e2d7265656e7472616e742e12105375646f01105375646f040c4b6579010030543a3a4163636f756e74496480000000000000000000000000000000000000000000000000000000000000000004842054686520604163636f756e74496460206f6620746865207375646f206b65792e0110107375646f041063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e547375646f5f756e636865636b65645f776569676874081063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e1c5f776569676874185765696768742839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e310120546869732066756e6374696f6e20646f6573206e6f7420636865636b2074686520776569676874206f66207468652063616c6c2c20616e6420696e737465616420616c6c6f777320746865b4205375646f207573657220746f20737065636966792074686520776569676874206f66207468652063616c6c2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292ed0202d2054686520776569676874206f6620746869732063616c6c20697320646566696e6564206279207468652063616c6c65722e302023203c2f7765696768743e1c7365745f6b6579040c6e65778c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652475012041757468656e74696361746573207468652063757272656e74207375646f206b657920616e6420736574732074686520676976656e204163636f756e7449642028606e6577602920617320746865206e6577207375646f206b65792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e1c7375646f5f6173080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2c51012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c207769746820605369676e656460206f726967696e2066726f6d44206120676976656e206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ec8202d20576569676874206f662064657269766174697665206063616c6c6020657865637574696f6e202b2031302c3030302e302023203c2f7765696768743e010c14537564696404384469737061746368526573756c74048c2041207375646f206a75737420746f6f6b20706c6163652e205c5b726573756c745c5d284b65794368616e67656404244163636f756e74496404010120546865205c5b7375646f65725c5d206a757374207377697463686564206964656e746974793b20746865206f6c64206b657920697320737570706c6965642e285375646f4173446f6e6504384469737061746368526573756c74048c2041207375646f206a75737420746f6f6b20706c6163652e205c5b726573756c745c5d00042c526571756972655375646f04802053656e646572206d75737420626520746865205375646f206163636f756e741320496d4f6e6c696e650120496d4f6e6c696e6510384865617274626561744166746572010038543a3a426c6f636b4e756d62657210000000002c1d012054686520626c6f636b206e756d6265722061667465722077686963682069742773206f6b20746f2073656e64206865617274626561747320696e207468652063757272656e74242073657373696f6e2e0025012041742074686520626567696e6e696e67206f6620656163682073657373696f6e20776520736574207468697320746f20612076616c756520746861742073686f756c642066616c6c350120726f7567686c7920696e20746865206d6964646c65206f66207468652073657373696f6e206475726174696f6e2e20546865206964656120697320746f206669727374207761697420666f721901207468652076616c696461746f727320746f2070726f64756365206120626c6f636b20696e207468652063757272656e742073657373696f6e2c20736f207468617420746865a820686561727462656174206c61746572206f6e2077696c6c206e6f74206265206e65636573736172792e00390120546869732076616c75652077696c6c206f6e6c79206265207573656420617320612066616c6c6261636b206966207765206661696c20746f2067657420612070726f7065722073657373696f6e2d012070726f677265737320657374696d6174652066726f6d20604e65787453657373696f6e526f746174696f6e602c2061732074686f736520657374696d617465732073686f756c642062650101206d6f7265206163637572617465207468656e207468652076616c75652077652063616c63756c61746520666f7220604865617274626561744166746572602e104b65797301004c5665633c543a3a417574686f7269747949643e040004d0205468652063757272656e7420736574206f66206b6579732074686174206d61792069737375652061206865617274626561742e485265636569766564486561727462656174730002053053657373696f6e496e6465782441757468496e6465781c5665633c75383e05040008f020466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206041757468496e6465786020746f8020606f6666636861696e3a3a4f70617175654e6574776f726b5374617465602e38417574686f726564426c6f636b730102053053657373696f6e496e6465783856616c696461746f7249643c543e0c75333205100000000008150120466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206056616c696461746f7249643c543e6020746f20746865c8206e756d626572206f6620626c6f636b7320617574686f7265642062792074686520676976656e20617574686f726974792e0104246865617274626561740824686561727462656174644865617274626561743c543a3a426c6f636b4e756d6265723e285f7369676e6174757265bc3c543a3a417574686f7269747949642061732052756e74696d654170705075626c69633e3a3a5369676e6174757265242c2023203c7765696768743e4101202d20436f6d706c65786974793a20604f284b202b20452960207768657265204b206973206c656e677468206f6620604b6579736020286865617274626561742e76616c696461746f72735f6c656e290101202020616e642045206973206c656e677468206f6620606865617274626561742e6e6574776f726b5f73746174652e65787465726e616c5f61646472657373608c2020202d20604f284b29603a206465636f64696e67206f66206c656e67746820604b60b02020202d20604f284529603a206465636f64696e672f656e636f64696e67206f66206c656e677468206045603d01202d20446252656164733a2070616c6c65745f73657373696f6e206056616c696461746f7273602c2070616c6c65745f73657373696f6e206043757272656e74496e646578602c20604b657973602c5c202020605265636569766564486561727462656174736084202d2044625772697465733a206052656365697665644865617274626561747360302023203c2f7765696768743e010c444865617274626561745265636569766564042c417574686f7269747949640405012041206e657720686561727462656174207761732072656365697665642066726f6d2060417574686f72697479496460205c5b617574686f726974795f69645c5d1c416c6c476f6f640004d42041742074686520656e64206f66207468652073657373696f6e2c206e6f206f6666656e63652077617320636f6d6d69747465642e2c536f6d654f66666c696e6504605665633c4964656e74696669636174696f6e5475706c653e043d012041742074686520656e64206f66207468652073657373696f6e2c206174206c65617374206f6e652076616c696461746f722077617320666f756e6420746f206265205c5b6f66666c696e655c5d2e000828496e76616c69644b65790464204e6f6e206578697374656e74207075626c6963206b65792e4c4475706c6963617465644865617274626561740458204475706c696361746564206865617274626561742e1448417574686f72697479446973636f76657279000000000015204f6666656e63657301204f6666656e6365730c1c5265706f727473000105345265706f727449644f663c543ed04f6666656e636544657461696c733c543a3a4163636f756e7449642c20543a3a4964656e74696669636174696f6e5475706c653e00040004490120546865207072696d61727920737472756374757265207468617420686f6c647320616c6c206f6666656e6365207265636f726473206b65796564206279207265706f7274206964656e746966696572732e58436f6e63757272656e745265706f727473496e646578010205104b696e64384f706171756554696d65536c6f74485665633c5265706f727449644f663c543e3e050400042901204120766563746f72206f66207265706f727473206f66207468652073616d65206b696e6420746861742068617070656e6564206174207468652073616d652074696d6520736c6f742e485265706f72747342794b696e64496e646578010105104b696e641c5665633c75383e00040018110120456e756d65726174657320616c6c207265706f727473206f662061206b696e6420616c6f6e672077697468207468652074696d6520746865792068617070656e65642e00bc20416c6c207265706f7274732061726520736f72746564206279207468652074696d65206f66206f6666656e63652e004901204e6f74652074686174207468652061637475616c2074797065206f662074686973206d617070696e6720697320605665633c75383e602c207468697320697320626563617573652076616c756573206f66690120646966666572656e7420747970657320617265206e6f7420737570706f7274656420617420746865206d6f6d656e7420736f2077652061726520646f696e6720746865206d616e75616c2073657269616c697a6174696f6e2e0001041c4f6666656e636508104b696e64384f706171756554696d65536c6f740c550120546865726520697320616e206f6666656e6365207265706f72746564206f662074686520676976656e20606b696e64602068617070656e656420617420746865206073657373696f6e5f696e6465786020616e64390120286b696e642d7370656369666963292074696d6520736c6f742e2054686973206576656e74206973206e6f74206465706f736974656420666f72206475706c696361746520736c61736865732e50205c5b6b696e642c2074696d65736c6f745c5d2e00001628486973746f726963616c0000000000176052616e646f6d6e657373436f6c6c656374697665466c6970016052616e646f6d6e657373436f6c6c656374697665466c6970043852616e646f6d4d6174657269616c0100305665633c543a3a486173683e04000c610120536572696573206f6620626c6f636b20686561646572732066726f6d20746865206c61737420383120626c6f636b73207468617420616374732061732072616e646f6d2073656564206d6174657269616c2e2054686973610120697320617272616e67656420617320612072696e672062756666657220776974682060626c6f636b5f6e756d626572202520383160206265696e672074686520696e64657820696e746f20746865206056656360206f664420746865206f6c6465737420686173682e0000000018204964656e7469747901204964656e7469747910284964656e746974794f6600010530543a3a4163636f756e74496468526567697374726174696f6e3c42616c616e63654f663c543e3e0004000c210120496e666f726d6174696f6e20746861742069732070657274696e656e7420746f206964656e746966792074686520656e7469747920626568696e6420616e206163636f756e742e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e1c53757065724f6600010230543a3a4163636f756e7449645028543a3a4163636f756e7449642c204461746129000400086101205468652073757065722d6964656e74697479206f6620616e20616c7465726e6174697665202273756222206964656e7469747920746f676574686572207769746820697473206e616d652c2077697468696e2074686174510120636f6e746578742e20496620746865206163636f756e74206973206e6f7420736f6d65206f74686572206163636f756e742773207375622d6964656e746974792c207468656e206a75737420604e6f6e65602e18537562734f6601010530543a3a4163636f756e744964842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e290044000000000000000000000000000000000014b820416c7465726e6174697665202273756222206964656e746974696573206f662074686973206163636f756e742e001d0120546865206669727374206974656d20697320746865206465706f7369742c20746865207365636f6e64206973206120766563746f72206f6620746865206163636f756e74732e00c02054574f582d4e4f54453a204f4b20e2809520604163636f756e7449646020697320612073656375726520686173682e28526567697374726172730100d85665633c4f7074696f6e3c526567697374726172496e666f3c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e3e0400104d012054686520736574206f6620726567697374726172732e204e6f7420657870656374656420746f206765742076657279206269672061732063616e206f6e6c79206265206164646564207468726f7567682061a8207370656369616c206f726967696e20286c696b656c79206120636f756e63696c206d6f74696f6e292e0029012054686520696e64657820696e746f20746869732063616e206265206361737420746f2060526567697374726172496e6465786020746f2067657420612076616c69642076616c75652e013c346164645f726567697374726172041c6163636f756e7430543a3a4163636f756e744964347c2041646420612072656769737472617220746f207468652073797374656d2e00010120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060543a3a5265676973747261724f726967696e602e00ac202d20606163636f756e74603a20746865206163636f756e74206f6620746865207265676973747261722e009820456d6974732060526567697374726172416464656460206966207375636365737366756c2e002c2023203c7765696768743e2901202d20604f2852296020776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e64656420616e6420636f64652d626f756e646564292e9c202d204f6e652073746f72616765206d75746174696f6e2028636f64656320604f28522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e307365745f6964656e746974790410696e666f304964656e74697479496e666f4c2d012053657420616e206163636f756e742773206964656e7469747920696e666f726d6174696f6e20616e6420726573657276652074686520617070726f707269617465206465706f7369742e00590120496620746865206163636f756e7420616c726561647920686173206964656e7469747920696e666f726d6174696f6e2c20746865206465706f7369742069732074616b656e2061732070617274207061796d656e745420666f7220746865206e6577206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0090202d2060696e666f603a20546865206964656e7469747920696e666f726d6174696f6e2e008c20456d69747320604964656e7469747953657460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2858202b205827202b2052296021012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e64656429e42020202d20776865726520605260206a756467656d656e74732d636f756e7420287265676973747261722d636f756e742d626f756e6465642984202d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e2501202d204f6e652073746f72616765206d75746174696f6e2028636f6465632d7265616420604f285827202b205229602c20636f6465632d777269746520604f2858202b20522960292e34202d204f6e65206576656e742e302023203c2f7765696768743e207365745f73756273041073756273645665633c28543a3a4163636f756e7449642c2044617461293e54902053657420746865207375622d6163636f756e7473206f66207468652073656e6465722e005901205061796d656e743a20416e79206167677265676174652062616c616e63652072657365727665642062792070726576696f757320607365745f73756273602063616c6c732077696c6c2062652072657475726e6564310120616e6420616e20616d6f756e7420605375624163636f756e744465706f736974602077696c6c20626520726573657276656420666f722065616368206974656d20696e206073756273602e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e00b4202d206073756273603a20546865206964656e74697479277320286e657729207375622d6163636f756e74732e002c2023203c7765696768743e34202d20604f2850202b20532960e82020202d20776865726520605060206f6c642d737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e88202d204174206d6f7374206f6e652062616c616e6365206f7065726174696f6e732e18202d2044423ae02020202d206050202b2053602073746f72616765206d75746174696f6e732028636f64656320636f6d706c657869747920604f2831296029c02020202d204f6e652073746f7261676520726561642028636f64656320636f6d706c657869747920604f28502960292ec42020202d204f6e652073746f726167652077726974652028636f64656320636f6d706c657869747920604f28532960292ed42020202d204f6e652073746f726167652d6578697374732028604964656e746974794f663a3a636f6e7461696e735f6b657960292e302023203c2f7765696768743e38636c6561725f6964656e7469747900483d0120436c65617220616e206163636f756e742773206964656e7469747920696e666f20616e6420616c6c207375622d6163636f756e747320616e642072657475726e20616c6c206465706f736974732e00f0205061796d656e743a20416c6c2072657365727665642062616c616e636573206f6e20746865206163636f756e74206172652072657475726e65642e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061207265676973746572656428206964656e746974792e009c20456d69747320604964656e74697479436c656172656460206966207375636365737366756c2e002c2023203c7765696768743e44202d20604f2852202b2053202b20582960d02020202d20776865726520605260207265676973747261722d636f756e742028676f7665726e616e63652d626f756e646564292ed82020202d2077686572652060536020737562732d636f756e742028686172642d20616e64206465706f7369742d626f756e646564292e25012020202d20776865726520605860206164646974696f6e616c2d6669656c642d636f756e7420286465706f7369742d626f756e64656420616e6420636f64652d626f756e646564292e8c202d204f6e652062616c616e63652d756e72657365727665206f7065726174696f6e2ecc202d206032602073746f7261676520726561647320616e64206053202b2032602073746f726167652064656c6574696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e44726571756573745f6a756467656d656e7408247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e1c6d61785f66656554436f6d706163743c42616c616e63654f663c543e3e5c9820526571756573742061206a756467656d656e742066726f6d2061207265676973747261722e005901205061796d656e743a204174206d6f737420606d61785f666565602077696c6c20626520726573657276656420666f72207061796d656e7420746f2074686520726567697374726172206966206a756467656d656e741c20676976656e2e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e002101202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973207265717565737465642e5901202d20606d61785f666565603a20546865206d6178696d756d206665652074686174206d617920626520706169642e20546869732073686f756c64206a757374206265206175746f2d706f70756c617465642061733a0034206060606e6f636f6d70696c65bc2053656c663a3a7265676973747261727328292e676574287265675f696e646578292e756e7772617028292e666565102060606000a820456d69747320604a756467656d656e7452657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2858202b205229602e34202d204f6e65206576656e742e302023203c2f7765696768743e3863616e63656c5f7265717565737404247265675f696e64657838526567697374726172496e646578446c2043616e63656c20612070726576696f757320726571756573742e00fc205061796d656e743a20412070726576696f75736c79207265736572766564206465706f7369742069732072657475726e6564206f6e20737563636573732e00390120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652061542072656769737465726564206964656e746974792e004901202d20607265675f696e646578603a2054686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206e6f206c6f6e676572207265717565737465642e00b020456d69747320604a756467656d656e74556e72657175657374656460206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e8c202d204f6e652073746f72616765206d75746174696f6e20604f2852202b205829602e30202d204f6e65206576656e74302023203c2f7765696768743e1c7365745f6665650814696e6465785c436f6d706163743c526567697374726172496e6465783e0c66656554436f6d706163743c42616c616e63654f663c543e3e341d0120536574207468652066656520726571756972656420666f722061206a756467656d656e7420746f206265207265717565737465642066726f6d2061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e58202d2060666565603a20746865206e6577206665652e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e333135202b2052202a20302e33323920c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e387365745f6163636f756e745f69640814696e6465785c436f6d706163743c526567697374726172496e6465783e0c6e657730543a3a4163636f756e74496434c0204368616e676520746865206163636f756e74206173736f63696174656420776974682061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e74202d20606e6577603a20746865206e6577206163636f756e742049442e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee4202d2042656e63686d61726b3a20382e383233202b2052202a20302e333220c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e287365745f6669656c64730814696e6465785c436f6d706163743c526567697374726172496e6465783e186669656c6473384964656e746974794669656c647334ac2053657420746865206669656c6420696e666f726d6174696f6e20666f722061207265676973747261722e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74a4206f6620746865207265676973747261722077686f736520696e6465782069732060696e646578602e00f8202d2060696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f73652066656520697320746f206265207365742e1101202d20606669656c6473603a20746865206669656c64732074686174207468652072656769737472617220636f6e6365726e73207468656d73656c76657320776974682e002c2023203c7765696768743e28202d20604f285229602e7c202d204f6e652073746f72616765206d75746174696f6e20604f285229602ee8202d2042656e63686d61726b3a20372e343634202b2052202a20302e33323520c2b57320286d696e207371756172657320616e616c7973697329302023203c2f7765696768743e4470726f766964655f6a756467656d656e740c247265675f696e6465785c436f6d706163743c526567697374726172496e6465783e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365246a756467656d656e745c4a756467656d656e743c42616c616e63654f663c543e3e4cbc2050726f766964652061206a756467656d656e7420666f7220616e206163636f756e742773206964656e746974792e00590120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420626520746865206163636f756e74b4206f6620746865207265676973747261722077686f736520696e64657820697320607265675f696e646578602e002501202d20607265675f696e646578603a2074686520696e646578206f6620746865207265676973747261722077686f7365206a756467656d656e74206973206265696e67206d6164652e5901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e4d01202d20606a756467656d656e74603a20746865206a756467656d656e74206f662074686520726567697374726172206f6620696e64657820607265675f696e646578602061626f75742060746172676574602e009820456d69747320604a756467656d656e74476976656e60206966207375636365737366756c2e002c2023203c7765696768743e38202d20604f2852202b205829602e88202d204f6e652062616c616e63652d7472616e73666572206f7065726174696f6e2e98202d20557020746f206f6e65206163636f756e742d6c6f6f6b7570206f7065726174696f6e2ebc202d2053746f726167653a2031207265616420604f285229602c2031206d757461746520604f2852202b205829602e34202d204f6e65206576656e742e302023203c2f7765696768743e346b696c6c5f6964656e7469747904187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263654c45012052656d6f766520616e206163636f756e742773206964656e7469747920616e64207375622d6163636f756e7420696e666f726d6174696f6e20616e6420736c61736820746865206465706f736974732e006501205061796d656e743a2052657365727665642062616c616e6365732066726f6d20607365745f737562736020616e6420607365745f6964656e74697479602061726520736c617368656420616e642068616e646c656420627949012060536c617368602e20566572696669636174696f6e2072657175657374206465706f7369747320617265206e6f742072657475726e65643b20746865792073686f756c642062652063616e63656c6c656484206d616e75616c6c79207573696e67206063616e63656c5f72657175657374602e00fc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206d617463682060543a3a466f7263654f726967696e602e005901202d2060746172676574603a20746865206163636f756e742077686f7365206964656e7469747920746865206a756467656d656e742069732075706f6e2e2054686973206d75737420626520616e206163636f756e74782020207769746820612072656769737465726564206964656e746974792e009820456d69747320604964656e746974794b696c6c656460206966207375636365737366756c2e002c2023203c7765696768743e48202d20604f2852202b2053202b205829602e84202d204f6e652062616c616e63652d72657365727665206f7065726174696f6e2e74202d206053202b2032602073746f72616765206d75746174696f6e732e34202d204f6e65206576656e742e302023203c2f7765696768743e1c6164645f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365106461746110446174611cb0204164642074686520676976656e206163636f756e7420746f207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656e616d655f737562080c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651064617461104461746110d020416c74657220746865206173736f636961746564206e616d65206f662074686520676976656e207375622d6163636f756e742e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e2872656d6f76655f737562040c7375628c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651cc42052656d6f76652074686520676976656e206163636f756e742066726f6d207468652073656e646572277320737562732e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c2062652072657061747269617465643c20746f207468652073656e6465722e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d7573742068617665206120726567697374657265645c20737562206964656e74697479206f662060737562602e20717569745f7375620028902052656d6f7665207468652073656e6465722061732061207375622d6163636f756e742e006101205061796d656e743a2042616c616e636520726573657276656420627920612070726576696f757320607365745f73756273602063616c6c20666f72206f6e65207375622077696c6c206265207265706174726961746564b820746f207468652073656e64657220282a6e6f742a20746865206f726967696e616c206465706f7369746f72292e00650120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d757374206861766520612072656769737465726564402073757065722d6964656e746974792e004901204e4f54453a20546869732073686f756c64206e6f74206e6f726d616c6c7920626520757365642c206275742069732070726f766964656420696e207468652063617365207468617420746865206e6f6e2d150120636f6e74726f6c6c6572206f6620616e206163636f756e74206973206d616c6963696f75736c7920726567697374657265642061732061207375622d6163636f756e742e01282c4964656e7469747953657404244163636f756e7449640411012041206e616d652077617320736574206f72207265736574202877686963682077696c6c2072656d6f766520616c6c206a756467656d656e7473292e205c5b77686f5c5d3c4964656e74697479436c656172656408244163636f756e7449641c42616c616e63650415012041206e616d652077617320636c65617265642c20616e642074686520676976656e2062616c616e63652072657475726e65642e205c5b77686f2c206465706f7369745c5d384964656e746974794b696c6c656408244163636f756e7449641c42616c616e6365040d012041206e616d65207761732072656d6f76656420616e642074686520676976656e2062616c616e636520736c61736865642e205c5b77686f2c206465706f7369745c5d484a756467656d656e7452657175657374656408244163636f756e74496438526567697374726172496e6465780405012041206a756467656d656e74207761732061736b65642066726f6d2061207265676973747261722e205c5b77686f2c207265676973747261725f696e6465785c5d504a756467656d656e74556e72657175657374656408244163636f756e74496438526567697374726172496e64657804f02041206a756467656d656e74207265717565737420776173207265747261637465642e205c5b77686f2c207265676973747261725f696e6465785c5d384a756467656d656e74476976656e08244163636f756e74496438526567697374726172496e6465780409012041206a756467656d656e742077617320676976656e2062792061207265676973747261722e205c5b7461726765742c207265676973747261725f696e6465785c5d3852656769737472617241646465640438526567697374726172496e64657804ac204120726567697374726172207761732061646465642e205c5b7265676973747261725f696e6465785c5d405375624964656e7469747941646465640c244163636f756e744964244163636f756e7449641c42616c616e63650455012041207375622d6964656e746974792077617320616464656420746f20616e206964656e7469747920616e6420746865206465706f73697420706169642e205c5b7375622c206d61696e2c206465706f7369745c5d485375624964656e7469747952656d6f7665640c244163636f756e744964244163636f756e7449641c42616c616e6365080d012041207375622d6964656e74697479207761732072656d6f7665642066726f6d20616e206964656e7469747920616e6420746865206465706f7369742066726565642e5c205c5b7375622c206d61696e2c206465706f7369745c5d485375624964656e746974795265766f6b65640c244163636f756e744964244163636f756e7449641c42616c616e6365081d012041207375622d6964656e746974792077617320636c65617265642c20616e642074686520676976656e206465706f7369742072657061747269617465642066726f6d207468652901206d61696e206964656e74697479206163636f756e7420746f20746865207375622d6964656e74697479206163636f756e742e205c5b7375622c206d61696e2c206465706f7369745c5d183042617369634465706f7369743042616c616e63654f663c543e400080c6a47e8d0300000000000000000004d42054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564206964656e74697479304669656c644465706f7369743042616c616e63654f663c543e4000a031a95fe300000000000000000000042d012054686520616d6f756e742068656c64206f6e206465706f73697420706572206164646974696f6e616c206669656c6420666f7220612072656769737465726564206964656e746974792e445375624163636f756e744465706f7369743042616c616e63654f663c543e400080f420e6b5000000000000000000000c65012054686520616d6f756e742068656c64206f6e206465706f73697420666f7220612072656769737465726564207375626163636f756e742e20546869732073686f756c64206163636f756e7420666f7220746865206661637471012074686174206f6e652073746f72616765206974656d27732076616c75652077696c6c20696e637265617365206279207468652073697a65206f6620616e206163636f756e742049442c20616e642074686572652077696c6c206265290120616e6f746865722074726965206974656d2077686f73652076616c7565206973207468652073697a65206f6620616e206163636f756e7420494420706c75732033322062797465732e384d61785375624163636f756e74730c7533321064000000040d0120546865206d6178696d756d206e756d626572206f66207375622d6163636f756e747320616c6c6f77656420706572206964656e746966696564206163636f756e742e4c4d61784164646974696f6e616c4669656c64730c7533321064000000086501204d6178696d756d206e756d626572206f66206164646974696f6e616c206669656c64732074686174206d61792062652073746f72656420696e20616e2049442e204e656564656420746f20626f756e642074686520492f4fe020726571756972656420746f2061636365737320616e206964656e746974792c206275742063616e2062652070726574747920686967682e344d6178526567697374726172730c7533321014000000085101204d61786d696d756d206e756d626572206f66207265676973747261727320616c6c6f77656420696e207468652073797374656d2e204e656564656420746f20626f756e642074686520636f6d706c65786974797c206f662c20652e672e2c207570646174696e67206a756467656d656e74732e4048546f6f4d616e795375624163636f756e7473046020546f6f206d616e7920737562732d6163636f756e74732e204e6f74466f756e640454204163636f756e742069736e277420666f756e642e204e6f744e616d65640454204163636f756e742069736e2774206e616d65642e28456d707479496e646578043420456d70747920696e6465782e284665654368616e676564044020466565206973206368616e6765642e284e6f4964656e74697479044c204e6f206964656e7469747920666f756e642e3c537469636b794a756467656d656e74044820537469636b79206a756467656d656e742e384a756467656d656e74476976656e0444204a756467656d656e7420676976656e2e40496e76616c69644a756467656d656e74044c20496e76616c6964206a756467656d656e742e30496e76616c6964496e64657804582054686520696e64657820697320696e76616c69642e34496e76616c6964546172676574045c205468652074617267657420697320696e76616c69642e34546f6f4d616e794669656c6473047020546f6f206d616e79206164646974696f6e616c206669656c64732e44546f6f4d616e795265676973747261727304ec204d6178696d756d20616d6f756e74206f66207265676973747261727320726561636865642e2043616e6e6f742061646420616e79206d6f72652e38416c7265616479436c61696d65640474204163636f756e7420494420697320616c7265616479206e616d65642e184e6f7453756204742053656e646572206973206e6f742061207375622d6163636f756e742e204e6f744f776e6564048c205375622d6163636f756e742069736e2774206f776e65642062792073656e6465722e191c536f6369657479011c536f6369657479401c466f756e646572000030543a3a4163636f756e7449640400044820546865206669727374206d656d6265722e1452756c657300001c543a3a48617368040008510120412068617368206f66207468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e2043616e206f6e6c7920626520736574206f6e636520616e6454206f6e6c792062792074686520666f756e6465722e2843616e6469646174657301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e0400043901205468652063757272656e7420736574206f662063616e646964617465733b206269646465727320746861742061726520617474656d7074696e6720746f206265636f6d65206d656d626572732e4c53757370656e64656443616e6469646174657300010530543a3a4163636f756e744964e42842616c616e63654f663c542c20493e2c204269644b696e643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e2900040004842054686520736574206f662073757370656e6465642063616e646964617465732e0c506f7401003c42616c616e63654f663c542c20493e400000000000000000000000000000000004410120416d6f756e74206f66206f7572206163636f756e742062616c616e63652074686174206973207370656369666963616c6c7920666f7220746865206e65787420726f756e642773206269642873292e1048656164000030543a3a4163636f756e744964040004e820546865206d6f7374207072696d6172792066726f6d20746865206d6f737420726563656e746c7920617070726f766564206d656d626572732e1c4d656d626572730100445665633c543a3a4163636f756e7449643e04000494205468652063757272656e7420736574206f66206d656d626572732c206f7264657265642e4053757370656e6465644d656d6265727301010530543a3a4163636f756e74496410626f6f6c00040004782054686520736574206f662073757370656e646564206d656d626572732e104269647301009c5665633c4269643c543a3a4163636f756e7449642c2042616c616e63654f663c542c20493e3e3e040004e8205468652063757272656e7420626964732c2073746f726564206f726465726564206279207468652076616c7565206f6620746865206269642e20566f756368696e6700010530543a3a4163636f756e74496438566f756368696e6753746174757300040004e4204d656d626572732063757272656e746c7920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e1c5061796f75747301010530543a3a4163636f756e744964985665633c28543a3a426c6f636b4e756d6265722c2042616c616e63654f663c542c20493e293e000400044d012050656e64696e67207061796f7574733b206f72646572656420627920626c6f636b206e756d6265722c20776974682074686520616d6f756e7420746861742073686f756c642062652070616964206f75742e1c537472696b657301010530543a3a4163636f756e7449642c537472696b65436f756e7400100000000004dc20546865206f6e676f696e67206e756d626572206f66206c6f73696e6720766f746573206361737420627920746865206d656d6265722e14566f74657300020530543a3a4163636f756e74496430543a3a4163636f756e74496410566f746505040004d020446f75626c65206d61702066726f6d2043616e646964617465202d3e20566f746572202d3e20284d617962652920566f74652e20446566656e646572000030543a3a4163636f756e744964040004c42054686520646566656e64696e67206d656d6265722063757272656e746c79206265696e67206368616c6c656e6765642e34446566656e646572566f74657300010530543a3a4163636f756e74496410566f7465000400046020566f74657320666f722074686520646566656e6465722e284d61784d656d6265727301000c753332100000000004dc20546865206d6178206e756d626572206f66206d656d6265727320666f722074686520736f6369657479206174206f6e652074696d652e01300c626964041476616c75653c42616c616e63654f663c542c20493e84e020412075736572206f757473696465206f662074686520736f63696574792063616e206d616b6520612062696420666f7220656e7472792e003901205061796d656e743a206043616e6469646174654465706f736974602077696c6c20626520726573657276656420666f72206d616b696e672061206269642e2049742069732072657475726e6564f0207768656e2074686520626964206265636f6d65732061206d656d6265722c206f7220696620746865206269642063616c6c732060756e626964602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a5901202d206076616c7565603a2041206f6e652074696d65207061796d656e74207468652062696420776f756c64206c696b6520746f2072656365697665207768656e206a6f696e696e672074686520736f63696574792e002c2023203c7765696768743e5501204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520726573657276652944202d2053746f726167652052656164733aec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f284329c820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d2948202d2053746f72616765205772697465733a810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3a2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6820092d204f6e65206576656e7420666f72206e6577206269642efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e14756e626964040c706f730c7533324cd82041206269646465722063616e2072656d6f76652074686569722062696420666f7220656e74727920696e746f20736f63696574792e010120427920646f696e6720736f2c20746865792077696c6c20686176652074686569722063616e646964617465206465706f7369742072657475726e6564206f728420746865792077696c6c20756e766f75636820746865697220766f75636865722e00fc205061796d656e743a2054686520626964206465706f73697420697320756e7265736572766564206966207468652075736572206d6164652061206269642e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206269646465722e003020506172616d65746572733a1901202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2077616e747320746f20756e6269642e002c2023203c7765696768743eb0204b65793a204220286c656e206f662062696473292c2058202862616c616e636520756e72657365727665290d01202d204f6e652073746f72616765207265616420616e6420777269746520746f20726574726965766520616e64207570646174652074686520626964732e204f2842294501202d20456974686572206f6e6520756e726573657276652062616c616e636520616374696f6e204f285829206f72206f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2842202b205829302023203c2f7765696768743e14766f7563680c0c77686f30543a3a4163636f756e7449641476616c75653c42616c616e63654f663c542c20493e0c7469703c42616c616e63654f663c542c20493eb045012041732061206d656d6265722c20766f75636820666f7220736f6d656f6e6520746f206a6f696e20736f636965747920627920706c6163696e67206120626964206f6e20746865697220626568616c662e005501205468657265206973206e6f206465706f73697420726571756972656420746f20766f75636820666f722061206e6577206269642c206275742061206d656d6265722063616e206f6e6c7920766f75636820666f725d01206f6e652062696420617420612074696d652e2049662074686520626964206265636f6d657320612073757370656e6465642063616e64696461746520616e6420756c74696d6174656c792072656a65637465642062794101207468652073757370656e73696f6e206a756467656d656e74206f726967696e2c20746865206d656d6265722077696c6c2062652062616e6e65642066726f6d20766f756368696e6720616761696e2e005901204173206120766f756368696e67206d656d6265722c20796f752063616e20636c61696d206120746970206966207468652063616e6469646174652069732061636365707465642e2054686973207469702077696c6c51012062652070616964206173206120706f7274696f6e206f66207468652072657761726420746865206d656d6265722077696c6c207265636569766520666f72206a6f696e696e672074686520736f63696574792e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733acc202d206077686f603a2054686520757365722077686f20796f7520776f756c64206c696b6520746f20766f75636820666f722e5101202d206076616c7565603a2054686520746f74616c2072657761726420746f2062652070616964206265747765656e20796f7520616e64207468652063616e6469646174652069662074686579206265636f6d65642061206d656d62657220696e2074686520736f63696574792e4901202d2060746970603a20596f757220637574206f662074686520746f74616c206076616c756560207061796f7574207768656e207468652063616e64696461746520697320696e64756374656420696e746f15012074686520736f63696574792e2054697073206c6172676572207468616e206076616c7565602077696c6c206265207361747572617465642075706f6e207061796f75742e002c2023203c7765696768743e0101204b65793a204220286c656e206f662062696473292c204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d626572732944202d2053746f726167652052656164733ac820092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c206d656d626572732e204f284d29090120092d204f6e652073746f72616765207265616420746f20636865636b206d656d626572206973206e6f7420616c726561647920766f756368696e672e204f283129ec20092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e6465642063616e6469646174652e204f283129e020092d204f6e652073746f72616765207265616420746f20636865636b20666f722073757370656e646564206d656d6265722e204f283129dc20092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e7420626964732e204f284229f420092d204f6e652073746f72616765207265616420746f20726574726965766520616c6c2063757272656e742063616e646964617465732e204f28432948202d2053746f72616765205772697465733a0d0120092d204f6e652073746f7261676520777269746520746f20696e7365727420766f756368696e672073746174757320746f20746865206d656d6265722e204f283129810120092d204f6e652073746f72616765206d757461746520746f206164642061206e65772062696420746f2074686520766563746f72204f2842292028544f444f3a20706f737369626c65206f7074696d697a6174696f6e20772f207265616429010120092d20557020746f206f6e652073746f726167652072656d6f76616c206966206269642e6c656e2829203e204d41585f4249445f434f554e542e204f2831295c202d204e6f7461626c6520436f6d7075746174696f6e3ac020092d204f286c6f67204d292073656172636820746f20636865636b2073656e6465722069732061206d656d6265722e2d0120092d204f2842202b2043202b206c6f67204d292073656172636820746f20636865636b2075736572206973206e6f7420616c726561647920612070617274206f6620736f63696574792ec420092d204f286c6f672042292073656172636820746f20696e7365727420746865206e65772062696420736f727465642e78202d2045787465726e616c204d6f64756c65204f7065726174696f6e733a9c20092d204f6e652062616c616e63652072657365727665206f7065726174696f6e2e204f285829210120092d20557020746f206f6e652062616c616e636520756e72657365727665206f7065726174696f6e20696620626964732e6c656e2829203e204d41585f4249445f434f554e542e28202d204576656e74733a6020092d204f6e65206576656e7420666f7220766f7563682efc20092d20557020746f206f6e65206576656e7420666f72204175746f556e626964206966206269642e6c656e2829203e204d41585f4249445f434f554e542e00c420546f74616c20436f6d706c65786974793a204f284d202b2042202b2043202b206c6f674d202b206c6f6742202b205829302023203c2f7765696768743e1c756e766f756368040c706f730c753332442d01204173206120766f756368696e67206d656d6265722c20756e766f7563682061206269642e2054686973206f6e6c7920776f726b73207768696c6520766f7563686564207573657220697394206f6e6c792061206269646465722028616e64206e6f7420612063616e646964617465292e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206120766f756368696e67206d656d6265722e003020506172616d65746572733a2d01202d2060706f73603a20506f736974696f6e20696e207468652060426964736020766563746f72206f6620746865206269642077686f2073686f756c6420626520756e766f75636865642e002c2023203c7765696768743e54204b65793a204220286c656e206f662062696473290901202d204f6e652073746f726167652072656164204f28312920746f20636865636b20746865207369676e6572206973206120766f756368696e67206d656d6265722eec202d204f6e652073746f72616765206d757461746520746f20726574726965766520616e64207570646174652074686520626964732e204f28422994202d204f6e6520766f756368696e672073746f726167652072656d6f76616c2e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f284229302023203c2f7765696768743e10766f7465082463616e6469646174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c617070726f766510626f6f6c4c882041732061206d656d6265722c20766f7465206f6e20612063616e6469646174652e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733a0d01202d206063616e646964617465603a205468652063616e646964617465207468617420746865206d656d62657220776f756c64206c696b6520746f20626964206f6e2ef4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265d82020202020202020202020202020617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743ebc204b65793a204320286c656e206f662063616e64696461746573292c204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722e58202d204f6e65206163636f756e74206c6f6f6b75702e2d01202d204f6e652073746f726167652072656164204f28432920616e64204f2843292073656172636820746f20636865636b2074686174207573657220697320612063616e6469646174652ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204329302023203c2f7765696768743e34646566656e6465725f766f7465041c617070726f766510626f6f6c408c2041732061206d656d6265722c20766f7465206f6e2074686520646566656e6465722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d6265722e003020506172616d65746572733af4202d2060617070726f7665603a204120626f6f6c65616e2077686963682073617973206966207468652063616e6469646174652073686f756c64206265a420617070726f766564202860747275656029206f722072656a656374656420286066616c736560292e002c2023203c7765696768743e68202d204b65793a204d20286c656e206f66206d656d62657273291d01202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b20757365722069732061206d656d6265722ebc202d204f6e652073746f7261676520777269746520746f2061646420766f746520746f20766f7465732e204f28312934202d204f6e65206576656e742e007820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d29302023203c2f7765696768743e187061796f757400504501205472616e7366657220746865206669727374206d617475726564207061796f757420666f72207468652073656e64657220616e642072656d6f76652069742066726f6d20746865207265636f7264732e006901204e4f54453a20546869732065787472696e736963206e6565647320746f2062652063616c6c6564206d756c7469706c652074696d657320746f20636c61696d206d756c7469706c65206d617475726564207061796f7574732e002101205061796d656e743a20546865206d656d6265722077696c6c20726563656976652061207061796d656e7420657175616c20746f207468656972206669727374206d61747572656478207061796f757420746f20746865697220667265652062616c616e63652e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642061206d656d62657220776974684c207061796f7574732072656d61696e696e672e002c2023203c7765696768743e1d01204b65793a204d20286c656e206f66206d656d62657273292c205020286e756d626572206f66207061796f75747320666f72206120706172746963756c6172206d656d626572292501202d204f6e652073746f726167652072656164204f284d2920616e64204f286c6f67204d292073656172636820746f20636865636b207369676e65722069732061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28502920746f2067657420616c6c207061796f75747320666f722061206d656d6265722ee4202d204f6e652073746f726167652072656164204f28312920746f20676574207468652063757272656e7420626c6f636b206e756d6265722e8c202d204f6e652063757272656e6379207472616e736665722063616c6c2e204f2858291101202d204f6e652073746f72616765207772697465206f722072656d6f76616c20746f2075706461746520746865206d656d6265722773207061796f7574732e204f285029009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2050202b205829302023203c2f7765696768743e14666f756e640c1c666f756e64657230543a3a4163636f756e7449642c6d61785f6d656d626572730c7533321472756c65731c5665633c75383e4c4c20466f756e642074686520736f63696574792e00f0205468697320697320646f6e65206173206120646973637265746520616374696f6e20696e206f7264657220746f20616c6c6f7720666f72207468651901206d6f64756c6520746f20626520696e636c7564656420696e746f20612072756e6e696e6720636861696e20616e642063616e206f6e6c7920626520646f6e65206f6e63652e001d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f466f756e6465725365744f726967696e5f2e003020506172616d65746572733a1901202d2060666f756e64657260202d20546865206669727374206d656d62657220616e642068656164206f6620746865206e65776c7920666f756e64656420736f63696574792e1501202d20606d61785f6d656d6265727360202d2054686520696e697469616c206d6178206e756d626572206f66206d656d6265727320666f722074686520736f63696574792ef4202d206072756c657360202d205468652072756c6573206f66207468697320736f636965747920636f6e6365726e696e67206d656d626572736869702e002c2023203c7765696768743ee0202d2054776f2073746f72616765206d75746174657320746f207365742060486561646020616e642060466f756e646572602e204f283129f4202d204f6e652073746f7261676520777269746520746f2061646420746865206669727374206d656d62657220746f20736f63696574792e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e1c756e666f756e6400348c20416e6e756c2074686520666f756e64696e67206f662074686520736f63696574792e005d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205369676e65642c20616e6420746865207369676e696e67206163636f756e74206d75737420626520626f74685901207468652060466f756e6465726020616e6420746865206048656164602e205468697320696d706c6965732074686174206974206d6179206f6e6c7920626520646f6e65207768656e207468657265206973206f6e6520206d656d6265722e002c2023203c7765696768743e68202d2054776f2073746f72616765207265616473204f2831292e78202d20466f75722073746f726167652072656d6f76616c73204f2831292e34202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e586a756467655f73757370656e6465645f6d656d626572080c77686f30543a3a4163636f756e7449641c666f726769766510626f6f6c6c2d0120416c6c6f772073757370656e73696f6e206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e646564206d656d6265722e00590120496620612073757370656e646564206d656d62657220697320666f72676976656e2c2077652073696d706c7920616464207468656d206261636b2061732061206d656d6265722c206e6f7420616666656374696e67cc20616e79206f6620746865206578697374696e672073746f72616765206974656d7320666f722074686174206d656d6265722e00490120496620612073757370656e646564206d656d6265722069732072656a65637465642c2072656d6f766520616c6c206173736f6369617465642073746f72616765206974656d732c20696e636c7564696e670101207468656972207061796f7574732c20616e642072656d6f766520616e7920766f7563686564206269647320746865792063757272656e746c7920686176652e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ab4202d206077686f60202d205468652073757370656e646564206d656d62657220746f206265206a75646765642e3501202d2060666f726769766560202d204120626f6f6c65616e20726570726573656e74696e672077686574686572207468652073757370656e73696f6e206a756467656d656e74206f726967696e2501202020202020202020202020202020666f726769766573202860747275656029206f722072656a6563747320286066616c7365602920612073757370656e646564206d656d6265722e002c2023203c7765696768743ea4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d6265727329f8202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e646564206d656d6265722e204f2831297101202d20557020746f206f6e652073746f72616765207772697465204f284d292077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d626572206261636b20746f20736f63696574792ef8202d20557020746f20332073746f726167652072656d6f76616c73204f28312920746f20636c65616e20757020612072656d6f766564206d656d6265722e4501202d20557020746f206f6e652073746f72616765207772697465204f2842292077697468204f2842292073656172636820746f2072656d6f766520766f7563686564206269642066726f6d20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e70202d204f6e652073746f726167652072656d6f76616c2e204f2831297c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e008820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b204229302023203c2f7765696768743e646a756467655f73757370656e6465645f63616e646964617465080c77686f30543a3a4163636f756e744964246a756467656d656e74244a756467656d656e74a0350120416c6c6f772073757370656e646564206a756467656d656e74206f726967696e20746f206d616b65206a756467656d656e74206f6e20612073757370656e6465642063616e6469646174652e005d0120496620746865206a756467656d656e742069732060417070726f7665602c20776520616464207468656d20746f20736f63696574792061732061206d656d62657220776974682074686520617070726f70726961746574207061796d656e7420666f72206a6f696e696e6720736f63696574792e00550120496620746865206a756467656d656e74206973206052656a656374602c2077652065697468657220736c61736820746865206465706f736974206f6620746865206269642c20676976696e67206974206261636b110120746f2074686520736f63696574792074726561737572792c206f722077652062616e2074686520766f75636865722066726f6d20766f756368696e6720616761696e2e005d0120496620746865206a756467656d656e7420697320605265626964602c20776520707574207468652063616e646964617465206261636b20696e207468652062696420706f6f6c20616e64206c6574207468656d20676f94207468726f7567682074686520696e64756374696f6e2070726f6365737320616761696e2e00410120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d20746865205f53757370656e73696f6e4a756467656d656e744f726967696e5f2e003020506172616d65746572733ac0202d206077686f60202d205468652073757370656e6465642063616e64696461746520746f206265206a75646765642ec4202d20606a756467656d656e7460202d2060417070726f7665602c206052656a656374602c206f7220605265626964602e002c2023203c7765696768743ef4204b65793a204220286c656e206f662062696473292c204d20286c656e206f66206d656d62657273292c2058202862616c616e636520616374696f6e29f0202d204f6e652073746f72616765207265616420746f20636865636b206077686f6020697320612073757370656e6465642063616e6469646174652ec8202d204f6e652073746f726167652072656d6f76616c206f66207468652073757370656e6465642063616e6469646174652e40202d20417070726f7665204c6f676963150120092d204f6e652073746f72616765207265616420746f206765742074686520617661696c61626c6520706f7420746f2070617920757365727320776974682e204f283129dc20092d204f6e652073746f7261676520777269746520746f207570646174652074686520617661696c61626c6520706f742e204f283129e820092d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f283129b420092d204f6e652073746f72616765207265616420746f2067657420616c6c206d656d626572732e204f284d29a020092d20557020746f206f6e6520756e726573657276652063757272656e637920616374696f6e2eb020092d20557020746f2074776f206e65772073746f726167652077726974657320746f207061796f7574732e4d0120092d20557020746f206f6e652073746f726167652077726974652077697468204f286c6f67204d292062696e6172792073656172636820746f206164642061206d656d62657220746f20736f63696574792e3c202d2052656a656374204c6f676963dc20092d20557020746f206f6e6520726570617472696174652072657365727665642063757272656e637920616374696f6e2e204f2858292d0120092d20557020746f206f6e652073746f7261676520777269746520746f2062616e2074686520766f756368696e67206d656d6265722066726f6d20766f756368696e6720616761696e2e38202d205265626964204c6f676963410120092d2053746f72616765206d75746174652077697468204f286c6f672042292062696e6172792073656172636820746f20706c616365207468652075736572206261636b20696e746f20626964732ed4202d20557020746f206f6e65206164646974696f6e616c206576656e7420696620756e766f7563682074616b657320706c6163652e5c202d204f6e652073746f726167652072656d6f76616c2e7c202d204f6e65206576656e7420666f7220746865206a756467656d656e742e009820546f74616c20436f6d706c65786974793a204f284d202b206c6f674d202b2042202b205829302023203c2f7765696768743e3c7365745f6d61785f6d656d62657273040c6d61780c753332381d0120416c6c6f777320726f6f74206f726967696e20746f206368616e676520746865206d6178696d756d206e756d626572206f66206d656d6265727320696e20736f63696574792eb4204d6178206d656d6265727368697020636f756e74206d7573742062652067726561746572207468616e20312e00dc20546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652066726f6d205f524f4f545f2e003020506172616d65746572733ae4202d20606d617860202d20546865206d6178696d756d206e756d626572206f66206d656d6265727320666f722074686520736f63696574792e002c2023203c7765696768743eb0202d204f6e652073746f7261676520777269746520746f2075706461746520746865206d61782e204f28312934202d204f6e65206576656e742e005c20546f74616c20436f6d706c65786974793a204f283129302023203c2f7765696768743e01401c466f756e64656404244163636f756e74496404e82054686520736f636965747920697320666f756e6465642062792074686520676976656e206964656e746974792e205c5b666f756e6465725c5d0c42696408244163636f756e7449641c42616c616e63650861012041206d656d6265727368697020626964206a7573742068617070656e65642e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e64207468656972206f666665729c20697320746865207365636f6e642e205c5b63616e6469646174655f69642c206f666665725c5d14566f7563680c244163636f756e7449641c42616c616e6365244163636f756e7449640861012041206d656d6265727368697020626964206a7573742068617070656e656420627920766f756368696e672e2054686520676976656e206163636f756e74206973207468652063616e646964617465277320494420616e647901207468656972206f6666657220697320746865207365636f6e642e2054686520766f756368696e67207061727479206973207468652074686972642e205c5b63616e6469646174655f69642c206f666665722c20766f756368696e675c5d244175746f556e62696404244163636f756e7449640419012041205c5b63616e6469646174655c5d207761732064726f70706564202864756520746f20616e20657863657373206f66206269647320696e207468652073797374656d292e14556e62696404244163636f756e74496404c02041205c5b63616e6469646174655c5d207761732064726f70706564202862792074686569722072657175657374292e1c556e766f75636804244163636f756e7449640409012041205c5b63616e6469646174655c5d207761732064726f70706564202862792072657175657374206f662077686f20766f756368656420666f72207468656d292e20496e64756374656408244163636f756e744964385665633c4163636f756e7449643e08590120412067726f7570206f662063616e646964617465732068617665206265656e20696e6475637465642e205468652062617463682773207072696d617279206973207468652066697273742076616c75652c20746865d420626174636820696e2066756c6c20697320746865207365636f6e642e205c5b7072696d6172792c2063616e646964617465735c5d6053757370656e6465644d656d6265724a756467656d656e7408244163636f756e74496410626f6f6c04d020412073757370656e646564206d656d62657220686173206265656e206a75646765642e205c5b77686f2c206a75646765645c5d4843616e64696461746553757370656e64656404244163636f756e744964048c2041205c5b63616e6469646174655c5d20686173206265656e2073757370656e6465643c4d656d62657253757370656e64656404244163636f756e74496404802041205c5b6d656d6265725c5d20686173206265656e2073757370656e646564284368616c6c656e67656404244163636f756e74496404842041205c5b6d656d6265725c5d20686173206265656e206368616c6c656e67656410566f74650c244163636f756e744964244163636f756e74496410626f6f6c04c8204120766f746520686173206265656e20706c61636564205c5b63616e6469646174652c20766f7465722c20766f74655c5d30446566656e646572566f746508244163636f756e74496410626f6f6c04f8204120766f746520686173206265656e20706c6163656420666f72206120646566656e64696e67206d656d626572205c5b766f7465722c20766f74655c5d344e65774d61784d656d62657273040c75333204a02041206e6577205c5b6d61785c5d206d656d62657220636f756e7420686173206265656e2073657424556e666f756e64656404244163636f756e744964048820536f636965747920697320756e666f756e6465642e205c5b666f756e6465725c5d1c4465706f736974041c42616c616e636504f820536f6d652066756e64732077657265206465706f736974656420696e746f2074686520736f6369657479206163636f756e742e205c5b76616c75655c5d204043616e6469646174654465706f7369743c42616c616e63654f663c542c20493e400080c6a47e8d0300000000000000000004fc20546865206d696e696d756d20616d6f756e74206f662061206465706f73697420726571756972656420666f7220612062696420746f206265206d6164652e4857726f6e6753696465446564756374696f6e3c42616c616e63654f663c542c20493e400080f420e6b5000000000000000000000855012054686520616d6f756e74206f662074686520756e70616964207265776172642074686174206765747320646564756374656420696e207468652063617365207468617420656974686572206120736b6570746963c020646f65736e277420766f7465206f7220736f6d656f6e6520766f74657320696e207468652077726f6e67207761792e284d6178537472696b65730c753332100a00000008750120546865206e756d626572206f662074696d65732061206d656d626572206d617920766f7465207468652077726f6e672077617920286f72206e6f7420617420616c6c2c207768656e207468657920617265206120736b65707469632978206265666f72652074686579206265636f6d652073757370656e6465642e2c506572696f645370656e643c42616c616e63654f663c542c20493e400000c52ebca2b1000000000000000000042d012054686520616d6f756e74206f6620696e63656e7469766520706169642077697468696e206561636820706572696f642e20446f65736e277420696e636c75646520566f7465725469702e38526f746174696f6e506572696f6438543a3a426c6f636b4e756d626572100077010004110120546865206e756d626572206f6620626c6f636b73206265747765656e2063616e6469646174652f6d656d6265727368697020726f746174696f6e20706572696f64732e3c4368616c6c656e6765506572696f6438543a3a426c6f636b4e756d626572108013030004d020546865206e756d626572206f6620626c6f636b73206265747765656e206d656d62657273686970206368616c6c656e6765732e2050616c6c657449642050616c6c657449642070792f736f63696504682054686520736f636965746965732773206d6f64756c65206964484d617843616e646964617465496e74616b650c753332100a0000000490204d6178696d756d2063616e64696461746520696e74616b652070657220726f756e642e482c426164506f736974696f6e049020416e20696e636f727265637420706f736974696f6e207761732070726f76696465642e244e6f744d656d62657204582055736572206973206e6f742061206d656d6265722e34416c72656164794d656d6265720468205573657220697320616c72656164792061206d656d6265722e2453757370656e646564044c20557365722069732073757370656e6465642e304e6f7453757370656e646564045c2055736572206973206e6f742073757370656e6465642e204e6f5061796f7574044c204e6f7468696e6720746f207061796f75742e38416c7265616479466f756e646564046420536f636965747920616c726561647920666f756e6465642e3c496e73756666696369656e74506f74049c204e6f7420656e6f75676820696e20706f7420746f206163636570742063616e6469646174652e3c416c7265616479566f756368696e6704e8204d656d62657220697320616c726561647920766f756368696e67206f722062616e6e65642066726f6d20766f756368696e6720616761696e2e2c4e6f74566f756368696e670460204d656d626572206973206e6f7420766f756368696e672e104865616404942043616e6e6f742072656d6f7665207468652068656164206f662074686520636861696e2e1c466f756e646572046c2043616e6e6f742072656d6f76652074686520666f756e6465722e28416c7265616479426964047420557365722068617320616c7265616479206d6164652061206269642e40416c726561647943616e6469646174650474205573657220697320616c726561647920612063616e6469646174652e304e6f7443616e64696461746504642055736572206973206e6f7420612063616e6469646174652e284d61784d656d62657273048420546f6f206d616e79206d656d6265727320696e2074686520736f63696574792e284e6f74466f756e646572047c205468652063616c6c6572206973206e6f742074686520666f756e6465722e1c4e6f74486561640470205468652063616c6c6572206973206e6f742074686520686561642e1a205265636f7665727901205265636f766572790c2c5265636f76657261626c6500010530543a3a4163636f756e744964e85265636f76657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e0004000409012054686520736574206f66207265636f76657261626c65206163636f756e747320616e64207468656972207265636f7665727920636f6e66696775726174696f6e2e404163746976655265636f76657269657300020530543a3a4163636f756e74496430543a3a4163636f756e744964e84163746976655265636f766572793c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e050400106820416374697665207265636f7665727920617474656d7074732e001501204669727374206163636f756e7420697320746865206163636f756e7420746f206265207265636f76657265642c20616e6420746865207365636f6e64206163636f756e74ac20697320746865207573657220747279696e6720746f207265636f76657220746865206163636f756e742e1450726f787900010230543a3a4163636f756e74496430543a3a4163636f756e7449640004000c9020546865206c697374206f6620616c6c6f7765642070726f7879206163636f756e74732e00f8204d61702066726f6d2074686520757365722077686f2063616e2061636365737320697420746f20746865207265636f7665726564206163636f756e742e01243061735f7265636f7665726564081c6163636f756e7430543a3a4163636f756e7449641063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e34a42053656e6420612063616c6c207468726f7567682061207265636f7665726564206163636f756e742e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a2501202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f752077616e7420746f206d616b6520612063616c6c206f6e2d626568616c662d6f662e0101202d206063616c6c603a205468652063616c6c20796f752077616e7420746f206d616b65207769746820746865207265636f7665726564206163636f756e742e002c2023203c7765696768743e94202d2054686520776569676874206f6620746865206063616c6c60202b2031302c3030302e0901202d204f6e652073746f72616765206c6f6f6b757020746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e347365745f7265636f766572656408106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e744964341d0120416c6c6f7720524f4f5420746f2062797061737320746865207265636f766572792070726f6365737320616e642073657420616e20612072657363756572206163636f756e747420666f722061206c6f7374206163636f756e74206469726563746c792e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f524f4f545f2e003020506172616d65746572733ab8202d20606c6f7374603a2054686520226c6f7374206163636f756e742220746f206265207265636f76657265642e1d01202d206072657363756572603a20546865202272657363756572206163636f756e74222077686963682063616e2063616c6c20617320746865206c6f7374206163636f756e742e002c2023203c7765696768743e64202d204f6e652073746f72616765207772697465204f28312930202d204f6e65206576656e74302023203c2f7765696768743e3c6372656174655f7265636f766572790c1c667269656e6473445665633c543a3a4163636f756e7449643e247468726573686f6c640c7531363064656c61795f706572696f6438543a3a426c6f636b4e756d6265726c5d01204372656174652061207265636f7665727920636f6e66696775726174696f6e20666f7220796f7572206163636f756e742e2054686973206d616b657320796f7572206163636f756e74207265636f76657261626c652e003101205061796d656e743a2060436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732062616c616e636549012077696c6c20626520726573657276656420666f722073746f72696e6720746865207265636f7665727920636f6e66696775726174696f6e2e2054686973206465706f7369742069732072657475726e6564bc20696e2066756c6c207768656e2074686520757365722063616c6c73206072656d6f76655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2501202d2060667269656e6473603a2041206c697374206f6620667269656e647320796f7520747275737420746f20766f75636820666f72207265636f7665727920617474656d7074732ed420202053686f756c64206265206f72646572656420616e6420636f6e7461696e206e6f206475706c69636174652076616c7565732e3101202d20607468726573686f6c64603a20546865206e756d626572206f6620667269656e64732074686174206d75737420766f75636820666f722061207265636f7665727920617474656d70741d012020206265666f726520746865206163636f756e742063616e206265207265636f76657265642e2053686f756c64206265206c657373207468616e206f7220657175616c20746f94202020746865206c656e677468206f6620746865206c697374206f6620667269656e64732e3d01202d206064656c61795f706572696f64603a20546865206e756d626572206f6620626c6f636b732061667465722061207265636f7665727920617474656d707420697320696e697469616c697a6564e820202074686174206e6565647320746f2070617373206265666f726520746865206163636f756e742063616e206265207265636f76657265642e002c2023203c7765696768743e68202d204b65793a204620286c656e206f6620667269656e6473292d01202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973206e6f7420616c7265616479207265636f76657261626c652e204f2831292eec202d204120636865636b20746861742074686520667269656e6473206c69737420697320736f7274656420616e6420756e697175652e204f2846299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f2858299c202d204f6e652073746f726167652077726974652e204f2831292e20436f646563204f2846292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e44696e6974696174655f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496458ec20496e697469617465207468652070726f6365737320666f72207265636f766572696e672061207265636f76657261626c65206163636f756e742e001d01205061796d656e743a20605265636f766572794465706f736974602062616c616e63652077696c6c20626520726573657276656420666f7220696e6974696174696e67207468652501207265636f766572792070726f636573732e2054686973206465706f7369742077696c6c20616c7761797320626520726570617472696174656420746f20746865206163636f756e74b820747279696e6720746f206265207265636f76657265642e205365652060636c6f73655f7265636f76657279602e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e2054686973206163636f756e7401012020206e6565647320746f206265207265636f76657261626c652028692e652e20686176652061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743ef8202d204f6e652073746f72616765207265616420746f20636865636b2074686174206163636f756e74206973207265636f76657261626c652e204f2846295101202d204f6e652073746f72616765207265616420746f20636865636b20746861742074686973207265636f766572792070726f63657373206861736e277420616c726561647920737461727465642e204f2831299c202d204f6e652063757272656e63792072657365727665206f7065726174696f6e2e204f285829e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831296c202d204f6e652073746f726167652077726974652e204f2831292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e38766f7563685f7265636f7665727908106c6f737430543a3a4163636f756e7449641c7265736375657230543a3a4163636f756e74496464290120416c6c6f7720612022667269656e6422206f662061207265636f76657261626c65206163636f756e7420746f20766f75636820666f7220616e20616374697665207265636f76657279682070726f6365737320666f722074686174206163636f756e742e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d75737420626520612022667269656e64227420666f7220746865207265636f76657261626c65206163636f756e742e003020506172616d65746572733ad4202d20606c6f7374603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f207265636f7665722e1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f2072657363756520746865206c6f7374206163636f756e74207468617420796f755420202077616e7420746f20766f75636820666f722e0025012054686520636f6d62696e6174696f6e206f662074686573652074776f20706172616d6574657273206d75737420706f696e7420746f20616e20616374697665207265636f76657279242070726f636573732e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629ec202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c6572206973206120667269656e642e204f286c6f6746291d01202d204f6e652062696e6172792073656172636820746f20636f6e6669726d2063616c6c657220686173206e6f7420616c726561647920766f75636865642e204f286c6f6756299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e00a420546f74616c20436f6d706c65786974793a204f2846202b206c6f6746202b2056202b206c6f675629302023203c2f7765696768743e38636c61696d5f7265636f76657279041c6163636f756e7430543a3a4163636f756e74496450f420416c6c6f772061207375636365737366756c207265736375657220746f20636c61696d207468656972207265636f7665726564206163636f756e742e002d0120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061202272657363756572221d012077686f20686173207375636365737366756c6c7920636f6d706c6574656420746865206163636f756e74207265636f766572792070726f636573733a20636f6c6c6563746564310120607468726573686f6c6460206f72206d6f726520766f75636865732c20776169746564206064656c61795f706572696f646020626c6f636b732073696e636520696e6974696174696f6e2e003020506172616d65746572733a2d01202d20606163636f756e74603a20546865206c6f7374206163636f756e74207468617420796f752077616e7420746f20636c61696d20686173206265656e207375636365737366756c6c79502020207265636f766572656420627920796f752e002c2023203c7765696768743efc204b65793a204620286c656e206f6620667269656e647320696e20636f6e666967292c205620286c656e206f6620766f756368696e6720667269656e6473291d01202d204f6e652073746f72616765207265616420746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846292101202d204f6e652073746f72616765207265616420746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629e4202d204f6e652073746f72616765207265616420746f20676574207468652063757272656e7420626c6f636b206e756d6265722e204f2831299c202d204f6e652073746f726167652077726974652e204f2831292c20436f646563204f2856292e34202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205629302023203c2f7765696768743e38636c6f73655f7265636f76657279041c7265736375657230543a3a4163636f756e7449645015012041732074686520636f6e74726f6c6c6572206f662061207265636f76657261626c65206163636f756e742c20636c6f736520616e20616374697665207265636f76657279682070726f6365737320666f7220796f7572206163636f756e742e002101205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e2c20746865207265636f76657261626c65206163636f756e742077696c6c2072656365697665f820746865207265636f76657279206465706f73697420605265636f766572794465706f7369746020706c616365642062792074686520726573637565722e00050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061f0207265636f76657261626c65206163636f756e74207769746820616e20616374697665207265636f766572792070726f6365737320666f722069742e003020506172616d65746572733a1101202d206072657363756572603a20546865206163636f756e7420747279696e6720746f207265736375652074686973207265636f76657261626c65206163636f756e742e002c2023203c7765696768743e84204b65793a205620286c656e206f6620766f756368696e6720667269656e6473293d01202d204f6e652073746f7261676520726561642f72656d6f766520746f206765742074686520616374697665207265636f766572792070726f636573732e204f2831292c20436f646563204f285629c0202d204f6e652062616c616e63652063616c6c20746f20726570617472696174652072657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2856202b205829302023203c2f7765696768743e3c72656d6f76655f7265636f7665727900545d012052656d6f766520746865207265636f766572792070726f6365737320666f7220796f7572206163636f756e742e205265636f7665726564206163636f756e747320617265207374696c6c2061636365737369626c652e001501204e4f54453a205468652075736572206d757374206d616b65207375726520746f2063616c6c2060636c6f73655f7265636f7665727960206f6e20616c6c206163746976650901207265636f7665727920617474656d707473206265666f72652063616c6c696e6720746869732066756e6374696f6e20656c73652069742077696c6c206661696c2e002501205061796d656e743a2042792063616c6c696e6720746869732066756e6374696f6e20746865207265636f76657261626c65206163636f756e742077696c6c20756e7265736572766598207468656972207265636f7665727920636f6e66696775726174696f6e206465706f7369742ef4202860436f6e6669674465706f7369744261736560202b2060467269656e644465706f736974466163746f7260202a20235f6f665f667269656e64732900050120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64206d7573742062652061e4207265636f76657261626c65206163636f756e742028692e652e206861732061207265636f7665727920636f6e66696775726174696f6e292e002c2023203c7765696768743e60204b65793a204620286c656e206f6620667269656e6473292901202d204f6e652073746f72616765207265616420746f206765742074686520707265666978206974657261746f7220666f7220616374697665207265636f7665726965732e204f2831293901202d204f6e652073746f7261676520726561642f72656d6f766520746f2067657420746865207265636f7665727920636f6e66696775726174696f6e2e204f2831292c20436f646563204f2846299c202d204f6e652062616c616e63652063616c6c20746f20756e72657365727665642e204f28582934202d204f6e65206576656e742e006c20546f74616c20436f6d706c65786974793a204f2846202b205829302023203c2f7765696768743e4063616e63656c5f7265636f7665726564041c6163636f756e7430543a3a4163636f756e7449642ce02043616e63656c20746865206162696c69747920746f20757365206061735f7265636f76657265646020666f7220606163636f756e74602e00150120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207265676973746572656420746fe82062652061626c6520746f206d616b652063616c6c73206f6e20626568616c66206f6620746865207265636f7665726564206163636f756e742e003020506172616d65746572733a1901202d20606163636f756e74603a20546865207265636f7665726564206163636f756e7420796f75206172652061626c6520746f2063616c6c206f6e2d626568616c662d6f662e002c2023203c7765696768743e1101202d204f6e652073746f72616765206d75746174696f6e20746f20636865636b206163636f756e74206973207265636f7665726564206279206077686f602e204f283129302023203c2f7765696768743e01183c5265636f766572794372656174656404244163636f756e74496404dc2041207265636f766572792070726f6365737320686173206265656e2073657420757020666f7220616e205c5b6163636f756e745c5d2e445265636f76657279496e6974696174656408244163636f756e744964244163636f756e744964082d012041207265636f766572792070726f6365737320686173206265656e20696e6974696174656420666f72206c6f7374206163636f756e742062792072657363756572206163636f756e742e48205c5b6c6f73742c20726573637565725c5d3c5265636f76657279566f75636865640c244163636f756e744964244163636f756e744964244163636f756e744964085d012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20766f756368656420666f722062792073656e6465722e68205c5b6c6f73742c20726573637565722c2073656e6465725c5d385265636f76657279436c6f73656408244163636f756e744964244163636f756e7449640821012041207265636f766572792070726f6365737320666f72206c6f7374206163636f756e742062792072657363756572206163636f756e7420686173206265656e20636c6f7365642e48205c5b6c6f73742c20726573637565725c5d404163636f756e745265636f766572656408244163636f756e744964244163636f756e744964080501204c6f7374206163636f756e7420686173206265656e207375636365737366756c6c79207265636f76657265642062792072657363756572206163636f756e742e48205c5b6c6f73742c20726573637565725c5d3c5265636f7665727952656d6f76656404244163636f756e74496404e02041207265636f766572792070726f6365737320686173206265656e2072656d6f76656420666f7220616e205c5b6163636f756e745c5d2e1044436f6e6669674465706f736974426173653042616c616e63654f663c543e4000406352bfc60100000000000000000010550120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e00010120546869732069732068656c6420666f7220616e206164646974696f6e616c2073746f72616765206974656d2077686f73652076616c75652073697a65206973a8206032202b2073697a656f6628426c6f636b4e756d6265722c2042616c616e636529602062797465732e4c467269656e644465706f736974466163746f723042616c616e63654f663c543e4000203d88792d000000000000000000000c69012054686520616d6f756e74206f662063757272656e6379206e656564656420706572206164646974696f6e616c2075736572207768656e206372656174696e672061207265636f7665727920636f6e66696775726174696f6e2e00690120546869732069732068656c6420666f7220616464696e67206073697a656f66284163636f756e7449642960206279746573206d6f726520696e746f2061207072652d6578697374696e672073746f726167652076616c75652e284d6178467269656e64730c753136080900040d0120546865206d6178696d756d20616d6f756e74206f6620667269656e647320616c6c6f77656420696e2061207265636f7665727920636f6e66696775726174696f6e2e3c5265636f766572794465706f7369743042616c616e63654f663c543e4000406352bfc6010000000000000000001c1d0120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72207374617274696e672061207265636f766572792e0035012054686973206973207072696d6172696c792068656c6420666f7220646574657272696e67206d616c6963696f7573207265636f7665727920617474656d7074732c20616e642073686f756c642901206861766520612076616c7565206c6172676520656e6f7567682074686174206120626164206163746f7220776f756c642063686f6f7365206e6f7420746f20706c61636520746869732901206465706f7369742e20497420616c736f206163747320746f2066756e64206164646974696f6e616c2073746f72616765206974656d2077686f73652076616c75652073697a652069734101206073697a656f6628426c6f636b4e756d6265722c2042616c616e6365202b2054202a204163636f756e74496429602062797465732e2057686572652054206973206120636f6e666967757261626c652c207468726573686f6c642e40284e6f74416c6c6f77656404f42055736572206973206e6f7420616c6c6f77656420746f206d616b6520612063616c6c206f6e20626568616c66206f662074686973206163636f756e74345a65726f5468726573686f6c640490205468726573686f6c64206d7573742062652067726561746572207468616e207a65726f404e6f74456e6f756768467269656e647304d420467269656e6473206c697374206d7573742062652067726561746572207468616e207a65726f20616e64207468726573686f6c64284d6178467269656e647304ac20467269656e6473206c697374206d757374206265206c657373207468616e206d617820667269656e6473244e6f74536f7274656404cc20467269656e6473206c697374206d75737420626520736f7274656420616e642066726565206f66206475706c696361746573384e6f745265636f76657261626c6504a02054686973206163636f756e74206973206e6f742073657420757020666f72207265636f7665727948416c72656164795265636f76657261626c6504b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f7665727938416c72656164795374617274656404e02041207265636f766572792070726f636573732068617320616c7265616479207374617274656420666f722074686973206163636f756e74284e6f745374617274656404d02041207265636f766572792070726f6365737320686173206e6f74207374617274656420666f7220746869732072657363756572244e6f74467269656e6404ac2054686973206163636f756e74206973206e6f74206120667269656e642077686f2063616e20766f7563682c44656c6179506572696f64041d012054686520667269656e64206d757374207761697420756e74696c207468652064656c617920706572696f6420746f20766f75636820666f722074686973207265636f7665727938416c7265616479566f756368656404c0205468697320757365722068617320616c726561647920766f756368656420666f722074686973207265636f76657279245468726573686f6c6404ec20546865207468726573686f6c6420666f72207265636f766572696e672074686973206163636f756e7420686173206e6f74206265656e206d65742c5374696c6c41637469766504010120546865726520617265207374696c6c20616374697665207265636f7665727920617474656d7074732074686174206e65656420746f20626520636c6f73656430416c726561647950726f787904b02054686973206163636f756e7420697320616c72656164792073657420757020666f72207265636f76657279204261645374617465047c20536f6d6520696e7465726e616c2073746174652069732062726f6b656e2e1b1c56657374696e67011c56657374696e67041c56657374696e6700010230543a3a4163636f756e744964a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e00040004d820496e666f726d6174696f6e20726567617264696e67207468652076657374696e67206f66206120676976656e206163636f756e742e011010766573740034bc20556e6c6f636b20616e79207665737465642066756e6473206f66207468652073656e646572206163636f756e742e00610120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e64207468652073656e646572206d75737420686176652066756e6473207374696c6c68206c6f636b656420756e64657220746869732070616c6c65742e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20322052656164732c203220577269746573fc20202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d010120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c205b53656e646572204163636f756e745d302023203c2f7765696768743e28766573745f6f7468657204187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653cbc20556e6c6f636b20616e79207665737465642066756e6473206f662061206074617267657460206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501202d2060746172676574603a20546865206163636f756e742077686f7365207665737465642066756e64732073686f756c6420626520756e6c6f636b65642e204d75737420686176652066756e6473207374696c6c68206c6f636b656420756e64657220746869732070616c6c65742e00d420456d69747320656974686572206056657374696e67436f6d706c6574656460206f72206056657374696e6755706461746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c203320577269746573f420202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e74f820202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e74302023203c2f7765696768743e3c7665737465645f7472616e7366657208187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e406820437265617465206120766573746564207472616e736665722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e001501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20332052656164732c2033205772697465733d0120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745d410120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c205b53656e646572204163636f756e745d302023203c2f7765696768743e54666f7263655f7665737465645f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365207363686564756c65a456657374696e67496e666f3c42616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e446420466f726365206120766573746564207472616e736665722e00c820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f2e00ec202d2060736f75726365603a20546865206163636f756e742077686f73652066756e64732073686f756c64206265207472616e736665727265642e1501202d2060746172676574603a20546865206163636f756e7420746861742073686f756c64206265207472616e7366657272656420746865207665737465642066756e64732e0101202d2060616d6f756e74603a2054686520616d6f756e74206f662066756e647320746f207472616e7366657220616e642077696c6c206265207665737465642ef4202d20607363686564756c65603a205468652076657374696e67207363686564756c6520617474616368656420746f20746865207472616e736665722e006020456d697473206056657374696e6743726561746564602e002c2023203c7765696768743e28202d20604f283129602e78202d2044625765696768743a20342052656164732c203420577269746573350120202020202d2052656164733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74390120202020202d205772697465733a2056657374696e672053746f726167652c2042616c616e636573204c6f636b732c20546172676574204163636f756e742c20536f75726365204163636f756e74302023203c2f7765696768743e01083856657374696e675570646174656408244163636f756e7449641c42616c616e63650c59012054686520616d6f756e742076657374656420686173206265656e20757064617465642e205468697320636f756c6420696e646963617465206d6f72652066756e64732061726520617661696c61626c652e2054686519012062616c616e636520676976656e2069732074686520616d6f756e74207768696368206973206c65667420756e7665737465642028616e642074687573206c6f636b6564292e58205c5b6163636f756e742c20756e7665737465645c5d4056657374696e67436f6d706c6574656404244163636f756e744964041d0120416e205c5b6163636f756e745c5d20686173206265636f6d652066756c6c79207665737465642e204e6f20667572746865722076657374696e672063616e2068617070656e2e04444d696e5665737465645472616e736665723042616c616e63654f663c543e400000c16ff2862300000000000000000004e820546865206d696e696d756d20616d6f756e74207472616e7366657272656420746f2063616c6c20607665737465645f7472616e73666572602e0c284e6f7456657374696e67048820546865206163636f756e7420676976656e206973206e6f742076657374696e672e5c4578697374696e6756657374696e675363686564756c65045d0120416e206578697374696e672076657374696e67207363686564756c6520616c72656164792065786973747320666f722074686973206163636f756e7420746861742063616e6e6f7420626520636c6f6262657265642e24416d6f756e744c6f7704090120416d6f756e74206265696e67207472616e7366657272656420697320746f6f206c6f7720746f2063726561746520612076657374696e67207363686564756c652e1c245363686564756c657201245363686564756c65720c184167656e646101010538543a3a426c6f636b4e756d62657271015665633c4f7074696f6e3c5363686564756c65643c3c5420617320436f6e6669673e3a3a43616c6c2c20543a3a426c6f636b4e756d6265722c20543a3a0a50616c6c6574734f726967696e2c20543a3a4163636f756e7449643e3e3e000400044d01204974656d7320746f2062652065786563757465642c20696e64657865642062792074686520626c6f636b206e756d626572207468617420746865792073686f756c64206265206578656375746564206f6e2e184c6f6f6b75700001051c5665633c75383e6c5461736b416464726573733c543a3a426c6f636b4e756d6265723e000400040101204c6f6f6b75702066726f6d206964656e7469747920746f2074686520626c6f636b206e756d62657220616e6420696e646578206f6620746865207461736b2e3853746f7261676556657273696f6e01002052656c656173657304000c7c2053746f726167652076657273696f6e206f66207468652070616c6c65742e0098204e6577206e6574776f726b732073746172742077697468206c6173742076657273696f6e2e0118207363686564756c6510107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e287420416e6f6e796d6f75736c79207363686564756c652061207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7390202d2042617365205765696768743a2032322e3239202b202e313236202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64615020202020202d2057726974653a204167656e64613d01202d2057696c6c20757365206261736520776569676874206f662032352077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e1863616e63656c08107768656e38543a3a426c6f636b4e756d62657214696e6465780c75333228982043616e63656c20616e20616e6f6e796d6f75736c79207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032322e3135202b20322e383639202a205320c2b57334202d204442205765696768743a4c20202020202d20526561643a204167656e64617020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f6e616d6564140869641c5665633c75383e107768656e38543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e285c205363686564756c652061206e616d6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c738c202d2042617365205765696768743a2032392e36202b202e313539202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704d01202d2057696c6c20757365206261736520776569676874206f662033352077686963682073686f756c6420626520676f6f6420666f72206d6f7265207468616e203330207363686564756c65642063616c6c73302023203c2f7765696768743e3063616e63656c5f6e616d6564040869641c5665633c75383e287c2043616e63656c2061206e616d6564207363686564756c6564207461736b2e002c2023203c7765696768743ea0202d2053203d204e756d626572206f6620616c7265616479207363686564756c65642063616c6c7394202d2042617365205765696768743a2032342e3931202b20322e393037202a205320c2b57334202d204442205765696768743a6c20202020202d20526561643a204167656e64612c204c6f6f6b75707020202020202d2057726974653a204167656e64612c204c6f6f6b75704101202d2057696c6c20757365206261736520776569676874206f66203130302077686963682073686f756c6420626520676f6f6420666f7220757020746f203330207363686564756c65642063616c6c73302023203c2f7765696768743e387363686564756c655f61667465721014616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e14ac20416e6f6e796d6f75736c79207363686564756c652061207461736b20616674657220612064656c61792e002c2023203c7765696768743e582053616d65206173205b607363686564756c65605d2e302023203c2f7765696768743e507363686564756c655f6e616d65645f6166746572140869641c5665633c75383e14616674657238543a3a426c6f636b4e756d626572386d617962655f706572696f646963a04f7074696f6e3c7363686564756c653a3a506572696f643c543a3a426c6f636b4e756d6265723e3e207072696f72697479487363686564756c653a3a5072696f726974791063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e1494205363686564756c652061206e616d6564207461736b20616674657220612064656c61792e002c2023203c7765696768743e702053616d65206173205b607363686564756c655f6e616d6564605d2e302023203c2f7765696768743e010c245363686564756c6564082c426c6f636b4e756d6265720c7533320494205363686564756c656420736f6d65207461736b2e205c5b7768656e2c20696e6465785c5d2043616e63656c6564082c426c6f636b4e756d6265720c75333204902043616e63656c656420736f6d65207461736b2e205c5b7768656e2c20696e6465785c5d28446973706174636865640c605461736b416464726573733c426c6f636b4e756d6265723e3c4f7074696f6e3c5665633c75383e3e384469737061746368526573756c7404ac204469737061746368656420736f6d65207461736b2e205c5b7461736b2c2069642c20726573756c745c5d0010404661696c6564546f5363686564756c650468204661696c656420746f207363686564756c6520612063616c6c204e6f74466f756e6404802043616e6e6f742066696e6420746865207363686564756c65642063616c6c2e5c546172676574426c6f636b4e756d626572496e5061737404a820476976656e2074617267657420626c6f636b206e756d62657220697320696e2074686520706173742e4852657363686564756c654e6f4368616e676504f42052657363686564756c65206661696c6564206265636175736520697420646f6573206e6f74206368616e6765207363686564756c65642074696d652e1d1450726f7879011450726f7879081c50726f7869657301010530543a3a4163636f756e744964a50128426f756e6465645665633c50726f7879446566696e6974696f6e3c543a3a4163636f756e7449642c20543a3a50726f7879547970652c20543a3a0a20426c6f636b4e756d6265723e2c20543a3a4d617850726f786965732c3e2c2042616c616e63654f663c543e29004400000000000000000000000000000000000845012054686520736574206f66206163636f756e742070726f786965732e204d61707320746865206163636f756e74207768696368206861732064656c65676174656420746f20746865206163636f756e7473210120776869636820617265206265696e672064656c65676174656420746f2c20746f67657468657220776974682074686520616d6f756e742068656c64206f6e206465706f7369742e34416e6e6f756e63656d656e747301010530543a3a4163636f756e744964a10128426f756e6465645665633c416e6e6f756e63656d656e743c543a3a4163636f756e7449642c2043616c6c486173684f663c543e2c20543a3a0a20426c6f636b4e756d6265723e2c20543a3a4d617850656e64696e672c3e2c2042616c616e63654f663c543e2c290044000000000000000000000000000000000004ac2054686520616e6e6f756e63656d656e7473206d616465206279207468652070726f787920286b6579292e01281470726f78790c107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e3c51012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f726973656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e246164645f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d62657234490120526567697374657220612070726f7879206163636f756e7420666f72207468652073656e64657220746861742069732061626c6520746f206d616b652063616c6c73206f6e2069747320626568616c662e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1501202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f206d616b6520612070726f78792e0101202d206070726f78795f74797065603a20546865207065726d697373696f6e7320616c6c6f77656420666f7220746869732070726f7879206163636f756e742e5101202d206064656c6179603a2054686520616e6e6f756e63656d656e7420706572696f64207265717569726564206f662074686520696e697469616c2070726f78792e2057696c6c2067656e6572616c6c7920626518207a65726f2e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3072656d6f76655f70726f78790c2064656c656761746530543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d6265722cac20556e726567697374657220612070726f7879206163636f756e7420666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a2901202d206070726f7879603a20546865206163636f756e74207468617420746865206063616c6c65726020776f756c64206c696b6520746f2072656d6f766520617320612070726f78792e4501202d206070726f78795f74797065603a20546865207065726d697373696f6e732063757272656e746c7920656e61626c656420666f72207468652072656d6f7665642070726f7879206163636f756e742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e3872656d6f76655f70726f786965730028b820556e726567697374657220616c6c2070726f7879206163636f756e747320666f72207468652073656e6465722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901205741524e494e473a2054686973206d61792062652063616c6c6564206f6e206163636f756e747320637265617465642062792060616e6f6e796d6f7573602c20686f776576657220696620646f6e652c207468656e5d012074686520756e726573657276656420666565732077696c6c20626520696e61636365737369626c652e202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e24616e6f6e796d6f75730c2870726f78795f7479706530543a3a50726f7879547970651464656c617938543a3a426c6f636b4e756d62657214696e6465780c7531365c3d0120537061776e2061206672657368206e6577206163636f756e7420746861742069732067756172616e7465656420746f206265206f746865727769736520696e61636365737369626c652c20616e64010120696e697469616c697a65206974207769746820612070726f7879206f66206070726f78795f747970656020666f7220606f726967696e602073656e6465722e0070205265717569726573206120605369676e656460206f726967696e2e005501202d206070726f78795f74797065603a205468652074797065206f66207468652070726f78792074686174207468652073656e6465722077696c6c2062652072656769737465726564206173206f766572207468655101206e6577206163636f756e742e20546869732077696c6c20616c6d6f737420616c7761797320626520746865206d6f7374207065726d697373697665206050726f7879547970656020706f737369626c6520746f7c20616c6c6f7720666f72206d6178696d756d20666c65786962696c6974792e5501202d2060696e646578603a204120646973616d626967756174696f6e20696e6465782c20696e206361736520746869732069732063616c6c6564206d756c7469706c652074696d657320696e207468652073616d656101207472616e73616374696f6e2028652e672e207769746820607574696c6974793a3a626174636860292e20556e6c65737320796f75277265207573696e67206062617463686020796f752070726f6261626c79206a757374442077616e7420746f20757365206030602e5101202d206064656c6179603a2054686520616e6e6f756e63656d656e7420706572696f64207265717569726564206f662074686520696e697469616c2070726f78792e2057696c6c2067656e6572616c6c7920626518207a65726f2e005501204661696c73207769746820604475706c69636174656020696620746869732068617320616c7265616479206265656e2063616c6c656420696e2074686973207472616e73616374696f6e2c2066726f6d207468659c2073616d652073656e6465722c2077697468207468652073616d6520706172616d65746572732e00e8204661696c732069662074686572652061726520696e73756666696369656e742066756e647320746f2070617920666f72206465706f7369742e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e9020544f444f3a204d69676874206265206f76657220636f756e74696e6720312072656164386b696c6c5f616e6f6e796d6f7573141c737061776e657230543a3a4163636f756e7449642870726f78795f7479706530543a3a50726f78795479706514696e6465780c753136186865696768745c436f6d706163743c543a3a426c6f636b4e756d6265723e246578745f696e64657830436f6d706163743c7533323e50b82052656d6f76657320612070726576696f75736c7920737061776e656420616e6f6e796d6f75732070726f78792e004d01205741524e494e473a202a2a416c6c2061636365737320746f2074686973206163636f756e742077696c6c206265206c6f73742e2a2a20416e792066756e64732068656c6420696e2069742077696c6c2062653820696e61636365737369626c652e005d01205265717569726573206120605369676e656460206f726967696e2c20616e64207468652073656e646572206163636f756e74206d7573742068617665206265656e206372656174656420627920612063616c6c20746fac2060616e6f6e796d6f757360207769746820636f72726573706f6e64696e6720706172616d65746572732e005101202d2060737061776e6572603a20546865206163636f756e742074686174206f726967696e616c6c792063616c6c65642060616e6f6e796d6f75736020746f206372656174652074686973206163636f756e742e5101202d2060696e646578603a2054686520646973616d626967756174696f6e20696e646578206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e2050726f6261626c79206030602e0501202d206070726f78795f74797065603a205468652070726f78792074797065206f726967696e616c6c792070617373656420746f2060616e6f6e796d6f7573602e4101202d2060686569676874603a2054686520686569676874206f662074686520636861696e207768656e207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e4d01202d20606578745f696e646578603a205468652065787472696e73696320696e64657820696e207768696368207468652063616c6c20746f2060616e6f6e796d6f757360207761732070726f6365737365642e004d01204661696c73207769746820604e6f5065726d697373696f6e6020696e2063617365207468652063616c6c6572206973206e6f7420612070726576696f75736c79206372656174656420616e6f6e796d6f7573f4206163636f756e742077686f73652060616e6f6e796d6f7573602063616c6c2068617320636f72726573706f6e64696e6720706172616d65746572732e002c2023203c7765696768743e01012057656967687420697320612066756e6374696f6e206f6620746865206e756d626572206f662070726f7869657320746865207573657220686173202850292e302023203c2f7765696768743e20616e6e6f756e636508107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e540901205075626c697368207468652068617368206f6620612070726f78792d63616c6c20746861742077696c6c206265206d61646520696e20746865206675747572652e0061012054686973206d7573742062652063616c6c656420736f6d65206e756d626572206f6620626c6f636b73206265666f72652074686520636f72726573706f6e64696e67206070726f78796020697320617474656d707465642901206966207468652064656c6179206173736f6369617465642077697468207468652070726f78792072656c6174696f6e736869702069732067726561746572207468616e207a65726f2e001501204e6f206d6f7265207468616e20604d617850656e64696e676020616e6e6f756e63656d656e7473206d6179206265206d61646520617420616e79206f6e652074696d652e000d0120546869732077696c6c2074616b652061206465706f736974206f662060416e6e6f756e63656d656e744465706f736974466163746f72602061732077656c6c2061731d012060416e6e6f756e63656d656e744465706f736974426173656020696620746865726520617265206e6f206f746865722070656e64696e6720616e6e6f756e63656d656e74732e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420612070726f7879206f6620607265616c602e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656d6f76655f616e6e6f756e63656d656e7408107265616c30543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40742052656d6f7665206120676976656e20616e6e6f756e63656d656e742e005d01204d61792062652063616c6c656420627920612070726f7879206163636f756e7420746f2072656d6f766520612063616c6c20746865792070726576696f75736c7920616e6e6f756e63656420616e642072657475726e3420746865206465706f7369742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e1901202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e4c72656a6563745f616e6e6f756e63656d656e74082064656c656761746530543a3a4163636f756e7449642463616c6c5f686173683443616c6c486173684f663c543e40b42052656d6f76652074686520676976656e20616e6e6f756e63656d656e74206f6620612064656c65676174652e006501204d61792062652063616c6c6564206279206120746172676574202870726f7869656429206163636f756e7420746f2072656d6f766520612063616c6c2074686174206f6e65206f662074686569722064656c656761746573290120286064656c656761746560292068617320616e6e6f756e63656420746865792077616e7420746f20657865637574652e20546865206465706f7369742069732072657475726e65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733af8202d206064656c6567617465603a20546865206163636f756e7420746861742070726576696f75736c7920616e6e6f756e636564207468652063616c6c2ec0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f206265206d6164652e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e3c70726f78795f616e6e6f756e636564102064656c656761746530543a3a4163636f756e744964107265616c30543a3a4163636f756e74496440666f7263655f70726f78795f74797065504f7074696f6e3c543a3a50726f7879547970653e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e4451012044697370617463682074686520676976656e206063616c6c602066726f6d20616e206163636f756e742074686174207468652073656e64657220697320617574686f72697a656420666f72207468726f7567683420606164645f70726f7879602e00ac2052656d6f76657320616e7920636f72726573706f6e64696e6720616e6e6f756e63656d656e742873292e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e003020506172616d65746572733a1101202d20607265616c603a20546865206163636f756e742074686174207468652070726f78792077696c6c206d616b6520612063616c6c206f6e20626568616c66206f662e6501202d2060666f7263655f70726f78795f74797065603a2053706563696679207468652065786163742070726f7879207479706520746f206265207573656420616e6420636865636b656420666f7220746869732063616c6c2ed4202d206063616c6c603a205468652063616c6c20746f206265206d6164652062792074686520607265616c60206163636f756e742e002c2023203c7765696768743e642057656967687420697320612066756e6374696f6e206f663a9c202d20413a20746865206e756d626572206f6620616e6e6f756e63656d656e7473206d6164652ea4202d20503a20746865206e756d626572206f662070726f78696573207468652075736572206861732e302023203c2f7765696768743e010c3450726f7879457865637574656404384469737061746368526573756c7404ec20412070726f78792077617320657865637574656420636f72726563746c792c20776974682074686520676976656e205c5b726573756c745c5d2e40416e6f6e796d6f75734372656174656410244163636f756e744964244163636f756e7449642450726f7879547970650c75313608ec20416e6f6e796d6f7573206163636f756e7420686173206265656e2063726561746564206279206e65772070726f7879207769746820676976656e690120646973616d626967756174696f6e20696e64657820616e642070726f787920747970652e205c5b616e6f6e796d6f75732c2077686f2c2070726f78795f747970652c20646973616d626967756174696f6e5f696e6465785c5d24416e6e6f756e6365640c244163636f756e744964244163636f756e744964104861736804510120416e20616e6e6f756e63656d656e742077617320706c6163656420746f206d616b6520612063616c6c20696e20746865206675747572652e205c5b7265616c2c2070726f78792c2063616c6c5f686173685c5d184050726f78794465706f736974426173653042616c616e63654f663c543e4000f09e544c390000000000000000000010110120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e6720612070726f78792e00010120546869732069732068656c6420666f7220616e206164646974696f6e616c2073746f72616765206974656d2077686f73652076616c75652073697a652069732501206073697a656f662842616c616e6365296020627974657320616e642077686f7365206b65792073697a65206973206073697a656f66284163636f756e74496429602062797465732e4850726f78794465706f736974466163746f723042616c616e63654f663c543e400060aa7714b40000000000000000000014bc2054686520616d6f756e74206f662063757272656e6379206e6565646564207065722070726f78792061646465642e00690120546869732069732068656c6420666f7220616464696e6720333220627974657320706c757320616e20696e7374616e6365206f66206050726f78795479706560206d6f726520696e746f2061207072652d6578697374696e6761012073746f726167652076616c75652e20546875732c207768656e20636f6e6669677572696e67206050726f78794465706f736974466163746f7260206f6e652073686f756c642074616b6520696e746f206163636f756e74c020603332202b2070726f78795f747970652e656e636f646528292e6c656e282960206279746573206f6620646174612e284d617850726f786965730c753332102000000004f020546865206d6178696d756d20616d6f756e74206f662070726f7869657320616c6c6f77656420666f7220612073696e676c65206163636f756e742e284d617850656e64696e670c753332102000000004450120546865206d6178696d756d20616d6f756e74206f662074696d652d64656c6179656420616e6e6f756e63656d656e747320746861742061726520616c6c6f77656420746f2062652070656e64696e672e5c416e6e6f756e63656d656e744465706f736974426173653042616c616e63654f663c543e4000f09e544c39000000000000000000000c310120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e6720616e20616e6e6f756e63656d656e742e00690120546869732069732068656c64207768656e2061206e65772073746f72616765206974656d20686f6c64696e672061206042616c616e636560206973206372656174656420287479706963616c6c79203136206279746573292e64416e6e6f756e63656d656e744465706f736974466163746f723042616c616e63654f663c543e4000c054ef28680100000000000000000010d42054686520616d6f756e74206f662063757272656e6379206e65656465642070657220616e6e6f756e63656d656e74206d6164652e00590120546869732069732068656c6420666f7220616464696e6720616e20604163636f756e744964602c2060486173686020616e642060426c6f636b4e756d6265726020287479706963616c6c79203638206279746573298c20696e746f2061207072652d6578697374696e672073746f726167652076616c75652e201c546f6f4d616e790425012054686572652061726520746f6f206d616e792070726f786965732072656769737465726564206f7220746f6f206d616e7920616e6e6f756e63656d656e74732070656e64696e672e204e6f74466f756e6404782050726f787920726567697374726174696f6e206e6f7420666f756e642e204e6f7450726f787904d02053656e646572206973206e6f7420612070726f7879206f6620746865206163636f756e7420746f2062652070726f786965642e2c556e70726f787961626c6504250120412063616c6c20776869636820697320696e636f6d70617469626c652077697468207468652070726f7879207479706527732066696c7465722077617320617474656d707465642e244475706c69636174650470204163636f756e7420697320616c726561647920612070726f78792e304e6f5065726d697373696f6e0419012043616c6c206d6179206e6f74206265206d6164652062792070726f78792062656361757365206974206d617920657363616c617465206974732070726976696c656765732e2c556e616e6e6f756e63656404d420416e6e6f756e63656d656e742c206966206d61646520617420616c6c2c20776173206d61646520746f6f20726563656e746c792e2c4e6f53656c6650726f787904682043616e6e6f74206164642073656c662061732070726f78792e1e204d756c746973696701204d756c746973696708244d756c74697369677300020530543a3a4163636f756e744964205b75383b2033325dd04d756c74697369673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e2c20543a3a4163636f756e7449643e02040004942054686520736574206f66206f70656e206d756c7469736967206f7065726174696f6e732e1443616c6c73000106205b75383b2033325da0284f706171756543616c6c2c20543a3a4163636f756e7449642c2042616c616e63654f663c543e290004000001105061735f6d756c74695f7468726573686f6c645f3108446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e1063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e40550120496d6d6564696174656c792064697370617463682061206d756c74692d7369676e61747572652063616c6c207573696e6720612073696e676c6520617070726f76616c2066726f6d207468652063616c6c65722e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e004101202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f206172652070617274206f66207468650501206d756c74692d7369676e61747572652c2062757420646f206e6f7420706172746963697061746520696e2074686520617070726f76616c2070726f636573732e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e00bc20526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c742e002c2023203c7765696768743e1d01204f285a202b204329207768657265205a20697320746865206c656e677468206f66207468652063616c6c20616e6420432069747320657865637574696f6e207765696768742e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d48202d204442205765696768743a204e6f6e654c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e2061735f6d756c746918247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e1063616c6c284f706171756543616c6c2873746f72655f63616c6c10626f6f6c286d61785f77656967687418576569676874b8590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e00b42049662074686572652061726520656e6f7567682c207468656e206469737061746368207468652063616c6c2e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2e8c202d206063616c6c603a205468652063616c6c20746f2062652065786563757465642e002101204e4f54453a20556e6c6573732074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2067656e6572616c6c792077616e7420746f207573651d012060617070726f76655f61735f6d756c74696020696e73746561642c2073696e6365206974206f6e6c7920726571756972657320612068617368206f66207468652063616c6c2e005d0120526573756c74206973206571756976616c656e7420746f20746865206469737061746368656420726573756c7420696620607468726573686f6c64602069732065786163746c79206031602e204f74686572776973655901206f6e20737563636573732c20726573756c7420697320604f6b6020616e642074686520726573756c742066726f6d2074686520696e746572696f722063616c6c2c206966206974207761732065786563757465642ce0206d617920626520666f756e6420696e20746865206465706f736974656420604d756c7469736967457865637574656460206576656e742e002c2023203c7765696768743e54202d20604f2853202b205a202b2043616c6c29602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2e2501202d204f6e652063616c6c20656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285a296020776865726520605a602069732074782d6c656e2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e70202d2054686520776569676874206f6620746865206063616c6c602e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e80202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a250120202020202d2052656164733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c6029290120202020202d205772697465733a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c2043616c6c7320286966206073746f72655f63616c6c60294c202d20506c75732043616c6c20576569676874302023203c2f7765696768743e40617070726f76655f61735f6d756c746914247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e3c6d617962655f74696d65706f696e74844f7074696f6e3c54696d65706f696e743c543a3a426c6f636b4e756d6265723e3e2463616c6c5f68617368205b75383b2033325d286d61785f7765696768741857656967687490590120526567697374657220617070726f76616c20666f72206120646973706174636820746f206265206d6164652066726f6d20612064657465726d696e697374696320636f6d706f73697465206163636f756e74206966fc20617070726f766564206279206120746f74616c206f6620607468726573686f6c64202d203160206f6620606f746865725f7369676e61746f72696573602e003101205061796d656e743a20604465706f73697442617365602077696c6c20626520726573657276656420696620746869732069732074686520666972737420617070726f76616c2c20706c7573410120607468726573686f6c64602074696d657320604465706f736974466163746f72602e2049742069732072657475726e6564206f6e636520746869732064697370617463682068617070656e73206f72382069732063616e63656c6c65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e5d01202d20606d617962655f74696d65706f696e74603a20496620746869732069732074686520666972737420617070726f76616c2c207468656e2074686973206d75737420626520604e6f6e65602e2049662069742069735501206e6f742074686520666972737420617070726f76616c2c207468656e206974206d7573742062652060536f6d65602c2077697468207468652074696d65706f696e742028626c6f636b206e756d62657220616e64d8207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c207472616e73616374696f6e2ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e003901204e4f54453a2049662074686973206973207468652066696e616c20617070726f76616c2c20796f752077696c6c2077616e7420746f20757365206061735f6d756c74696020696e73746561642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602ed8202d20557020746f206f6e652062696e6172792073656172636820616e6420696e736572742028604f286c6f6753202b20532960292efc202d20492f4f3a2031207265616420604f285329602c20757020746f2031206d757461746520604f285329602e20557020746f206f6e652072656d6f76652e34202d204f6e65206576656e742e3101202d2053746f726167653a20696e7365727473206f6e65206974656d2c2076616c75652073697a6520626f756e64656420627920604d61785369676e61746f72696573602c20776974682061902020206465706f7369742074616b656e20666f7220697473206c69666574696d65206f66b4202020604465706f73697442617365202b207468726573686f6c64202a204465706f736974466163746f72602e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743abc20202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745dc020202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d302023203c2f7765696768743e3c63616e63656c5f61735f6d756c746910247468726573686f6c640c753136446f746865725f7369676e61746f72696573445665633c543a3a4163636f756e7449643e2474696d65706f696e746454696d65706f696e743c543a3a426c6f636b4e756d6265723e2463616c6c5f68617368205b75383b2033325d6859012043616e63656c2061207072652d6578697374696e672c206f6e2d676f696e67206d756c7469736967207472616e73616374696f6e2e20416e79206465706f7369742072657365727665642070726576696f75736c79c820666f722074686973206f7065726174696f6e2077696c6c20626520756e7265736572766564206f6e20737563636573732e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005901202d20607468726573686f6c64603a2054686520746f74616c206e756d626572206f6620617070726f76616c7320666f722074686973206469737061746368206265666f72652069742069732065786563757465642e4501202d20606f746865725f7369676e61746f72696573603a20546865206163636f756e747320286f74686572207468616e207468652073656e646572292077686f2063616e20617070726f76652074686973702064697370617463682e204d6179206e6f7420626520656d7074792e6101202d206074696d65706f696e74603a205468652074696d65706f696e742028626c6f636b206e756d62657220616e64207472616e73616374696f6e20696e64657829206f662074686520666972737420617070726f76616c7c207472616e73616374696f6e20666f7220746869732064697370617463682ed0202d206063616c6c5f68617368603a205468652068617368206f66207468652063616c6c20746f2062652065786563757465642e002c2023203c7765696768743e28202d20604f285329602ed0202d20557020746f206f6e652062616c616e63652d72657365727665206f7220756e72657365727665206f7065726174696f6e2e4101202d204f6e6520706173737468726f756768206f7065726174696f6e2c206f6e6520696e736572742c20626f746820604f285329602077686572652060536020697320746865206e756d626572206f6649012020207369676e61746f726965732e206053602069732063617070656420627920604d61785369676e61746f72696573602c207769746820776569676874206265696e672070726f706f7274696f6e616c2ec0202d204f6e6520656e636f6465202620686173682c20626f7468206f6620636f6d706c657869747920604f285329602e34202d204f6e65206576656e742e88202d20492f4f3a2031207265616420604f285329602c206f6e652072656d6f76652e74202d2053746f726167653a2072656d6f766573206f6e65206974656d2e8c202d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d2d34202d204442205765696768743a190120202020202d20526561643a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c731d0120202020202d2057726974653a204d756c74697369672053746f726167652c205b43616c6c6572204163636f756e745d2c20526566756e64204163636f756e742c2043616c6c73302023203c2f7765696768743e01102c4e65774d756c74697369670c244163636f756e744964244163636f756e7449642043616c6c48617368041d012041206e6577206d756c7469736967206f7065726174696f6e2068617320626567756e2e205c5b617070726f76696e672c206d756c74697369672c2063616c6c5f686173685c5d404d756c7469736967417070726f76616c10244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c4861736808cc2041206d756c7469736967206f7065726174696f6e20686173206265656e20617070726f76656420627920736f6d656f6e652eb8205c5b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d404d756c7469736967457865637574656414244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c48617368384469737061746368526573756c740459012041206d756c7469736967206f7065726174696f6e20686173206265656e2065786563757465642e205c5b617070726f76696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d444d756c746973696743616e63656c6c656410244163636f756e7449645854696d65706f696e743c426c6f636b4e756d6265723e244163636f756e7449642043616c6c486173680461012041206d756c7469736967206f7065726174696f6e20686173206265656e2063616e63656c6c65642e205c5b63616e63656c6c696e672c2074696d65706f696e742c206d756c74697369672c2063616c6c5f686173685c5d0c2c4465706f736974426173653042616c616e63654f663c543e4000f01c0adbed0100000000000000000018710120546865206261736520616d6f756e74206f662063757272656e6379206e656564656420746f207265736572766520666f72206372656174696e672061206d756c746973696720657865637574696f6e206f7220746f2073746f72656c20612064697370617463682063616c6c20666f72206c617465722e00010120546869732069732068656c6420666f7220616e206164646974696f6e616c2073746f72616765206974656d2077686f73652076616c75652073697a652069733101206034202b2073697a656f662828426c6f636b4e756d6265722c2042616c616e63652c204163636f756e74496429296020627974657320616e642077686f7365206b65792073697a652069738020603332202b2073697a656f66284163636f756e74496429602062797465732e344465706f736974466163746f723042616c616e63654f663c543e400000cc7b9fae000000000000000000000c55012054686520616d6f756e74206f662063757272656e6379206e65656465642070657220756e6974207468726573686f6c64207768656e206372656174696e672061206d756c746973696720657865637574696f6e2e00250120546869732069732068656c6420666f7220616464696e67203332206279746573206d6f726520696e746f2061207072652d6578697374696e672073746f726167652076616c75652e384d61785369676e61746f726965730c75313608640004ec20546865206d6178696d756d20616d6f756e74206f66207369676e61746f7269657320616c6c6f77656420696e20746865206d756c74697369672e38404d696e696d756d5468726573686f6c640480205468726573686f6c64206d7573742062652032206f7220677265617465722e3c416c7265616479417070726f76656404b02043616c6c20697320616c726561647920617070726f7665642062792074686973207369676e61746f72792e444e6f417070726f76616c734e656564656404a02043616c6c20646f65736e2774206e65656420616e7920286d6f72652920617070726f76616c732e44546f6f4665775369676e61746f7269657304ac2054686572652061726520746f6f20666577207369676e61746f7269657320696e20746865206c6973742e48546f6f4d616e795369676e61746f7269657304b02054686572652061726520746f6f206d616e79207369676e61746f7269657320696e20746865206c6973742e545369676e61746f726965734f75744f664f7264657204110120546865207369676e61746f7269657320776572652070726f7669646564206f7574206f66206f726465723b20746865792073686f756c64206265206f7264657265642e4c53656e646572496e5369676e61746f72696573041101205468652073656e6465722077617320636f6e7461696e656420696e20746865206f74686572207369676e61746f726965733b2069742073686f756c646e27742062652e204e6f74466f756e6404e0204d756c7469736967206f7065726174696f6e206e6f7420666f756e64207768656e20617474656d7074696e6720746f2063616e63656c2e204e6f744f776e6572043101204f6e6c7920746865206163636f756e742074686174206f726967696e616c6c79206372656174656420746865206d756c74697369672069732061626c6520746f2063616e63656c2069742e2c4e6f54696d65706f696e74042101204e6f2074696d65706f696e742077617320676976656e2c2079657420746865206d756c7469736967206f7065726174696f6e20697320616c726561647920756e6465727761792e3857726f6e6754696d65706f696e74043101204120646966666572656e742074696d65706f696e742077617320676976656e20746f20746865206d756c7469736967206f7065726174696f6e207468617420697320756e6465727761792e4c556e657870656374656454696d65706f696e7404f820412074696d65706f696e742077617320676976656e2c20796574206e6f206d756c7469736967206f7065726174696f6e20697320756e6465727761792e3c4d6178576569676874546f6f4c6f7704d420546865206d6178696d756d2077656967687420696e666f726d6174696f6e2070726f76696465642077617320746f6f206c6f772e34416c726561647953746f72656404a420546865206461746120746f2062652073746f72656420697320616c72656164792073746f7265642e1f20426f756e7469657301205472656173757279102c426f756e7479436f756e7401002c426f756e7479496e646578100000000004c0204e756d626572206f6620626f756e74792070726f706f73616c7320746861742068617665206265656e206d6164652e20426f756e746965730001052c426f756e7479496e646578c8426f756e74793c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265723e000400047820426f756e7469657320746861742068617665206265656e206d6164652e48426f756e74794465736372697074696f6e730001052c426f756e7479496e6465781c5665633c75383e000400048020546865206465736372697074696f6e206f66206561636820626f756e74792e3c426f756e7479417070726f76616c730100405665633c426f756e7479496e6465783e040004ec20426f756e747920696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f74207965742066756e6465642e01243870726f706f73655f626f756e7479081476616c756554436f6d706163743c42616c616e63654f663c543e3e2c6465736372697074696f6e1c5665633c75383e30582050726f706f73652061206e657720626f756e74792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c20617355012060446174614465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e2049742077696c6c20626520756e72657365727665642075706f6e20617070726f76616c2c68206f7220736c6173686564207768656e2072656a65637465642e00fc202d206063757261746f72603a205468652063757261746f72206163636f756e742077686f6d2077696c6c206d616e616765207468697320626f756e74792e68202d2060666565603a205468652063757261746f72206665652e2901202d206076616c7565603a2054686520746f74616c207061796d656e7420616d6f756e74206f66207468697320626f756e74792c2063757261746f722066656520696e636c756465642ec4202d20606465736372697074696f6e603a20546865206465736372697074696f6e206f66207468697320626f756e74792e38617070726f76655f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e20610120417070726f7665206120626f756e74792070726f706f73616c2e2041742061206c617465722074696d652c2074686520626f756e74792077696c6c2062652066756e64656420616e64206265636f6d6520616374697665ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e3c70726f706f73655f63757261746f720c24626f756e74795f696450436f6d706163743c426f756e7479496e6465783e1c63757261746f728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263650c66656554436f6d706163743c42616c616e63654f663c543e3e1c942041737369676e20612063757261746f7220746f20612066756e64656420626f756e74792e00b0204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a417070726f76654f726967696e602e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e40756e61737369676e5f63757261746f720424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e488020556e61737369676e2063757261746f722066726f6d206120626f756e74792e00210120546869732066756e6374696f6e2063616e206f6e6c792062652063616c6c656420627920746865206052656a6563744f726967696e602061207369676e6564206f726967696e2e00690120496620746869732066756e6374696f6e2069732063616c6c656420627920746865206052656a6563744f726967696e602c20776520617373756d652074686174207468652063757261746f72206973206d616c6963696f75730d01206f7220696e6163746976652e204173206120726573756c742c2077652077696c6c20736c617368207468652063757261746f72207768656e20706f737369626c652e00650120496620746865206f726967696e206973207468652063757261746f722c2077652074616b6520746869732061732061207369676e20746865792061726520756e61626c6520746f20646f207468656972206a6f6220616e64610120746865792077696c6c696e676c7920676976652075702e20576520636f756c6420736c617368207468656d2c2062757420666f72206e6f7720776520616c6c6f77207468656d20746f207265636f7665722074686569723901206465706f73697420616e64206578697420776974686f75742069737375652e20285765206d61792077616e7420746f206368616e67652074686973206966206974206973206162757365642e290061012046696e616c6c792c20746865206f726967696e2063616e20626520616e796f6e6520696620616e64206f6e6c79206966207468652063757261746f722069732022696e616374697665222e205468697320616c6c6f7773650120616e796f6e6520696e2074686520636f6d6d756e69747920746f2063616c6c206f7574207468617420612063757261746f72206973206e6f7420646f696e67207468656972206475652064696c6967656e63652c20616e643d012077652073686f756c64207069636b2061206e65772063757261746f722e20496e20746869732063617365207468652063757261746f722073686f756c6420616c736f20626520736c61736865642e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e386163636570745f63757261746f720424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e209820416363657074207468652063757261746f7220726f6c6520666f72206120626f756e74792e2d012041206465706f7369742077696c6c2062652072657365727665642066726f6d2063757261746f7220616e6420726566756e642075706f6e207375636365737366756c207061796f75742e0094204d6179206f6e6c792062652063616c6c65642066726f6d207468652063757261746f722e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e3061776172645f626f756e74790824626f756e74795f696450436f6d706163743c426f756e7479496e6465783e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528990120417761726420626f756e747920746f20612062656e6566696369617279206163636f756e742e205468652062656e65666963696172792077696c6c2062652061626c6520746f20636c61696d207468652066756e647320616674657220612064656c61792e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652063757261746f72206f66207468697320626f756e74792e008c202d2060626f756e74795f6964603a20426f756e747920494420746f2061776172642e1d01202d206062656e6566696369617279603a205468652062656e6566696369617279206163636f756e742077686f6d2077696c6c207265636569766520746865207061796f75742e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e30636c61696d5f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e24f020436c61696d20746865207061796f75742066726f6d20616e206177617264656420626f756e7479206166746572207061796f75742064656c61792e00290120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652062656e6566696369617279206f66207468697320626f756e74792e008c202d2060626f756e74795f6964603a20426f756e747920494420746f20636c61696d2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e30636c6f73655f626f756e74790424626f756e74795f696450436f6d706163743c426f756e7479496e6465783e283d012043616e63656c20612070726f706f736564206f722061637469766520626f756e74792e20416c6c207468652066756e64732077696c6c2062652073656e7420746f20747265617375727920616e64d0207468652063757261746f72206465706f7369742077696c6c20626520756e726573657276656420696620706f737369626c652e00cc204f6e6c792060543a3a52656a6563744f726967696e602069732061626c6520746f2063616e63656c206120626f756e74792e0090202d2060626f756e74795f6964603a20426f756e747920494420746f2063616e63656c2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e50657874656e645f626f756e74795f6578706972790824626f756e74795f696450436f6d706163743c426f756e7479496e6465783e1c5f72656d61726b1c5665633c75383e28b020457874656e6420746865206578706972792074696d65206f6620616e2061637469766520626f756e74792e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265207468652063757261746f72206f66207468697320626f756e74792e0090202d2060626f756e74795f6964603a20426f756e747920494420746f20657874656e642e90202d206072656d61726b603a206164646974696f6e616c20696e666f726d6174696f6e2e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e011c38426f756e747950726f706f736564042c426f756e7479496e646578047c204e657720626f756e74792070726f706f73616c2e205c5b696e6465785c5d38426f756e747952656a6563746564082c426f756e7479496e6465781c42616c616e6365041101204120626f756e74792070726f706f73616c207761732072656a65637465643b2066756e6473207765726520736c61736865642e205c5b696e6465782c20626f6e645c5d48426f756e7479426563616d65416374697665042c426f756e7479496e64657804e4204120626f756e74792070726f706f73616c2069732066756e64656420616e6420626563616d65206163746976652e205c5b696e6465785c5d34426f756e747941776172646564082c426f756e7479496e646578244163636f756e74496404f4204120626f756e7479206973206177617264656420746f20612062656e65666963696172792e205c5b696e6465782c2062656e65666963696172795c5d34426f756e7479436c61696d65640c2c426f756e7479496e6465781c42616c616e6365244163636f756e744964040d01204120626f756e747920697320636c61696d65642062792062656e65666963696172792e205c5b696e6465782c207061796f75742c2062656e65666963696172795c5d38426f756e747943616e63656c6564042c426f756e7479496e6465780484204120626f756e74792069732063616e63656c6c65642e205c5b696e6465785c5d38426f756e7479457874656e646564042c426f756e7479496e646578049c204120626f756e74792065787069727920697320657874656e6465642e205c5b696e6465785c5d1c48446174614465706f736974506572427974653042616c616e63654f663c543e400010a5d4e8000000000000000000000004fc2054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e20626f756e7479206465736372697074696f6e2e44426f756e74794465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004e82054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120626f756e74792070726f706f73616c2e60426f756e74794465706f7369745061796f757444656c617938543a3a426c6f636b4e756d6265721080700000045901205468652064656c617920706572696f6420666f72207768696368206120626f756e74792062656e6566696369617279206e65656420746f2077616974206265666f726520636c61696d20746865207061796f75742e48426f756e7479557064617465506572696f6438543a3a426c6f636b4e756d6265721000270600046c20426f756e7479206475726174696f6e20696e20626c6f636b732e50426f756e747943757261746f724465706f7369741c5065726d696c6c1020a10700046d012050657263656e74616765206f66207468652063757261746f722066656520746861742077696c6c20626520726573657276656420757066726f6e74206173206465706f73697420666f7220626f756e74792063757261746f722e48426f756e747956616c75654d696e696d756d3042616c616e63654f663c543e4000406352bfc6010000000000000000000470204d696e696d756d2076616c756520666f72206120626f756e74792e4c4d6178696d756d526561736f6e4c656e6774680c75333210004000000488204d6178696d756d2061636365707461626c6520726561736f6e206c656e6774682e2470496e73756666696369656e7450726f706f7365727342616c616e6365047c2050726f706f73657227732062616c616e636520697320746f6f206c6f772e30496e76616c6964496e6465780494204e6f2070726f706f73616c206f7220626f756e7479206174207468617420696e6465782e30526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e40556e657870656374656453746174757304842054686520626f756e74792073746174757320697320756e65787065637465642e385265717569726543757261746f720460205265717569726520626f756e74792063757261746f722e30496e76616c696456616c7565045820496e76616c696420626f756e74792076616c75652e28496e76616c6964466565045020496e76616c696420626f756e7479206665652e3450656e64696e675061796f75740870204120626f756e7479207061796f75742069732070656e64696e672efc20546f2063616e63656c2074686520626f756e74792c20796f75206d75737420756e61737369676e20616e6420736c617368207468652063757261746f722e245072656d61747572650449012054686520626f756e746965732063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e201054697073012054726561737572790810546970730001051c543a3a48617368f04f70656e5469703c543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d6265722c20543a3a486173683e0004000c650120546970734d6170207468617420617265206e6f742079657420636f6d706c657465642e204b65796564206279207468652068617368206f66206028726561736f6e2c2077686f29602066726f6d207468652076616c75652e3d012054686973206861732074686520696e73656375726520656e756d657261626c6520686173682066756e6374696f6e2073696e636520746865206b657920697473656c6620697320616c7265616479802067756172616e7465656420746f20626520612073656375726520686173682e1c526561736f6e730001061c543a3a486173681c5665633c75383e0004000849012053696d706c6520707265696d616765206c6f6f6b75702066726f6d2074686520726561736f6e2773206861736820746f20746865206f726967696e616c20646174612e20416761696e2c2068617320616e610120696e73656375726520656e756d657261626c6520686173682073696e636520746865206b65792069732067756172616e7465656420746f2062652074686520726573756c74206f6620612073656375726520686173682e0118387265706f72745f617765736f6d650818726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e7449644c5d01205265706f727420736f6d657468696e672060726561736f6e60207468617420646573657276657320612074697020616e6420636c61696d20616e79206576656e7475616c207468652066696e6465722773206665652e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e005501205061796d656e743a20605469705265706f72744465706f73697442617365602077696c6c2062652072657365727665642066726f6d20746865206f726967696e206163636f756e742c2061732077656c6c206173c02060446174614465706f736974506572427974656020666f722065616368206279746520696e2060726561736f6e602e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743ecc202d20436f6d706c65786974793a20604f2852296020776865726520605260206c656e677468206f662060726561736f6e602e942020202d20656e636f64696e6720616e642068617368696e67206f662027726561736f6e2774202d20446252656164733a2060526561736f6e73602c2060546970736078202d2044625772697465733a2060526561736f6e73602c20605469707360302023203c2f7765696768743e2c726574726163745f7469700410686173681c543a3a486173684c550120526574726163742061207072696f72207469702d7265706f72742066726f6d20607265706f72745f617765736f6d65602c20616e642063616e63656c207468652070726f63657373206f662074697070696e672e00e0204966207375636365737366756c2c20746865206f726967696e616c206465706f7369742077696c6c20626520756e72657365727665642e00510120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e642074686520746970206964656e746966696564206279206068617368604501206d7573742068617665206265656e207265706f7274656420627920746865207369676e696e67206163636f756e74207468726f75676820607265706f72745f617765736f6d65602028616e64206e6f7450207468726f75676820607469705f6e657760292e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e009020456d697473206054697052657472616374656460206966207375636365737366756c2e002c2023203c7765696768743e54202d20436f6d706c65786974793a20604f28312960dc2020202d20446570656e6473206f6e20746865206c656e677468206f662060543a3a48617368602077686963682069732066697865642e90202d20446252656164733a206054697073602c20606f726967696e206163636f756e7460c0202d2044625772697465733a2060526561736f6e73602c206054697073602c20606f726967696e206163636f756e7460302023203c2f7765696768743e1c7469705f6e65770c18726561736f6e1c5665633c75383e0c77686f30543a3a4163636f756e744964247469705f76616c756554436f6d706163743c42616c616e63654f663c543e3e58f4204769766520612074697020666f7220736f6d657468696e67206e65773b206e6f2066696e6465722773206665652077696c6c2062652074616b656e2e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006101202d2060726561736f6e603a2054686520726561736f6e20666f722c206f7220746865207468696e6720746861742064657365727665732c20746865207469703b2067656e6572616c6c7920746869732077696c6c2062655c20202061205554462d382d656e636f6465642055524c2eec202d206077686f603a20546865206163636f756e742077686963682073686f756c6420626520637265646974656420666f7220746865207469702e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e007820456d69747320604e657754697060206966207375636365737366756c2e002c2023203c7765696768743e5501202d20436f6d706c65786974793a20604f2852202b2054296020776865726520605260206c656e677468206f662060726561736f6e602c2060546020697320746865206e756d626572206f6620746970706572732ec02020202d20604f285429603a206465636f64696e6720605469707065726020766563206f66206c656e6774682060546009012020202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e0d0120202020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602ee42020202d20604f285229603a2068617368696e6720616e6420656e636f64696e67206f6620726561736f6e206f66206c656e6774682060526080202d20446252656164733a206054697070657273602c2060526561736f6e736078202d2044625772697465733a2060526561736f6e73602c20605469707360302023203c2f7765696768743e0c7469700810686173681c543a3a48617368247469705f76616c756554436f6d706163743c42616c616e63654f663c543e3e64b4204465636c6172652061207469702076616c756520666f7220616e20616c72656164792d6f70656e207469702e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20616e6420746865207369676e696e67206163636f756e74206d757374206265206174206d656d626572206f662074686520605469707065727360207365742e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f66207468652068617368206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279382020206163636f756e742049442e5101202d20607469705f76616c7565603a2054686520616d6f756e74206f66207469702074686174207468652073656e64657220776f756c64206c696b6520746f20676976652e20546865206d656469616e20746970d820202076616c7565206f662061637469766520746970706572732077696c6c20626520676976656e20746f20746865206077686f602e00650120456d6974732060546970436c6f73696e676020696620746865207468726573686f6c64206f66207469707065727320686173206265656e207265616368656420616e642074686520636f756e74646f776e20706572696f64342068617320737461727465642e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e15012020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602c20696e736572742074697020616e6420636865636b20636c6f73696e672c0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602e00610120202041637475616c6c792077656967687420636f756c64206265206c6f77657220617320697420646570656e6473206f6e20686f77206d616e7920746970732061726520696e20604f70656e5469706020627574206974d4202020697320776569676874656420617320696620616c6d6f73742066756c6c20692e65206f66206c656e6774682060542d31602e74202d20446252656164733a206054697070657273602c206054697073604c202d2044625772697465733a20605469707360302023203c2f7765696768743e24636c6f73655f7469700410686173681c543a3a48617368446020436c6f736520616e64207061796f75742061207469702e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e0019012054686520746970206964656e74696669656420627920606861736860206d75737420686176652066696e69736865642069747320636f756e74646f776e20706572696f642e006501202d206068617368603a20546865206964656e74697479206f6620746865206f70656e2074697020666f722077686963682061207469702076616c7565206973206465636c617265642e205468697320697320666f726d656461012020206173207468652068617368206f6620746865207475706c65206f6620746865206f726967696e616c207469702060726561736f6e6020616e64207468652062656e6566696369617279206163636f756e742049442e002c2023203c7765696768743ee4202d20436f6d706c65786974793a20604f285429602077686572652060546020697320746865206e756d626572206f6620746970706572732e9c2020206465636f64696e6720605469707065726020766563206f66206c656e677468206054602e0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602eac202d20446252656164733a206054697073602c206054697070657273602c20607469702066696e64657260dc202d2044625772697465733a2060526561736f6e73602c206054697073602c206054697070657273602c20607469702066696e64657260302023203c2f7765696768743e24736c6173685f7469700410686173681c543a3a4861736830982052656d6f766520616e6420736c61736820616e20616c72656164792d6f70656e207469702e00ac204d6179206f6e6c792062652063616c6c65642066726f6d2060543a3a52656a6563744f726967696e602e00f8204173206120726573756c742c207468652066696e64657220697320736c617368656420616e6420746865206465706f7369747320617265206c6f73742e008820456d6974732060546970536c617368656460206966207375636365737366756c2e002c2023203c7765696768743e0101202020605460206973206368617267656420617320757070657220626f756e6420676976656e2062792060436f6e7461696e734c656e677468426f756e64602e05012020205468652061637475616c20636f737420646570656e6473206f6e2074686520696d706c656d656e746174696f6e206f662060543a3a54697070657273602e302023203c2f7765696768743e0114184e657754697004104861736804cc2041206e6577207469702073756767657374696f6e20686173206265656e206f70656e65642e205c5b7469705f686173685c5d28546970436c6f73696e670410486173680411012041207469702073756767657374696f6e206861732072656163686564207468726573686f6c6420616e6420697320636c6f73696e672e205c5b7469705f686173685c5d24546970436c6f7365640c1048617368244163636f756e7449641c42616c616e636504f02041207469702073756767657374696f6e20686173206265656e20636c6f7365642e205c5b7469705f686173682c2077686f2c207061796f75745c5d3054697052657472616374656404104861736804c82041207469702073756767657374696f6e20686173206265656e207265747261637465642e205c5b7469705f686173685c5d28546970536c61736865640c1048617368244163636f756e7449641c42616c616e63650405012041207469702073756767657374696f6e20686173206265656e20736c61736865642e205c5b7469705f686173682c2066696e6465722c206465706f7369745c5d1430546970436f756e74646f776e38543a3a426c6f636b4e756d62657210807000000445012054686520706572696f6420666f722077686963682061207469702072656d61696e73206f70656e20616674657220697320686173206163686965766564207468726573686f6c6420746970706572732e3454697046696e646572734665651c50657263656e7404140431012054686520616d6f756e74206f66207468652066696e616c2074697020776869636820676f657320746f20746865206f726967696e616c207265706f72746572206f6620746865207469702e505469705265706f72744465706f736974426173653042616c616e63654f663c543e4000407a10f35a0000000000000000000004d42054686520616d6f756e742068656c64206f6e206465706f73697420666f7220706c6163696e67206120746970207265706f72742e48446174614465706f736974506572427974653042616c616e63654f663c543e400010a5d4e800000000000000000000000409012054686520616d6f756e742068656c64206f6e206465706f7369742070657220627974652077697468696e2074686520746970207265706f727420726561736f6e2e4c4d6178696d756d526561736f6e4c656e6774680c75333210004000000488204d6178696d756d2061636365707461626c6520726561736f6e206c656e6774682e1830526561736f6e546f6f42696704882054686520726561736f6e20676976656e206973206a75737420746f6f206269672e30416c72656164794b6e6f776e048c20546865207469702077617320616c726561647920666f756e642f737461727465642e28556e6b6e6f776e54697004642054686520746970206861736820697320756e6b6e6f776e2e244e6f7446696e64657204210120546865206163636f756e7420617474656d7074696e6720746f20726574726163742074686520746970206973206e6f74207468652066696e646572206f6620746865207469702e245374696c6c4f70656e042d0120546865207469702063616e6e6f7420626520636c61696d65642f636c6f736564206265636175736520746865726520617265206e6f7420656e6f7567682074697070657273207965742e245072656d617475726504350120546865207469702063616e6e6f7420626520636c61696d65642f636c6f73656420626563617573652069742773207374696c6c20696e2074686520636f756e74646f776e20706572696f642e211841737365747301184173736574731014417373657400010228543a3a41737365744964f8417373657444657461696c733c543a3a42616c616e63652c20543a3a4163636f756e7449642c204465706f73697442616c616e63654f663c542c20493e3e00040004542044657461696c73206f6620616e2061737365742e1c4163636f756e7401020228543a3a4173736574496430543a3a4163636f756e74496488417373657442616c616e63653c543a3a42616c616e63652c20543a3a45787472613e02280000000000000000000004e420546865206e756d626572206f6620756e697473206f66206173736574732068656c6420627920616e7920676976656e206163636f756e742e24417070726f76616c7300030c28543a3a4173736574496430543a3a4163636f756e74496430543a3a4163636f756e7449640c020202b0417070726f76616c3c543a3a42616c616e63652c204465706f73697442616c616e63654f663c542c20493e3e04000c590120417070726f7665642062616c616e6365207472616e73666572732e2046697273742062616c616e63652069732074686520616d6f756e7420617070726f76656420666f72207472616e736665722e205365636f6e64e82069732074686520616d6f756e74206f662060543a3a43757272656e63796020726573657276656420666f722073746f72696e6720746869732e4901204669727374206b6579206973207468652061737365742049442c207365636f6e64206b657920697320746865206f776e657220616e64207468697264206b6579206973207468652064656c65676174652e204d6574616461746101010228543a3a41737365744964190141737365744d657461646174613c4465706f73697442616c616e63654f663c542c20493e2c20426f756e6465645665633c75382c20543a3a537472696e674c696d69743e0a3e005000000000000000000000000000000000000000000458204d65746164617461206f6620616e2061737365742e015c186372656174650c0869644c436f6d706163743c543a3a417373657449643e1461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c6d696e5f62616c616e636528543a3a42616c616e63654cec2049737375652061206e657720636c617373206f662066756e6769626c65206173736574732066726f6d2061207075626c6963206f726967696e2e0029012054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c7920616e6420697473206f776e657220697320746865206f726967696e2e00290120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d75737420686176652073756666696369656e742066756e647320667265652e00c02046756e6473206f662073656e64657220617265207265736572766564206279206041737365744465706f736974602e003020506172616d65746572733a5d01202d20606964603a20546865206964656e746966696572206f6620746865206e65772061737365742e2054686973206d757374206e6f742062652063757272656e746c7920696e2075736520746f206964656e746966794c20616e206578697374696e672061737365742e5d01202d206061646d696e603a205468652061646d696e206f66207468697320636c617373206f66206173736574732e205468652061646d696e2069732074686520696e697469616c2061646472657373206f662065616368a0206d656d626572206f662074686520617373657420636c61737327732061646d696e207465616d2e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e009c20456d69747320604372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f2831296030666f7263655f637265617465100869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653469735f73756666696369656e7410626f6f6c2c6d696e5f62616c616e63654c436f6d706163743c543a3a42616c616e63653e4cfc2049737375652061206e657720636c617373206f662066756e6769626c65206173736574732066726f6d20612070726976696c65676564206f726967696e2e00b82054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c792e00a820546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e602e00a020556e6c696b652060637265617465602c206e6f2066756e6473206172652072657365727665642e005d01202d20606964603a20546865206964656e746966696572206f6620746865206e65772061737365742e2054686973206d757374206e6f742062652063757272656e746c7920696e2075736520746f206964656e746966794c20616e206578697374696e672061737365742e5d01202d20606f776e6572603a20546865206f776e6572206f66207468697320636c617373206f66206173736574732e20546865206f776e6572206861732066756c6c20737570657275736572207065726d697373696f6e737d01206f76657220746869732061737365742c20627574206d6179206c61746572206368616e676520616e6420636f6e66696775726520746865207065726d697373696f6e73207573696e6720607472616e736665725f6f776e657273686970604020616e6420607365745f7465616d602e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e00b020456d6974732060466f7263654372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f283129601c64657374726f79080869644c436f6d706163743c543a3a417373657449643e1c7769746e6573733844657374726f795769746e65737348902044657374726f79206120636c617373206f662066756e6769626c65206173736574732e00590120546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e60206f72206d757374206265205369676e656420616e64207468652073656e646572206d7573742062652074686564206f776e6572206f662074686520617373657420606964602e005101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652064657374726f7965642e2054686973206d757374206964656e7469667920616e206578697374696e671c2061737365742e00a420456d697473206044657374726f79656460206576656e74207768656e207375636365737366756c2e004901204e4f54453a2049742063616e2062652068656c7066756c20746f20666972737420667265657a6520616e206173736574206265666f72652064657374726f79696e6720697420736f207468617420796f754d012063616e2070726f76696465206163637572617465207769746e65737320696e666f726d6174696f6e20616e642070726576656e742075736572732066726f6d206d616e6970756c6174696e67207374617465b420696e20612077617920746861742063616e206d616b652069742068617264657220746f2064657374726f792e0078205765696768743a20604f2863202b2070202b206129602077686572653ac4202d206063203d20287769746e6573732e6163636f756e7473202d207769746e6573732e73756666696369656e7473296070202d206073203d207769746e6573732e73756666696369656e74736068202d206061203d207769746e6573732e617070726f76616c7360106d696e740c0869644c436f6d706163743c543a3a417373657449643e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e308c204d696e7420617373657473206f66206120706172746963756c617220636c6173732e003d0120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d7573742062652074686520497373756572206f662074686520617373657420606964602e000101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74206d696e7465642e1101202d206062656e6566696369617279603a20546865206163636f756e7420746f206265206372656469746564207769746820746865206d696e746564206173736574732ec8202d2060616d6f756e74603a2054686520616d6f756e74206f662074686520617373657420746f206265206d696e7465642e009820456d697473206049737375656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f283129605901204d6f6465733a205072652d6578697374696e672062616c616e6365206f66206062656e6566696369617279603b204163636f756e74207072652d6578697374656e6365206f66206062656e6566696369617279602e106275726e0c0869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e3c490120526564756365207468652062616c616e6365206f66206077686f60206279206173206d75636820617320706f737369626c6520757020746f2060616d6f756e746020617373657473206f6620606964602e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204d616e61676572206f662074686520617373657420606964602e00dc204261696c732077697468206042616c616e63655a65726f6020696620746865206077686f6020697320616c726561647920646561642e000101202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74206275726e65642ea4202d206077686f603a20546865206163636f756e7420746f20626520646562697465642066726f6d2e2d01202d2060616d6f756e74603a20546865206d6178696d756d20616d6f756e74206279207768696368206077686f6027732062616c616e63652073686f756c6420626520726564756365642e00550120456d69747320604275726e6564602077697468207468652061637475616c20616d6f756e74206275726e65642e20496620746869732074616b6573207468652062616c616e636520746f2062656c6f77207468653d01206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74206275726e656420697320696e6372656173656420746f2074616b6520697420746f207a65726f2e003c205765696768743a20604f283129600d01204d6f6465733a20506f73742d6578697374656e6365206f66206077686f603b20507265202620706f7374205a6f6d6269652d737461747573206f66206077686f602e207472616e736665720c0869644c436f6d706163743c543a3a417373657449643e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e48d4204d6f766520736f6d65206173736574732066726f6d207468652073656e646572206163636f756e7420746f20616e6f746865722e005c204f726967696e206d757374206265205369676e65642e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642ea0202d2060746172676574603a20546865206163636f756e7420746f2062652063726564697465642e5501202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652073656e64657227732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e64650120607461726765746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e6101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652073656e6465722062616c616e63652061626f7665207a65726f206275742062656c6f77c020746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605501204d6f6465733a205072652d6578697374656e6365206f662060746172676574603b20506f73742d6578697374656e6365206f662073656e6465723b204163636f756e74207072652d6578697374656e6365206f66282060746172676574602e4c7472616e736665725f6b6565705f616c6976650c0869644c436f6d706163743c543a3a417373657449643e187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e485d01204d6f766520736f6d65206173736574732066726f6d207468652073656e646572206163636f756e7420746f20616e6f746865722c206b656570696e67207468652073656e646572206163636f756e7420616c6976652e005c204f726967696e206d757374206265205369676e65642e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642ea0202d2060746172676574603a20546865206163636f756e7420746f2062652063726564697465642e5501202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652073656e64657227732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e64650120607461726765746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e6101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652073656e6465722062616c616e63652061626f7665207a65726f206275742062656c6f77c020746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605501204d6f6465733a205072652d6578697374656e6365206f662060746172676574603b20506f73742d6578697374656e6365206f662073656e6465723b204163636f756e74207072652d6578697374656e6365206f66282060746172676574602e38666f7263655f7472616e73666572100869644c436f6d706163743c543a3a417373657449643e18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e4cb8204d6f766520736f6d65206173736574732066726f6d206f6e65206163636f756e7420746f20616e6f746865722e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e001501202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206861766520736f6d6520616d6f756e74207472616e736665727265642e9c202d2060736f75726365603a20546865206163636f756e7420746f20626520646562697465642e98202d206064657374603a20546865206163636f756e7420746f2062652063726564697465642e5d01202d2060616d6f756e74603a2054686520616d6f756e74206279207768696368207468652060736f757263656027732062616c616e6365206f66206173736574732073686f756c64206265207265647563656420616e645d012060646573746027732062616c616e636520696e637265617365642e2054686520616d6f756e742061637475616c6c79207472616e73666572726564206d617920626520736c696768746c79206772656174657220696e5101207468652063617365207468617420746865207472616e7366657220776f756c64206f74686572776973652074616b65207468652060736f75726365602062616c616e63652061626f7665207a65726f20627574d82062656c6f7720746865206d696e696d756d2062616c616e63652e204d7573742062652067726561746572207468616e207a65726f2e00650120456d69747320605472616e73666572726564602077697468207468652061637475616c20616d6f756e74207472616e736665727265642e20496620746869732074616b65732074686520736f757263652062616c616e6365610120746f2062656c6f7720746865206d696e696d756d20666f72207468652061737365742c207468656e2074686520616d6f756e74207472616e7366657272656420697320696e6372656173656420746f2074616b652069742420746f207a65726f2e003c205765696768743a20604f283129605501204d6f6465733a205072652d6578697374656e6365206f66206064657374603b20506f73742d6578697374656e6365206f662060736f75726365603b204163636f756e74207072652d6578697374656e6365206f6620206064657374602e18667265657a65080869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528e420446973616c6c6f77206675727468657220756e70726976696c65676564207472616e73666572732066726f6d20616e206163636f756e742e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e8c202d206077686f603a20546865206163636f756e7420746f2062652066726f7a656e2e004020456d697473206046726f7a656e602e003c205765696768743a20604f283129601074686177080869644c436f6d706163743c543a3a417373657449643e0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636528d020416c6c6f7720756e70726976696c65676564207472616e73666572732066726f6d20616e206163636f756e7420616761696e2e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e94202d206077686f603a20546865206163636f756e7420746f20626520756e66726f7a656e2e004020456d6974732060546861776564602e003c205765696768743a20604f2831296030667265657a655f6173736574040869644c436f6d706163743c543a3a417373657449643e24f420446973616c6c6f77206675727468657220756e70726976696c65676564207472616e736665727320666f722074686520617373657420636c6173732e003901204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2e004020456d697473206046726f7a656e602e003c205765696768743a20604f2831296028746861775f6173736574040869644c436f6d706163743c543a3a417373657449643e24c820416c6c6f7720756e70726976696c65676564207472616e736665727320666f722074686520617373657420616761696e2e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f206265207468617765642e004020456d6974732060546861776564602e003c205765696768743a20604f28312960487472616e736665725f6f776e657273686970080869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652878204368616e676520746865204f776e6572206f6620616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742ea0202d20606f776e6572603a20546865206e6577204f776e6572206f6620746869732061737365742e005820456d69747320604f776e65724368616e676564602e003c205765696768743a20604f28312960207365745f7465616d100869644c436f6d706163743c543a3a417373657449643e186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636530c8204368616e676520746865204973737565722c2041646d696e20616e6420467265657a6572206f6620616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00c8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f2062652066726f7a656e2ea8202d2060697373756572603a20546865206e657720497373756572206f6620746869732061737365742ea0202d206061646d696e603a20546865206e65772041646d696e206f6620746869732061737365742eb0202d2060667265657a6572603a20546865206e657720467265657a6572206f6620746869732061737365742e005420456d69747320605465616d4368616e676564602e003c205765696768743a20604f28312960307365745f6d65746164617461100869644c436f6d706163743c543a3a417373657449643e106e616d651c5665633c75383e1873796d626f6c1c5665633c75383e20646563696d616c73087538407c2053657420746865206d6574616461746120666f7220616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00dc2046756e6473206f662073656e64657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613a550120604d657461646174614465706f73697442617365202b204d657461646174614465706f73697450657242797465202a20286e616d652e6c656e202b2073796d626f6c2e6c656e29602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e00bc202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f207570646174652e5101202d20606e616d65603a20546865207573657220667269656e646c79206e616d65206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e5101202d206073796d626f6c603a205468652065786368616e67652073796d626f6c20666f7220746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3101202d2060646563696d616c73603a20546865206e756d626572206f6620646563696d616c732074686973206173736574207573657320746f20726570726573656e74206f6e6520756e69742e005420456d69747320604d65746164617461536574602e003c205765696768743a20604f2831296038636c6561725f6d65746164617461040869644c436f6d706163743c543a3a417373657449643e2c8420436c65617220746865206d6574616461746120666f7220616e2061737365742e003101204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f662074686520617373657420606964602e00a820416e79206465706f73697420697320667265656420666f7220746865206173736574206f776e65722e00b8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f20636c6561722e006420456d69747320604d65746164617461436c6561726564602e003c205765696768743a20604f2831296048666f7263655f7365745f6d65746164617461140869644c436f6d706163743c543a3a417373657449643e106e616d651c5665633c75383e1873796d626f6c1c5665633c75383e20646563696d616c730875382469735f66726f7a656e10626f6f6c38bc20466f72636520746865206d6574616461746120666f7220616e20617373657420746f20736f6d652076616c75652e0070204f726967696e206d75737420626520466f7263654f726967696e2e006c20416e79206465706f736974206973206c65667420616c6f6e652e00bc202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f207570646174652e5101202d20606e616d65603a20546865207573657220667269656e646c79206e616d65206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e5101202d206073796d626f6c603a205468652065786368616e67652073796d626f6c20666f7220746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3101202d2060646563696d616c73603a20546865206e756d626572206f6620646563696d616c732074686973206173736574207573657320746f20726570726573656e74206f6e6520756e69742e005420456d69747320604d65746164617461536574602e005501205765696768743a20604f284e202b20532960207768657265204e20616e6420532061726520746865206c656e677468206f6620746865206e616d6520616e642073796d626f6c20726573706563746976656c792e50666f7263655f636c6561725f6d65746164617461040869644c436f6d706163743c543a3a417373657449643e2c8420436c65617220746865206d6574616461746120666f7220616e2061737365742e0070204f726967696e206d75737420626520466f7263654f726967696e2e006420416e79206465706f7369742069732072657475726e65642e00b8202d20606964603a20546865206964656e746966696572206f662074686520617373657420746f20636c6561722e006420456d69747320604d65746164617461436c6561726564602e003c205765696768743a20604f2831296048666f7263655f61737365745f737461747573200869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c6d696e5f62616c616e63654c436f6d706163743c543a3a42616c616e63653e3469735f73756666696369656e7410626f6f6c2469735f66726f7a656e10626f6f6c589c20416c746572207468652061747472696275746573206f66206120676976656e2061737365742e0078204f726967696e206d7573742062652060466f7263654f726967696e602e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742ea0202d20606f776e6572603a20546865206e6577204f776e6572206f6620746869732061737365742ea8202d2060697373756572603a20546865206e657720497373756572206f6620746869732061737365742ea0202d206061646d696e603a20546865206e65772041646d696e206f6620746869732061737365742eb0202d2060667265657a6572603a20546865206e657720467265657a6572206f6620746869732061737365742e5101202d20606d696e5f62616c616e6365603a20546865206d696e696d756d2062616c616e6365206f662074686973206e6577206173736574207468617420616e792073696e676c65206163636f756e74206d757374410120686176652e20496620616e206163636f756e7427732062616c616e636520697320726564756365642062656c6f7720746869732c207468656e20697420636f6c6c617073657320746f207a65726f2e5501202d206069735f73756666696369656e74603a20576865746865722061206e6f6e2d7a65726f2062616c616e6365206f662074686973206173736574206973206465706f736974206f662073756666696369656e7451012076616c756520746f206163636f756e7420666f722074686520737461746520626c6f6174206173736f6369617465642077697468206974732062616c616e63652073746f726167652e2049662073657420746f5901206074727565602c207468656e206e6f6e2d7a65726f2062616c616e636573206d61792062652073746f72656420776974686f757420612060636f6e73756d657260207265666572656e63652028616e642074687573510120616e20454420696e207468652042616c616e6365732070616c6c6574206f7220776861746576657220656c7365206973207573656420746f20636f6e74726f6c20757365722d6163636f756e74207374617465242067726f777468292e4101202d206069735f66726f7a656e603a2057686574686572207468697320617373657420636c6173732069732066726f7a656e2065786365707420666f72207065726d697373696f6e65642f61646d696e3820696e737472756374696f6e732e00ec20456d697473206041737365745374617475734368616e67656460207769746820746865206964656e74697479206f66207468652061737365742e003c205765696768743a20604f2831296040617070726f76655f7472616e736665720c0869644c436f6d706163743c543a3a417373657449643e2064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e50310120417070726f766520616e20616d6f756e74206f6620617373657420666f72207472616e7366657220627920612064656c6567617465642074686972642d7061727479206163636f756e742e005c204f726967696e206d757374206265205369676e65642e00510120456e737572657320746861742060417070726f76616c4465706f7369746020776f727468206f66206043757272656e6379602069732072657365727665642066726f6d207369676e696e67206163636f756e74590120666f722074686520707572706f7365206f6620686f6c64696e672074686520617070726f76616c2e20496620736f6d65206e6f6e2d7a65726f20616d6f756e74206f662061737365747320697320616c72656164794d0120617070726f7665642066726f6d207369676e696e67206163636f756e7420746f206064656c6567617465602c207468656e20697420697320746f70706564207570206f7220756e726573657276656420746f58206d656574207468652072696768742076616c75652e004901204e4f54453a20546865207369676e696e67206163636f756e7420646f6573206e6f74206e65656420746f206f776e2060616d6f756e7460206f66206173736574732061742074686520706f696e74206f6648206d616b696e6720746869732063616c6c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e1101202d206064656c6567617465603a20546865206163636f756e7420746f2064656c6567617465207065726d697373696f6e20746f207472616e736665722061737365742e4d01202d2060616d6f756e74603a2054686520616d6f756e74206f662061737365742074686174206d6179206265207472616e73666572726564206279206064656c6567617465602e204966207468657265206973e420616c726561647920616e20617070726f76616c20696e20706c6163652c207468656e207468697320616374732061646469746976656c792e009420456d6974732060417070726f7665645472616e7366657260206f6e20737563636573732e003c205765696768743a20604f283129603c63616e63656c5f617070726f76616c080869644c436f6d706163743c543a3a417373657449643e2064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365344d012043616e63656c20616c6c206f6620736f6d6520617373657420617070726f76656420666f722064656c656761746564207472616e7366657220627920612074686972642d7061727479206163636f756e742e004101204f726967696e206d757374206265205369676e656420616e64207468657265206d75737420626520616e20617070726f76616c20696e20706c616365206265747765656e207369676e657220616e6430206064656c6567617465602e004d0120556e726573657276657320616e79206465706f7369742070726576696f75736c792072657365727665642062792060617070726f76655f7472616e736665726020666f722074686520617070726f76616c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e0901202d206064656c6567617465603a20546865206163636f756e742064656c656761746564207065726d697373696f6e20746f207472616e736665722061737365742e009820456d6974732060417070726f76616c43616e63656c6c656460206f6e20737563636573732e003c205765696768743a20604f2831296054666f7263655f63616e63656c5f617070726f76616c0c0869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365344d012043616e63656c20616c6c206f6620736f6d6520617373657420617070726f76656420666f722064656c656761746564207472616e7366657220627920612074686972642d7061727479206163636f756e742e004d01204f726967696e206d7573742062652065697468657220466f7263654f726967696e206f72205369676e6564206f726967696e207769746820746865207369676e6572206265696e67207468652041646d696e6c206163636f756e74206f662074686520617373657420606964602e004d0120556e726573657276657320616e79206465706f7369742070726576696f75736c792072657365727665642062792060617070726f76655f7472616e736665726020666f722074686520617070726f76616c2e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e0901202d206064656c6567617465603a20546865206163636f756e742064656c656761746564207065726d697373696f6e20746f207472616e736665722061737365742e009820456d6974732060417070726f76616c43616e63656c6c656460206f6e20737563636573732e003c205765696768743a20604f28312960447472616e736665725f617070726f766564100869644c436f6d706163743c543a3a417373657449643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c64657374696e6174696f6e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636518616d6f756e744c436f6d706163743c543a3a42616c616e63653e485101205472616e7366657220736f6d652061737365742062616c616e63652066726f6d20612070726576696f75736c792064656c656761746564206163636f756e7420746f20736f6d652074686972642d706172747924206163636f756e742e004d01204f726967696e206d757374206265205369676e656420616e64207468657265206d75737420626520616e20617070726f76616c20696e20706c6163652062792074686520606f776e65726020746f2074686520207369676e65722e005d012049662074686520656e7469726520616d6f756e7420617070726f76656420666f72207472616e73666572206973207472616e736665727265642c207468656e20616e79206465706f7369742070726576696f75736c79b82072657365727665642062792060617070726f76655f7472616e736665726020697320756e72657365727665642e0094202d20606964603a20546865206964656e746966696572206f66207468652061737365742e6501202d20606f776e6572603a20546865206163636f756e742077686963682070726576696f75736c7920617070726f76656420666f722061207472616e73666572206f66206174206c656173742060616d6f756e746020616e64c02066726f6d207768696368207468652061737365742062616c616e63652077696c6c2062652077697468647261776e2e6501202d206064657374696e6174696f6e603a20546865206163636f756e7420746f207768696368207468652061737365742062616c616e6365206f662060616d6f756e74602077696c6c206265207472616e736665727265642eb8202d2060616d6f756e74603a2054686520616d6f756e74206f662061737365747320746f207472616e736665722e00a020456d69747320605472616e73666572726564417070726f76656460206f6e20737563636573732e003c205765696768743a20604f2831296001481c437265617465640c1c41737365744964244163636f756e744964244163636f756e74496404ec20536f6d6520617373657420636c6173732077617320637265617465642e205c5b61737365745f69642c2063726561746f722c206f776e65725c5d184973737565640c1c41737365744964244163636f756e7449641c42616c616e636504ec20536f6d65206173736574732077657265206973737565642e205c5b61737365745f69642c206f776e65722c20746f74616c5f737570706c795c5d2c5472616e73666572726564101c41737365744964244163636f756e744964244163636f756e7449641c42616c616e636504f420536f6d65206173736574732077657265207472616e736665727265642e205c5b61737365745f69642c2066726f6d2c20746f2c20616d6f756e745c5d184275726e65640c1c41737365744964244163636f756e7449641c42616c616e636504e420536f6d652061737365747320776572652064657374726f7965642e205c5b61737365745f69642c206f776e65722c2062616c616e63655c5d2c5465616d4368616e676564101c41737365744964244163636f756e744964244163636f756e744964244163636f756e74496404050120546865206d616e6167656d656e74207465616d206368616e676564205c5b61737365745f69642c206973737565722c2061646d696e2c20667265657a65725c5d304f776e65724368616e676564081c41737365744964244163636f756e744964049820546865206f776e6572206368616e676564205c5b61737365745f69642c206f776e65725c5d1846726f7a656e081c41737365744964244163636f756e74496404c420536f6d65206163636f756e74206077686f60207761732066726f7a656e2e205c5b61737365745f69642c2077686f5c5d18546861776564081c41737365744964244163636f756e74496404c420536f6d65206163636f756e74206077686f6020776173207468617765642e205c5b61737365745f69642c2077686f5c5d2c417373657446726f7a656e041c4173736574496404bc20536f6d65206173736574206061737365745f696460207761732066726f7a656e2e205c5b61737365745f69645c5d2c4173736574546861776564041c4173736574496404bc20536f6d65206173736574206061737365745f69646020776173207468617765642e205c5b61737365745f69645c5d2444657374726f796564041c41737365744964047820416e20617373657420636c617373207761732064657374726f7965642e30466f72636543726561746564081c41737365744964244163636f756e74496404e020536f6d6520617373657420636c6173732077617320666f7263652d637265617465642e205c5b61737365745f69642c206f776e65725c5d2c4d65746164617461536574141c417373657449641c5665633c75383e1c5665633c75383e08753810626f6f6c046101204e6577206d6574616461746120686173206265656e2073657420666f7220616e2061737365742e205c5b61737365745f69642c206e616d652c2073796d626f6c2c20646563696d616c732c2069735f66726f7a656e5c5d3c4d65746164617461436c6561726564041c4173736574496404d4204d6574616461746120686173206265656e20636c656172656420666f7220616e2061737365742e205c5b61737365745f69645c5d40417070726f7665645472616e73666572101c41737365744964244163636f756e744964244163636f756e7449641c42616c616e636508350120284164646974696f6e616c292066756e64732068617665206265656e20617070726f76656420666f72207472616e7366657220746f20612064657374696e6174696f6e206163636f756e742e9c205c5b61737365745f69642c20736f757263652c2064656c65676174652c20616d6f756e745c5d44417070726f76616c43616e63656c6c65640c1c41737365744964244163636f756e744964244163636f756e74496408f420416e20617070726f76616c20666f72206163636f756e74206064656c656761746560207761732063616e63656c6c656420627920606f776e6572602e60205c5b69642c206f776e65722c2064656c65676174655c5d4c5472616e73666572726564417070726f766564141c41737365744964244163636f756e744964244163636f756e744964244163636f756e7449641c42616c616e63650c350120416e2060616d6f756e746020776173207472616e7366657272656420696e2069747320656e7469726574792066726f6d20606f776e65726020746f206064657374696e6174696f6e60206279642074686520617070726f766564206064656c6567617465602e94205c5b69642c206f776e65722c2064656c65676174652c2064657374696e6174696f6e5c5d4841737365745374617475734368616e676564041c4173736574496408fc20416e2061737365742068617320686164206974732061747472696275746573206368616e676564206279207468652060466f72636560206f726967696e2e1c205c5b69645c5d00302842616c616e63654c6f77041901204163636f756e742062616c616e6365206d7573742062652067726561746572207468616e206f7220657175616c20746f20746865207472616e7366657220616d6f756e742e2c42616c616e63655a65726f04702042616c616e63652073686f756c64206265206e6f6e2d7a65726f2e304e6f5065726d697373696f6e04ec20546865207369676e696e67206163636f756e7420686173206e6f207065726d697373696f6e20746f20646f20746865206f7065726174696f6e2e1c556e6b6e6f776e047c2054686520676976656e20617373657420494420697320756e6b6e6f776e2e1846726f7a656e047820546865206f726967696e206163636f756e742069732066726f7a656e2e14496e557365047c2054686520617373657420494420697320616c72656164792074616b656e2e284261645769746e657373047020496e76616c6964207769746e657373206461746120676976656e2e384d696e42616c616e63655a65726f0490204d696e696d756d2062616c616e63652073686f756c64206265206e6f6e2d7a65726f2e284e6f50726f7669646572046501204e6f2070726f7669646572207265666572656e63652065786973747320746f20616c6c6f772061206e6f6e2d7a65726f2062616c616e6365206f662061206e6f6e2d73656c662d73756666696369656e742061737365742e2c4261644d65746164617461046020496e76616c6964206d6574616461746120676976656e2e28556e617070726f76656404c8204e6f20617070726f76616c20657869737473207468617420776f756c6420616c6c6f7720746865207472616e736665722e20576f756c644469650439012054686520736f75726365206163636f756e7420776f756c64206e6f74207375727669766520746865207472616e7366657220616e64206974206e6565647320746f207374617920616c6976652e220c4d6d72014c4d65726b6c654d6f756e7461696e52616e67650c20526f6f74486173680100583c5420617320436f6e6669673c493e3e3a3a486173688000000000000000000000000000000000000000000000000000000000000000000458204c6174657374204d4d5220526f6f7420686173682e384e756d6265724f664c656176657301000c75363420000000000000000004b02043757272656e742073697a65206f6620746865204d4d5220286e756d626572206f66206c6561766573292e144e6f6465730001060c753634583c5420617320436f6e6669673c493e3e3a3a48617368000400108020486173686573206f6620746865206e6f64657320696e20746865204d4d522e002d01204e6f7465207468697320636f6c6c656374696f6e206f6e6c7920636f6e7461696e73204d4d52207065616b732c2074686520696e6e6572206e6f6465732028616e64206c656176657329bc20617265207072756e656420616e64206f6e6c792073746f72656420696e20746865204f6666636861696e2044422e00000000231c4c6f7474657279011c4c6f747465727918304c6f7474657279496e64657801000c7533321000000000001c4c6f74746572790000ac4c6f7474657279436f6e6669673c543a3a426c6f636b4e756d6265722c2042616c616e63654f663c543e3e040004ac2054686520636f6e66696775726174696f6e20666f72207468652063757272656e74206c6f74746572792e305061727469636970616e747301010530543a3a4163636f756e74496454287533322c205665633c43616c6c496e6465783e29001400000000000419012055736572732077686f2068617665207075726368617365642061207469636b65742e20284c6f747465727920496e6465782c205469636b6574732050757263686173656429305469636b657473436f756e7401000c7533321000000000047820546f74616c206e756d626572206f66207469636b65747320736f6c642e1c5469636b6574730001050c75333230543a3a4163636f756e74496400040010542045616368207469636b65742773206f776e65722e006101204d6179206861766520726573696475616c2073746f726167652066726f6d2070726576696f7573206c6f747465726965732e2055736520605469636b657473436f756e746020746f20736565207768696368206f6e657390206172652061637475616c6c792076616c6964207469636b6574206d617070696e67732e2c43616c6c496e64696365730100385665633c43616c6c496e6465783e0400083901205468652063616c6c732073746f72656420696e20746869732070616c6c657420746f206265207573656420696e20616e20616374697665206c6f747465727920696620636f6e666967757265646c2062792060436f6e6669673a3a56616c696461746543616c6c602e0110286275795f7469636b6574041063616c6c60426f783c3c5420617320436f6e6669673e3a3a43616c6c3e2c8c204275792061207469636b657420746f20656e74657220746865206c6f74746572792e00050120546869732065787472696e7369632061637473206173206120706173737468726f7567682066756e6374696f6e20666f72206063616c6c602e20496e20616c6c0d0120736974756174696f6e73207768657265206063616c6c6020616c6f6e6520776f756c6420737563636565642c20746869732065787472696e7369632073686f756c642420737563636565642e001101204966206063616c6c60206973207375636365737366756c2c207468656e2077652077696c6c20617474656d707420746f2070757263686173652061207469636b65742c1501207768696368206d6179206661696c2073696c656e746c792e20546f206465746563742073756363657373206f662061207469636b65742070757263686173652c20796f75b02073686f756c64206c697374656e20666f722074686520605469636b6574426f7567687460206576656e742e00c820546869732065787472696e736963206d7573742062652063616c6c65642062792061207369676e6564206f726967696e2e247365745f63616c6c73041463616c6c73605665633c3c5420617320436f6e6669673e3a3a43616c6c3e181501205365742063616c6c7320696e2073746f726167652077686963682063616e206265207573656420746f2070757263686173652061206c6f7474657279207469636b65742e00210120546869732066756e6374696f6e206f6e6c79206d61747465727320696620796f752075736520746865206056616c696461746543616c6c6020696d706c656d656e746174696f6e29012070726f766964656420627920746869732070616c6c65742c20776869636820757365732073746f7261676520746f2064657465726d696e65207468652076616c69642063616c6c732e00d420546869732065787472696e736963206d7573742062652063616c6c656420627920746865204d616e61676572206f726967696e2e3473746172745f6c6f7474657279101470726963653042616c616e63654f663c543e186c656e67746838543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d6265721872657065617410626f6f6c28c82053746172742061206c6f7474657279207573696e67207468652070726f766964656420636f6e66696775726174696f6e2e00d820546869732065787472696e736963206d7573742062652063616c6c65642062792074686520604d616e616765724f726967696e602e003020506172616d65746572733a00a0202a20607072696365603a2054686520636f7374206f6620612073696e676c65207469636b65742e3d01202a20606c656e677468603a20486f77206c6f6e6720746865206c6f74746572792073686f756c642072756e20666f72207374617274696e67206174207468652063757272656e7420626c6f636b2e4901202a206064656c6179603a20486f77206c6f6e6720616674657220746865206c6f747465727920656e642077652073686f756c642077616974206265666f7265207069636b696e6720612077696e6e65722ee4202a2060726570656174603a20496620746865206c6f74746572792073686f756c6420726570656174207768656e20636f6d706c657465642e2c73746f705f726570656174001001012049662061206c6f747465727920697320726570656174696e672c20796f752063616e20757365207468697320746f2073746f7020746865207265706561742ec020546865206c6f74746572792077696c6c20636f6e74696e756520746f2072756e20746f20636f6d706c6574696f6e2e00d820546869732065787472696e736963206d7573742062652063616c6c65642062792074686520604d616e616765724f726967696e602e0110384c6f7474657279537461727465640004702041206c6f747465727920686173206265656e2073746172746564213043616c6c73557064617465640004882041206e657720736574206f662063616c6c732068617665206265656e20736574211857696e6e657208244163636f756e7449641c42616c616e6365046820412077696e6e657220686173206265656e2063686f73656e21305469636b6574426f7567687408244163636f756e7449642443616c6c496e64657804682041207469636b657420686173206265656e20626f7567687421082050616c6c657449642050616c6c657449642070792f6c6f74746f046020546865204c6f747465727927732070616c6c6574206964204d617843616c6c730c753332100a00000004dc20546865206d6178206e756d626572206f662063616c6c7320617661696c61626c6520696e20612073696e676c65206c6f74746572792e1c344e6f74436f6e66696775726564048c2041206c6f747465727920686173206e6f74206265656e20636f6e666967757265642e28496e50726f677265737304882041206c6f747465727920697320616c726561647920696e2070726f67726573732e30416c7265616479456e64656404742041206c6f74746572792068617320616c726561647920656e6465642e2c496e76616c696443616c6c04ac205468652063616c6c206973206e6f742076616c696420666f7220616e206f70656e206c6f74746572792e50416c726561647950617274696369706174696e6704f420596f752061726520616c72656164792070617274696369706174696e6720696e20746865206c6f7474657279207769746820746869732063616c6c2e30546f6f4d616e7943616c6c73049420546f6f206d616e792063616c6c7320666f7220612073696e676c65206c6f74746572792e38456e636f64696e674661696c6564045c204661696c656420746f20656e636f64652063616c6c73241047696c74011047696c74102c5175657565546f74616c730100605665633c287533322c2042616c616e63654f663c543e293e04001461012054686520746f74616c73206f66206974656d7320616e642062616c616e6365732077697468696e20656163682071756575652e2053617665732061206c6f74206f662073746f7261676520726561647320696e20746865802063617365206f66207370617273656c79207061636b6564207175657565732e006d012054686520766563746f7220697320696e6465786564206279206475726174696f6e20696e2060506572696f6460732c206f6666736574206279206f6e652c20736f20696e666f726d6174696f6e206f6e20746865207175657565d42077686f7365206475726174696f6e206973206f6e652060506572696f646020776f756c642062652073746f72616765206030602e185175657565730101020c753332a05665633c47696c744269643c42616c616e63654f663c543e2c20543a3a4163636f756e7449643e3e0004000439012054686520717565756573206f66206269647320726561647920746f206265636f6d652067696c74732e20496e6465786564206279206475726174696f6e2028696e2060506572696f646073292e2c416374697665546f74616c01007841637469766547696c7473546f74616c3c42616c616e63654f663c543e3e9000000000000000000000000000000000000000000000000000000000000000000000000004d020496e666f726d6174696f6e2072656c6174696e6720746f207468652067696c74732063757272656e746c79206163746976652e184163746976650001022c416374697665496e646578a50141637469766547696c743c42616c616e63654f663c543e2c3c54206173206672616d655f73797374656d3a3a436f6e6669673e3a3a4163636f756e7449642c3c0a54206173206672616d655f73797374656d3a3a436f6e6669673e3a3a426c6f636b4e756d6265723e000400042101205468652063757272656e746c79206163746976652067696c74732c20696e6465786564206163636f7264696e6720746f20746865206f72646572206f66206372656174696f6e2e011024706c6163655f6269640818616d6f756e7454436f6d706163743c42616c616e63654f663c543e3e206475726174696f6e0c753332349420506c61636520612062696420666f7220612067696c7420746f206265206973737565642e004101204f726967696e206d757374206265205369676e65642c20616e64206163636f756e74206d7573742068617665206174206c656173742060616d6f756e746020696e20667265652062616c616e63652e003d01202d2060616d6f756e74603a2054686520616d6f756e74206f6620746865206269643b2074686573652066756e64732077696c6c2062652072657365727665642e20496620746865206269642069734101207375636365737366756c6c7920656c65766174656420696e746f20616e206973737565642067696c742c207468656e2074686573652066756e64732077696c6c20636f6e74696e756520746f206265fc20726573657276656420756e74696c207468652067696c7420657870697265732e204d757374206265206174206c6561737420604d696e467265657a65602e5901202d20606475726174696f6e603a20546865206e756d626572206f6620706572696f647320666f72207768696368207468652066756e64732077696c6c206265206c6f636b6564206966207468652067696c742069735d01206973737565642e2049742077696c6c20657870697265206f6e6c79206166746572207468697320706572696f642068617320656c61707365642061667465722074686520706f696e74206f662069737375616e63652ed8204d7573742062652067726561746572207468616e203120616e64206e6f206d6f7265207468616e20605175657565436f756e74602e003820436f6d706c657869746965733ab0202d20605175657565735b6475726174696f6e5d2e6c656e28296020286a7573742074616b65206d6178292e2c726574726163745f6269640818616d6f756e7454436f6d706163743c42616c616e63654f663c543e3e206475726174696f6e0c7533321c84205265747261637420612070726576696f75736c7920706c61636564206269642e006101204f726967696e206d757374206265205369676e65642c20616e6420746865206163636f756e742073686f756c6420686176652070726576696f75736c79206973737565642061207374696c6c2d6163746976652062696470206f662060616d6f756e746020666f7220606475726174696f6e602e00b0202d2060616d6f756e74603a2054686520616d6f756e74206f66207468652070726576696f7573206269642ec0202d20606475726174696f6e603a20546865206475726174696f6e206f66207468652070726576696f7573206269642e287365745f746172676574041874617267657450436f6d706163743c5065727175696e74696c6c3e189420536574207461726765742070726f706f7274696f6e206f662067696c742d66756e64732e0078204f726967696e206d757374206265206041646d696e4f726967696e602e005d01202d2060746172676574603a20546865207461726765742070726f706f7274696f6e206f6620656666656374697665206973737565642066756e647320746861742073686f756c6420626520756e6465722067696c74734420617420616e79206f6e652074696d652e10746861770414696e64657850436f6d706163743c416374697665496e6465783e1c59012052656d6f766520616e206163746976652062757420657870697265642067696c742e2052657365727665642066756e647320756e6465722067696c742061726520667265656420616e642062616c616e63652069735d012061646a757374656420746f20656e737572652074686174207468652066756e64732067726f77206f7220736872696e6b20746f206d61696e7461696e20746865206571756976616c656e742070726f706f7274696f6e84206f662065666665637469766520746f74616c206973737565642066756e64732e006101204f726967696e206d757374206265205369676e656420616e6420746865206163636f756e74206d75737420626520746865206f776e6572206f66207468652067696c74206f662074686520676976656e20696e6465782e00bc202d2060696e646578603a2054686520696e646578206f66207468652067696c7420746f206265207468617765642e011024426964506c616365640c244163636f756e7449643042616c616e63654f663c543e0c753332087c20412062696420776173207375636365737366756c6c7920706c616365642e70205c5b2077686f2c20616d6f756e742c206475726174696f6e205c5d304269645265747261637465640c244163636f756e7449643042616c616e63654f663c543e0c75333208090120412062696420776173207375636365737366756c6c792072656d6f76656420286265666f7265206265696e6720616363657074656420617320612067696c74292e70205c5b2077686f2c20616d6f756e742c206475726174696f6e205c5d2847696c74497373756564102c416374697665496e64657838543a3a426c6f636b4e756d626572244163636f756e7449643042616c616e63654f663c543e0831012041206269642077617320616363657074656420617320612067696c742e205468652062616c616e6365206d6179206e6f742062652072656c656173656420756e74696c206578706972792e84205c5b20696e6465782c206578706972792c2077686f2c20616d6f756e74205c5d2847696c74546861776564102c416374697665496e646578244163636f756e7449643042616c616e63654f663c543e3042616c616e63654f663c543e088420416e20657870697265642067696c7420686173206265656e207468617765642ed4205c5b20696e6465782c2077686f2c206f726967696e616c5f616d6f756e742c206164646974696f6e616c5f616d6f756e74205c5d1c285175657565436f756e740c753332102c010000085d01204e756d626572206f66206475726174696f6e2071756575657320696e20746f74616c2e2054686973207365747320746865206d6178696d756d206475726174696f6e20737570706f727465642c2077686963682069738c20746869732076616c7565206d756c7469706c6965642062792060506572696f64602e2c4d617851756575654c656e0c75333210e803000004f0204d6178696d756d206e756d626572206f66206974656d732074686174206d617920626520696e2065616368206475726174696f6e2071756575652e304669666f51756575654c656e0c75333210f40100000c090120506f7274696f6e206f662074686520717565756520776869636820697320667265652066726f6d206f72646572696e6720616e64206a7573742061204649464f2e009c204d757374206265206e6f2067726561746572207468616e20604d617851756575654c656e602e18506572696f6438543a3a426c6f636b4e756d62657210002f0d0008410120546865206261736520706572696f6420666f7220746865206475726174696f6e207175657565732e20546869732069732074686520636f6d6d6f6e206d756c7469706c65206163726f737320616c6ccc20737570706f7274656420667265657a696e67206475726174696f6e7320746861742063616e206265206269642075706f6e2e244d696e467265657a653042616c616e63654f663c543e400000c16ff2862300000000000000000018550120546865206d696e696d756d20616d6f756e74206f662066756e64732074686174206d6179206265206f66666572656420746f20667265657a6520666f7220612067696c742e204e6f746520746861742074686973510120646f6573206e6f742061637475616c6c79206c696d69742074686520616d6f756e74207768696368206d61792062652066726f7a656e20696e20612067696c742073696e63652067696c7473206d617920626519012073706c697420757020696e206f7264657220746f207361746973667920746865206465736972656420616d6f756e74206f662066756e647320756e6465722067696c74732e0065012049742073686f756c64206265206174206c656173742062696720656e6f75676820746f20656e737572652074686174207468657265206973206e6f20706f737369626c652073746f72616765207370616d2061747461636b64206f722071756575652d66696c6c696e672061747461636b2e30496e74616b65506572696f6438543a3a426c6f636b4e756d626572100a00000014590120546865206e756d626572206f6620626c6f636b73206265747765656e20636f6e736563757469766520617474656d70747320746f206973737565206d6f72652067696c747320696e20616e206566666f727420746f9c2067657420746f207468652074617267657420616d6f756e7420746f2062652066726f7a656e2e005d012041206c61726765722076616c756520726573756c747320696e2066657765722073746f726167652068697473206561636820626c6f636b2c20627574206120736c6f77657220706572696f6420746f2067657420746f3020746865207461726765742e344d6178496e74616b65426964730c753332100a0000000c550120546865206d6178696d756d20616d6f756e74206f66206269647320746861742063616e206265207475726e656420696e746f206973737565642067696c7473206561636820626c6f636b2e2041206c617267657261012076616c75652068657265206d65616e73206c657373206f662074686520626c6f636b20617661696c61626c6520666f72207472616e73616374696f6e732073686f756c64207468657265206265206120676c7574206f66b4206269647320746f206d616b6520696e746f2067696c747320746f20726561636820746865207461726765742e20404475726174696f6e546f6f536d616c6c04a820546865206475726174696f6e206f662074686520626964206973206c657373207468616e206f6e652e384475726174696f6e546f6f42696704f820546865206475726174696f6e20697320746865206269642069732067726561746572207468616e20746865206e756d626572206f66207175657565732e38416d6f756e74546f6f536d616c6c04e02054686520616d6f756e74206f662074686520626964206973206c657373207468616e20746865206d696e696d756d20616c6c6f7765642e24426964546f6f4c6f770865012054686520717565756520666f7220746865206269642773206475726174696f6e2069732066756c6c20616e642074686520616d6f756e742062696420697320746f6f206c6f7720746f2067657420696e207468726f7567686c207265706c6163696e6720616e206578697374696e67206269642e1c556e6b6e6f776e045c2047696c7420696e64657820697320756e6b6e6f776e2e204e6f744f776e6572046c204e6f7420746865206f776e6572206f66207468652067696c742e284e6f744578706972656404742047696c74206e6f74207965742061742065787069727920646174652e204e6f74466f756e6404ac2054686520676976656e2062696420666f722072657472616374696f6e206973206e6f7420666f756e642e251c556e6971756573011c556e69717565731814436c61737300010228543a3a436c6173734964c8436c61737344657461696c733c543a3a4163636f756e7449642c204465706f73697442616c616e63654f663c542c20493e3e000400046c2044657461696c73206f6620616e20617373657420636c6173732e1c4163636f756e7400030c30543a3a4163636f756e74496428543a3a436c617373496434543a3a496e7374616e636549640c020202082829040008610120546865206173736574732068656c6420627920616e7920676976656e206163636f756e743b20736574206f757420746869732077617920736f207468617420617373657473206f776e656420627920612073696e676c656c206163636f756e742063616e20626520656e756d6572617465642e14417373657400020228543a3a436c617373496434543a3a496e7374616e63654964d4496e7374616e636544657461696c733c543a3a4163636f756e7449642c204465706f73697442616c616e63654f663c542c20493e3e02040004d4205468652061737365747320696e206578697374656e636520616e64207468656972206f776e6572736869702064657461696c732e3c436c6173734d657461646174614f6600010228543a3a436c6173734964d4436c6173734d657461646174613c4465706f73697442616c616e63654f663c542c20493e2c20543a3a537472696e674c696d69743e0004000470204d65746164617461206f6620616e20617373657420636c6173732e48496e7374616e63654d657461646174614f6600020228543a3a436c617373496434543a3a496e7374616e63654964e0496e7374616e63654d657461646174613c4465706f73697442616c616e63654f663c542c20493e2c20543a3a537472696e674c696d69743e020400047c204d65746164617461206f6620616e20617373657420696e7374616e63652e2441747472696275746500030c28543a3a436c6173734964544f7074696f6e3c543a3a496e7374616e636549643e6c426f756e6465645665633c75382c20543a3a4b65794c696d69743e0c020202dc28426f756e6465645665633c75382c20543a3a56616c75654c696d69743e2c204465706f73697442616c616e63654f663c542c20493e2904000470204d65746164617461206f6620616e20617373657420636c6173732e0158186372656174650814636c6173734c436f6d706163743c543a3a436c61737349643e1461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636540fc2049737375652061206e657720636c617373206f66206e6f6e2d66756e6769626c65206173736574732066726f6d2061207075626c6963206f726967696e2e0029012054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c7920616e6420697473206f776e657220697320746865206f726967696e2e00290120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d75737420686176652073756666696369656e742066756e647320667265652e00b4206041737365744465706f736974602066756e6473206f662073656e646572206172652072657365727665642e003020506172616d65746572733a5501202d2060636c617373603a20546865206964656e746966696572206f6620746865206e657720617373657420636c6173732e2054686973206d757374206e6f742062652063757272656e746c7920696e207573652e5d01202d206061646d696e603a205468652061646d696e206f66207468697320636c617373206f66206173736574732e205468652061646d696e2069732074686520696e697469616c2061646472657373206f662065616368a0206d656d626572206f662074686520617373657420636c61737327732061646d696e207465616d2e009c20456d69747320604372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f2831296030666f7263655f6372656174650c14636c6173734c436f6d706163743c543a3a436c61737349643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636530667265655f686f6c64696e6710626f6f6c400d012049737375652061206e657720636c617373206f66206e6f6e2d66756e6769626c65206173736574732066726f6d20612070726976696c65676564206f726967696e2e00b82054686973206e657720617373657420636c61737320686173206e6f2061737365747320696e697469616c6c792e00a820546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e602e00a020556e6c696b652060637265617465602c206e6f2066756e6473206172652072657365727665642e003d01202d2060636c617373603a20546865206964656e746966696572206f6620746865206e65772061737365742e2054686973206d757374206e6f742062652063757272656e746c7920696e207573652e5d01202d20606f776e6572603a20546865206f776e6572206f66207468697320636c617373206f66206173736574732e20546865206f776e6572206861732066756c6c20737570657275736572207065726d697373696f6e732901206f76657220746869732061737365742c20627574206d6179206c61746572206368616e676520616e6420636f6e66696775726520746865207065726d697373696f6e73207573696e679420607472616e736665725f6f776e6572736869706020616e6420607365745f7465616d602e00b020456d6974732060466f7263654372656174656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f283129601c64657374726f790814636c6173734c436f6d706163743c543a3a436c61737349643e1c7769746e6573733844657374726f795769746e6573733c902044657374726f79206120636c617373206f662066756e6769626c65206173736574732e00610120546865206f726967696e206d75737420636f6e666f726d20746f2060466f7263654f726967696e60206f72206d75737420626520605369676e65646020616e64207468652073656e646572206d7573742062652074686570206f776e6572206f66207468652061737365742060636c617373602e00f8202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c61737320746f2062652064657374726f7965642e4901202d20607769746e657373603a20496e666f726d6174696f6e206f6e2074686520696e7374616e636573206d696e74656420696e2074686520617373657420636c6173732e2054686973206d7573742062652420636f72726563742e00a420456d697473206044657374726f79656460206576656e74207768656e207375636365737366756c2e0068205765696768743a20604f286e202b206d29602077686572653a68202d20606e203d207769746e6573732e696e7374616e636573608c202d20606d203d207769746e6573732e696e7374616e63655f6d6574616461746173606c202d206061203d207769746e6573732e6174747269627574657360106d696e740c14636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652cb8204d696e7420616e20617373657420696e7374616e6365206f66206120706172746963756c617220636c6173732e00490120546865206f726967696e206d757374206265205369676e656420616e64207468652073656e646572206d7573742062652074686520497373756572206f66207468652061737365742060636c617373602e00c0202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f206265206d696e7465642ef0202d2060696e7374616e6365603a2054686520696e7374616e63652076616c7565206f662074686520617373657420746f206265206d696e7465642ee0202d206062656e6566696369617279603a2054686520696e697469616c206f776e6572206f6620746865206d696e7465642061737365742e009820456d697473206049737375656460206576656e74207768656e207375636365737366756c2e003c205765696768743a20604f28312960106275726e0c14636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e2c636865636b5f6f776e6572ac4f7074696f6e3c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e34842044657374726f7920612073696e676c6520617373657420696e7374616e63652e003d01204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f66207468652061737365742060636c617373602e00c0202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f206265206275726e65642ed8202d2060696e7374616e6365603a2054686520696e7374616e6365206f662074686520617373657420746f206265206275726e65642e5501202d2060636865636b5f6f776e6572603a2049662060536f6d6560207468656e20746865206f7065726174696f6e2077696c6c206661696c2077697468206057726f6e674f776e65726020756e6c65737320746865802020206173736574206973206f776e656420627920746869732076616c75652e00b820456d69747320604275726e6564602077697468207468652061637475616c20616d6f756e74206275726e65642e003c205765696768743a20604f2831296080204d6f6465733a2060636865636b5f6f776e65722e69735f736f6d652829602e207472616e736665720c14636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e10646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653cc8204d6f766520616e2061737365742066726f6d207468652073656e646572206163636f756e7420746f20616e6f746865722e00f8204f726967696e206d757374206265205369676e656420616e6420746865207369676e696e67206163636f756e74206d757374206265206569746865723a88202d207468652041646d696e206f66207468652061737365742060636c617373603b94202d20746865204f776e6572206f66207468652061737365742060696e7374616e6365603b6101202d2074686520617070726f7665642064656c656761746520666f72207468652061737365742060696e7374616e6365602028696e207468697320636173652c2074686520617070726f76616c206973207265736574292e002c20417267756d656e74733ad4202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f206265207472616e736665727265642eec202d2060696e7374616e6365603a2054686520696e7374616e6365206f662074686520617373657420746f206265207472616e736665727265642ee4202d206064657374603a20546865206163636f756e7420746f2072656365697665206f776e657273686970206f66207468652061737365742e005420456d69747320605472616e73666572726564602e003c205765696768743a20604f283129602472656465706f7369740814636c6173734c436f6d706163743c543a3a436c61737349643e24696e7374616e636573485665633c543a3a496e7374616e636549643e44a02052656576616c7561746520746865206465706f73697473206f6e20736f6d65206173736574732e003d01204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468652061737365742060636c617373602e00c0202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f2062652066726f7a656e2e5101202d2060696e7374616e636573603a2054686520696e7374616e636573206f662074686520617373657420636c6173732077686f7365206465706f736974732077696c6c2062652072656576616c75617465642e005901204e4f54453a205468697320657869737473206173206120626573742d6566666f72742066756e6374696f6e2e20416e7920617373657420696e7374616e6365732077686963682061726520756e6b6e6f776e206f723d0120696e207468652063617365207468617420746865206f776e6572206163636f756e7420646f6573206e6f7420686176652072657365727661626c652066756e647320746f2070617920666f7220616101206465706f73697420696e637265617365206172652069676e6f7265642e2047656e6572616c6c7920746865206f776e65722069736e277420676f696e6720746f2063616c6c2074686973206f6e20696e7374616e63657359012077686f7365206578697374696e67206465706f736974206973206c657373207468616e2074686520726566726573686564206465706f73697420617320697420776f756c64206f6e6c7920636f7374207468656d2c7c20736f2069742773206f66206c6974746c6520636f6e73657175656e63652e0055012049742077696c6c207374696c6c2072657475726e20616e206572726f7220696e20746865206361736520746861742074686520636c61737320697320756e6b6e6f776e206f6620746865207369676e657220697368206e6f74207065726d697474656420746f2063616c6c2069742e0074205765696768743a20604f28696e7374616e6365732e6c656e2829296018667265657a650814636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e28f420446973616c6c6f77206675727468657220756e70726976696c65676564207472616e73666572206f6620616e20617373657420696e7374616e63652e004501204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f66207468652061737365742060636c617373602e00c0202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f2062652066726f7a656e2ed8202d2060696e7374616e6365603a2054686520696e7374616e6365206f662074686520617373657420746f2062652066726f7a656e2e004020456d697473206046726f7a656e602e003c205765696768743a20604f2831296010746861770814636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e28d42052652d616c6c6f7720756e70726976696c65676564207472616e73666572206f6620616e20617373657420696e7374616e63652e004501204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f66207468652061737365742060636c617373602e00c0202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f206265207468617765642ed8202d2060696e7374616e6365603a2054686520696e7374616e6365206f662074686520617373657420746f206265207468617765642e004020456d6974732060546861776564602e003c205765696768743a20604f2831296030667265657a655f636c6173730414636c6173734c436f6d706163743c543a3a436c61737349643e24050120446973616c6c6f77206675727468657220756e70726976696c65676564207472616e736665727320666f7220612077686f6c6520617373657420636c6173732e004501204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c642062652074686520467265657a6572206f66207468652061737365742060636c617373602e00a4202d2060636c617373603a2054686520617373657420636c61737320746f2062652066726f7a656e2e005420456d6974732060436c61737346726f7a656e602e003c205765696768743a20604f2831296028746861775f636c6173730414636c6173734c436f6d706163743c543a3a436c61737349643e24e42052652d616c6c6f7720756e70726976696c65676564207472616e736665727320666f7220612077686f6c6520617373657420636c6173732e003d01204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c64206265207468652041646d696e206f66207468652061737365742060636c617373602e008c202d2060636c617373603a2054686520636c61737320746f206265207468617765642e005420456d6974732060436c617373546861776564602e003c205765696768743a20604f28312960487472616e736665725f6f776e6572736869700814636c6173734c436f6d706163743c543a3a436c61737349643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652890204368616e676520746865204f776e6572206f6620616e20617373657420636c6173732e003d01204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468652061737365742060636c617373602e00e8202d2060636c617373603a2054686520617373657420636c6173732077686f7365206f776e65722073686f756c64206265206368616e6765642eb8202d20606f776e6572603a20546865206e6577204f776e6572206f66207468697320617373657420636c6173732e005820456d69747320604f776e65724368616e676564602e003c205765696768743a20604f28312960207365745f7465616d1014636c6173734c436f6d706163743c543a3a436c61737349643e186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636530e0204368616e676520746865204973737565722c2041646d696e20616e6420467265657a6572206f6620616e20617373657420636c6173732e003d01204f726967696e206d757374206265205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468652061737365742060636c617373602e00e4202d2060636c617373603a2054686520617373657420636c6173732077686f7365207465616d2073686f756c64206265206368616e6765642ec0202d2060697373756572603a20546865206e657720497373756572206f66207468697320617373657420636c6173732eb8202d206061646d696e603a20546865206e65772041646d696e206f66207468697320617373657420636c6173732ec8202d2060667265657a6572603a20546865206e657720467265657a6572206f66207468697320617373657420636c6173732e005420456d69747320605465616d4368616e676564602e003c205765696768743a20604f2831296040617070726f76655f7472616e736665720c14636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e2064656c65676174658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c290120417070726f766520616e20696e7374616e636520746f206265207472616e7366657272656420627920612064656c6567617465642074686972642d7061727479206163636f756e742e001501204f726967696e206d757374206265205369676e656420616e64206d75737420626520746865206f776e6572206f66207468652061737365742060696e7374616e6365602e002501202d2060636c617373603a2054686520636c617373206f662074686520617373657420746f20626520617070726f76656420666f722064656c656761746564207472616e736665722e3d01202d2060696e7374616e6365603a2054686520696e7374616e6365206f662074686520617373657420746f20626520617070726f76656420666f722064656c656761746564207472616e736665722e2101202d206064656c6567617465603a20546865206163636f756e7420746f2064656c6567617465207065726d697373696f6e20746f207472616e73666572207468652061737365742e009420456d6974732060417070726f7665645472616e7366657260206f6e20737563636573732e003c205765696768743a20604f283129603c63616e63656c5f617070726f76616c0c14636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e506d617962655f636865636b5f64656c6567617465ac4f7074696f6e3c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e4019012043616e63656c20746865207072696f7220617070726f76616c20666f7220746865207472616e73666572206f6620616e20617373657420627920612064656c65676174652e005c204f726967696e206d757374206265206569746865723a58202d207468652060466f72636560206f726967696e3b0501202d20605369676e656460207769746820746865207369676e6572206265696e67207468652041646d696e206f66207468652061737365742060636c617373603b1101202d20605369676e656460207769746820746865207369676e6572206265696e6720746865204f776e6572206f66207468652061737365742060696e7374616e6365603b002c20417267756d656e74733a1d01202d2060636c617373603a2054686520636c617373206f6620746865206173736574206f662077686f736520617070726f76616c2077696c6c2062652063616e63656c6c65642e3501202d2060696e7374616e6365603a2054686520696e7374616e6365206f6620746865206173736574206f662077686f736520617070726f76616c2077696c6c2062652063616e63656c6c65642e5501202d20606d617962655f636865636b5f64656c6567617465603a2049662060536f6d65602077696c6c20656e7375726520746861742074686520676976656e206163636f756e7420697320746865206f6e6520746fb42020207768696368207065726d697373696f6e206f66207472616e736665722069732064656c6567617465642e009820456d6974732060417070726f76616c43616e63656c6c656460206f6e20737563636573732e003c205765696768743a20604f2831296048666f7263655f61737365745f7374617475731c14636c6173734c436f6d706163743c543a3a436c61737349643e146f776e65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365186973737565728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651461646d696e8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651c667265657a65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636530667265655f686f6c64696e6710626f6f6c2469735f66726f7a656e10626f6f6c449c20416c746572207468652061747472696275746573206f66206120676976656e2061737365742e0078204f726967696e206d7573742062652060466f7263654f726967696e602e00a0202d2060636c617373603a20546865206964656e746966696572206f66207468652061737365742ea0202d20606f776e6572603a20546865206e6577204f776e6572206f6620746869732061737365742ea8202d2060697373756572603a20546865206e657720497373756572206f6620746869732061737365742ea0202d206061646d696e603a20546865206e65772041646d696e206f6620746869732061737365742eb0202d2060667265657a6572603a20546865206e657720467265657a6572206f6620746869732061737365742e4d01202d2060667265655f686f6c64696e67603a20576865746865722061206465706f7369742069732074616b656e20666f7220686f6c64696e6720616e20696e7374616e6365206f66207468697320617373657424202020636c6173732e4101202d206069735f66726f7a656e603a2057686574686572207468697320617373657420636c6173732069732066726f7a656e2065786365707420666f72207065726d697373696f6e65642f61646d696e3820696e737472756374696f6e732e00ec20456d697473206041737365745374617475734368616e67656460207769746820746865206964656e74697479206f66207468652061737365742e003c205765696768743a20604f28312960347365745f6174747269627574651014636c6173734c436f6d706163743c543a3a436c61737349643e386d617962655f696e7374616e6365544f7074696f6e3c543a3a496e7374616e636549643e0c6b65796c426f756e6465645665633c75382c20543a3a4b65794c696d69743e1476616c756574426f756e6465645665633c75382c20543a3a56616c75654c696d69743e44c42053657420616e2061747472696275746520666f7220616e20617373657420636c617373206f7220696e7374616e63652e006101204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f72205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468653c2061737365742060636c617373602e00550120496620746865206f726967696e206973205369676e65642c207468656e2066756e6473206f66207369676e657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613a2d0120604d657461646174614465706f73697442617365202b204465706f73697450657242797465202a20286b65792e6c656e202b2076616c75652e6c656e29602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e003d01202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c6173732077686f736520696e7374616e63652773206d6574616461746120746f207365742e4101202d20606d617962655f696e7374616e6365603a20546865206964656e746966696572206f662074686520617373657420696e7374616e63652077686f7365206d6574616461746120746f207365742e8c202d20606b6579603a20546865206b6579206f6620746865206174747269627574652ed0202d206076616c7565603a205468652076616c756520746f20776869636820746f2073657420746865206174747269627574652e005820456d6974732060417474726962757465536574602e003c205765696768743a20604f283129603c636c6561725f6174747269627574650c14636c6173734c436f6d706163743c543a3a436c61737349643e386d617962655f696e7374616e6365544f7074696f6e3c543a3a496e7374616e636549643e0c6b65796c426f756e6465645665633c75382c20543a3a4b65794c696d69743e44c42053657420616e2061747472696275746520666f7220616e20617373657420636c617373206f7220696e7374616e63652e006101204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f72205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468653c2061737365742060636c617373602e00550120496620746865206f726967696e206973205369676e65642c207468656e2066756e6473206f66207369676e657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613a2d0120604d657461646174614465706f73697442617365202b204465706f73697450657242797465202a20286b65792e6c656e202b2076616c75652e6c656e29602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e003d01202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c6173732077686f736520696e7374616e63652773206d6574616461746120746f207365742e2901202d2060696e7374616e6365603a20546865206964656e746966696572206f662074686520617373657420696e7374616e63652077686f7365206d6574616461746120746f207365742e8c202d20606b6579603a20546865206b6579206f6620746865206174747269627574652ed0202d206076616c7565603a205468652076616c756520746f20776869636820746f2073657420746865206174747269627574652e005820456d6974732060417474726962757465536574602e003c205765696768743a20604f28312960307365745f6d657461646174611014636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e106461746178426f756e6465645665633c75382c20543a3a537472696e674c696d69743e2469735f66726f7a656e10626f6f6c44a02053657420746865206d6574616461746120666f7220616e20617373657420696e7374616e63652e006101204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f72205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f66207468653c2061737365742060636c617373602e00550120496620746865206f726967696e206973205369676e65642c207468656e2066756e6473206f66207369676e657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613af820604d657461646174614465706f73697442617365202b204465706f73697450657242797465202a20646174612e6c656e602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e003d01202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c6173732077686f736520696e7374616e63652773206d6574616461746120746f207365742e2901202d2060696e7374616e6365603a20546865206964656e746966696572206f662074686520617373657420696e7374616e63652077686f7365206d6574616461746120746f207365742e5501202d206064617461603a205468652067656e6572616c20696e666f726d6174696f6e206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3901202d206069735f66726f7a656e603a205768657468657220746865206d657461646174612073686f756c642062652066726f7a656e20616761696e73742066757274686572206368616e6765732e005420456d69747320604d65746164617461536574602e003c205765696768743a20604f2831296038636c6561725f6d657461646174610814636c6173734c436f6d706163743c543a3a436c61737349643e20696e7374616e636558436f6d706163743c543a3a496e7374616e636549643e34a820436c65617220746865206d6574616461746120666f7220616e20617373657420696e7374616e63652e006101204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f72205369676e656420616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f6620746865482061737365742060696e7374616e6365602e00c020416e79206465706f73697420697320667265656420666f722074686520617373657420636c617373206f776e65722e004501202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c6173732077686f736520696e7374616e63652773206d6574616461746120746f20636c6561722e3101202d2060696e7374616e6365603a20546865206964656e746966696572206f662074686520617373657420696e7374616e63652077686f7365206d6574616461746120746f20636c6561722e006420456d69747320604d65746164617461436c6561726564602e003c205765696768743a20604f28312960487365745f636c6173735f6d657461646174610c14636c6173734c436f6d706163743c543a3a436c61737349643e106461746178426f756e6465645665633c75382c20543a3a537472696e674c696d69743e2469735f66726f7a656e10626f6f6c40942053657420746865206d6574616461746120666f7220616e20617373657420636c6173732e005901204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f7220605369676e65646020616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f664c207468652061737365742060636c617373602e005d0120496620746865206f726967696e20697320605369676e6564602c207468656e2066756e6473206f66207369676e657220617265207265736572766564206163636f7264696e6720746f2074686520666f726d756c613af820604d657461646174614465706f73697442617365202b204465706f73697450657242797465202a20646174612e6c656e602074616b696e6720696e746f90206163636f756e7420616e7920616c72656164792072657365727665642066756e64732e000501202d2060636c617373603a20546865206964656e746966696572206f66207468652061737365742077686f7365206d6574616461746120746f207570646174652e5501202d206064617461603a205468652067656e6572616c20696e666f726d6174696f6e206f6620746869732061737365742e204c696d6974656420696e206c656e6774682062792060537472696e674c696d6974602e3901202d206069735f66726f7a656e603a205768657468657220746865206d657461646174612073686f756c642062652066726f7a656e20616761696e73742066757274686572206368616e6765732e006820456d6974732060436c6173734d65746164617461536574602e003c205765696768743a20604f2831296050636c6561725f636c6173735f6d657461646174610414636c6173734c436f6d706163743c543a3a436c61737349643e309c20436c65617220746865206d6574616461746120666f7220616e20617373657420636c6173732e005901204f726967696e206d757374206265206569746865722060466f7263654f726967696e60206f7220605369676e65646020616e64207468652073656e6465722073686f756c6420626520746865204f776e6572206f664c207468652061737365742060636c617373602e00c020416e79206465706f73697420697320667265656420666f722074686520617373657420636c617373206f776e65722e001901202d2060636c617373603a20546865206964656e746966696572206f662074686520617373657420636c6173732077686f7365206d6574616461746120746f20636c6561722e007820456d6974732060436c6173734d65746164617461436c6561726564602e003c205765696768743a20604f2831296001581c437265617465640c1c436c6173734964244163636f756e744964244163636f756e74496404e020416e20617373657420636c6173732077617320637265617465642e205c5b20636c6173732c2063726561746f722c206f776e6572205c5d30466f72636543726561746564081c436c6173734964244163636f756e74496404d420416e20617373657420636c6173732077617320666f7263652d637265617465642e205c5b20636c6173732c206f776e6572205c5d2444657374726f796564041c436c617373496404b020416e2061737365742060636c61737360207761732064657374726f7965642e205c5b20636c617373205c5d184973737565640c1c436c617373496428496e7374616e63654964244163636f756e74496404f020416e2061737365742060696e73746163656020776173206973737565642e205c5b20636c6173732c20696e7374616e63652c206f776e6572205c5d2c5472616e73666572726564101c436c617373496428496e7374616e63654964244163636f756e744964244163636f756e74496404110120416e2061737365742060696e73746163656020776173207472616e736665727265642e205c5b20636c6173732c20696e7374616e63652c2066726f6d2c20746f205c5d184275726e65640c1c436c617373496428496e7374616e63654964244163636f756e74496404010120416e2061737365742060696e7374616e636560207761732064657374726f7965642e205c5b20636c6173732c20696e7374616e63652c206f776e6572205c5d1846726f7a656e081c436c617373496428496e7374616e6365496404e020536f6d652061737365742060696e7374616e636560207761732066726f7a656e2e205c5b20636c6173732c20696e7374616e6365205c5d18546861776564081c436c617373496428496e7374616e6365496404e020536f6d652061737365742060696e7374616e63656020776173207468617765642e205c5b20636c6173732c20696e7374616e6365205c5d2c436c61737346726f7a656e041c436c617373496404ac20536f6d652061737365742060636c61737360207761732066726f7a656e2e205c5b20636c617373205c5d2c436c617373546861776564041c436c617373496404ac20536f6d652061737365742060636c6173736020776173207468617765642e205c5b20636c617373205c5d304f776e65724368616e676564081c436c6173734964244163636f756e74496404a420546865206f776e6572206368616e676564205c5b20636c6173732c206e65775f6f776e6572205c5d2c5465616d4368616e676564101c436c6173734964244163636f756e744964244163636f756e744964244163636f756e74496404010120546865206d616e6167656d656e74207465616d206368616e676564205c5b20636c6173732c206973737565722c2061646d696e2c20667265657a6572205c5d40417070726f7665645472616e73666572101c436c617373496428496e7374616e63654964244163636f756e744964244163636f756e7449640c550120416e2060696e7374616e636560206f6620616e2061737365742060636c6173736020686173206265656e20617070726f7665642062792074686520606f776e65726020666f72207472616e73666572206279206130206064656c6567617465602e9c205c5b20636c6173732c20696e7374616e63652c206f776e65722c2064656c6567617465205c5d44417070726f76616c43616e63656c6c6564101c436c617373496428496e7374616e63654964244163636f756e744964244163636f756e7449640c610120416e20617070726f76616c20666f722061206064656c656761746560206163636f756e7420746f207472616e73666572207468652060696e7374616e636560206f6620616e2061737365742060636c6173736020776173682063616e63656c6c65642062792069747320606f776e6572602e9c205c5b20636c6173732c20696e7374616e63652c206f776e65722c2064656c6567617465205c5d4841737365745374617475734368616e676564041c436c6173734964081d0120416e2061737365742060636c617373602068617320686164206974732061747472696275746573206368616e676564206279207468652060466f72636560206f726967696e2e30205c5b20636c617373205c5d40436c6173734d657461646174615365740c1c436c617373496478426f756e6465645665633c75382c20543a3a537472696e674c696d69743e10626f6f6c042d01204e6577206d6574616461746120686173206265656e2073657420666f7220616e20617373657420636c6173732e205c5b20636c6173732c20646174612c2069735f66726f7a656e205c5d50436c6173734d65746164617461436c6561726564041c436c617373496404e8204d6574616461746120686173206265656e20636c656172656420666f7220616e20617373657420636c6173732e205c5b20636c617373205c5d2c4d65746164617461536574101c436c617373496428496e7374616e6365496478426f756e6465645665633c75382c20543a3a537472696e674c696d69743e10626f6f6c08c4204e6577206d6574616461746120686173206265656e2073657420666f7220616e20617373657420696e7374616e63652e9c205c5b20636c6173732c20696e7374616e63652c20646174612c2069735f66726f7a656e205c5d3c4d65746164617461436c6561726564081c436c617373496428496e7374616e63654964041d01204d6574616461746120686173206265656e20636c656172656420666f7220616e20617373657420696e7374616e63652e205c5b20636c6173732c20696e7374616e6365205c5d2c52656465706f7369746564081c436c6173734964485665633c543a3a496e7374616e636549643e044d01204d6574616461746120686173206265656e20636c656172656420666f7220616e20617373657420696e7374616e63652e205c5b20636c6173732c207375636365737366756c5f696e7374616e636573205c5d30417474726962757465536574101c436c6173734964544f7074696f6e3c543a3a496e7374616e636549643e6c426f756e6465645665633c75382c20543a3a4b65794c696d69743e74426f756e6465645665633c75382c20543a3a56616c75654c696d69743e081101204e657720617474726962757465206d6574616461746120686173206265656e2073657420666f7220616e20617373657420636c617373206f7220696e7374616e63652ea0205c5b20636c6173732c206d617962655f696e7374616e63652c206b65792c2076616c7565205c5d40417474726962757465436c65617265640c1c436c6173734964544f7074696f6e3c543a3a496e7374616e636549643e6c426f756e6465645665633c75382c20543a3a4b65794c696d69743e08110120417474726962757465206d6574616461746120686173206265656e20636c656172656420666f7220616e20617373657420636c617373206f7220696e7374616e63652eb8205c5b20636c6173732c206d617962655f696e7374616e63652c206b65792c206d617962655f76616c7565205c5d0028304e6f5065726d697373696f6e04ec20546865207369676e696e67206163636f756e7420686173206e6f207065726d697373696f6e20746f20646f20746865206f7065726174696f6e2e1c556e6b6e6f776e047c2054686520676976656e20617373657420494420697320756e6b6e6f776e2e34416c726561647945786973747304e82054686520617373657420696e7374616e63652049442068617320616c7265616479206265656e207573656420666f7220616e2061737365742e2857726f6e674f776e657204ec20546865206f776e6572207475726e6564206f757420746f20626520646966666572656e7420746f2077686174207761732065787065637465642e284261645769746e657373047020496e76616c6964207769746e657373206461746120676976656e2e14496e557365047c2054686520617373657420494420697320616c72656164792074616b656e2e1846726f7a656e049c2054686520617373657420696e7374616e6365206f7220636c6173732069732066726f7a656e2e3457726f6e6744656c656761746504f8205468652064656c6567617465207475726e6564206f757420746f20626520646966666572656e7420746f2077686174207761732065787065637465642e284e6f44656c6567617465047c205468657265206973206e6f2064656c656761746520617070726f7665642e28556e617070726f76656404c8204e6f20617070726f76616c20657869737473207468617420776f756c6420616c6c6f7720746865207472616e736665722e26485472616e73616374696f6e53746f7261676501485472616e73616374696f6e53746f7261676524305472616e73616374696f6e7300010238543a3a426c6f636b4e756d626572505665633c5472616e73616374696f6e496e666f3e00040004d020436f6c6c656374696f6e206f66207472616e73616374696f6e206d6574616461746120627920626c6f636b206e756d6265722e284368756e6b436f756e7401010238543a3a426c6f636b4e756d6265720c753332001000000000049420436f756e7420696e6465786564206368756e6b7320666f72206561636820626c6f636b2e1c4279746546656500003042616c616e63654f663c543e040004582053746f72616765206665652070657220627974652e20456e74727946656500003042616c616e63654f663c543e040004742053746f726167652066656520706572207472616e73616374696f6e2e484d61785472616e73616374696f6e53697a6501000c753332100000000004cc204d6178696d756d20646174612073657420696e20612073696e676c65207472616e73616374696f6e20696e2062797465732e504d6178426c6f636b5472616e73616374696f6e7301000c753332100000000004d4204d6178696d756d206e756d626572206f6620696e6465786564207472616e73616374696f6e7320696e2074686520626c6f636b2e3453746f72616765506572696f64010038543a3a426c6f636b4e756d6265721000000000086d012053746f7261676520706572696f6420666f72206461746120696e20626c6f636b732e2053686f756c64206d61746368206073705f73746f726167655f70726f6f663a3a44454641554c545f53544f524147455f504552494f44605420666f7220626c6f636b20617574686f72696e672e44426c6f636b5472616e73616374696f6e730100505665633c5472616e73616374696f6e496e666f3e0400003050726f6f66436865636b6564010010626f6f6c0400049420576173207468652070726f6f6620636865636b656420696e207468697320626c6f636b3f010c1473746f72650410646174611c5665633c75383e18790120496e64657820616e642073746f72652064617461206f6e20636861696e2e204d696e696d756d20646174612073697a6520697320312062797465732c206d6178696d756d20697320604d61785472616e73616374696f6e53697a65602e390120446174612077696c6c2062652072656d6f766564206166746572206053544f524147455f504552494f446020626c6f636b732c20756e6c657373206072656e6577602069732063616c6c65642e2c2023203c7765696768743e1501202d206e2a6c6f67286e29206f6620646174612073697a652c20617320616c6c20646174612069732070757368656420746f20616e20696e2d6d656d6f727920747269652e88204164646974696f6e616c6c7920636f6e7461696e7320612044422077726974652e302023203c2f7765696768743e1472656e65770814626c6f636b38543a3a426c6f636b4e756d62657214696e6465780c7533321c31012052656e65772070726576696f75736c792073746f72656420646174612e20506172616d6574657273206172652074686520626c6f636b206e756d626572207468617420636f6e7461696e7329012070726576696f7573206073746f726560206f72206072656e6577602063616c6c20616e64207472616e73616374696f6e20696e6465782077697468696e207468617420626c6f636b2e0501205472616e73616374696f6e20696e64657820697320656d697474656420696e20746865206053746f72656460206f72206052656e6577656460206576656e742e78204170706c6965732073616d652066656573206173206073746f7265602e2c2023203c7765696768743e30202d20436f6e7374616e742e302023203c2f7765696768743e2c636865636b5f70726f6f66041470726f6f665c5472616e73616374696f6e53746f7261676550726f6f661c1d0120436865636b2073746f726167652070726f6f6620666f7220626c6f636b206e756d6265722060626c6f636b5f6e756d6265722829202d2053746f72616765506572696f64602e0501204966207375636820626c6f636b20646f6573206e6f74206578697374207468652070726f6f6620697320657870656374656420746f20626520604e6f6e65602e2c2023203c7765696768743e6901202d204c696e65617220772e722e7420746865206e756d626572206f6620696e6465786564207472616e73616374696f6e7320696e207468652070726f76656420626c6f636b20666f722072616e646f6d2070726f62696e672ea020546865726527732061204442207265616420666f722065616368207472616e73616374696f6e2ed4204865726520776520617373756d652061206d6178696d756d206f66203130302070726f626564207472616e73616374696f6e732e302023203c2f7765696768743e010c1853746f726564040c753332048c2053746f726564206461746120756e6465722073706563696669656420696e6465782e1c52656e65776564040c75333204902052656e65776564206461746120756e6465722073706563696669656420696e6465782e3050726f6f66436865636b65640004a02053746f726167652070726f6f6620776173207375636365737366756c6c7920636865636b65642e003444496e73756666696369656e7446756e6473047820496e73756666696369656e74206163636f756e742062616c616e63652e344e6f74436f6e66696775726564045c20496e76616c696420636f6e66696775726174696f6e2e3c52656e657765644e6f74466f756e6404802052656e657765642065787472696e736963206973206e6f7420666f756e642e40456d7074795472616e73616374696f6e049820417474656d7074696e6720746f2073746f726520656d707479207472616e73616374696f6e3c556e657870656374656450726f6f6604982050726f6f6620776173206e6f7420657870656374656420696e207468697320626c6f636b2e30496e76616c696450726f6f66046c2050726f6f66206661696c656420766572696669636174696f6e2e304d697373696e6750726f6f66045c204d697373696e672073746f726167652070726f6f662e404d697373696e6753746174654461746104d820556e61626c6520746f207665726966792070726f6f6620626563617375652073746174652064617461206973206d697373696e672e2c446f75626c65436865636b048420446f75626c652070726f6f6620636865636b20696e2074686520626c6f636b2e3c50726f6f664e6f74436865636b656404b02053746f726167652070726f6f6620776173206e6f7420636865636b656420696e2074686520626c6f636b2e4c5472616e73616374696f6e546f6f4c617267650468205472616e73616374696f6e20697320746f6f206c617267652e4c546f6f4d616e795472616e73616374696f6e73049020546f6f206d616e79207472616e73616374696f6e7320696e2074686520626c6f636b2e28426164436f6e7465787404d820417474656d7074656420746f2063616c6c206073746f726560206f757473696465206f6620626c6f636b20657865637574696f6e2e27041c40436865636b5370656356657273696f6e38436865636b547856657273696f6e30436865636b47656e6573697338436865636b4d6f7274616c69747928436865636b4e6f6e63652c436865636b576569676874604368617267655472616e73616374696f6e5061796d656e74 \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v13.json b/packages/polkadot/tests/meta/v13.json new file mode 100644 index 00000000..8b1bfd2d --- /dev/null +++ b/packages/polkadot/tests/meta/v13.json @@ -0,0 +1,16490 @@ +{ + "magicNumber": 1635018093, + "metadata": { + "v13": { + "modules": [ + { + "name": "System", + "storage": { + "prefix": "System", + "items": [ + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountInfo", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The full account information for a particular account ID." + ] + }, + { + "name": "ExtrinsicCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total extrinsics count for the current block." + ] + }, + { + "name": "BlockWeight", + "modifier": "Default", + "type": { + "plain": "ConsumedWeight" + }, + "fallback": "0x000000000000000000000000000000000000000000000000", + "docs": [ + " The current weight for the block." + ] + }, + { + "name": "AllExtrinsicsLen", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total length (in bytes) for all extrinsics put together, for the current block." + ] + }, + { + "name": "BlockHash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Map of block numbers to block hashes." + ] + }, + { + "name": "ExtrinsicData", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Extrinsics data for the current block (maps an extrinsic's index to its data)." + ] + }, + { + "name": "Number", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The current block number being processed. Set by `execute_block`." + ] + }, + { + "name": "ParentHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Hash of the previous block." + ] + }, + { + "name": "Digest", + "modifier": "Default", + "type": { + "plain": "DigestOf" + }, + "fallback": "0x00", + "docs": [ + " Digest of the current block, also part of the block header." + ] + }, + { + "name": "Events", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Events deposited for the current block." + ] + }, + { + "name": "EventCount", + "modifier": "Default", + "type": { + "plain": "EventIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of events in the `Events` list." + ] + }, + { + "name": "EventTopics", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "Hash", + "value": "Vec<(BlockNumber,EventIndex)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Mapping between a topic (represented by T::Hash) and a vector of indexes", + " of events in the `>` list.", + "", + " All topic vectors have deterministic storage locations depending on the topic. This", + " allows light-clients to leverage the changes trie storage tracking mechanism and", + " in case of changes fetch the list of events of interest.", + "", + " The value has the type `(T::BlockNumber, EventIndex)` because if we used only just", + " the `EventIndex` then in case if the topic has the same contents on the next block", + " no notification will be triggered thus the event might be lost." + ] + }, + { + "name": "LastRuntimeUpgrade", + "modifier": "Optional", + "type": { + "plain": "LastRuntimeUpgradeInfo" + }, + "fallback": "0x00", + "docs": [ + " Stores the `spec_version` and `spec_name` of when the last runtime upgrade happened." + ] + }, + { + "name": "UpgradedToU32RefCount", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if we have upgraded so that `type RefCount` is `u32`. False (default) if not." + ] + }, + { + "name": "UpgradedToTripleRefCount", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if we have upgraded so that AccountInfo contains three types of `RefCount`. False", + " (default) if not." + ] + }, + { + "name": "ExecutionPhase", + "modifier": "Optional", + "type": { + "plain": "Phase" + }, + "fallback": "0x00", + "docs": [ + " The execution phase of the block." + ] + } + ] + }, + "calls": [ + { + "name": "fill_block", + "args": [ + { + "name": "_ratio", + "type": "Perbill" + } + ], + "docs": [ + " A dispatch that will fill the block weight up to the given ratio." + ] + }, + { + "name": "remark", + "args": [ + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark.", + "", + " # ", + " - `O(1)`", + " # " + ] + }, + { + "name": "set_heap_pages", + "args": [ + { + "name": "pages", + "type": "u64" + } + ], + "docs": [ + " Set the number of pages in the WebAssembly environment's heap.", + "", + " # ", + " - `O(1)`", + " - 1 storage write.", + " - Base Weight: 1.405 µs", + " - 1 write to HEAP_PAGES", + " # " + ] + }, + { + "name": "set_code", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code.", + "", + " # ", + " - `O(C + S)` where `C` length of `code` and `S` complexity of `can_set_code`", + " - 1 storage write (codec `O(C)`).", + " - 1 call to `can_set_code`: `O(S)` (calls `sp_io::misc::runtime_version` which is expensive).", + " - 1 event.", + " The weight of this function is dependent on the runtime, but generally this is very expensive.", + " We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_code_without_checks", + "args": [ + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Set the new runtime code without doing any checks of the given `code`.", + "", + " # ", + " - `O(C)` where `C` length of `code`", + " - 1 storage write (codec `O(C)`).", + " - 1 event.", + " The weight of this function is dependent on the runtime. We will treat this as a full block.", + " # " + ] + }, + { + "name": "set_changes_trie_config", + "args": [ + { + "name": "changes_trie_config", + "type": "Option" + } + ], + "docs": [ + " Set the new changes trie configuration.", + "", + " # ", + " - `O(1)`", + " - 1 storage write or delete (codec `O(1)`).", + " - 1 call to `deposit_log`: Uses `append` API, so O(1)", + " - Base Weight: 7.218 µs", + " - DB Weight:", + " - Writes: Changes Trie, System Digest", + " # " + ] + }, + { + "name": "set_storage", + "args": [ + { + "name": "items", + "type": "Vec" + } + ], + "docs": [ + " Set some items of storage.", + "", + " # ", + " - `O(I)` where `I` length of `items`", + " - `I` storage writes (`O(1)`).", + " - Base Weight: 0.568 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_storage", + "args": [ + { + "name": "keys", + "type": "Vec" + } + ], + "docs": [ + " Kill some items from storage.", + "", + " # ", + " - `O(IK)` where `I` length of `keys` and `K` length of one key", + " - `I` storage deletions.", + " - Base Weight: .378 * i µs", + " - Writes: Number of items", + " # " + ] + }, + { + "name": "kill_prefix", + "args": [ + { + "name": "prefix", + "type": "Key" + }, + { + "name": "_subkeys", + "type": "u32" + } + ], + "docs": [ + " Kill all storage items with a key that starts with the given prefix.", + "", + " **NOTE:** We rely on the Root origin to provide us the number of subkeys under", + " the prefix we are removing to accurately calculate the weight of this function.", + "", + " # ", + " - `O(P)` where `P` amount of keys with prefix `prefix`", + " - `P` storage deletions.", + " - Base Weight: 0.834 * P µs", + " - Writes: Number of subkeys + 1", + " # " + ] + }, + { + "name": "remark_with_event", + "args": [ + { + "name": "remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark and emit event.", + "", + " # ", + " - `O(b)` where b is the length of the remark.", + " - 1 event.", + " # " + ] + } + ], + "events": [ + { + "name": "ExtrinsicSuccess", + "args": [ + "DispatchInfo" + ], + "docs": [ + " An extrinsic completed successfully. \\[info\\]" + ] + }, + { + "name": "ExtrinsicFailed", + "args": [ + "DispatchError", + "DispatchInfo" + ], + "docs": [ + " An extrinsic failed. \\[error, info\\]" + ] + }, + { + "name": "CodeUpdated", + "args": [], + "docs": [ + " `:code` was updated." + ] + }, + { + "name": "NewAccount", + "args": [ + "AccountId" + ], + "docs": [ + " A new \\[account\\] was created." + ] + }, + { + "name": "KilledAccount", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] was reaped." + ] + }, + { + "name": "Remarked", + "args": [ + "AccountId", + "Hash" + ], + "docs": [ + " On on-chain remark happened. \\[origin, remark_hash\\]" + ] + } + ], + "constants": [ + { + "name": "BlockWeights", + "type": "BlockWeights", + "value": "0x00f2052a0100000000204aa9d1010000405973070000000001c06e96a62e010000010098f73e5d010000010000000000000000405973070000000001c0f6e810a30100000100204aa9d1010000010088526a740000004059730700000000000000", + "docs": [ + " Block & extrinsics weights: base values and limits." + ] + }, + { + "name": "BlockLength", + "type": "BlockLength", + "value": "0x00003c000000500000005000", + "docs": [ + " The maximum length of a block (in bytes)." + ] + }, + { + "name": "BlockHashCount", + "type": "BlockNumber", + "value": "0x60090000", + "docs": [ + " Maximum number of block number to block hash mappings to keep (oldest pruned first)." + ] + }, + { + "name": "DbWeight", + "type": "RuntimeDbWeight", + "value": "0x40787d010000000000e1f50500000000", + "docs": [ + " The weight of runtime database operations the runtime can invoke." + ] + }, + { + "name": "Version", + "type": "RuntimeVersion", + "value": "0x106e6f6465387375627374726174652d6e6f64650a0000000b0100000000000034df6acb689907609b0300000037e397fc7c91f5e40100000040fe3ad401f8959a05000000d2bc9897eed08f1503000000f78b278be53f454c02000000ed99c5acb25eedf502000000cbca25e39f14238702000000687ad44ad37f03c201000000bc9d89904f5b923f0100000068b66ba122c93fa70100000037c8bb1350a9a2a80100000091d5df18b0d2cf5801000000ab3c0572291feb8b0100000002000000", + "docs": [ + " Get the chain's current version." + ] + }, + { + "name": "SS58Prefix", + "type": "u16", + "value": "0x2a00", + "docs": [ + " The designated SS85 prefix of this chain.", + "", + " This replaces the \"ss58Format\" property declared in the chain spec. Reason is", + " that the runtime should know about the prefix in order to make use of it as", + " an identifier of the chain." + ] + } + ], + "errors": [ + { + "name": "InvalidSpecName", + "docs": [ + " The name of specification does not match between the current runtime", + " and the new runtime." + ] + }, + { + "name": "SpecVersionNeedsToIncrease", + "docs": [ + " The specification version is not allowed to decrease between the current runtime", + " and the new runtime." + ] + }, + { + "name": "FailedToExtractRuntimeVersion", + "docs": [ + " Failed to extract the runtime version from the new runtime.", + "", + " Either calling `Core_version` or decoding `RuntimeVersion` failed." + ] + }, + { + "name": "NonDefaultComposite", + "docs": [ + " Suicide called when the account has non-default composite data." + ] + }, + { + "name": "NonZeroRefCount", + "docs": [ + " There is a non-zero reference count preventing the account from being purged." + ] + } + ], + "index": 0 + }, + { + "name": "Utility", + "storage": null, + "calls": [ + { + "name": "batch", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " If origin is root then call are dispatch without checking origin filter. (This includes", + " bypassing `frame_system::Config::BaseCallFilter`).", + "", + " # ", + " - Complexity: O(C) where C is the number of calls to be batched.", + " # ", + "", + " This will return `Ok` in all circumstances. To determine the success of the batch, an", + " event is deposited. If a call failed and the batch was interrupted, then the", + " `BatchInterrupted` event is deposited, along with the number of successful calls made", + " and the error of the failed call. If all were successful, then the `BatchCompleted`", + " event is deposited." + ] + }, + { + "name": "as_derivative", + "args": [ + { + "name": "index", + "type": "u16" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through an indexed pseudonym of the sender.", + "", + " Filter from origin are passed along. The call will be dispatched with an origin which", + " use the same filter as the origin of this call.", + "", + " NOTE: If you need to ensure that any account-based filtering is not honored (i.e.", + " because you expect `proxy` to have been used prior in the call stack and you do not want", + " the call restrictions to apply to any sub-accounts), then use `as_multi_threshold_1`", + " in the Multisig pallet instead.", + "", + " NOTE: Prior to version *12, this was called `as_limited_sub`.", + "", + " The dispatch origin for this call must be _Signed_." + ] + }, + { + "name": "batch_all", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls and atomically execute them.", + " The whole transaction will rollback and fail if any of the calls failed.", + "", + " May be called from any origin.", + "", + " - `calls`: The calls to be dispatched from the same origin.", + "", + " If origin is root then call are dispatch without checking origin filter. (This includes", + " bypassing `frame_system::Config::BaseCallFilter`).", + "", + " # ", + " - Complexity: O(C) where C is the number of calls to be batched.", + " # " + ] + } + ], + "events": [ + { + "name": "BatchInterrupted", + "args": [ + "u32", + "DispatchError" + ], + "docs": [ + " Batch of dispatches did not complete fully. Index of first failing dispatch given, as", + " well as the error. \\[index, error\\]" + ] + }, + { + "name": "BatchCompleted", + "args": [], + "docs": [ + " Batch of dispatches completed fully with no error." + ] + }, + { + "name": "ItemCompleted", + "args": [], + "docs": [ + " A single item within a Batch of dispatches has completed with no error." + ] + } + ], + "constants": [], + "errors": [], + "index": 1 + }, + { + "name": "Babe", + "storage": { + "prefix": "Babe", + "items": [ + { + "name": "EpochIndex", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current epoch index." + ] + }, + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Current epoch authorities." + ] + }, + { + "name": "GenesisSlot", + "modifier": "Default", + "type": { + "plain": "Slot" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The slot at which the first epoch actually started. This is 0", + " until the first block of the chain." + ] + }, + { + "name": "CurrentSlot", + "modifier": "Default", + "type": { + "plain": "Slot" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current slot number." + ] + }, + { + "name": "Randomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The epoch randomness for the *current* epoch.", + "", + " # Security", + "", + " This MUST NOT be used for gambling, as it can be influenced by a", + " malicious validator in the short term. It MAY be used in many", + " cryptographic protocols, however, so long as one remembers that this", + " (like everything else on-chain) it is public. For example, it can be", + " used where a number is needed that cannot have been chosen by an", + " adversary, for purposes such as public-coin zero-knowledge proofs." + ] + }, + { + "name": "PendingEpochConfigChange", + "modifier": "Optional", + "type": { + "plain": "NextConfigDescriptor" + }, + "fallback": "0x00", + "docs": [ + " Pending epoch configuration change that will be applied when the next epoch is enacted." + ] + }, + { + "name": "NextRandomness", + "modifier": "Default", + "type": { + "plain": "Randomness" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Next epoch randomness." + ] + }, + { + "name": "NextAuthorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Next epoch authorities." + ] + }, + { + "name": "SegmentIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Randomness under construction.", + "", + " We make a tradeoff between storage accesses and list length.", + " We store the under-construction randomness in segments of up to", + " `UNDER_CONSTRUCTION_SEGMENT_LENGTH`.", + "", + " Once a segment reaches this length, we begin the next one.", + " We reset all segments and return to `0` at the beginning of every", + " epoch." + ] + }, + { + "name": "UnderConstruction", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " TWOX-NOTE: `SegmentIndex` is an increasing integer, so this is okay." + ] + }, + { + "name": "Initialized", + "modifier": "Optional", + "type": { + "plain": "MaybeRandomness" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) which is `Some`", + " if per-block initialization has already been called for current block." + ] + }, + { + "name": "AuthorVrfRandomness", + "modifier": "Default", + "type": { + "plain": "MaybeRandomness" + }, + "fallback": "0x00", + "docs": [ + " This field should always be populated during block processing unless", + " secondary plain slots are enabled (which don't contain a VRF output).", + "", + " It is set in `on_initialize`, before it will contain the value from the last block." + ] + }, + { + "name": "EpochStart", + "modifier": "Default", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The block numbers when the last and current epoch have started, respectively `N-1` and", + " `N`.", + " NOTE: We track this is in order to annotate the block number when a given pool of", + " entropy was fixed (i.e. it was known to chain observers). Since epochs are defined in", + " slots, which may be skipped, the block numbers may not line up with the slot numbers." + ] + }, + { + "name": "Lateness", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " How late the current block is compared to its parent.", + "", + " This entry is populated as part of block execution and is cleaned up", + " on block finalization. Querying this storage entry outside of block", + " execution context should always yield zero." + ] + }, + { + "name": "EpochConfig", + "modifier": "Optional", + "type": { + "plain": "BabeEpochConfiguration" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the current epoch. Should never be `None` as it is initialized in genesis." + ] + }, + { + "name": "NextEpochConfig", + "modifier": "Optional", + "type": { + "plain": "BabeEpochConfiguration" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the next epoch, `None` if the config will not change", + " (you can fallback to `EpochConfig` instead in that case)." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "BabeEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report authority equivocation/misbehavior. This method will verify", + " the equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence will", + " be reported.", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + }, + { + "name": "plan_config_change", + "args": [ + { + "name": "config", + "type": "NextConfigDescriptor" + } + ], + "docs": [ + " Plan an epoch config change. The epoch config change is recorded and will be enacted on", + " the next call to `enact_epoch_change`. The config will be activated one epoch after.", + " Multiple calls to this method will replace any existing planned config change that had", + " not been enacted yet." + ] + } + ], + "events": null, + "constants": [ + { + "name": "EpochDuration", + "type": "u64", + "value": "0xc800000000000000", + "docs": [ + " The amount of time, in slots, that each epoch should last.", + " NOTE: Currently it is not possible to change the epoch duration after", + " the chain has started. Attempting to do so will brick block production." + ] + }, + { + "name": "ExpectedBlockTime", + "type": "Moment", + "value": "0xb80b000000000000", + "docs": [ + " The expected average block time at which BABE should be creating", + " blocks. Since BABE is probabilistic it is not trivial to figure out", + " what the expected average block time should be based on the slot", + " duration and the security parameter `c` (where `1 - c` represents", + " the probability of a slot being empty)." + ] + } + ], + "errors": [ + { + "name": "InvalidEquivocationProof", + "docs": [ + " An equivocation proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "InvalidKeyOwnershipProof", + "docs": [ + " A key ownership proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "DuplicateOffenceReport", + "docs": [ + " A given equivocation report is valid but already previously reported." + ] + } + ], + "index": 2 + }, + { + "name": "Timestamp", + "storage": { + "prefix": "Timestamp", + "items": [ + { + "name": "Now", + "modifier": "Default", + "type": { + "plain": "Moment" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current time for the current block." + ] + }, + { + "name": "DidUpdate", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Did the timestamp get updated in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "set", + "args": [ + { + "name": "now", + "type": "Compact" + } + ], + "docs": [ + " Set the current time.", + "", + " This call should be invoked exactly once per block. It will panic at the finalization", + " phase, if this call hasn't been invoked by that time.", + "", + " The timestamp should be greater than the previous one by the amount specified by", + " `MinimumPeriod`.", + "", + " The dispatch origin for this call must be `Inherent`.", + "", + " # ", + " - `O(1)` (Note that implementations of `OnTimestampSet` must also be `O(1)`)", + " - 1 storage read and 1 storage mutation (codec `O(1)`). (because of `DidUpdate::take` in `on_finalize`)", + " - 1 event handler `on_timestamp_set`. Must be `O(1)`.", + " # " + ] + } + ], + "events": null, + "constants": [ + { + "name": "MinimumPeriod", + "type": "Moment", + "value": "0xdc05000000000000", + "docs": [ + " The minimum period between blocks. Beware that this is different to the *expected* period", + " that the block production apparatus provides. Your chosen consensus system will generally", + " work with this to determine a sensible block time. e.g. For Aura, it will be double this", + " period on default settings." + ] + } + ], + "errors": [], + "index": 3 + }, + { + "name": "Authorship", + "storage": { + "prefix": "Authorship", + "items": [ + { + "name": "Uncles", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Uncles" + ] + }, + { + "name": "Author", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " Author of current block." + ] + }, + { + "name": "DidSetUncles", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Whether uncles were already set in this block." + ] + } + ] + }, + "calls": [ + { + "name": "set_uncles", + "args": [ + { + "name": "new_uncles", + "type": "Vec
" + } + ], + "docs": [ + " Provide a set of uncles." + ] + } + ], + "events": null, + "constants": [ + { + "name": "UncleGenerations", + "type": "BlockNumber", + "value": "0x05000000", + "docs": [ + " The number of blocks back we should accept uncles.", + " This means that we will deal with uncle-parents that are", + " `UncleGenerations + 1` before `now`." + ] + } + ], + "errors": [ + { + "name": "InvalidUncleParent", + "docs": [ + " The uncle parent not in the chain." + ] + }, + { + "name": "UnclesAlreadySet", + "docs": [ + " Uncles already set in the block." + ] + }, + { + "name": "TooManyUncles", + "docs": [ + " Too many uncles." + ] + }, + { + "name": "GenesisUncle", + "docs": [ + " The uncle is genesis." + ] + }, + { + "name": "TooHighUncle", + "docs": [ + " The uncle is too high in chain." + ] + }, + { + "name": "UncleAlreadyIncluded", + "docs": [ + " The uncle is already included." + ] + }, + { + "name": "OldUncle", + "docs": [ + " The uncle isn't recent enough to be included." + ] + } + ], + "index": 4 + }, + { + "name": "Indices", + "storage": { + "prefix": "Indices", + "items": [ + { + "name": "Accounts", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountIndex", + "value": "(AccountId,BalanceOf,bool)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The lookup from index to account." + ] + } + ] + }, + "calls": [ + { + "name": "claim", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an previously unassigned index.", + "", + " Payment: `Deposit` is reserved from the sender account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be claimed. This must not be in use.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Assign an index already owned by the sender to another account. The balance reservation", + " is effectively transferred to the new account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `index`: the index to be re-assigned. This must be owned by the sender.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One transfer operation.", + " - One event.", + " -------------------", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (recipient)", + " - Writes: Indices Accounts, System Account (recipient)", + " # " + ] + }, + { + "name": "free", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Free up an index owned by the sender.", + "", + " Payment: Any previous deposit placed for the index is unreserved in the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must own the index.", + "", + " - `index`: the index to be freed. This must be owned by the sender.", + "", + " Emits `IndexFreed` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - One reserve operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "new", + "type": "AccountId" + }, + { + "name": "index", + "type": "AccountIndex" + }, + { + "name": "freeze", + "type": "bool" + } + ], + "docs": [ + " Force an index to an account. This doesn't require a deposit. If the index is already", + " held, then any deposit is reimbursed to its current owner.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `index`: the index to be (re-)assigned.", + " - `new`: the new owner of the index. This function is a no-op if it is equal to sender.", + " - `freeze`: if set to `true`, will freeze the index so it cannot be transferred.", + "", + " Emits `IndexAssigned` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one reserve operation.", + " - One event.", + " -------------------", + " - DB Weight:", + " - Reads: Indices Accounts, System Account (original owner)", + " - Writes: Indices Accounts, System Account (original owner)", + " # " + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "index", + "type": "AccountIndex" + } + ], + "docs": [ + " Freeze an index so it will always point to the sender account. This consumes the deposit.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must have a", + " non-frozen account `index`.", + "", + " - `index`: the index to be frozen in place.", + "", + " Emits `IndexFrozen` if successful.", + "", + " # ", + " - `O(1)`.", + " - One storage mutation (codec `O(1)`).", + " - Up to one slash operation.", + " - One event.", + " -------------------", + " - DB Weight: 1 Read/Write (Accounts)", + " # " + ] + } + ], + "events": [ + { + "name": "IndexAssigned", + "args": [ + "AccountId", + "AccountIndex" + ], + "docs": [ + " A account index was assigned. \\[index, who\\]" + ] + }, + { + "name": "IndexFreed", + "args": [ + "AccountIndex" + ], + "docs": [ + " A account index has been freed up (unassigned). \\[index\\]" + ] + }, + { + "name": "IndexFrozen", + "args": [ + "AccountIndex", + "AccountId" + ], + "docs": [ + " A account index has been frozen to its current account ID. \\[index, who\\]" + ] + } + ], + "constants": [ + { + "name": "Deposit", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The deposit needed for reserving an index." + ] + } + ], + "errors": [ + { + "name": "NotAssigned", + "docs": [ + " The index was not already assigned." + ] + }, + { + "name": "NotOwner", + "docs": [ + " The index is assigned to another account." + ] + }, + { + "name": "InUse", + "docs": [ + " The index was not available." + ] + }, + { + "name": "NotTransfer", + "docs": [ + " The source and destination accounts are identical." + ] + }, + { + "name": "Permanent", + "docs": [ + " The index is permanent and may not be freed/changed." + ] + } + ], + "index": 5 + }, + { + "name": "Balances", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "TotalIssuance", + "modifier": "Default", + "type": { + "plain": "Balance" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total units issued in the system." + ] + }, + { + "name": "Account", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountData", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The balance of an account.", + "", + " NOTE: This is only used in the case that this pallet is used to store balances." + ] + }, + { + "name": "Locks", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Any liquidity locks on some account balances.", + " NOTE: Should only be accessed when setting, changing and freeing a lock." + ] + }, + { + "name": "Reserves", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Named reserves on some account balances." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " This is set to v2.0.0 for new networks." + ] + } + ] + }, + "calls": [ + { + "name": "transfer", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Transfer some liquid free balance to another account.", + "", + " `transfer` will set the `FreeBalance` of the sender and receiver.", + " It will decrease the total issuance of the system by the `TransferFee`.", + " If the sender's account is below the existential deposit as a result", + " of the transfer, the account will be reaped.", + "", + " The dispatch origin for this call must be `Signed` by the transactor.", + "", + " # ", + " - Dependent on arguments but not critical, given proper implementations for", + " input config types. See related functions below.", + " - It contains a limited number of reads and writes internally and no complex computation.", + "", + " Related functions:", + "", + " - `ensure_can_withdraw` is always called internally but has a bounded complexity.", + " - Transferring balances to accounts that did not exist before will cause", + " `T::OnNewAccount::on_new_account` to be called.", + " - Removing enough funds from an account will trigger `T::DustRemoval::on_unbalanced`.", + " - `transfer_keep_alive` works the same way as `transfer`, but has an additional", + " check that the transfer will not kill the origin account.", + " ---------------------------------", + " - Base Weight: 73.64 µs, worst case scenario (account created, account removed)", + " - DB Weight: 1 Read and 1 Write to destination account", + " - Origin account is already in memory, so no DB operations for them.", + " # " + ] + }, + { + "name": "set_balance", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "new_free", + "type": "Compact" + }, + { + "name": "new_reserved", + "type": "Compact" + } + ], + "docs": [ + " Set the balances of a given account.", + "", + " This will alter `FreeBalance` and `ReservedBalance` in storage. it will", + " also decrease the total issuance of the system (`TotalIssuance`).", + " If the new free or reserved balance is below the existential deposit,", + " it will reset the account nonce (`frame_system::AccountNonce`).", + "", + " The dispatch origin for this call is `root`.", + "", + " # ", + " - Independent of the arguments.", + " - Contains a limited number of reads and writes.", + " ---------------------", + " - Base Weight:", + " - Creating: 27.56 µs", + " - Killing: 35.11 µs", + " - DB Weight: 1 Read, 1 Write to `who`", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Exactly as `transfer`, except the origin must be root and the source account may be", + " specified.", + " # ", + " - Same as transfer, but additional read and write because the source account is", + " not assumed to be in the overlay.", + " # " + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Same as the [`transfer`] call, but with a check that the transfer will not kill the", + " origin account.", + "", + " 99% of the time you want [`transfer`] instead.", + "", + " [`transfer`]: struct.Pallet.html#method.transfer", + " # ", + " - Cheaper than transfer because account cannot be killed.", + " - Base Weight: 51.4 µs", + " - DB Weight: 1 Read and 1 Write to dest (sender is in overlay already)", + " #" + ] + }, + { + "name": "transfer_all", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "keep_alive", + "type": "bool" + } + ], + "docs": [ + " Transfer the entire transferable balance from the caller account.", + "", + " NOTE: This function only attempts to transfer _transferable_ balances. This means that", + " any locked, reserved, or existential deposits (when `keep_alive` is `true`), will not be", + " transferred by this function. To ensure that this function results in a killed account,", + " you might need to prepare the account by removing any reference counters, storage", + " deposits, etc...", + "", + " The dispatch origin of this call must be Signed.", + "", + " - `dest`: The recipient of the transfer.", + " - `keep_alive`: A boolean to determine if the `transfer_all` operation should send all", + " of the funds the account has, causing the sender account to be killed (false), or", + " transfer everything except at least the existential deposit, which will guarantee to", + " keep the sender account alive (true).", + " # ", + " - O(1). Just like transfer, but reading the user's transferable balance first.", + " #" + ] + } + ], + "events": [ + { + "name": "Endowed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was created with some free balance. \\[account, free_balance\\]" + ] + }, + { + "name": "DustLost", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account was removed whose balance was non-zero but below ExistentialDeposit,", + " resulting in an outright loss. \\[account, balance\\]" + ] + }, + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " Transfer succeeded. \\[from, to, value\\]" + ] + }, + { + "name": "BalanceSet", + "args": [ + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " A balance was set by root. \\[who, free, reserved\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some amount was deposited (e.g. for transaction fees). \\[who, deposit\\]" + ] + }, + { + "name": "Reserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was reserved (moved from free to reserved). \\[who, value\\]" + ] + }, + { + "name": "Unreserved", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " Some balance was unreserved (moved from reserved to free). \\[who, value\\]" + ] + }, + { + "name": "ReserveRepatriated", + "args": [ + "AccountId", + "AccountId", + "Balance", + "BalanceStatus" + ], + "docs": [ + " Some balance was moved from the reserve of the first account to the second account.", + " Final argument indicates the destination balance type.", + " \\[from, to, balance, destination_status\\]" + ] + } + ], + "constants": [ + { + "name": "ExistentialDeposit", + "type": "Balance", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to keep an account open." + ] + }, + { + "name": "MaxLocks", + "type": "u32", + "value": "0x32000000", + "docs": [ + " The maximum number of locks that should exist on an account.", + " Not strictly enforced, but used for weight estimation." + ] + }, + { + "name": "MaxReserves", + "type": "u32", + "value": "0x32000000", + "docs": [ + " The maximum number of named reserves that can exist on an account." + ] + } + ], + "errors": [ + { + "name": "VestingBalance", + "docs": [ + " Vesting balance too high to send value" + ] + }, + { + "name": "LiquidityRestrictions", + "docs": [ + " Account liquidity restrictions prevent withdrawal" + ] + }, + { + "name": "InsufficientBalance", + "docs": [ + " Balance too low to send value" + ] + }, + { + "name": "ExistentialDeposit", + "docs": [ + " Value too low to create account due to existential deposit" + ] + }, + { + "name": "KeepAlive", + "docs": [ + " Transfer/payment would kill account" + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " A vesting schedule already exists for this account" + ] + }, + { + "name": "DeadAccount", + "docs": [ + " Beneficiary account must pre-exist" + ] + }, + { + "name": "TooManyReserves", + "docs": [ + " Number of named reserves exceed MaxReserves" + ] + } + ], + "index": 6 + }, + { + "name": "TransactionPayment", + "storage": { + "prefix": "TransactionPayment", + "items": [ + { + "name": "NextFeeMultiplier", + "modifier": "Default", + "type": { + "plain": "Multiplier" + }, + "fallback": "0x000064a7b3b6e00d0000000000000000", + "docs": [] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": null, + "events": null, + "constants": [ + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + }, + { + "name": "WeightToFee", + "type": "Vec", + "value": "0x0401000000000000000000000000000000000000000001", + "docs": [ + " The polynomial that is applied in order to derive fee from weight." + ] + } + ], + "errors": [], + "index": 7 + }, + { + "name": "ElectionProviderMultiPhase", + "storage": { + "prefix": "ElectionProviderMultiPhase", + "items": [ + { + "name": "Round", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x01000000", + "docs": [ + " Internal counter for the number of rounds.", + "", + " This is useful for de-duplication of transactions submitted to the pool, and general", + " diagnostics of the pallet.", + "", + " This is merely incremented once per every time that an upstream `elect` is called." + ] + }, + { + "name": "CurrentPhase", + "modifier": "Default", + "type": { + "plain": "ElectionPhase" + }, + "fallback": "0x00", + "docs": [ + " Current phase." + ] + }, + { + "name": "QueuedSolution", + "modifier": "Optional", + "type": { + "plain": "ReadySolution" + }, + "fallback": "0x00", + "docs": [ + " Current best solution, signed or unsigned, queued to be returned upon `elect`." + ] + }, + { + "name": "Snapshot", + "modifier": "Optional", + "type": { + "plain": "RoundSnapshot" + }, + "fallback": "0x00", + "docs": [ + " Snapshot data of the round.", + "", + " This is created at the beginning of the signed phase and cleared upon calling `elect`." + ] + }, + { + "name": "DesiredTargets", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Desired number of targets to elect for this round.", + "", + " Only exists when [`Snapshot`] is present." + ] + }, + { + "name": "SnapshotMetadata", + "modifier": "Optional", + "type": { + "plain": "SolutionOrSnapshotSize" + }, + "fallback": "0x00", + "docs": [ + " The metadata of the [`RoundSnapshot`]", + "", + " Only exists when [`Snapshot`] is present." + ] + }, + { + "name": "SignedSubmissionNextIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The next index to be assigned to an incoming signed submission.", + "", + " Every accepted submission is assigned a unique index; that index is bound to that particular", + " submission for the duration of the election. On election finalization, the next index is", + " reset to 0.", + "", + " We can't just use `SignedSubmissionIndices.len()`, because that's a bounded set; past its", + " capacity, it will simply saturate. We can't just iterate over `SignedSubmissionsMap`,", + " because iteration is slow. Instead, we store the value here." + ] + }, + { + "name": "SignedSubmissionIndices", + "modifier": "Default", + "type": { + "plain": "SubmissionIndicesOf" + }, + "fallback": "0x00", + "docs": [ + " A sorted, bounded set of `(score, index)`, where each `index` points to a value in", + " `SignedSubmissions`.", + "", + " We never need to process more than a single signed submission at a time. Signed submissions", + " can be quite large, so we're willing to pay the cost of multiple database accesses to access", + " them one at a time instead of reading and decoding all of them at once." + ] + }, + { + "name": "SignedSubmissionsMap", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "SignedSubmissionOf", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000", + "docs": [ + " Unchecked, signed solutions.", + "", + " Together with `SubmissionIndices`, this stores a bounded set of `SignedSubmissions` while", + " allowing us to keep only a single one in memory at a time.", + "", + " Twox note: the key of the map is an auto-incrementing index which users cannot inspect or", + " affect; we shouldn't need a cryptographically secure hasher." + ] + }, + { + "name": "MinimumUntrustedScore", + "modifier": "Optional", + "type": { + "plain": "ElectionScore" + }, + "fallback": "0x00", + "docs": [ + " The minimum score that each 'untrusted' solution must attain in order to be considered", + " feasible.", + "", + " Can be set via `set_minimum_untrusted_score`." + ] + } + ] + }, + "calls": [ + { + "name": "submit_unsigned", + "args": [ + { + "name": "solution", + "type": "RawSolution" + }, + { + "name": "witness", + "type": "SolutionOrSnapshotSize" + } + ], + "docs": [ + " Submit a solution for the unsigned phase.", + "", + " The dispatch origin fo this call must be __none__.", + "", + " This submission is checked on the fly. Moreover, this unsigned solution is only", + " validated when submitted to the pool from the **local** node. Effectively, this means", + " that only active validators can submit this transaction when authoring a block (similar", + " to an inherent).", + "", + " To prevent any incorrect solution (and thus wasted time/weight), this transaction will", + " panic if the solution submitted by the validator is invalid in any way, effectively", + " putting their authoring reward at risk.", + "", + " No deposit or reward is associated with this submission." + ] + }, + { + "name": "set_minimum_untrusted_score", + "args": [ + { + "name": "maybe_next_score", + "type": "Option" + } + ], + "docs": [ + " Set a new value for `MinimumUntrustedScore`.", + "", + " Dispatch origin must be aligned with `T::ForceOrigin`.", + "", + " This check can be turned off by setting the value to `None`." + ] + }, + { + "name": "set_emergency_election_result", + "args": [ + { + "name": "supports", + "type": "Supports" + } + ], + "docs": [ + " Set a solution in the queue, to be handed out to the client of this pallet in the next", + " call to `ElectionProvider::elect`.", + "", + " This can only be set by `T::ForceOrigin`, and only when the phase is `Emergency`.", + "", + " The solution is not checked for any feasibility and is assumed to be trustworthy, as any", + " feasibility check itself can in principle cause the election process to fail (due to", + " memory/weight constrains)." + ] + }, + { + "name": "submit", + "args": [ + { + "name": "solution", + "type": "RawSolution" + }, + { + "name": "num_signed_submissions", + "type": "u32" + } + ], + "docs": [ + " Submit a solution for the signed phase.", + "", + " The dispatch origin fo this call must be __signed__.", + "", + " The solution is potentially queued, based on the claimed score and processed at the end", + " of the signed phase.", + "", + " A deposit is reserved and recorded for the solution. Based on the outcome, the solution", + " might be rewarded, slashed, or get all or a part of the deposit back.", + "", + " # ", + " Queue size must be provided as witness data.", + " # " + ] + } + ], + "events": [ + { + "name": "SolutionStored", + "args": [ + "ElectionCompute", + "bool" + ], + "docs": [ + " A solution was stored with the given compute.", + "", + " If the solution is signed, this means that it hasn't yet been processed. If the", + " solution is unsigned, this means that it has also been processed.", + "", + " The `bool` is `true` when a previous solution was ejected to make room for this one." + ] + }, + { + "name": "ElectionFinalized", + "args": [ + "Option" + ], + "docs": [ + " The election has been finalized, with `Some` of the given computation, or else if the", + " election failed, `None`." + ] + }, + { + "name": "Rewarded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has been rewarded for their signed submission being finalized." + ] + }, + { + "name": "Slashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has been slashed for submitting an invalid signed submission." + ] + }, + { + "name": "SignedPhaseStarted", + "args": [ + "u32" + ], + "docs": [ + " The signed phase of the given round has started." + ] + }, + { + "name": "UnsignedPhaseStarted", + "args": [ + "u32" + ], + "docs": [ + " The unsigned phase of the given round has started." + ] + } + ], + "constants": [ + { + "name": "UnsignedPhase", + "type": "BlockNumber", + "value": "0x32000000", + "docs": [ + " Duration of the unsigned phase." + ] + }, + { + "name": "SignedPhase", + "type": "BlockNumber", + "value": "0x32000000", + "docs": [ + " Duration of the signed phase." + ] + }, + { + "name": "SolutionImprovementThreshold", + "type": "Perbill", + "value": "0xa0860100", + "docs": [ + " The minimum amount of improvement to the solution score that defines a solution as", + " \"better\" (in any phase)." + ] + }, + { + "name": "OffchainRepeat", + "type": "BlockNumber", + "value": "0x05000000", + "docs": [ + " The repeat threshold of the offchain worker.", + "", + " For example, if it is 5, that means that at least 5 blocks will elapse between attempts", + " to submit the worker's solution." + ] + }, + { + "name": "MinerTxPriority", + "type": "TransactionPriority", + "value": "0xfeffffffffffff7f", + "docs": [ + " The priority of the unsigned transaction submitted in the unsigned-phase" + ] + }, + { + "name": "MinerMaxIterations", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Maximum number of iteration of balancing that will be executed in the embedded miner of", + " the pallet." + ] + }, + { + "name": "MinerMaxWeight", + "type": "Weight", + "value": "0xc07c907c2d010000", + "docs": [ + " Maximum weight that the miner should consume.", + "", + " The miner will ensure that the total weight of the unsigned solution will not exceed", + " this value, based on [`WeightInfo::submit_unsigned`]." + ] + }, + { + "name": "SignedMaxSubmissions", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Maximum number of signed submissions that can be queued.", + "", + " It is best to avoid adjusting this during an election, as it impacts downstream data", + " structures. In particular, `SignedSubmissionIndices` is bounded on this value. If you", + " update this value during an election, you _must_ ensure that", + " `SignedSubmissionIndices.len()` is less than or equal to the new value. Otherwise,", + " attempts to submit new solutions may cause a runtime panic." + ] + }, + { + "name": "SignedMaxWeight", + "type": "Weight", + "value": "0xc07c907c2d010000", + "docs": [ + " Maximum weight of a signed solution.", + "", + " This should probably be similar to [`Config::MinerMaxWeight`]." + ] + }, + { + "name": "SignedRewardBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Base reward for a signed solution" + ] + }, + { + "name": "SignedDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Base deposit for a signed solution." + ] + }, + { + "name": "SignedDepositByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " Per-byte deposit for a signed solution." + ] + }, + { + "name": "SignedDepositWeight", + "type": "BalanceOf", + "value": "0x00000000000000000000000000000000", + "docs": [ + " Per-weight deposit for a signed solution." + ] + }, + { + "name": "MinerMaxLength", + "type": "u32", + "value": "0x00003600", + "docs": [ + " Maximum length (bytes) that the mined solution should consume.", + "", + " The miner will ensure that the total length of the unsigned solution will not exceed", + " this value." + ] + } + ], + "errors": [ + { + "name": "PreDispatchEarlySubmission", + "docs": [ + " Submission was too early." + ] + }, + { + "name": "PreDispatchWrongWinnerCount", + "docs": [ + " Wrong number of winners presented." + ] + }, + { + "name": "PreDispatchWeakSubmission", + "docs": [ + " Submission was too weak, score-wise." + ] + }, + { + "name": "SignedQueueFull", + "docs": [ + " The queue was full, and the solution was not better than any of the existing ones." + ] + }, + { + "name": "SignedCannotPayDeposit", + "docs": [ + " The origin failed to pay the deposit." + ] + }, + { + "name": "SignedInvalidWitness", + "docs": [ + " Witness data to dispatchable is invalid." + ] + }, + { + "name": "SignedTooMuchWeight", + "docs": [ + " The signed submission consumes too much weight" + ] + }, + { + "name": "OcwCallWrongEra", + "docs": [ + " OCW submitted solution for wrong round" + ] + }, + { + "name": "MissingSnapshotMetadata", + "docs": [ + " Snapshot metadata should exist but didn't." + ] + }, + { + "name": "InvalidSubmissionIndex", + "docs": [ + " `Self::insert_submission` returned an invalid index." + ] + }, + { + "name": "CallNotAllowed", + "docs": [ + " The call is not allowed at this point." + ] + } + ], + "index": 8 + }, + { + "name": "Staking", + "storage": { + "prefix": "Staking", + "items": [ + { + "name": "HistoryDepth", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x54000000", + "docs": [ + " Number of eras to keep in history.", + "", + " Information is kept for eras in `[current_era - history_depth; current_era]`.", + "", + " Must be more than the number of eras delayed by session otherwise. I.e. active era must", + " always be in history. I.e. `active_era > current_era - history_depth` must be", + " guaranteed." + ] + }, + { + "name": "ValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The ideal number of staking participants." + ] + }, + { + "name": "MinimumValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Minimum number of staking participants before emergency conditions are imposed." + ] + }, + { + "name": "Invulnerables", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Any validators that may never be slashed or forcibly kicked. It's a Vec since they're", + " easy to initialize and the performance hit is minimal (we expect no more than four", + " invulnerables) and restricted to testnets." + ] + }, + { + "name": "Bonded", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all locked \"stash\" accounts to the controller account." + ] + }, + { + "name": "MinNominatorBond", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The minimum active bond to become and maintain the role of a nominator." + ] + }, + { + "name": "MinValidatorBond", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The minimum active bond to become and maintain the role of a validator." + ] + }, + { + "name": "Ledger", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "StakingLedger", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all (unlocked) \"controller\" accounts to the info regarding the staking." + ] + }, + { + "name": "Payee", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RewardDestination", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Where the reward payment should be made. Keyed by stash." + ] + }, + { + "name": "Validators", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ValidatorPrefs", + "linked": false + } + }, + "fallback": "0x0000", + "docs": [ + " The map from (wannabe) validator stash key to the preferences of that validator.", + "", + " When updating this storage item, you must also update the `CounterForValidators`." + ] + }, + { + "name": "CounterForValidators", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " A tracker to keep count of the number of items in the `Validators` map." + ] + }, + { + "name": "MaxValidatorsCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " The maximum validator count before we stop allowing new validators to join.", + "", + " When this value is not set, no limits are enforced." + ] + }, + { + "name": "Nominators", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Nominations", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The map from nominator stash key to the set of stash keys of all validators to nominate.", + "", + " When updating this storage item, you must also update the `CounterForNominators`." + ] + }, + { + "name": "CounterForNominators", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " A tracker to keep count of the number of items in the `Nominators` map." + ] + }, + { + "name": "MaxNominatorsCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " The maximum nominator count before we stop allowing new validators to join.", + "", + " When this value is not set, no limits are enforced." + ] + }, + { + "name": "CurrentEra", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The current era index.", + "", + " This is the latest planned era, depending on how the Session pallet queues the validator", + " set, it might be active or not." + ] + }, + { + "name": "ActiveEra", + "modifier": "Optional", + "type": { + "plain": "ActiveEraInfo" + }, + "fallback": "0x00", + "docs": [ + " The active era information, it holds index and start.", + "", + " The active era is the era being currently rewarded. Validator set of this era must be", + " equal to [`SessionInterface::validators`]." + ] + }, + { + "name": "ErasStartSessionIndex", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The session index at which the era start for the last `HISTORY_DEPTH` eras.", + "", + " Note: This tracks the starting session (i.e. session index when era start being active)", + " for the eras in `[CurrentEra - HISTORY_DEPTH, CurrentEra]`." + ] + }, + { + "name": "ErasStakers", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Exposure of validator at era.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasStakersClipped", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "Exposure", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x000000", + "docs": [ + " Clipped Exposure of validator at era.", + "", + " This is similar to [`ErasStakers`] but number of nominators exposed is reduced to the", + " `T::MaxNominatorRewardedPerValidator` biggest stakers.", + " (Note: the field `total` and `own` of the exposure remains unchanged).", + " This is used to limit the i/o cost for the nominator payout.", + "", + " This is keyed fist by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras.", + " If stakers hasn't been set or has been removed then empty exposure is returned." + ] + }, + { + "name": "ErasValidatorPrefs", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "ValidatorPrefs", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x0000", + "docs": [ + " Similar to `ErasStakers`, this holds the preferences of validators.", + "", + " This is keyed first by the era index to allow bulk deletion and then the stash account.", + "", + " Is it removed after `HISTORY_DEPTH` eras." + ] + }, + { + "name": "ErasValidatorReward", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The total validator era payout for the last `HISTORY_DEPTH` eras.", + "", + " Eras that haven't finished yet or has been removed doesn't have reward." + ] + }, + { + "name": "ErasRewardPoints", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "EraRewardPoints", + "linked": false + } + }, + "fallback": "0x0000000000", + "docs": [ + " Rewards for the last `HISTORY_DEPTH` eras.", + " If reward hasn't been set or has been removed then 0 reward is returned." + ] + }, + { + "name": "ErasTotalStake", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total amount staked for the last `HISTORY_DEPTH` eras.", + " If total hasn't been set or has been removed then 0 stake is returned." + ] + }, + { + "name": "ForceEra", + "modifier": "Default", + "type": { + "plain": "Forcing" + }, + "fallback": "0x00", + "docs": [ + " Mode of era forcing." + ] + }, + { + "name": "SlashRewardFraction", + "modifier": "Default", + "type": { + "plain": "Perbill" + }, + "fallback": "0x00000000", + "docs": [ + " The percentage of the slash that is distributed to reporters.", + "", + " The rest of the slashed value is handled by the `Slash`." + ] + }, + { + "name": "CanceledSlashPayout", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of currency given to reporters of a slash event which was", + " canceled by extraordinary circumstances (e.g. governance)." + ] + }, + { + "name": "UnappliedSlashes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "EraIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " All unapplied slashes that are queued for later." + ] + }, + { + "name": "BondedEras", + "modifier": "Default", + "type": { + "plain": "Vec<(EraIndex,SessionIndex)>" + }, + "fallback": "0x00", + "docs": [ + " A mapping from still-bonded eras to the first session index of that era.", + "", + " Must contains information for eras for the range:", + " `[active_era - bounding_duration; active_era]`" + ] + }, + { + "name": "ValidatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "(Perbill,BalanceOf)", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on validators, mapped by era to the highest slash proportion", + " and slash value of the era." + ] + }, + { + "name": "NominatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "EraIndex", + "key2": "AccountId", + "value": "BalanceOf", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on nominators, mapped by era to the highest slash value of the era." + ] + }, + { + "name": "SlashingSpans", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SlashingSpans", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Slashing spans for stash accounts." + ] + }, + { + "name": "SpanSlash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(AccountId,SpanIndex)", + "value": "SpanRecord", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Records information about the maximum slash of a stash within a slashing span,", + " as well as how much reward has been paid out." + ] + }, + { + "name": "EarliestUnappliedSlash", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The earliest era for which we have a pending, unapplied slash." + ] + }, + { + "name": "CurrentPlannedSession", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The last planned session scheduled by the session pallet.", + "", + " This is basically in sync with the call to [`pallet_session::SessionManager::new_session`]." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x06", + "docs": [ + " True if network has been upgraded to this version.", + " Storage version of the pallet.", + "", + " This is set to v7.0.0 for new networks." + ] + }, + { + "name": "ChillThreshold", + "modifier": "Optional", + "type": { + "plain": "Percent" + }, + "fallback": "0x00", + "docs": [ + " The threshold for when users can start calling `chill_other` for other validators / nominators.", + " The threshold is compared to the actual number of validators / nominators (`CountFor*`) in", + " the system compared to the configured max (`Max*Count`)." + ] + } + ] + }, + "calls": [ + { + "name": "bond", + "args": [ + { + "name": "controller", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " Take the origin account as a stash and lock up `value` of its balance. `controller` will", + " be the account that controls it.", + "", + " `value` must be more than the `minimum_balance` specified by `T::Currency`.", + "", + " The dispatch origin for this call must be _Signed_ by the stash account.", + "", + " Emits `Bonded`.", + " # ", + " - Independent of the arguments. Moderate complexity.", + " - O(1).", + " - Three extra DB entries.", + "", + " NOTE: Two of the storage writes (`Self::bonded`, `Self::payee`) are _never_ cleaned", + " unless the `origin` falls below _existential deposit_ and gets removed as dust.", + " ------------------", + " # " + ] + }, + { + "name": "bond_extra", + "args": [ + { + "name": "max_additional", + "type": "Compact" + } + ], + "docs": [ + " Add some extra amount that have appeared in the stash `free_balance` into the balance up", + " for staking.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " Use this if there are additional funds in your stash account that you wish to bond.", + " Unlike [`bond`](Self::bond) or [`unbond`](Self::unbond) this function does not impose any limitation", + " on the amount that can be added.", + "", + " Emits `Bonded`.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - O(1).", + " # " + ] + }, + { + "name": "unbond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Schedule a portion of the stash to be unlocked ready for transfer out after the bond", + " period ends. If this leaves an amount actively bonded less than", + " T::Currency::minimum_balance(), then it is increased to the full amount.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " Once the unlock period is done, you can call `withdraw_unbonded` to actually move", + " the funds out of management ready for transfer.", + "", + " No more than a limited number of unlocking chunks (see `MAX_UNLOCKING_CHUNKS`)", + " can co-exists at the same time. In that case, [`Call::withdraw_unbonded`] need", + " to be called first to remove some of the chunks (if possible).", + "", + " If a user encounters the `InsufficientBond` error when calling this extrinsic,", + " they should call `chill` first in order to free up their bonded funds.", + "", + " Emits `Unbonded`.", + "", + " See also [`Call::withdraw_unbonded`]." + ] + }, + { + "name": "withdraw_unbonded", + "args": [ + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove any unlocked chunks from the `unlocking` queue from our management.", + "", + " This essentially frees up that balance to be used by the stash account to do", + " whatever it wants.", + "", + " The dispatch origin for this call must be _Signed_ by the controller.", + "", + " Emits `Withdrawn`.", + "", + " See also [`Call::unbond`].", + "", + " # ", + " Complexity O(S) where S is the number of slashing spans to remove", + " NOTE: Weight annotation is the kill scenario, we refund otherwise.", + " # " + ] + }, + { + "name": "validate", + "args": [ + { + "name": "prefs", + "type": "ValidatorPrefs" + } + ], + "docs": [ + " Declare the desire to validate for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash." + ] + }, + { + "name": "nominate", + "args": [ + { + "name": "targets", + "type": "Vec" + } + ], + "docs": [ + " Declare the desire to nominate `targets` for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - The transaction's complexity is proportional to the size of `targets` (N)", + " which is capped at CompactAssignments::LIMIT (MAX_NOMINATIONS).", + " - Both the reads and writes follow a similar pattern.", + " # " + ] + }, + { + "name": "chill", + "args": [], + "docs": [ + " Declare no desire to either validate or nominate.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains one read.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_payee", + "args": [ + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " (Re-)set the payment target for a controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ---------", + " - Weight: O(1)", + " - DB Weight:", + " - Read: Ledger", + " - Write: Payee", + " # " + ] + }, + { + "name": "set_controller", + "args": [ + { + "name": "controller", + "type": "LookupSource" + } + ], + "docs": [ + " (Re-)set the controller of a stash.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " ----------", + " Weight: O(1)", + " DB Weight:", + " - Read: Bonded, Ledger New Controller, Ledger Old Controller", + " - Write: Bonded, Ledger New Controller, Ledger Old Controller", + " # " + ] + }, + { + "name": "set_validator_count", + "args": [ + { + "name": "new", + "type": "Compact" + } + ], + "docs": [ + " Sets the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Weight: O(1)", + " Write: Validator Count", + " # " + ] + }, + { + "name": "increase_validator_count", + "args": [ + { + "name": "additional", + "type": "Compact" + } + ], + "docs": [ + " Increments the ideal number of validators.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Same as [`Self::set_validator_count`].", + " # " + ] + }, + { + "name": "scale_validator_count", + "args": [ + { + "name": "factor", + "type": "Percent" + } + ], + "docs": [ + " Scale up the ideal number of validators by a factor.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " Same as [`Self::set_validator_count`].", + " # " + ] + }, + { + "name": "force_no_eras", + "args": [], + "docs": [ + " Force there to be no new eras indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # Warning", + "", + " The election process starts multiple blocks before the end of the era.", + " Thus the election process may be ongoing when this is called. In this case the", + " election will continue until the next era is triggered.", + "", + " # ", + " - No arguments.", + " - Weight: O(1)", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "force_new_era", + "args": [], + "docs": [ + " Force there to be a new era at the end of the next session. After this, it will be", + " reset to normal (non-forced) behaviour.", + "", + " The dispatch origin must be Root.", + "", + " # Warning", + "", + " The election process starts multiple blocks before the end of the era.", + " If this is called just before a new era is triggered, the election process may not", + " have enough blocks to get a result.", + "", + " # ", + " - No arguments.", + " - Weight: O(1)", + " - Write ForceEra", + " # " + ] + }, + { + "name": "set_invulnerables", + "args": [ + { + "name": "invulnerables", + "type": "Vec" + } + ], + "docs": [ + " Set the validators who cannot be slashed (if any).", + "", + " The dispatch origin must be Root.", + "", + " # ", + " - O(V)", + " - Write: Invulnerables", + " # " + ] + }, + { + "name": "force_unstake", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Force a current staker to become completely unstaked, immediately.", + "", + " The dispatch origin must be Root.", + "", + " # ", + " O(S) where S is the number of slashing spans to be removed", + " Reads: Bonded, Slashing Spans, Account, Locks", + " Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Account, Locks", + " Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "force_new_era_always", + "args": [], + "docs": [ + " Force there to be a new era at the end of sessions indefinitely.", + "", + " The dispatch origin must be Root.", + "", + " # Warning", + "", + " The election process starts multiple blocks before the end of the era.", + " If this is called just before a new era is triggered, the election process may not", + " have enough blocks to get a result.", + "", + " # ", + " - Weight: O(1)", + " - Write: ForceEra", + " # " + ] + }, + { + "name": "cancel_deferred_slash", + "args": [ + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "slash_indices", + "type": "Vec" + } + ], + "docs": [ + " Cancel enactment of a deferred slash.", + "", + " Can be called by the `T::SlashCancelOrigin`.", + "", + " Parameters: era and indices of the slashes for that era to kill.", + "", + " # ", + " Complexity: O(U + S)", + " with U unapplied slashes weighted with U=1000", + " and S is the number of slash indices to be canceled.", + " - Read: Unapplied Slashes", + " - Write: Unapplied Slashes", + " # " + ] + }, + { + "name": "payout_stakers", + "args": [ + { + "name": "validator_stash", + "type": "AccountId" + }, + { + "name": "era", + "type": "EraIndex" + } + ], + "docs": [ + " Pay out all the stakers behind a single validator for a single era.", + "", + " - `validator_stash` is the stash account of the validator. Their nominators, up to", + " `T::MaxNominatorRewardedPerValidator`, will also receive their rewards.", + " - `era` may be any era between `[current_era - history_depth; current_era]`.", + "", + " The origin of this call must be _Signed_. Any account can call this function, even if", + " it is not one of the stakers.", + "", + " # ", + " - Time complexity: at most O(MaxNominatorRewardedPerValidator).", + " - Contains a limited number of reads and writes.", + " -----------", + " N is the Number of payouts for the validator (including the validator)", + " Weight:", + " - Reward Destination Staked: O(N)", + " - Reward Destination Controller (Creating): O(N)", + "", + " NOTE: weights are assuming that payouts are made to alive stash account (Staked).", + " Paying even a dead controller is cheaper weight-wise. We don't do any refunds here.", + " # " + ] + }, + { + "name": "rebond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Rebond a portion of the stash scheduled to be unlocked.", + "", + " The dispatch origin must be signed by the controller.", + "", + " # ", + " - Time complexity: O(L), where L is unlocking chunks", + " - Bounded by `MAX_UNLOCKING_CHUNKS`.", + " - Storage changes: Can't increase storage, only decrease it.", + " # " + ] + }, + { + "name": "set_history_depth", + "args": [ + { + "name": "new_history_depth", + "type": "Compact" + }, + { + "name": "_era_items_deleted", + "type": "Compact" + } + ], + "docs": [ + " Set `HistoryDepth` value. This function will delete any history information", + " when `HistoryDepth` is reduced.", + "", + " Parameters:", + " - `new_history_depth`: The new history depth you would like to set.", + " - `era_items_deleted`: The number of items that will be deleted by this dispatch.", + " This should report all the storage items that will be deleted by clearing old", + " era history. Needed to report an accurate weight for the dispatch. Trusted by", + " `Root` to report an accurate number.", + "", + " Origin must be root.", + "", + " # ", + " - E: Number of history depths removed, i.e. 10 -> 7 = 3", + " - Weight: O(E)", + " - DB Weight:", + " - Reads: Current Era, History Depth", + " - Writes: History Depth", + " - Clear Prefix Each: Era Stakers, EraStakersClipped, ErasValidatorPrefs", + " - Writes Each: ErasValidatorReward, ErasRewardPoints, ErasTotalStake, ErasStartSessionIndex", + " # " + ] + }, + { + "name": "reap_stash", + "args": [ + { + "name": "stash", + "type": "AccountId" + }, + { + "name": "num_slashing_spans", + "type": "u32" + } + ], + "docs": [ + " Remove all data structure concerning a staker/stash once its balance is at the minimum.", + " This is essentially equivalent to `withdraw_unbonded` except it can be called by anyone", + " and the target `stash` must have no funds left beyond the ED.", + "", + " This can be called from any origin.", + "", + " - `stash`: The stash account to reap. Its balance must be zero.", + "", + " # ", + " Complexity: O(S) where S is the number of slashing spans on the account.", + " DB Weight:", + " - Reads: Stash Account, Bonded, Slashing Spans, Locks", + " - Writes: Bonded, Slashing Spans (if S > 0), Ledger, Payee, Validators, Nominators, Stash Account, Locks", + " - Writes Each: SpanSlash * S", + " # " + ] + }, + { + "name": "kick", + "args": [ + { + "name": "who", + "type": "Vec" + } + ], + "docs": [ + " Remove the given nominations from the calling validator.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " - `who`: A list of nominator stash accounts who are nominating this validator which", + " should no longer be nominating this validator.", + "", + " Note: Making this call only makes sense if you first set the validator preferences to", + " block any further nominations." + ] + }, + { + "name": "set_staking_limits", + "args": [ + { + "name": "min_nominator_bond", + "type": "BalanceOf" + }, + { + "name": "min_validator_bond", + "type": "BalanceOf" + }, + { + "name": "max_nominator_count", + "type": "Option" + }, + { + "name": "max_validator_count", + "type": "Option" + }, + { + "name": "threshold", + "type": "Option" + } + ], + "docs": [ + " Update the various staking limits this pallet.", + "", + " * `min_nominator_bond`: The minimum active bond needed to be a nominator.", + " * `min_validator_bond`: The minimum active bond needed to be a validator.", + " * `max_nominator_count`: The max number of users who can be a nominator at once.", + " When set to `None`, no limit is enforced.", + " * `max_validator_count`: The max number of users who can be a validator at once.", + " When set to `None`, no limit is enforced.", + "", + " Origin must be Root to call this function.", + "", + " NOTE: Existing nominators and validators will not be affected by this update.", + " to kick people under the new limits, `chill_other` should be called." + ] + }, + { + "name": "chill_other", + "args": [ + { + "name": "controller", + "type": "AccountId" + } + ], + "docs": [ + " Declare a `controller` to stop participating as either a validator or nominator.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_, but can be called by anyone.", + "", + " If the caller is the same as the controller being targeted, then no further checks are", + " enforced, and this function behaves just like `chill`.", + "", + " If the caller is different than the controller being targeted, the following conditions", + " must be met:", + " * A `ChillThreshold` must be set and checked which defines how close to the max", + " nominators or validators we must reach before users can start chilling one-another.", + " * A `MaxNominatorCount` and `MaxValidatorCount` must be set which is used to determine", + " how close we are to the threshold.", + " * A `MinNominatorBond` and `MinValidatorBond` must be set and checked, which determines", + " if this is a person that should be chilled because they have not met the threshold", + " bond required.", + "", + " This can be helpful if bond requirements are updated, and we need to remove old users", + " who do not satisfy these requirements." + ] + } + ], + "events": [ + { + "name": "EraPaid", + "args": [ + "EraIndex", + "Balance", + "Balance" + ], + "docs": [ + " The era payout has been set; the first balance is the validator-payout; the second is", + " the remainder from the maximum amount of reward.", + " \\[era_index, validator_payout, remainder\\]" + ] + }, + { + "name": "Rewarded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The nominator has been rewarded by this amount. \\[stash, amount\\]" + ] + }, + { + "name": "Slashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " One validator (and its nominators) has been slashed by the given amount.", + " \\[validator, amount\\]" + ] + }, + { + "name": "OldSlashingReportDiscarded", + "args": [ + "SessionIndex" + ], + "docs": [ + " An old slashing report from a prior era was discarded because it could", + " not be processed. \\[session_index\\]" + ] + }, + { + "name": "StakersElected", + "args": [], + "docs": [ + " A new set of stakers was elected." + ] + }, + { + "name": "Bonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has bonded this amount. \\[stash, amount\\]", + "", + " NOTE: This event is only emitted when funds are bonded via a dispatchable. Notably,", + " it will not be emitted for staking rewards when they are added to stake." + ] + }, + { + "name": "Unbonded", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has unbonded this amount. \\[stash, amount\\]" + ] + }, + { + "name": "Withdrawn", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " An account has called `withdraw_unbonded` and removed unbonding chunks worth `Balance`", + " from the unlocking queue. \\[stash, amount\\]" + ] + }, + { + "name": "Kicked", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A nominator has been kicked from a validator. \\[nominator, stash\\]" + ] + }, + { + "name": "StakingElectionFailed", + "args": [], + "docs": [ + " The election failed. No new era is planned." + ] + }, + { + "name": "Chilled", + "args": [ + "AccountId" + ], + "docs": [ + " An account has stopped participating as either a validator or nominator.", + " \\[stash\\]" + ] + }, + { + "name": "PayoutStarted", + "args": [ + "EraIndex", + "AccountId" + ], + "docs": [ + " The stakers' rewards are getting paid. \\[era_index, validator_stash\\]" + ] + } + ], + "constants": [ + { + "name": "SessionsPerEra", + "type": "SessionIndex", + "value": "0x06000000", + "docs": [ + " Number of sessions per era." + ] + }, + { + "name": "BondingDuration", + "type": "EraIndex", + "value": "0xa0020000", + "docs": [ + " Number of eras that staked funds must remain bonded for." + ] + }, + { + "name": "SlashDeferDuration", + "type": "EraIndex", + "value": "0xa8000000", + "docs": [ + " Number of eras that slashes are deferred by, after computation.", + "", + " This should be less than the bonding duration. Set to 0 if slashes", + " should be applied immediately, without opportunity for intervention." + ] + }, + { + "name": "MaxNominatorRewardedPerValidator", + "type": "u32", + "value": "0x00010000", + "docs": [ + " The maximum number of nominators rewarded for each validator.", + "", + " For each validator only the `$MaxNominatorRewardedPerValidator` biggest stakers can claim", + " their reward. This used to limit the i/o cost for the nominator payout." + ] + }, + { + "name": "MaxNominations", + "type": "u32", + "value": "0x10000000", + "docs": [] + } + ], + "errors": [ + { + "name": "NotController", + "docs": [ + " Not a controller account." + ] + }, + { + "name": "NotStash", + "docs": [ + " Not a stash account." + ] + }, + { + "name": "AlreadyBonded", + "docs": [ + " Stash is already bonded." + ] + }, + { + "name": "AlreadyPaired", + "docs": [ + " Controller is already paired." + ] + }, + { + "name": "EmptyTargets", + "docs": [ + " Targets cannot be empty." + ] + }, + { + "name": "DuplicateIndex", + "docs": [ + " Duplicate index." + ] + }, + { + "name": "InvalidSlashIndex", + "docs": [ + " Slash record index out of bounds." + ] + }, + { + "name": "InsufficientBond", + "docs": [ + " Can not bond with value less than minimum required." + ] + }, + { + "name": "NoMoreChunks", + "docs": [ + " Can not schedule more unlock chunks." + ] + }, + { + "name": "NoUnlockChunk", + "docs": [ + " Can not rebond without unlocking chunks." + ] + }, + { + "name": "FundedTarget", + "docs": [ + " Attempting to target a stash that still has funds." + ] + }, + { + "name": "InvalidEraToReward", + "docs": [ + " Invalid era to reward." + ] + }, + { + "name": "InvalidNumberOfNominations", + "docs": [ + " Invalid number of nominations." + ] + }, + { + "name": "NotSortedAndUnique", + "docs": [ + " Items are not sorted and unique." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Rewards for this era have already been claimed for this validator." + ] + }, + { + "name": "IncorrectHistoryDepth", + "docs": [ + " Incorrect previous history depth input provided." + ] + }, + { + "name": "IncorrectSlashingSpans", + "docs": [ + " Incorrect number of slashing spans provided." + ] + }, + { + "name": "BadState", + "docs": [ + " Internal state has become somehow corrupted and the operation cannot continue." + ] + }, + { + "name": "TooManyTargets", + "docs": [ + " Too many nomination targets supplied." + ] + }, + { + "name": "BadTarget", + "docs": [ + " A nomination target was supplied that was blocked or otherwise not a validator." + ] + }, + { + "name": "CannotChillOther", + "docs": [ + " The user has enough bond and thus cannot be chilled forcefully by an external person." + ] + }, + { + "name": "TooManyNominators", + "docs": [ + " There are too many nominators in the system. Governance needs to adjust the staking settings", + " to keep things safe for the runtime." + ] + }, + { + "name": "TooManyValidators", + "docs": [ + " There are too many validators in the system. Governance needs to adjust the staking settings", + " to keep things safe for the runtime." + ] + } + ], + "index": 9 + }, + { + "name": "Session", + "storage": { + "prefix": "Session", + "items": [ + { + "name": "Validators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of validators." + ] + }, + { + "name": "CurrentIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Current index of the session." + ] + }, + { + "name": "QueuedChanged", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the underlying economic identities or weighting behind the validators", + " has changed in the queued validator set." + ] + }, + { + "name": "QueuedKeys", + "modifier": "Default", + "type": { + "plain": "Vec<(ValidatorId,Keys)>" + }, + "fallback": "0x00", + "docs": [ + " The queued keys for the next session. When the next session begins, these keys", + " will be used to determine the validator's session keys." + ] + }, + { + "name": "DisabledValidators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Indices of disabled validators.", + "", + " The set is cleared when `on_session_ending` returns a new set of identities." + ] + }, + { + "name": "NextKeys", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ValidatorId", + "value": "Keys", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The next session keys for a validator." + ] + }, + { + "name": "KeyOwner", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "(KeyTypeId,Bytes)", + "value": "ValidatorId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The owner of a key. The key is the `KeyTypeId` + the encoded key." + ] + } + ] + }, + "calls": [ + { + "name": "set_keys", + "args": [ + { + "name": "keys", + "type": "Keys" + }, + { + "name": "proof", + "type": "Bytes" + } + ], + "docs": [ + " Sets the session key(s) of the function caller to `keys`.", + " Allows an account to set its session key prior to becoming a validator.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)`", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `origin account`, `T::ValidatorIdOf`, `NextKeys`", + " - DbWrites: `origin account`, `NextKeys`", + " - DbReads per key id: `KeyOwner`", + " - DbWrites per key id: `KeyOwner`", + " # " + ] + }, + { + "name": "purge_keys", + "args": [], + "docs": [ + " Removes any session key(s) of the function caller.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - Complexity: `O(1)` in number of key types.", + " Actual cost depends on the number of length of `T::Keys::key_ids()` which is fixed.", + " - DbReads: `T::ValidatorIdOf`, `NextKeys`, `origin account`", + " - DbWrites: `NextKeys`, `origin account`", + " - DbWrites per key id: `KeyOwner`", + " # " + ] + } + ], + "events": [ + { + "name": "NewSession", + "args": [ + "SessionIndex" + ], + "docs": [ + " New session has happened. Note that the argument is the \\[session_index\\], not the block", + " number as the type might suggest." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InvalidProof", + "docs": [ + " Invalid ownership proof." + ] + }, + { + "name": "NoAssociatedValidatorId", + "docs": [ + " No associated validator ID for account." + ] + }, + { + "name": "DuplicatedKey", + "docs": [ + " Registered duplicate key." + ] + }, + { + "name": "NoKeys", + "docs": [ + " No keys are associated with this account." + ] + }, + { + "name": "NoAccount", + "docs": [ + " Key setting account is not live, so it's impossible to associate keys." + ] + } + ], + "index": 10 + }, + { + "name": "Democracy", + "storage": { + "prefix": "Democracy", + "items": [ + { + "name": "PublicPropCount", + "modifier": "Default", + "type": { + "plain": "PropIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of (public) proposals that have been made so far." + ] + }, + { + "name": "PublicProps", + "modifier": "Default", + "type": { + "plain": "Vec<(PropIndex,Hash,AccountId)>" + }, + "fallback": "0x00", + "docs": [ + " The public proposals. Unsorted. The second item is the proposal's hash." + ] + }, + { + "name": "DepositOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "PropIndex", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Those who have locked a deposit.", + "", + " TWOX-NOTE: Safe, as increasing integer keys are safe." + ] + }, + { + "name": "Preimages", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "PreimageStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map of hashes to the proposal preimage, along with who registered it and their deposit.", + " The block number is the block at which it was deposited." + ] + }, + { + "name": "ReferendumCount", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free referendum index, aka the number of referenda started so far." + ] + }, + { + "name": "LowestUnbaked", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The lowest referendum index representing an unbaked referendum. Equal to", + " `ReferendumCount` if there isn't a unbaked referendum." + ] + }, + { + "name": "ReferendumInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReferendumIndex", + "value": "ReferendumInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information concerning any given referendum.", + "", + " TWOX-NOTE: SAFE as indexes are not under an attacker’s control." + ] + }, + { + "name": "VotingOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Voting", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " All votes for a particular voter. We store the balance for the number of votes that we", + " have recorded. The second item is the total amount of delegations, that will be added.", + "", + " TWOX-NOTE: SAFE as `AccountId`s are crypto hashes anyway." + ] + }, + { + "name": "Locks", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "BlockNumber", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Accounts for which there are locks in action which may be removed at some point in the", + " future. The value is the block number at which the lock expires and may be removed.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "LastTabledWasExternal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the last referendum tabled was submitted externally. False if it was a public", + " proposal." + ] + }, + { + "name": "NextExternal", + "modifier": "Optional", + "type": { + "plain": "(Hash,VoteThreshold)" + }, + "fallback": "0x00", + "docs": [ + " The referendum to be tabled whenever it would be valid to table an external proposal.", + " This happens when a referendum needs to be tabled and one of two conditions are met:", + " - `LastTabledWasExternal` is `false`; or", + " - `PublicProps` is empty." + ] + }, + { + "name": "Blacklist", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "(BlockNumber,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A record of who vetoed what. Maps proposal hash to a possible existent block number", + " (until when it may not be resubmitted) and who vetoed it." + ] + }, + { + "name": "Cancellations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Record of all proposals that have been subject to emergency cancellation." + ] + }, + { + "name": "StorageVersion", + "modifier": "Optional", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " The dispatch origin of this call must be _Signed_ and the sender must", + " have funds to cover the deposit.", + "", + " - `proposal_hash`: The hash of the proposal preimage.", + " - `value`: The amount of deposit (must be at least `MinimumDeposit`).", + "", + " Emits `Proposed`.", + "", + " Weight: `O(p)`" + ] + }, + { + "name": "second", + "args": [ + { + "name": "proposal", + "type": "Compact" + }, + { + "name": "seconds_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Signals agreement with a particular proposal.", + "", + " The dispatch origin of this call must be _Signed_ and the sender", + " must have funds to cover the deposit, equal to the original deposit.", + "", + " - `proposal`: The index of the proposal to second.", + " - `seconds_upper_bound`: an upper bound on the current number of seconds on this", + " proposal. Extrinsic is weighted according to this value with no refund.", + "", + " Weight: `O(S)` where S is the number of seconds a proposal already has." + ] + }, + { + "name": "vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "AccountVote" + } + ], + "docs": [ + " Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;", + " otherwise it is a vote to keep the status quo.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `ref_index`: The index of the referendum to vote for.", + " - `vote`: The vote configuration.", + "", + " Weight: `O(R)` where R is the number of referendums the voter has voted on." + ] + }, + { + "name": "emergency_cancel", + "args": [ + { + "name": "ref_index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Schedule an emergency cancellation of a referendum. Cannot happen twice to the same", + " referendum.", + "", + " The dispatch origin of this call must be `CancellationOrigin`.", + "", + " -`ref_index`: The index of the referendum to cancel.", + "", + " Weight: `O(1)`." + ] + }, + { + "name": "external_propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a referendum to be tabled once it is legal to schedule an external", + " referendum.", + "", + " The dispatch origin of this call must be `ExternalOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Weight: `O(V)` with V number of vetoers in the blacklist of proposal.", + " Decoding vec of length V. Charged as maximum" + ] + }, + { + "name": "external_propose_majority", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a majority-carries referendum to be tabled next once it is legal to schedule", + " an external referendum.", + "", + " The dispatch of this call must be `ExternalMajorityOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "external_propose_default", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a negative-turnout-bias referendum to be tabled next once it is legal to", + " schedule an external referendum.", + "", + " The dispatch of this call must be `ExternalDefaultOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "fast_track", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "voting_period", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Schedule the currently externally-proposed majority-carries referendum to be tabled", + " immediately. If there is no externally-proposed referendum currently, or if there is one", + " but it is not a majority-carries referendum then it fails.", + "", + " The dispatch of this call must be `FastTrackOrigin`.", + "", + " - `proposal_hash`: The hash of the current external proposal.", + " - `voting_period`: The period that is allowed for voting on this proposal. Increased to", + " `FastTrackVotingPeriod` if too low.", + " - `delay`: The number of block after voting has ended in approval and this should be", + " enacted. This doesn't have a minimum amount.", + "", + " Emits `Started`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "veto_external", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Veto and blacklist the external proposal hash.", + "", + " The dispatch origin of this call must be `VetoOrigin`.", + "", + " - `proposal_hash`: The preimage hash of the proposal to veto and blacklist.", + "", + " Emits `Vetoed`.", + "", + " Weight: `O(V + log(V))` where V is number of `existing vetoers`" + ] + }, + { + "name": "cancel_referendum", + "args": [ + { + "name": "ref_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a referendum.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `ref_index`: The index of the referendum to cancel.", + "", + " # Weight: `O(1)`." + ] + }, + { + "name": "cancel_queued", + "args": [ + { + "name": "which", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Cancel a proposal queued for enactment.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " - `which`: The index of the referendum to cancel.", + "", + " Weight: `O(D)` where `D` is the items in the dispatch queue. Weighted as `D = 10`." + ] + }, + { + "name": "delegate", + "args": [ + { + "name": "to", + "type": "AccountId" + }, + { + "name": "conviction", + "type": "Conviction" + }, + { + "name": "balance", + "type": "BalanceOf" + } + ], + "docs": [ + " Delegate the voting power (with some given conviction) of the sending account.", + "", + " The balance delegated is locked for as long as it's delegated, and thereafter for the", + " time appropriate for the conviction's lock period.", + "", + " The dispatch origin of this call must be _Signed_, and the signing account must either:", + " - be delegating already; or", + " - have no voting activity (if there is, then it will need to be removed/consolidated", + " through `reap_vote` or `unvote`).", + "", + " - `to`: The account whose voting the `target` account's voting power will follow.", + " - `conviction`: The conviction that will be attached to the delegated votes. When the", + " account is undelegated, the funds will be locked for the corresponding period.", + " - `balance`: The amount of the account's balance to be used in delegating. This must", + " not be more than the account's current balance.", + "", + " Emits `Delegated`.", + "", + " Weight: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes." + ] + }, + { + "name": "undelegate", + "args": [], + "docs": [ + " Undelegate the voting power of the sending account.", + "", + " Tokens may be unlocked following once an amount of time consistent with the lock period", + " of the conviction with which the delegation was issued.", + "", + " The dispatch origin of this call must be _Signed_ and the signing account must be", + " currently delegating.", + "", + " Emits `Undelegated`.", + "", + " Weight: `O(R)` where R is the number of referendums the voter delegating to has", + " voted on. Weight is charged as if maximum votes." + ] + }, + { + "name": "clear_public_proposals", + "args": [], + "docs": [ + " Clears all public proposals.", + "", + " The dispatch origin of this call must be _Root_.", + "", + " Weight: `O(1)`." + ] + }, + { + "name": "note_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This doesn't require the proposal to be", + " in the dispatch queue but does require a deposit, returned once enacted.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " Weight: `O(E)` with E size of `encoded_proposal` (protected by a required deposit)." + ] + }, + { + "name": "note_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "note_imminent_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This requires the proposal to be", + " in the dispatch queue. No deposit is needed. When this call is successful, i.e.", + " the preimage has not been uploaded before and matches some imminent proposal,", + " no fee is paid.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `encoded_proposal`: The preimage of a proposal.", + "", + " Emits `PreimageNoted`.", + "", + " Weight: `O(E)` with E size of `encoded_proposal` (protected by a required deposit)." + ] + }, + { + "name": "note_imminent_preimage_operational", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Same as `note_imminent_preimage` but origin is `OperationalPreimageOrigin`." + ] + }, + { + "name": "reap_preimage", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "proposal_len_upper_bound", + "type": "Compact" + } + ], + "docs": [ + " Remove an expired proposal preimage and collect the deposit.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `proposal_hash`: The preimage hash of a proposal.", + " - `proposal_length_upper_bound`: an upper bound on length of the proposal.", + " Extrinsic is weighted according to this value with no refund.", + "", + " This will only work after `VotingPeriod` blocks from the time that the preimage was", + " noted, if it's the same account doing it. If it's a different account, then it'll only", + " work an additional `EnactmentPeriod` later.", + "", + " Emits `PreimageReaped`.", + "", + " Weight: `O(D)` where D is length of proposal." + ] + }, + { + "name": "unlock", + "args": [ + { + "name": "target", + "type": "AccountId" + } + ], + "docs": [ + " Unlock tokens that have an expired lock.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account to remove the lock on.", + "", + " Weight: `O(R)` with R number of vote of target." + ] + }, + { + "name": "remove_vote", + "args": [ + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If:", + " - the referendum was cancelled, or", + " - the referendum is ongoing, or", + " - the referendum has ended such that", + " - the vote of the account was in opposition to the result; or", + " - there was no conviction to the account's vote; or", + " - the account made a split vote", + " ...then the vote is removed cleanly and a following call to `unlock` may result in more", + " funds being available.", + "", + " If, however, the referendum has ended and:", + " - it finished corresponding to the vote of the account, and", + " - the account made a standard vote with conviction, and", + " - the lock period of the conviction is not over", + " ...then the lock will be aggregated into the overall account's lock, which may involve", + " *overlocking* (where the two locks are combined into a single lock that is the maximum", + " of both the amount locked and the time is it locked for).", + "", + " The dispatch origin of this call must be _Signed_, and the signer must have a vote", + " registered for referendum `index`.", + "", + " - `index`: The index of referendum of the vote to be removed.", + "", + " Weight: `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote." + ] + }, + { + "name": "remove_other_vote", + "args": [ + { + "name": "target", + "type": "AccountId" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Remove a vote for a referendum.", + "", + " If the `target` is equal to the signer, then this function is exactly equivalent to", + " `remove_vote`. If not equal to the signer, then the vote must have expired,", + " either because the referendum was cancelled, because the voter lost the referendum or", + " because the conviction period is over.", + "", + " The dispatch origin of this call must be _Signed_.", + "", + " - `target`: The account of the vote to be removed; this account must have voted for", + " referendum `index`.", + " - `index`: The index of referendum of the vote to be removed.", + "", + " Weight: `O(R + log R)` where R is the number of referenda that `target` has voted on.", + " Weight is calculated for the maximum number of vote." + ] + }, + { + "name": "enact_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Enact a proposal from a referendum. For now we just make the weight be the maximum." + ] + }, + { + "name": "blacklist", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "maybe_ref_index", + "type": "Option" + } + ], + "docs": [ + " Permanently place a proposal into the blacklist. This prevents it from ever being", + " proposed again.", + "", + " If called on a queued public or external proposal, then this will result in it being", + " removed. If the `ref_index` supplied is an active referendum with the proposal hash,", + " then it will be cancelled.", + "", + " The dispatch origin of this call must be `BlacklistOrigin`.", + "", + " - `proposal_hash`: The proposal hash to blacklist permanently.", + " - `ref_index`: An ongoing referendum whose hash is `proposal_hash`, which will be", + " cancelled.", + "", + " Weight: `O(p)` (though as this is an high-privilege dispatch, we assume it has a", + " reasonable value)." + ] + }, + { + "name": "cancel_proposal", + "args": [ + { + "name": "prop_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a proposal.", + "", + " The dispatch origin of this call must be `CancelProposalOrigin`.", + "", + " - `prop_index`: The index of the proposal to cancel.", + "", + " Weight: `O(p)` where `p = PublicProps::::decode_len()`" + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "PropIndex", + "Balance" + ], + "docs": [ + " A motion has been proposed by a public account. \\[proposal_index, deposit\\]" + ] + }, + { + "name": "Tabled", + "args": [ + "PropIndex", + "Balance", + "Vec" + ], + "docs": [ + " A public proposal has been tabled for referendum vote. \\[proposal_index, deposit, depositors\\]" + ] + }, + { + "name": "ExternalTabled", + "args": [], + "docs": [ + " An external proposal has been tabled." + ] + }, + { + "name": "Started", + "args": [ + "ReferendumIndex", + "VoteThreshold" + ], + "docs": [ + " A referendum has begun. \\[ref_index, threshold\\]" + ] + }, + { + "name": "Passed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been approved by referendum. \\[ref_index\\]" + ] + }, + { + "name": "NotPassed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been rejected by referendum. \\[ref_index\\]" + ] + }, + { + "name": "Cancelled", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A referendum has been cancelled. \\[ref_index\\]" + ] + }, + { + "name": "Executed", + "args": [ + "ReferendumIndex", + "DispatchResult" + ], + "docs": [ + " A proposal has been enacted. \\[ref_index, result\\]" + ] + }, + { + "name": "Delegated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " An account has delegated their vote to another account. \\[who, target\\]" + ] + }, + { + "name": "Undelegated", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has cancelled a previous delegation operation." + ] + }, + { + "name": "Vetoed", + "args": [ + "AccountId", + "Hash", + "BlockNumber" + ], + "docs": [ + " An external proposal has been vetoed. \\[who, proposal_hash, until\\]" + ] + }, + { + "name": "PreimageNoted", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal's preimage was noted, and the deposit taken. \\[proposal_hash, who, deposit\\]" + ] + }, + { + "name": "PreimageUsed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal preimage was removed and used (the deposit was returned).", + " \\[proposal_hash, provider, deposit\\]" + ] + }, + { + "name": "PreimageInvalid", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was invalid.", + " \\[proposal_hash, ref_index\\]" + ] + }, + { + "name": "PreimageMissing", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was missing.", + " \\[proposal_hash, ref_index\\]" + ] + }, + { + "name": "PreimageReaped", + "args": [ + "Hash", + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A registered preimage was removed and the deposit collected by the reaper.", + " \\[proposal_hash, provider, deposit, reaper\\]" + ] + }, + { + "name": "Unlocked", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has been unlocked successfully." + ] + }, + { + "name": "Blacklisted", + "args": [ + "Hash" + ], + "docs": [ + " A proposal \\[hash\\] has been blacklisted permanently." + ] + } + ], + "constants": [ + { + "name": "EnactmentPeriod", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The minimum period of locking and the period between a proposal being approved and enacted.", + "", + " It should generally be a little more than the unstake period to ensure that", + " voting stakers have an opportunity to remove themselves from the system in the case where", + " they are on the losing side of a vote." + ] + }, + { + "name": "LaunchPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) new public referenda are launched." + ] + }, + { + "name": "VotingPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) to check for new votes." + ] + }, + { + "name": "MinimumDeposit", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be used as a deposit for a public referendum proposal." + ] + }, + { + "name": "InstantAllowed", + "type": "bool", + "value": "0x01", + "docs": [ + " Indicator for whether an emergency origin is even allowed to happen. Some chains may want", + " to set this permanently to `false`, others may want to condition it on things such as", + " an upgrade having happened recently." + ] + }, + { + "name": "FastTrackVotingPeriod", + "type": "BlockNumber", + "value": "0x80510100", + "docs": [ + " Minimum voting period allowed for a fast-track referendum." + ] + }, + { + "name": "CooloffPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " Period in blocks where an external proposal may not be re-submitted after being vetoed." + ] + }, + { + "name": "PreimageByteDeposit", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of balance that must be deposited per byte of preimage stored." + ] + }, + { + "name": "MaxVotes", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of votes for an account.", + "", + " Also used to compute weight, an overly big value can", + " lead to extrinsic with very big weight: see `delegate` for instance." + ] + }, + { + "name": "MaxProposals", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of public proposals that can exist at any time." + ] + } + ], + "errors": [ + { + "name": "ValueLow", + "docs": [ + " Value too low" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal does not exist" + ] + }, + { + "name": "BadIndex", + "docs": [ + " Unknown index" + ] + }, + { + "name": "AlreadyCanceled", + "docs": [ + " Cannot cancel the same proposal twice" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Proposal already made" + ] + }, + { + "name": "ProposalBlacklisted", + "docs": [ + " Proposal still blacklisted" + ] + }, + { + "name": "NotSimpleMajority", + "docs": [ + " Next external proposal not simple majority" + ] + }, + { + "name": "InvalidHash", + "docs": [ + " Invalid hash" + ] + }, + { + "name": "NoProposal", + "docs": [ + " No external proposal" + ] + }, + { + "name": "AlreadyVetoed", + "docs": [ + " Identity may not veto a proposal twice" + ] + }, + { + "name": "NotDelegated", + "docs": [ + " Not delegated" + ] + }, + { + "name": "DuplicatePreimage", + "docs": [ + " Preimage already noted" + ] + }, + { + "name": "NotImminent", + "docs": [ + " Not imminent" + ] + }, + { + "name": "TooEarly", + "docs": [ + " Too early" + ] + }, + { + "name": "Imminent", + "docs": [ + " Imminent" + ] + }, + { + "name": "PreimageMissing", + "docs": [ + " Preimage not found" + ] + }, + { + "name": "ReferendumInvalid", + "docs": [ + " Vote given for invalid referendum" + ] + }, + { + "name": "PreimageInvalid", + "docs": [ + " Invalid preimage" + ] + }, + { + "name": "NoneWaiting", + "docs": [ + " No proposals waiting" + ] + }, + { + "name": "NotLocked", + "docs": [ + " The target account does not have a lock." + ] + }, + { + "name": "NotExpired", + "docs": [ + " The lock on the account to be unlocked has not yet expired." + ] + }, + { + "name": "NotVoter", + "docs": [ + " The given account did not vote on the referendum." + ] + }, + { + "name": "NoPermission", + "docs": [ + " The actor has no permission to conduct the action." + ] + }, + { + "name": "AlreadyDelegating", + "docs": [ + " The account is already delegating." + ] + }, + { + "name": "InsufficientFunds", + "docs": [ + " Too high a balance was provided that the account cannot afford." + ] + }, + { + "name": "NotDelegating", + "docs": [ + " The account is not currently delegating." + ] + }, + { + "name": "VotesExist", + "docs": [ + " The account currently has votes attached to it and the operation cannot succeed until", + " these are removed, either through `unvote` or `reap_vote`." + ] + }, + { + "name": "InstantNotAllowed", + "docs": [ + " The instant referendum origin is currently disallowed." + ] + }, + { + "name": "Nonsense", + "docs": [ + " Delegation to oneself makes no sense." + ] + }, + { + "name": "WrongUpperBound", + "docs": [ + " Invalid upper bound." + ] + }, + { + "name": "MaxVotesReached", + "docs": [ + " Maximum number of votes reached." + ] + }, + { + "name": "InvalidWitness", + "docs": [ + " The provided witness data is wrong." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " Maximum number of proposals reached." + ] + } + ], + "index": 11 + }, + { + "name": "Council", + "storage": { + "prefix": "Instance1Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The prime member that helps determine the default vote behavior in case of absentations." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " Transaction fees will be waived if the member is voting on any particular proposal", + " for the first time and the call is successful. Subsequent vote changes will charge a fee.", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " If the close operation completes successfully with disapproval, the transaction fee will", + " be waived. Otherwise execution of the approved operation will be charged to the caller.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " \\[account, proposal_index, proposal_hash, threshold\\]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " \\[account, proposal_hash, voted, yes, no\\]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " \\[proposal_hash, yes, no\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ], + "index": 12 + }, + { + "name": "TechnicalCommittee", + "storage": { + "prefix": "Instance2Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The prime member that helps determine the default vote behavior in case of absentations." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + }, + { + "name": "prime", + "type": "Option" + }, + { + "name": "old_count", + "type": "MemberCount" + } + ], + "docs": [ + " Set the collective's membership.", + "", + " - `new_members`: The new member list. Be nice to the chain and provide it sorted.", + " - `prime`: The prime member whose vote sets the default.", + " - `old_count`: The upper bound for the previous number of members in storage.", + " Used for weight estimation.", + "", + " Requires root origin.", + "", + " NOTE: Does not enforce the expected `MaxMembers` limit on the amount of members, but", + " the weight estimations rely on it to estimate dispatchable weight.", + "", + " # ", + " ## Weight", + " - `O(MP + N)` where:", + " - `M` old-members-count (code- and governance-bounded)", + " - `N` new-members-count (code- and governance-bounded)", + " - `P` proposals-count (code-bounded)", + " - DB:", + " - 1 storage mutation (codec `O(M)` read, `O(N)` write) for reading and writing the members", + " - 1 storage read (codec `O(P)`) for reading the proposals", + " - `P` storage mutations (codec `O(M)`) for updating the votes for each proposal", + " - 1 storage write (codec `O(1)`) for deleting the old `prime` and setting the new one", + " # " + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective.", + "", + " # ", + " ## Weight", + " - `O(M + P)` where `M` members-count (code-bounded) and `P` complexity of dispatching `proposal`", + " - DB: 1 read (codec `O(M)`) + DB access of `proposal`", + " - 1 event", + " # " + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Add a new proposal to either be voted on or executed directly.", + "", + " Requires the sender to be member.", + "", + " `threshold` determines whether `proposal` is executed directly (`threshold < 2`)", + " or put up for voting.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1)` or `O(B + M + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - branching is influenced by `threshold` where:", + " - `P1` is proposal execution complexity (`threshold < 2`)", + " - `P2` is proposals-count (code-bounded) (`threshold >= 2`)", + " - DB:", + " - 1 storage read `is_member` (codec `O(M)`)", + " - 1 storage read `ProposalOf::contains_key` (codec `O(1)`)", + " - DB accesses influenced by `threshold`:", + " - EITHER storage accesses done by `proposal` (`threshold < 2`)", + " - OR proposal insertion (`threshold <= 2`)", + " - 1 storage mutation `Proposals` (codec `O(P2)`)", + " - 1 storage mutation `ProposalCount` (codec `O(1)`)", + " - 1 storage write `ProposalOf` (codec `O(B)`)", + " - 1 storage write `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " Add an aye or nay vote for the sender to the given proposal.", + "", + " Requires the sender to be a member.", + "", + " Transaction fees will be waived if the member is voting on any particular proposal", + " for the first time and the call is successful. Subsequent vote changes will charge a fee.", + " # ", + " ## Weight", + " - `O(M)` where `M` is members-count (code- and governance-bounded)", + " - DB:", + " - 1 storage read `Members` (codec `O(M)`)", + " - 1 storage mutation `Voting` (codec `O(M)`)", + " - 1 event", + " # " + ] + }, + { + "name": "close", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "proposal_weight_bound", + "type": "Compact" + }, + { + "name": "length_bound", + "type": "Compact" + } + ], + "docs": [ + " Close a vote that is either approved, disapproved or whose voting period has ended.", + "", + " May be called by any signed account in order to finish voting and close the proposal.", + "", + " If called before the end of the voting period it will only close the vote if it is", + " has enough votes to be approved or disapproved.", + "", + " If called after the end of the voting period abstentions are counted as rejections", + " unless there is a prime member set and the prime member cast an approval.", + "", + " If the close operation completes successfully with disapproval, the transaction fee will", + " be waived. Otherwise execution of the approved operation will be charged to the caller.", + "", + " + `proposal_weight_bound`: The maximum amount of weight consumed by executing the closed proposal.", + " + `length_bound`: The upper bound for the length of the proposal in storage. Checked via", + " `storage::read` so it is `size_of::() == 4` larger than the pure length.", + "", + " # ", + " ## Weight", + " - `O(B + M + P1 + P2)` where:", + " - `B` is `proposal` size in bytes (length-fee-bounded)", + " - `M` is members-count (code- and governance-bounded)", + " - `P1` is the complexity of `proposal` preimage.", + " - `P2` is proposal-count (code-bounded)", + " - DB:", + " - 2 storage reads (`Members`: codec `O(M)`, `Prime`: codec `O(1)`)", + " - 3 mutations (`Voting`: codec `O(M)`, `ProposalOf`: codec `O(B)`, `Proposals`: codec `O(P2)`)", + " - any mutations done while executing `proposal` (`P1`)", + " - up to 3 events", + " # " + ] + }, + { + "name": "disapprove_proposal", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Disapprove a proposal, close, and remove it from the system, regardless of its current state.", + "", + " Must be called by the Root origin.", + "", + " Parameters:", + " * `proposal_hash`: The hash of the proposal that should be disapproved.", + "", + " # ", + " Complexity: O(P) where P is the number of max proposals", + " DB Weight:", + " * Reads: Proposals", + " * Writes: Voting, Proposals, ProposalOf", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`).", + " \\[account, proposal_index, proposal_hash, threshold\\]" + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`).", + " \\[account, proposal_hash, voted, yes, no\\]" + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold.", + " \\[proposal_hash\\]" + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A motion was executed; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "DispatchResult" + ], + "docs": [ + " A single member did some action; result will be `Ok` if it returned without error.", + " \\[proposal_hash, result\\]" + ] + }, + { + "name": "Closed", + "args": [ + "Hash", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A proposal was closed because its threshold was reached or after its duration was up.", + " \\[proposal_hash, yes, no\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "NotMember", + "docs": [ + " Account is not a member" + ] + }, + { + "name": "DuplicateProposal", + "docs": [ + " Duplicate proposals not allowed" + ] + }, + { + "name": "ProposalMissing", + "docs": [ + " Proposal must exist" + ] + }, + { + "name": "WrongIndex", + "docs": [ + " Mismatched index" + ] + }, + { + "name": "DuplicateVote", + "docs": [ + " Duplicate vote ignored" + ] + }, + { + "name": "AlreadyInitialized", + "docs": [ + " Members are already initialized!" + ] + }, + { + "name": "TooEarly", + "docs": [ + " The close call was made too early, before the end of the voting." + ] + }, + { + "name": "TooManyProposals", + "docs": [ + " There can only be a maximum of `MaxProposals` active proposals." + ] + }, + { + "name": "WrongProposalWeight", + "docs": [ + " The given weight bound for the proposal was too low." + ] + }, + { + "name": "WrongProposalLength", + "docs": [ + " The given length bound for the proposal was too low." + ] + } + ], + "index": 13 + }, + { + "name": "Elections", + "storage": { + "prefix": "Elections", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current elected members.", + "", + " Invariant: Always sorted based on account id." + ] + }, + { + "name": "RunnersUp", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current reserved runners-up.", + "", + " Invariant: Always sorted based on rank (worse to best). Upon removal of a member, the", + " last (i.e. _best_) runner-up will be replaced." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The present candidate list. A current member or runner-up can never enter this vector", + " and is always implicitly assumed to be a candidate.", + "", + " Second element is the deposit.", + "", + " Invariant: Always sorted based on account id." + ] + }, + { + "name": "ElectionRounds", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The total number of vote rounds that have happened, excluding the upcoming one." + ] + }, + { + "name": "Voting", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Voter", + "linked": false + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Votes and locked stake of a particular voter.", + "", + " TWOX-NOTE: SAFE as `AccountId` is a crypto hash." + ] + } + ] + }, + "calls": [ + { + "name": "vote", + "args": [ + { + "name": "votes", + "type": "Vec" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Vote for a set of candidates for the upcoming round of election. This can be called to", + " set the initial votes, or update already existing votes.", + "", + " Upon initial voting, `value` units of `who`'s balance is locked and a deposit amount is", + " reserved. The deposit is based on the number of votes and can be updated over time.", + "", + " The `votes` should:", + " - not be empty.", + " - be less than the number of possible candidates. Note that all current members and", + " runners-up are also automatically candidates for the next round.", + "", + " If `value` is more than `who`'s total balance, then the maximum of the two is used.", + "", + " The dispatch origin of this call must be signed.", + "", + " ### Warning", + "", + " It is the responsibility of the caller to **NOT** place all of their balance into the", + " lock and keep some for further operations.", + "", + " # ", + " We assume the maximum weight among all 3 cases: vote_equal, vote_more and vote_less.", + " # " + ] + }, + { + "name": "remove_voter", + "args": [], + "docs": [ + " Remove `origin` as a voter.", + "", + " This removes the lock and returns the deposit.", + "", + " The dispatch origin of this call must be signed and be a voter." + ] + }, + { + "name": "submit_candidacy", + "args": [ + { + "name": "candidate_count", + "type": "Compact" + } + ], + "docs": [ + " Submit oneself for candidacy. A fixed amount of deposit is recorded.", + "", + " All candidates are wiped at the end of the term. They either become a member/runner-up,", + " or leave the system while their deposit is slashed.", + "", + " The dispatch origin of this call must be signed.", + "", + " ### Warning", + "", + " Even if a candidate ends up being a member, they must call [`Call::renounce_candidacy`]", + " to get their deposit back. Losing the spot in an election will always lead to a slash.", + "", + " # ", + " The number of current candidates must be provided as witness data.", + " # " + ] + }, + { + "name": "renounce_candidacy", + "args": [ + { + "name": "renouncing", + "type": "Renouncing" + } + ], + "docs": [ + " Renounce one's intention to be a candidate for the next election round. 3 potential", + " outcomes exist:", + "", + " - `origin` is a candidate and not elected in any set. In this case, the deposit is", + " unreserved, returned and origin is removed as a candidate.", + " - `origin` is a current runner-up. In this case, the deposit is unreserved, returned and", + " origin is removed as a runner-up.", + " - `origin` is a current member. In this case, the deposit is unreserved and origin is", + " removed as a member, consequently not being a candidate for the next round anymore.", + " Similar to [`remove_member`](Self::remove_member), if replacement runners exists,", + " they are immediately used. If the prime is renouncing, then no prime will exist until", + " the next round.", + "", + " The dispatch origin of this call must be signed, and have one of the above roles.", + "", + " # ", + " The type of renouncing must be provided as witness data.", + " # " + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "has_replacement", + "type": "bool" + } + ], + "docs": [ + " Remove a particular member from the set. This is effective immediately and the bond of", + " the outgoing member is slashed.", + "", + " If a runner-up is available, then the best runner-up will be removed and replaces the", + " outgoing member. Otherwise, a new phragmen election is started.", + "", + " The dispatch origin of this call must be root.", + "", + " Note that this does not affect the designated block number of the next election.", + "", + " # ", + " If we have a replacement, we use a small weight. Else, since this is a root call and", + " will go into phragmen, we assume full block for now.", + " # " + ] + }, + { + "name": "clean_defunct_voters", + "args": [ + { + "name": "_num_voters", + "type": "u32" + }, + { + "name": "_num_defunct", + "type": "u32" + } + ], + "docs": [ + " Clean all voters who are defunct (i.e. they do not serve any purpose at all). The", + " deposit of the removed voters are returned.", + "", + " This is an root function to be used only for cleaning the state.", + "", + " The dispatch origin of this call must be root.", + "", + " # ", + " The total number of voters and those that are defunct must be provided as witness data.", + " # " + ] + } + ], + "events": [ + { + "name": "NewTerm", + "args": [ + "Vec<(AccountId,Balance)>" + ], + "docs": [ + " A new term with \\[new_members\\]. This indicates that enough candidates existed to run", + " the election, not that enough have has been elected. The inner value must be examined", + " for this purpose. A `NewTerm(\\[\\])` indicates that some candidates got their bond", + " slashed and none were elected, whilst `EmptyTerm` means that no candidates existed to", + " begin with." + ] + }, + { + "name": "EmptyTerm", + "args": [], + "docs": [ + " No (or not enough) candidates existed for this round. This is different from", + " `NewTerm(\\[\\])`. See the description of `NewTerm`." + ] + }, + { + "name": "ElectionError", + "args": [], + "docs": [ + " Internal error happened while trying to perform election." + ] + }, + { + "name": "MemberKicked", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been removed. This should always be followed by either `NewTerm` or", + " `EmptyTerm`." + ] + }, + { + "name": "Renounced", + "args": [ + "AccountId" + ], + "docs": [ + " Someone has renounced their candidacy." + ] + }, + { + "name": "CandidateSlashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A \\[candidate\\] was slashed by \\[amount\\] due to failing to obtain a seat as member or", + " runner-up.", + "", + " Note that old members and runners-up are also candidates." + ] + }, + { + "name": "SeatHolderSlashed", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A \\[seat holder\\] was slashed by \\[amount\\] by being forcefully removed from the set." + ] + } + ], + "constants": [ + { + "name": "PalletId", + "type": "LockIdentifier", + "value": "0x706872656c656374", + "docs": [ + " Identifier for the elections-phragmen pallet's lock" + ] + }, + { + "name": "CandidacyBond", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " How much should be locked up in order to submit one's candidacy." + ] + }, + { + "name": "VotingBondBase", + "type": "BalanceOf", + "value": "0x00f0436de36a01000000000000000000", + "docs": [ + " Base deposit associated with voting.", + "", + " This should be sensibly high to economically ensure the pallet cannot be attacked by", + " creating a gigantic number of votes." + ] + }, + { + "name": "VotingBondFactor", + "type": "BalanceOf", + "value": "0x0000cc7b9fae00000000000000000000", + "docs": [ + " The amount of bond that need to be locked for each vote (32 bytes)." + ] + }, + { + "name": "DesiredMembers", + "type": "u32", + "value": "0x0d000000", + "docs": [ + " Number of members to elect." + ] + }, + { + "name": "DesiredRunnersUp", + "type": "u32", + "value": "0x07000000", + "docs": [ + " Number of runners_up to keep." + ] + }, + { + "name": "TermDuration", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " How long each seat is kept. This defines the next block number at which an election", + " round will happen. If set to zero, no elections are ever triggered and the module will", + " be in passive mode." + ] + } + ], + "errors": [ + { + "name": "UnableToVote", + "docs": [ + " Cannot vote when no candidates or members exist." + ] + }, + { + "name": "NoVotes", + "docs": [ + " Must vote for at least one candidate." + ] + }, + { + "name": "TooManyVotes", + "docs": [ + " Cannot vote more than candidates." + ] + }, + { + "name": "MaximumVotesExceeded", + "docs": [ + " Cannot vote more than maximum allowed." + ] + }, + { + "name": "LowBalance", + "docs": [ + " Cannot vote with stake less than minimum balance." + ] + }, + { + "name": "UnableToPayBond", + "docs": [ + " Voter can not pay voting bond." + ] + }, + { + "name": "MustBeVoter", + "docs": [ + " Must be a voter." + ] + }, + { + "name": "ReportSelf", + "docs": [ + " Cannot report self." + ] + }, + { + "name": "DuplicatedCandidate", + "docs": [ + " Duplicated candidate submission." + ] + }, + { + "name": "MemberSubmit", + "docs": [ + " Member cannot re-submit candidacy." + ] + }, + { + "name": "RunnerUpSubmit", + "docs": [ + " Runner cannot re-submit candidacy." + ] + }, + { + "name": "InsufficientCandidateFunds", + "docs": [ + " Candidate does not have enough funds." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + }, + { + "name": "InvalidWitnessData", + "docs": [ + " The provided count of number of candidates is incorrect." + ] + }, + { + "name": "InvalidVoteCount", + "docs": [ + " The provided count of number of votes is incorrect." + ] + }, + { + "name": "InvalidRenouncing", + "docs": [ + " The renouncing origin presented a wrong `Renouncing` parameter." + ] + }, + { + "name": "InvalidReplacement", + "docs": [ + " Prediction regarding replacement after member removal is wrong." + ] + } + ], + "index": 14 + }, + { + "name": "TechnicalMembership", + "storage": { + "prefix": "Instance1Membership", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current membership, stored as an ordered Vec." + ] + }, + { + "name": "Prime", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The current prime member, if one exists." + ] + } + ] + }, + "calls": [ + { + "name": "add_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Add a member `who` to the set.", + "", + " May only be called from `T::AddOrigin`." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Remove a member `who` from the set.", + "", + " May only be called from `T::RemoveOrigin`." + ] + }, + { + "name": "swap_member", + "args": [ + { + "name": "remove", + "type": "AccountId" + }, + { + "name": "add", + "type": "AccountId" + } + ], + "docs": [ + " Swap out one member `remove` for another `add`.", + "", + " May only be called from `T::SwapOrigin`.", + "", + " Prime membership is *not* passed from `remove` to `add`, if extant." + ] + }, + { + "name": "reset_members", + "args": [ + { + "name": "members", + "type": "Vec" + } + ], + "docs": [ + " Change the membership to a new set, disregarding the existing membership. Be nice and", + " pass `members` pre-sorted.", + "", + " May only be called from `T::ResetOrigin`." + ] + }, + { + "name": "change_key", + "args": [ + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Swap out the sending member for some other key `new`.", + "", + " May only be called from `Signed` origin of a current member.", + "", + " Prime membership is passed from the origin account to `new`, if extant." + ] + }, + { + "name": "set_prime", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Set the prime member. Must be a current member.", + "", + " May only be called from `T::PrimeOrigin`." + ] + }, + { + "name": "clear_prime", + "args": [], + "docs": [ + " Remove the prime member if it exists.", + "", + " May only be called from `T::PrimeOrigin`." + ] + } + ], + "events": [ + { + "name": "MemberAdded", + "args": [], + "docs": [ + " The given member was added; see the transaction for who." + ] + }, + { + "name": "MemberRemoved", + "args": [], + "docs": [ + " The given member was removed; see the transaction for who." + ] + }, + { + "name": "MembersSwapped", + "args": [], + "docs": [ + " Two members were swapped; see the transaction for who." + ] + }, + { + "name": "MembersReset", + "args": [], + "docs": [ + " The membership was reset; see the transaction for who the new set is." + ] + }, + { + "name": "KeyChanged", + "args": [], + "docs": [ + " One of the members' keys changed." + ] + }, + { + "name": "Dummy", + "args": [ + "PhantomData" + ], + "docs": [ + " Phantom member, never used." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "AlreadyMember", + "docs": [ + " Already a member." + ] + }, + { + "name": "NotMember", + "docs": [ + " Not a member." + ] + } + ], + "index": 15 + }, + { + "name": "Grandpa", + "storage": { + "prefix": "Grandpa", + "items": [ + { + "name": "State", + "modifier": "Default", + "type": { + "plain": "StoredState" + }, + "fallback": "0x00", + "docs": [ + " State of the current authority set." + ] + }, + { + "name": "PendingChange", + "modifier": "Optional", + "type": { + "plain": "StoredPendingChange" + }, + "fallback": "0x00", + "docs": [ + " Pending change: (signaled at, scheduled change)." + ] + }, + { + "name": "NextForced", + "modifier": "Optional", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00", + "docs": [ + " next block number where we can force a change." + ] + }, + { + "name": "Stalled", + "modifier": "Optional", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x00", + "docs": [ + " `true` if we are currently stalled." + ] + }, + { + "name": "CurrentSetId", + "modifier": "Default", + "type": { + "plain": "SetId" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The number of changes (both in terms of keys and underlying economic responsibilities)", + " in the \"set\" of Grandpa validators from genesis." + ] + }, + { + "name": "SetIdSession", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "SetId", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from grandpa set ID to the index of the *most recent* session for which its", + " members were responsible.", + "", + " TWOX-NOTE: `SetId` is not under user control." + ] + } + ] + }, + "calls": [ + { + "name": "report_equivocation", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported." + ] + }, + { + "name": "report_equivocation_unsigned", + "args": [ + { + "name": "equivocation_proof", + "type": "GrandpaEquivocationProof" + }, + { + "name": "key_owner_proof", + "type": "KeyOwnerProof" + } + ], + "docs": [ + " Report voter equivocation/misbehavior. This method will verify the", + " equivocation proof and validate the given key ownership proof", + " against the extracted offender. If both are valid, the offence", + " will be reported.", + "", + " This extrinsic must be called unsigned and it is expected that only", + " block authors will call it (validated in `ValidateUnsigned`), as such", + " if the block author is defined it will be defined as the equivocation", + " reporter." + ] + }, + { + "name": "note_stalled", + "args": [ + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "best_finalized_block_number", + "type": "BlockNumber" + } + ], + "docs": [ + " Note that the current authority set of the GRANDPA finality gadget has", + " stalled. This will trigger a forced authority set change at the beginning", + " of the next session, to be enacted `delay` blocks after that. The delay", + " should be high enough to safely assume that the block signalling the", + " forced change will not be re-orged (e.g. 1000 blocks). The GRANDPA voters", + " will start the new authority set using the given finalized block as base.", + " Only callable by root." + ] + } + ], + "events": [ + { + "name": "NewAuthorities", + "args": [ + "AuthorityList" + ], + "docs": [ + " New authority set has been applied. \\[authority_set\\]" + ] + }, + { + "name": "Paused", + "args": [], + "docs": [ + " Current authority set has been paused." + ] + }, + { + "name": "Resumed", + "args": [], + "docs": [ + " Current authority set has been resumed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "PauseFailed", + "docs": [ + " Attempt to signal GRANDPA pause when the authority set isn't live", + " (either paused or already pending pause)." + ] + }, + { + "name": "ResumeFailed", + "docs": [ + " Attempt to signal GRANDPA resume when the authority set isn't paused", + " (either live or already pending resume)." + ] + }, + { + "name": "ChangePending", + "docs": [ + " Attempt to signal GRANDPA change with one already pending." + ] + }, + { + "name": "TooSoon", + "docs": [ + " Cannot signal forced change so soon after last." + ] + }, + { + "name": "InvalidKeyOwnershipProof", + "docs": [ + " A key ownership proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "InvalidEquivocationProof", + "docs": [ + " An equivocation proof provided as part of an equivocation report is invalid." + ] + }, + { + "name": "DuplicateOffenceReport", + "docs": [ + " A given equivocation report is valid but already previously reported." + ] + } + ], + "index": 16 + }, + { + "name": "Treasury", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "ProposalIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of proposals that have been made." + ] + }, + { + "name": "Proposals", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ProposalIndex", + "value": "TreasuryProposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Proposals that have been made." + ] + }, + { + "name": "Approvals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Proposal indices that have been approved but not yet awarded." + ] + } + ] + }, + "calls": [ + { + "name": "propose_spend", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Put forward a suggestion for spending. A deposit proportional to the value", + " is reserved and slashed if the proposal is rejected. It is returned once the", + " proposal is awarded.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `ProposalCount`, `origin account`", + " - DbWrites: `ProposalCount`, `Proposals`, `origin account`", + " # " + ] + }, + { + "name": "reject_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Reject a proposed spend. The original deposit will be slashed.", + "", + " May only be called from `T::RejectOrigin`.", + "", + " # ", + " - Complexity: O(1)", + " - DbReads: `Proposals`, `rejected proposer account`", + " - DbWrites: `Proposals`, `rejected proposer account`", + " # " + ] + }, + { + "name": "approve_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a proposal. At a later time, the proposal will be allocated to the beneficiary", + " and the original deposit will be returned.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - Complexity: O(1).", + " - DbReads: `Proposals`, `Approvals`", + " - DbWrite: `Approvals`", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "ProposalIndex" + ], + "docs": [ + " New proposal. \\[proposal_index\\]" + ] + }, + { + "name": "Spending", + "args": [ + "Balance" + ], + "docs": [ + " We have ended a spend period and will now allocate funds. \\[budget_remaining\\]" + ] + }, + { + "name": "Awarded", + "args": [ + "ProposalIndex", + "Balance", + "AccountId" + ], + "docs": [ + " Some funds have been allocated. \\[proposal_index, award, beneficiary\\]" + ] + }, + { + "name": "Rejected", + "args": [ + "ProposalIndex", + "Balance" + ], + "docs": [ + " A proposal was rejected; funds were slashed. \\[proposal_index, slashed\\]" + ] + }, + { + "name": "Burnt", + "args": [ + "Balance" + ], + "docs": [ + " Some of our funds have been burnt. \\[burn\\]" + ] + }, + { + "name": "Rollover", + "args": [ + "Balance" + ], + "docs": [ + " Spending has finished; this is the amount that rolls over until next spend.", + " \\[budget_remaining\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds have been deposited. \\[deposit\\]" + ] + } + ], + "constants": [ + { + "name": "ProposalBond", + "type": "Permill", + "value": "0x50c30000", + "docs": [ + " Fraction of a proposal's value that should be bonded in order to place the proposal.", + " An accepted proposal gets these back. A rejected proposal does not." + ] + }, + { + "name": "ProposalBondMinimum", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Minimum amount of funds that should be placed in a deposit for making a proposal." + ] + }, + { + "name": "SpendPeriod", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " Period between successive spends." + ] + }, + { + "name": "Burn", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of spare funds (if any) that are burnt per spend period." + ] + }, + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f7472737279", + "docs": [ + " The treasury's pallet id, used for deriving its sovereign account ID." + ] + }, + { + "name": "MaxApprovals", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of approvals that can wait in the spending queue." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " No proposal or bounty at that index." + ] + }, + { + "name": "TooManyApprovals", + "docs": [ + " Too many approvals in the queue." + ] + } + ], + "index": 17 + }, + { + "name": "Contracts", + "storage": { + "prefix": "Contracts", + "items": [ + { + "name": "PristineCode", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from an original code hash to the original code, untouched by instrumentation." + ] + }, + { + "name": "CodeStorage", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "CodeHash", + "value": "PrefabWasmModule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping between an original code hash and instrumented wasm code, ready for execution." + ] + }, + { + "name": "AccountCounter", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The subtrie counter." + ] + }, + { + "name": "ContractInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "ContractInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The code associated with a given account.", + "", + " TWOX-NOTE: SAFE since `AccountId` is a secure hash." + ] + }, + { + "name": "DeletionQueue", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Evicted contracts that await child trie deletion.", + "", + " Child trie deletion is a heavy operation depending on the amount of storage items", + " stored in said trie. Therefore this operation is performed lazily in `on_initialize`." + ] + } + ] + }, + "calls": [ + { + "name": "call", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Makes a call to an account, optionally transferring some balance.", + "", + " * If the account is a smart-contract account, the associated code will be", + " executed and any value will be transferred.", + " * If the account is a regular account, any value will be transferred.", + " * If no account exists and the call value is not less than `existential_deposit`,", + " a regular account will be created and any value will be transferred." + ] + }, + { + "name": "instantiate_with_code", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code", + "type": "Bytes" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "salt", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a new contract from the supplied `code` optionally transferring", + " some balance.", + "", + " This is the only function that can deploy new code to the chain.", + "", + " # Parameters", + "", + " * `endowment`: The balance to transfer from the `origin` to the newly created contract.", + " * `gas_limit`: The gas limit enforced when executing the constructor.", + " * `code`: The contract code to deploy in raw bytes.", + " * `data`: The input data to pass to the contract constructor.", + " * `salt`: Used for the address derivation. See [`Pallet::contract_address`].", + "", + " Instantiation is executed as follows:", + "", + " - The supplied `code` is instrumented, deployed, and a `code_hash` is created for that code.", + " - If the `code_hash` already exists on the chain the underlying `code` will be shared.", + " - The destination address is computed based on the sender, code_hash and the salt.", + " - The smart-contract account is created at the computed address.", + " - The `endowment` is transferred to the new account.", + " - The `deploy` function is executed in the context of the newly-created account." + ] + }, + { + "name": "instantiate", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code_hash", + "type": "CodeHash" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "salt", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a contract from a previously deployed wasm binary.", + "", + " This function is identical to [`Self::instantiate_with_code`] but without the", + " code deployment step. Instead, the `code_hash` of an on-chain deployed wasm binary", + " must be supplied." + ] + }, + { + "name": "claim_surcharge", + "args": [ + { + "name": "dest", + "type": "AccountId" + }, + { + "name": "aux_sender", + "type": "Option" + } + ], + "docs": [ + " Allows block producers to claim a small reward for evicting a contract. If a block", + " producer fails to do so, a regular users will be allowed to claim the reward.", + "", + " In case of a successful eviction no fees are charged from the sender. However, the", + " reward is capped by the total amount of rent that was paid by the contract while", + " it was alive.", + "", + " If contract is not evicted as a result of this call, [`Error::ContractNotEvictable`]", + " is returned and the sender is not eligible for the reward." + ] + } + ], + "events": [ + { + "name": "Instantiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract deployed by address at the specified address. \\[deployer, contract\\]" + ] + }, + { + "name": "Evicted", + "args": [ + "AccountId" + ], + "docs": [ + " Contract has been evicted and is now in tombstone state. \\[contract\\]" + ] + }, + { + "name": "Terminated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract has been terminated without leaving a tombstone.", + " \\[contract, beneficiary\\]", + "", + " # Params", + "", + " - `contract`: The contract that was terminated.", + " - `beneficiary`: The account that received the contracts remaining balance.", + "", + " # Note", + "", + " The only way for a contract to be removed without a tombstone and emitting", + " this event is by calling `seal_terminate`." + ] + }, + { + "name": "Restored", + "args": [ + "AccountId", + "AccountId", + "Hash", + "Balance" + ], + "docs": [ + " Restoration of a contract has been successful.", + " \\[restorer, dest, code_hash, rent_allowance\\]", + "", + " # Params", + "", + " - `restorer`: Account ID of the restoring contract.", + " - `dest`: Account ID of the restored contract.", + " - `code_hash`: Code hash of the restored contract.", + " - `rent_allowance`: Rent allowance of the restored contract." + ] + }, + { + "name": "CodeStored", + "args": [ + "Hash" + ], + "docs": [ + " Code with the specified hash has been stored. \\[code_hash\\]" + ] + }, + { + "name": "ScheduleUpdated", + "args": [ + "u32" + ], + "docs": [ + " Triggered when the current schedule is updated.", + " \\[version\\]", + "", + " # Params", + "", + " - `version`: The version of the newly set schedule." + ] + }, + { + "name": "ContractEmitted", + "args": [ + "AccountId", + "Bytes" + ], + "docs": [ + " A custom event emitted by the contract.", + " \\[contract, data\\]", + "", + " # Params", + "", + " - `contract`: The contract that emitted the event.", + " - `data`: Data supplied by the contract. Metadata generated during contract", + " compilation is needed to decode it." + ] + }, + { + "name": "CodeRemoved", + "args": [ + "Hash" + ], + "docs": [ + " A code with the specified hash was removed.", + " \\[code_hash\\]", + "", + " This happens when the last contract that uses this code hash was removed or evicted." + ] + } + ], + "constants": [ + { + "name": "Schedule", + "type": "Schedule", + "value": "0x0400000000020000000100008000000010000000001000000001000020000000200000000040000000000200020000008e0f0000b04602009a8c0300a9720000767600005e380000ea5e00000753000097000000579e030088130500b60000007a170000c11100005721000099370000483a0000d0110000d8d12c08bc4300005c430000bb2e0000a942000000260000b72300009c370000ad540000de540000ca5400000354000018550000e553000011550000c053000007540000da540000a0530000e85300008d5400004a690000bd680000a56a000096670000b053000013540000055400006a5500009255000060550000f455000033550000cae32900000000007a332a00000000004041290000000000a6fb5d000000000060c02a0000000000e6d6290000000000065329000000000062002a0000000000d425290000000000b0522a00000000005cb3540000000000b41c1600000000008057640000000000000100000000000008f6380000000000710200000000000078d68a210000000098d6de2a000000007c75640900000000466d6f000000000070baac0000000000ec73de07000000007406000000000000922c190000000000fc9f1d00000000008618ee0900000000450200000000000082dc6108000000003e573102000000002704000000000000cc94430b000000009406e1100000000096fa930800000000dc010000000000009c020000000000001843c12400000000f001000000000000b80200000000000094070000000000008a9b2a0000000000561200000000000046432b0000000000ab0c000000000000c08c260000000000b005000000000000acd2260000000000b005000000000000", + "docs": [ + " Cost schedule and limits." + ] + }, + { + "name": "SignedClaimHandicap", + "type": "BlockNumber", + "value": "0x02000000", + "docs": [ + " Number of block delay an extrinsic claim surcharge has.", + "", + " When claim surcharge is called by an extrinsic the rent is checked", + " for current_block - delay" + ] + }, + { + "name": "TombstoneDeposit", + "type": "BalanceOf", + "value": "0x00f0e8857a9c02000000000000000000", + "docs": [ + " The minimum amount required to generate a tombstone." + ] + }, + { + "name": "DepositPerContract", + "type": "BalanceOf", + "value": "0x00f0e8857a9c02000000000000000000", + "docs": [ + " The balance every contract needs to deposit to stay alive indefinitely.", + "", + " This is different from the [`Self::TombstoneDeposit`] because this only needs to be", + " deposited while the contract is alive. Costs for additional storage are added to", + " this base cost.", + "", + " This is a simple way to ensure that contracts with empty storage eventually get deleted by", + " making them pay rent. This creates an incentive to remove them early in order to save rent." + ] + }, + { + "name": "DepositPerStorageByte", + "type": "BalanceOf", + "value": "0x0060defb740500000000000000000000", + "docs": [ + " The balance a contract needs to deposit per storage byte to stay alive indefinitely.", + "", + " Let's suppose the deposit is 1,000 BU (balance units)/byte and the rent is 1 BU/byte/day,", + " then a contract with 1,000,000 BU that uses 1,000 bytes of storage would pay no rent.", + " But if the balance reduced to 500,000 BU and the storage stayed the same at 1,000,", + " then it would pay 500 BU/day." + ] + }, + { + "name": "DepositPerStorageItem", + "type": "BalanceOf", + "value": "0x00f0ab75a40d00000000000000000000", + "docs": [ + " The balance a contract needs to deposit per storage item to stay alive indefinitely.", + "", + " It works the same as [`Self::DepositPerStorageByte`] but for storage items." + ] + }, + { + "name": "RentFraction", + "type": "Perbill", + "value": "0x85040000", + "docs": [ + " The fraction of the deposit that should be used as rent per block.", + "", + " When a contract hasn't enough balance deposited to stay alive indefinitely it needs", + " to pay per block for the storage it consumes that is not covered by the deposit.", + " This determines how high this rent payment is per block as a fraction of the deposit." + ] + }, + { + "name": "SurchargeReward", + "type": "BalanceOf", + "value": "0x005cb2ec220000000000000000000000", + "docs": [ + " Reward that is received by the party whose touch has led", + " to removal of a contract." + ] + }, + { + "name": "DeletionQueueDepth", + "type": "u32", + "value": "0x1a040000", + "docs": [ + " The maximum number of tries that can be queued for deletion." + ] + }, + { + "name": "DeletionWeightLimit", + "type": "Weight", + "value": "0x00d0ed902e000000", + "docs": [ + " The maximum amount of weight that can be consumed per block for lazy trie removal." + ] + } + ], + "errors": [ + { + "name": "InvalidScheduleVersion", + "docs": [ + " A new schedule must have a greater version than the current one." + ] + }, + { + "name": "InvalidSurchargeClaim", + "docs": [ + " An origin must be signed or inherent and auxiliary sender only provided on inherent." + ] + }, + { + "name": "InvalidSourceContract", + "docs": [ + " Cannot restore from nonexisting or tombstone contract." + ] + }, + { + "name": "InvalidDestinationContract", + "docs": [ + " Cannot restore to nonexisting or alive contract." + ] + }, + { + "name": "InvalidTombstone", + "docs": [ + " Tombstones don't match." + ] + }, + { + "name": "InvalidContractOrigin", + "docs": [ + " An origin TrieId written in the current block." + ] + }, + { + "name": "OutOfGas", + "docs": [ + " The executed contract exhausted its gas limit." + ] + }, + { + "name": "OutputBufferTooSmall", + "docs": [ + " The output buffer supplied to a contract API call was too small." + ] + }, + { + "name": "BelowSubsistenceThreshold", + "docs": [ + " Performing the requested transfer would have brought the contract below", + " the subsistence threshold. No transfer is allowed to do this in order to allow", + " for a tombstone to be created. Use `seal_terminate` to remove a contract without", + " leaving a tombstone behind." + ] + }, + { + "name": "NewContractNotFunded", + "docs": [ + " The newly created contract is below the subsistence threshold after executing", + " its contructor. No contracts are allowed to exist below that threshold." + ] + }, + { + "name": "TransferFailed", + "docs": [ + " Performing the requested transfer failed for a reason originating in the", + " chosen currency implementation of the runtime. Most probably the balance is", + " too low or locks are placed on it." + ] + }, + { + "name": "MaxCallDepthReached", + "docs": [ + " Performing a call was denied because the calling depth reached the limit", + " of what is specified in the schedule." + ] + }, + { + "name": "ContractNotFound", + "docs": [ + " No contract was found at the specified address." + ] + }, + { + "name": "ContractIsTombstone", + "docs": [ + " A tombstone exist at the specified address.", + "", + " Tombstone cannot be called. Anyone can use `seal_restore_to` in order to revive", + " the contract, though." + ] + }, + { + "name": "RentNotPaid", + "docs": [ + " The called contract does not have enough balance to pay for its storage.", + "", + " The contract ran out of balance and is therefore eligible for eviction into a", + " tombstone. Anyone can evict the contract by submitting a `claim_surcharge`", + " extrinsic. Alternatively, a plain balance transfer can be used in order to", + " increase the contracts funds so that it can be called again." + ] + }, + { + "name": "CodeTooLarge", + "docs": [ + " The code supplied to `instantiate_with_code` exceeds the limit specified in the", + " current schedule." + ] + }, + { + "name": "CodeNotFound", + "docs": [ + " No code could be found at the supplied code hash." + ] + }, + { + "name": "OutOfBounds", + "docs": [ + " A buffer outside of sandbox memory was passed to a contract API function." + ] + }, + { + "name": "DecodingFailed", + "docs": [ + " Input passed to a contract API function failed to decode as expected type." + ] + }, + { + "name": "ContractTrapped", + "docs": [ + " Contract trapped during execution." + ] + }, + { + "name": "ValueTooLarge", + "docs": [ + " The size defined in `T::MaxValueSize` was exceeded." + ] + }, + { + "name": "TerminatedWhileReentrant", + "docs": [ + " Termination of a contract is not allowed while the contract is already", + " on the call stack. Can be triggered by `seal_terminate` or `seal_restore_to." + ] + }, + { + "name": "InputForwarded", + "docs": [ + " `seal_call` forwarded this contracts input. It therefore is no longer available." + ] + }, + { + "name": "RandomSubjectTooLong", + "docs": [ + " The subject passed to `seal_random` exceeds the limit." + ] + }, + { + "name": "TooManyTopics", + "docs": [ + " The amount of topics passed to `seal_deposit_events` exceeds the limit." + ] + }, + { + "name": "DuplicateTopics", + "docs": [ + " The topics passed to `seal_deposit_events` contains at least one duplicate." + ] + }, + { + "name": "NoChainExtension", + "docs": [ + " The chain does not provide a chain extension. Calling the chain extension results", + " in this error. Note that this usually shouldn't happen as deploying such contracts", + " is rejected." + ] + }, + { + "name": "DeletionQueueFull", + "docs": [ + " Removal of a contract failed because the deletion queue is full.", + "", + " This can happen when either calling [`Pallet::claim_surcharge`] or `seal_terminate`.", + " The queue is filled by deleting contracts and emptied by a fixed amount each block.", + " Trying again during another block is the only way to resolve this issue." + ] + }, + { + "name": "ContractNotEvictable", + "docs": [ + " A contract could not be evicted because it has enough balance to pay rent.", + "", + " This can be returned from [`Pallet::claim_surcharge`] because the target", + " contract has enough balance to pay for its rent." + ] + }, + { + "name": "StorageExhausted", + "docs": [ + " A storage modification exhausted the 32bit type that holds the storage size.", + "", + " This can either happen when the accumulated storage in bytes is too large or", + " when number of storage items is too large." + ] + }, + { + "name": "DuplicateContract", + "docs": [ + " A contract with the same AccountId already exists." + ] + }, + { + "name": "TerminatedInConstructor", + "docs": [ + " A contract self destructed in its constructor.", + "", + " This can be triggered by a call to `seal_terminate` or `seal_restore_to`." + ] + }, + { + "name": "DebugMessageInvalidUTF8", + "docs": [ + " The debug message specified to `seal_debug_message` does contain invalid UTF-8." + ] + }, + { + "name": "ReentranceDenied", + "docs": [ + " A call tried to invoke a contract that is flagged as non-reentrant." + ] + } + ], + "index": 18 + }, + { + "name": "Sudo", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "Key", + "modifier": "Default", + "type": { + "plain": "AccountId" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The `AccountId` of the sudo key." + ] + } + ] + }, + "calls": [ + { + "name": "sudo", + "args": [ + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + }, + { + "name": "sudo_unchecked_weight", + "args": [ + { + "name": "call", + "type": "Call" + }, + { + "name": "_weight", + "type": "Weight" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + " This function does not check the weight of the call, and instead allows the", + " Sudo user to specify the weight of the call.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - The weight of this call is defined by the caller.", + " # " + ] + }, + { + "name": "set_key", + "args": [ + { + "name": "new", + "type": "LookupSource" + } + ], + "docs": [ + " Authenticates the current sudo key and sets the given AccountId (`new`) as the new sudo key.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "sudo_as", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Signed` origin from", + " a given account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Weight of derivative `call` execution + 10,000.", + " # " + ] + } + ], + "events": [ + { + "name": "Sudid", + "args": [ + "DispatchResult" + ], + "docs": [ + " A sudo just took place. \\[result\\]" + ] + }, + { + "name": "KeyChanged", + "args": [ + "AccountId" + ], + "docs": [ + " The \\[sudoer\\] just switched identity; the old key is supplied." + ] + }, + { + "name": "SudoAsDone", + "args": [ + "DispatchResult" + ], + "docs": [ + " A sudo just took place. \\[result\\]" + ] + } + ], + "constants": [], + "errors": [ + { + "name": "RequireSudo", + "docs": [ + " Sender must be the Sudo account" + ] + } + ], + "index": 19 + }, + { + "name": "ImOnline", + "storage": { + "prefix": "ImOnline", + "items": [ + { + "name": "HeartbeatAfter", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The block number after which it's ok to send heartbeats in the current", + " session.", + "", + " At the beginning of each session we set this to a value that should fall", + " roughly in the middle of the session duration. The idea is to first wait for", + " the validators to produce a block in the current session, so that the", + " heartbeat later on will not be necessary.", + "", + " This value will only be used as a fallback if we fail to get a proper session", + " progress estimate from `NextSessionRotation`, as those estimates should be", + " more accurate then the value we calculate for `HeartbeatAfter`." + ] + }, + { + "name": "Keys", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of keys that may issue a heartbeat." + ] + }, + { + "name": "ReceivedHeartbeats", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "AuthIndex", + "value": "Bytes", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " For each session index, we keep a mapping of `AuthIndex` to", + " `offchain::OpaqueNetworkState`." + ] + }, + { + "name": "AuthoredBlocks", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "SessionIndex", + "key2": "ValidatorId", + "value": "u32", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00000000", + "docs": [ + " For each session index, we keep a mapping of `ValidatorId` to the", + " number of blocks authored by the given authority." + ] + } + ] + }, + "calls": [ + { + "name": "heartbeat", + "args": [ + { + "name": "heartbeat", + "type": "Heartbeat" + }, + { + "name": "_signature", + "type": "Signature" + } + ], + "docs": [ + " # ", + " - Complexity: `O(K + E)` where K is length of `Keys` (heartbeat.validators_len)", + " and E is length of `heartbeat.network_state.external_address`", + " - `O(K)`: decoding of length `K`", + " - `O(E)`: decoding/encoding of length `E`", + " - DbReads: pallet_session `Validators`, pallet_session `CurrentIndex`, `Keys`,", + " `ReceivedHeartbeats`", + " - DbWrites: `ReceivedHeartbeats`", + " # " + ] + } + ], + "events": [ + { + "name": "HeartbeatReceived", + "args": [ + "AuthorityId" + ], + "docs": [ + " A new heartbeat was received from `AuthorityId` \\[authority_id\\]" + ] + }, + { + "name": "AllGood", + "args": [], + "docs": [ + " At the end of the session, no offence was committed." + ] + }, + { + "name": "SomeOffline", + "args": [ + "Vec" + ], + "docs": [ + " At the end of the session, at least one validator was found to be \\[offline\\]." + ] + } + ], + "constants": [ + { + "name": "UnsignedPriority", + "type": "TransactionPriority", + "value": "0xffffffffffffffff", + "docs": [ + " A configuration for base priority of unsigned transactions.", + "", + " This is exposed so that it can be tuned for particular runtime, when", + " multiple pallets send unsigned transactions." + ] + } + ], + "errors": [ + { + "name": "InvalidKey", + "docs": [ + " Non existent public key." + ] + }, + { + "name": "DuplicatedHeartbeat", + "docs": [ + " Duplicated heartbeat." + ] + } + ], + "index": 20 + }, + { + "name": "AuthorityDiscovery", + "storage": null, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 21 + }, + { + "name": "Offences", + "storage": { + "prefix": "Offences", + "items": [ + { + "name": "Reports", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "ReportIdOf", + "value": "OffenceDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The primary structure that holds all offence records keyed by report identifiers." + ] + }, + { + "name": "ConcurrentReportsIndex", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Kind", + "key2": "OpaqueTimeSlot", + "value": "Vec", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " A vector of reports of the same kind that happened at the same time slot." + ] + }, + { + "name": "ReportsByKindIndex", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Kind", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Enumerates all reports of a kind along with the time they happened.", + "", + " All reports are sorted by the time of offence.", + "", + " Note that the actual type of this mapping is `Vec`, this is because values of", + " different types are not supported at the moment so we are doing the manual serialization." + ] + } + ] + }, + "calls": null, + "events": [ + { + "name": "Offence", + "args": [ + "Kind", + "OpaqueTimeSlot" + ], + "docs": [ + " There is an offence reported of the given `kind` happened at the `session_index` and", + " (kind-specific) time slot. This event is not deposited for duplicate slashes.", + " \\[kind, timeslot\\]." + ] + } + ], + "constants": [], + "errors": [], + "index": 22 + }, + { + "name": "Historical", + "storage": null, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 23 + }, + { + "name": "RandomnessCollectiveFlip", + "storage": { + "prefix": "RandomnessCollectiveFlip", + "items": [ + { + "name": "RandomMaterial", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Series of block headers from the last 81 blocks that acts as random seed material. This", + " is arranged as a ring buffer with `block_number % 81` being the index into the `Vec` of", + " the oldest hash." + ] + } + ] + }, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 24 + }, + { + "name": "Identity", + "storage": { + "prefix": "Identity", + "items": [ + { + "name": "IdentityOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Registration", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information that is pertinent to identify the entity behind an account.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "SuperOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "(AccountId,Data)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The super-identity of an alternative \"sub\" identity together with its name, within that", + " context. If the account is not some other account's sub-identity, then just `None`." + ] + }, + { + "name": "SubsOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " Alternative \"sub\" identities of this account.", + "", + " The first item is the deposit, the second is a vector of the accounts.", + "", + " TWOX-NOTE: OK ― `AccountId` is a secure hash." + ] + }, + { + "name": "Registrars", + "modifier": "Default", + "type": { + "plain": "Vec>" + }, + "fallback": "0x00", + "docs": [ + " The set of registrars. Not expected to get very big as can only be added through a", + " special origin (likely a council motion).", + "", + " The index into this can be cast to `RegistrarIndex` to get a valid value." + ] + } + ] + }, + "calls": [ + { + "name": "add_registrar", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Add a registrar to the system.", + "", + " The dispatch origin for this call must be `T::RegistrarOrigin`.", + "", + " - `account`: the account of the registrar.", + "", + " Emits `RegistrarAdded` if successful.", + "", + " # ", + " - `O(R)` where `R` registrar-count (governance-bounded and code-bounded).", + " - One storage mutation (codec `O(R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_identity", + "args": [ + { + "name": "info", + "type": "IdentityInfo" + } + ], + "docs": [ + " Set an account's identity information and reserve the appropriate deposit.", + "", + " If the account already has identity information, the deposit is taken as part payment", + " for the new deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `info`: The identity information.", + "", + " Emits `IdentitySet` if successful.", + "", + " # ", + " - `O(X + X' + R)`", + " - where `X` additional-field-count (deposit-bounded and code-bounded)", + " - where `R` judgements-count (registrar-count-bounded)", + " - One balance reserve operation.", + " - One storage mutation (codec-read `O(X' + R)`, codec-write `O(X + R)`).", + " - One event.", + " # " + ] + }, + { + "name": "set_subs", + "args": [ + { + "name": "subs", + "type": "Vec<(AccountId,Data)>" + } + ], + "docs": [ + " Set the sub-accounts of the sender.", + "", + " Payment: Any aggregate balance reserved by previous `set_subs` calls will be returned", + " and an amount `SubAccountDeposit` will be reserved for each item in `subs`.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " - `subs`: The identity's (new) sub-accounts.", + "", + " # ", + " - `O(P + S)`", + " - where `P` old-subs-count (hard- and deposit-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - At most one balance operations.", + " - DB:", + " - `P + S` storage mutations (codec complexity `O(1)`)", + " - One storage read (codec complexity `O(P)`).", + " - One storage write (codec complexity `O(S)`).", + " - One storage-exists (`IdentityOf::contains_key`).", + " # " + ] + }, + { + "name": "clear_identity", + "args": [], + "docs": [ + " Clear an account's identity info and all sub-accounts and return all deposits.", + "", + " Payment: All reserved balances on the account are returned.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " identity.", + "", + " Emits `IdentityCleared` if successful.", + "", + " # ", + " - `O(R + S + X)`", + " - where `R` registrar-count (governance-bounded).", + " - where `S` subs-count (hard- and deposit-bounded).", + " - where `X` additional-field-count (deposit-bounded and code-bounded).", + " - One balance-unreserve operation.", + " - `2` storage reads and `S + 2` storage deletions.", + " - One event.", + " # " + ] + }, + { + "name": "request_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "max_fee", + "type": "Compact" + } + ], + "docs": [ + " Request a judgement from a registrar.", + "", + " Payment: At most `max_fee` will be reserved for payment to the registrar if judgement", + " given.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is requested.", + " - `max_fee`: The maximum fee that may be paid. This should just be auto-populated as:", + "", + " ```nocompile", + " Self::registrars().get(reg_index).unwrap().fee", + " ```", + "", + " Emits `JudgementRequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(X + R)`.", + " - One event.", + " # " + ] + }, + { + "name": "cancel_request", + "args": [ + { + "name": "reg_index", + "type": "RegistrarIndex" + } + ], + "docs": [ + " Cancel a previous request.", + "", + " Payment: A previously reserved deposit is returned on success.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a", + " registered identity.", + "", + " - `reg_index`: The index of the registrar whose judgement is no longer requested.", + "", + " Emits `JudgementUnrequested` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-reserve operation.", + " - One storage mutation `O(R + X)`.", + " - One event", + " # " + ] + }, + { + "name": "set_fee", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Set the fee required for a judgement to be requested from a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fee`: the new fee.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.315 + R * 0.329 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_account_id", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Change the account associated with a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `new`: the new account ID.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 8.823 + R * 0.32 µs (min squares analysis)", + " # " + ] + }, + { + "name": "set_fields", + "args": [ + { + "name": "index", + "type": "Compact" + }, + { + "name": "fields", + "type": "IdentityFields" + } + ], + "docs": [ + " Set the field information for a registrar.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `index`.", + "", + " - `index`: the index of the registrar whose fee is to be set.", + " - `fields`: the fields that the registrar concerns themselves with.", + "", + " # ", + " - `O(R)`.", + " - One storage mutation `O(R)`.", + " - Benchmark: 7.464 + R * 0.325 µs (min squares analysis)", + " # " + ] + }, + { + "name": "provide_judgement", + "args": [ + { + "name": "reg_index", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "judgement", + "type": "IdentityJudgement" + } + ], + "docs": [ + " Provide a judgement for an account's identity.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must be the account", + " of the registrar whose index is `reg_index`.", + "", + " - `reg_index`: the index of the registrar whose judgement is being made.", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + " - `judgement`: the judgement of the registrar of index `reg_index` about `target`.", + "", + " Emits `JudgementGiven` if successful.", + "", + " # ", + " - `O(R + X)`.", + " - One balance-transfer operation.", + " - Up to one account-lookup operation.", + " - Storage: 1 read `O(R)`, 1 mutate `O(R + X)`.", + " - One event.", + " # " + ] + }, + { + "name": "kill_identity", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Remove an account's identity and sub-account information and slash the deposits.", + "", + " Payment: Reserved balances from `set_subs` and `set_identity` are slashed and handled by", + " `Slash`. Verification request deposits are not returned; they should be cancelled", + " manually using `cancel_request`.", + "", + " The dispatch origin for this call must match `T::ForceOrigin`.", + "", + " - `target`: the account whose identity the judgement is upon. This must be an account", + " with a registered identity.", + "", + " Emits `IdentityKilled` if successful.", + "", + " # ", + " - `O(R + S + X)`.", + " - One balance-reserve operation.", + " - `S + 2` storage mutations.", + " - One event.", + " # " + ] + }, + { + "name": "add_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Add the given account to the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "rename_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + }, + { + "name": "data", + "type": "Data" + } + ], + "docs": [ + " Alter the associated name of the given sub-account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "remove_sub", + "args": [ + { + "name": "sub", + "type": "LookupSource" + } + ], + "docs": [ + " Remove the given account from the sender's subs.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " sub identity of `sub`." + ] + }, + { + "name": "quit_sub", + "args": [], + "docs": [ + " Remove the sender as a sub-account.", + "", + " Payment: Balance reserved by a previous `set_subs` call for one sub will be repatriated", + " to the sender (*not* the original depositor).", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have a registered", + " super-identity.", + "", + " NOTE: This should not normally be used, but is provided in the case that the non-", + " controller of an account is maliciously registered as a sub-account." + ] + } + ], + "events": [ + { + "name": "IdentitySet", + "args": [ + "AccountId" + ], + "docs": [ + " A name was set or reset (which will remove all judgements). \\[who\\]" + ] + }, + { + "name": "IdentityCleared", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was cleared, and the given balance returned. \\[who, deposit\\]" + ] + }, + { + "name": "IdentityKilled", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was removed and the given balance slashed. \\[who, deposit\\]" + ] + }, + { + "name": "JudgementRequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was asked from a registrar. \\[who, registrar_index\\]" + ] + }, + { + "name": "JudgementUnrequested", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement request was retracted. \\[who, registrar_index\\]" + ] + }, + { + "name": "JudgementGiven", + "args": [ + "AccountId", + "RegistrarIndex" + ], + "docs": [ + " A judgement was given by a registrar. \\[target, registrar_index\\]" + ] + }, + { + "name": "RegistrarAdded", + "args": [ + "RegistrarIndex" + ], + "docs": [ + " A registrar was added. \\[registrar_index\\]" + ] + }, + { + "name": "SubIdentityAdded", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was added to an identity and the deposit paid. \\[sub, main, deposit\\]" + ] + }, + { + "name": "SubIdentityRemoved", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was removed from an identity and the deposit freed.", + " \\[sub, main, deposit\\]" + ] + }, + { + "name": "SubIdentityRevoked", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " A sub-identity was cleared, and the given deposit repatriated from the", + " main identity account to the sub-identity account. \\[sub, main, deposit\\]" + ] + } + ], + "constants": [ + { + "name": "BasicDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The amount held on deposit for a registered identity" + ] + }, + { + "name": "FieldDeposit", + "type": "BalanceOf", + "value": "0x00a031a95fe300000000000000000000", + "docs": [ + " The amount held on deposit per additional field for a registered identity." + ] + }, + { + "name": "SubAccountDeposit", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount held on deposit for a registered subaccount. This should account for the fact", + " that one storage item's value will increase by the size of an account ID, and there will be", + " another trie item whose value is the size of an account ID plus 32 bytes." + ] + }, + { + "name": "MaxSubAccounts", + "type": "u32", + "value": "0x64000000", + "docs": [ + " The maximum number of sub-accounts allowed per identified account." + ] + }, + { + "name": "MaxAdditionalFields", + "type": "u32", + "value": "0x64000000", + "docs": [ + " Maximum number of additional fields that may be stored in an ID. Needed to bound the I/O", + " required to access an identity, but can be pretty high." + ] + }, + { + "name": "MaxRegistrars", + "type": "u32", + "value": "0x14000000", + "docs": [ + " Maxmimum number of registrars allowed in the system. Needed to bound the complexity", + " of, e.g., updating judgements." + ] + } + ], + "errors": [ + { + "name": "TooManySubAccounts", + "docs": [ + " Too many subs-accounts." + ] + }, + { + "name": "NotFound", + "docs": [ + " Account isn't found." + ] + }, + { + "name": "NotNamed", + "docs": [ + " Account isn't named." + ] + }, + { + "name": "EmptyIndex", + "docs": [ + " Empty index." + ] + }, + { + "name": "FeeChanged", + "docs": [ + " Fee is changed." + ] + }, + { + "name": "NoIdentity", + "docs": [ + " No identity found." + ] + }, + { + "name": "StickyJudgement", + "docs": [ + " Sticky judgement." + ] + }, + { + "name": "JudgementGiven", + "docs": [ + " Judgement given." + ] + }, + { + "name": "InvalidJudgement", + "docs": [ + " Invalid judgement." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " The index is invalid." + ] + }, + { + "name": "InvalidTarget", + "docs": [ + " The target is invalid." + ] + }, + { + "name": "TooManyFields", + "docs": [ + " Too many additional fields." + ] + }, + { + "name": "TooManyRegistrars", + "docs": [ + " Maximum amount of registrars reached. Cannot add any more." + ] + }, + { + "name": "AlreadyClaimed", + "docs": [ + " Account ID is already named." + ] + }, + { + "name": "NotSub", + "docs": [ + " Sender is not a sub-account." + ] + }, + { + "name": "NotOwned", + "docs": [ + " Sub-account isn't owned by sender." + ] + } + ], + "index": 25 + }, + { + "name": "Society", + "storage": { + "prefix": "Society", + "items": [ + { + "name": "Founder", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The first member." + ] + }, + { + "name": "Rules", + "modifier": "Optional", + "type": { + "plain": "Hash" + }, + "fallback": "0x00", + "docs": [ + " A hash of the rules of this society concerning membership. Can only be set once and", + " only by the founder." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of candidates; bidders that are attempting to become members." + ] + }, + { + "name": "SuspendedCandidates", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(BalanceOf,BidKind)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended candidates." + ] + }, + { + "name": "Pot", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Amount of our account balance that is specifically for the next round's bid(s)." + ] + }, + { + "name": "Head", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The most primary from the most recently approved members." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of members, ordered." + ] + }, + { + "name": "SuspendedMembers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of suspended members." + ] + }, + { + "name": "Bids", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current bids, stored ordered by the value of the bid." + ] + }, + { + "name": "Vouching", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "VouchingStatus", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Members currently vouching or banned from vouching again" + ] + }, + { + "name": "Payouts", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "Vec<(BlockNumber,BalanceOf)>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Pending payouts; ordered by block number, with the amount that should be paid out." + ] + }, + { + "name": "Strikes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "StrikeCount", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " The ongoing number of losing votes cast by the member." + ] + }, + { + "name": "Votes", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "SocietyVote", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Double map from Candidate -> Voter -> (Maybe) Vote." + ] + }, + { + "name": "Defender", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " The defending member currently being challenged." + ] + }, + { + "name": "DefenderVotes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "SocietyVote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes for the defender." + ] + }, + { + "name": "MaxMembers", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The max number of members for the society at one time." + ] + } + ] + }, + "calls": [ + { + "name": "bid", + "args": [ + { + "name": "value", + "type": "BalanceOf" + } + ], + "docs": [ + " A user outside of the society can make a bid for entry.", + "", + " Payment: `CandidateDeposit` will be reserved for making a bid. It is returned", + " when the bid becomes a member, or if the bid calls `unbid`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `value`: A one time payment the bid would like to receive when joining the society.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members), X (balance reserve)", + " - Storage Reads:", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " \t- One storage read to retrieve all members. O(M)", + " - Storage Writes:", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for new bid.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unbid", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " A bidder can remove their bid for entry into society.", + " By doing so, they will have their candidate deposit returned or", + " they will unvouch their voucher.", + "", + " Payment: The bid deposit is unreserved if the user made a bid.", + "", + " The dispatch origin for this call must be _Signed_ and a bidder.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who wants to unbid.", + "", + " # ", + " Key: B (len of bids), X (balance unreserve)", + " - One storage read and write to retrieve and update the bids. O(B)", + " - Either one unreserve balance action O(X) or one vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B + X)", + " # " + ] + }, + { + "name": "vouch", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "value", + "type": "BalanceOf" + }, + { + "name": "tip", + "type": "BalanceOf" + } + ], + "docs": [ + " As a member, vouch for someone to join society by placing a bid on their behalf.", + "", + " There is no deposit required to vouch for a new bid, but a member can only vouch for", + " one bid at a time. If the bid becomes a suspended candidate and ultimately rejected by", + " the suspension judgement origin, the member will be banned from vouching again.", + "", + " As a vouching member, you can claim a tip if the candidate is accepted. This tip will", + " be paid as a portion of the reward the member will receive for joining the society.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `who`: The user who you would like to vouch for.", + " - `value`: The total reward to be paid between you and the candidate if they become", + " a member in the society.", + " - `tip`: Your cut of the total `value` payout when the candidate is inducted into", + " the society. Tips larger than `value` will be saturated upon payout.", + "", + " # ", + " Key: B (len of bids), C (len of candidates), M (len of members)", + " - Storage Reads:", + " \t- One storage read to retrieve all members. O(M)", + " \t- One storage read to check member is not already vouching. O(1)", + " \t- One storage read to check for suspended candidate. O(1)", + " \t- One storage read to check for suspended member. O(1)", + " \t- One storage read to retrieve all current bids. O(B)", + " \t- One storage read to retrieve all current candidates. O(C)", + " - Storage Writes:", + " \t- One storage write to insert vouching status to the member. O(1)", + " \t- One storage mutate to add a new bid to the vector O(B) (TODO: possible optimization w/ read)", + " \t- Up to one storage removal if bid.len() > MAX_BID_COUNT. O(1)", + " - Notable Computation:", + " \t- O(log M) search to check sender is a member.", + " \t- O(B + C + log M) search to check user is not already a part of society.", + " \t- O(log B) search to insert the new bid sorted.", + " - External Module Operations:", + " \t- One balance reserve operation. O(X)", + " \t- Up to one balance unreserve operation if bids.len() > MAX_BID_COUNT.", + " - Events:", + " \t- One event for vouch.", + " \t- Up to one event for AutoUnbid if bid.len() > MAX_BID_COUNT.", + "", + " Total Complexity: O(M + B + C + logM + logB + X)", + " # " + ] + }, + { + "name": "unvouch", + "args": [ + { + "name": "pos", + "type": "u32" + } + ], + "docs": [ + " As a vouching member, unvouch a bid. This only works while vouched user is", + " only a bidder (and not a candidate).", + "", + " The dispatch origin for this call must be _Signed_ and a vouching member.", + "", + " Parameters:", + " - `pos`: Position in the `Bids` vector of the bid who should be unvouched.", + "", + " # ", + " Key: B (len of bids)", + " - One storage read O(1) to check the signer is a vouching member.", + " - One storage mutate to retrieve and update the bids. O(B)", + " - One vouching storage removal. O(1)", + " - One event.", + "", + " Total Complexity: O(B)", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "candidate", + "type": "LookupSource" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on a candidate.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `candidate`: The candidate that the member would like to bid on.", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " Key: C (len of candidates), M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One account lookup.", + " - One storage read O(C) and O(C) search to check that user is a candidate.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM + C)", + " # " + ] + }, + { + "name": "defender_vote", + "args": [ + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " As a member, vote on the defender.", + "", + " The dispatch origin for this call must be _Signed_ and a member.", + "", + " Parameters:", + " - `approve`: A boolean which says if the candidate should be", + " approved (`true`) or rejected (`false`).", + "", + " # ", + " - Key: M (len of members)", + " - One storage read O(M) and O(log M) search to check user is a member.", + " - One storage write to add vote to votes. O(1)", + " - One event.", + "", + " Total Complexity: O(M + logM)", + " # " + ] + }, + { + "name": "payout", + "args": [], + "docs": [ + " Transfer the first matured payout for the sender and remove it from the records.", + "", + " NOTE: This extrinsic needs to be called multiple times to claim multiple matured payouts.", + "", + " Payment: The member will receive a payment equal to their first matured", + " payout to their free balance.", + "", + " The dispatch origin for this call must be _Signed_ and a member with", + " payouts remaining.", + "", + " # ", + " Key: M (len of members), P (number of payouts for a particular member)", + " - One storage read O(M) and O(log M) search to check signer is a member.", + " - One storage read O(P) to get all payouts for a member.", + " - One storage read O(1) to get the current block number.", + " - One currency transfer call. O(X)", + " - One storage write or removal to update the member's payouts. O(P)", + "", + " Total Complexity: O(M + logM + P + X)", + " # " + ] + }, + { + "name": "found", + "args": [ + { + "name": "founder", + "type": "AccountId" + }, + { + "name": "max_members", + "type": "u32" + }, + { + "name": "rules", + "type": "Bytes" + } + ], + "docs": [ + " Found the society.", + "", + " This is done as a discrete action in order to allow for the", + " module to be included into a running chain and can only be done once.", + "", + " The dispatch origin for this call must be from the _FounderSetOrigin_.", + "", + " Parameters:", + " - `founder` - The first member and head of the newly founded society.", + " - `max_members` - The initial max number of members for the society.", + " - `rules` - The rules of this society concerning membership.", + "", + " # ", + " - Two storage mutates to set `Head` and `Founder`. O(1)", + " - One storage write to add the first member to society. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "unfound", + "args": [], + "docs": [ + " Annul the founding of the society.", + "", + " The dispatch origin for this call must be Signed, and the signing account must be both", + " the `Founder` and the `Head`. This implies that it may only be done when there is one", + " member.", + "", + " # ", + " - Two storage reads O(1).", + " - Four storage removals O(1).", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + }, + { + "name": "judge_suspended_member", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "forgive", + "type": "bool" + } + ], + "docs": [ + " Allow suspension judgement origin to make judgement on a suspended member.", + "", + " If a suspended member is forgiven, we simply add them back as a member, not affecting", + " any of the existing storage items for that member.", + "", + " If a suspended member is rejected, remove all associated storage items, including", + " their payouts, and remove any vouched bids they currently have.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended member to be judged.", + " - `forgive` - A boolean representing whether the suspension judgement origin", + " forgives (`true`) or rejects (`false`) a suspended member.", + "", + " # ", + " Key: B (len of bids), M (len of members)", + " - One storage read to check `who` is a suspended member. O(1)", + " - Up to one storage write O(M) with O(log M) binary search to add a member back to society.", + " - Up to 3 storage removals O(1) to clean up a removed member.", + " - Up to one storage write O(B) with O(B) search to remove vouched bid from bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal. O(1)", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B)", + " # " + ] + }, + { + "name": "judge_suspended_candidate", + "args": [ + { + "name": "who", + "type": "AccountId" + }, + { + "name": "judgement", + "type": "SocietyJudgement" + } + ], + "docs": [ + " Allow suspended judgement origin to make judgement on a suspended candidate.", + "", + " If the judgement is `Approve`, we add them to society as a member with the appropriate", + " payment for joining society.", + "", + " If the judgement is `Reject`, we either slash the deposit of the bid, giving it back", + " to the society treasury, or we ban the voucher from vouching again.", + "", + " If the judgement is `Rebid`, we put the candidate back in the bid pool and let them go", + " through the induction process again.", + "", + " The dispatch origin for this call must be from the _SuspensionJudgementOrigin_.", + "", + " Parameters:", + " - `who` - The suspended candidate to be judged.", + " - `judgement` - `Approve`, `Reject`, or `Rebid`.", + "", + " # ", + " Key: B (len of bids), M (len of members), X (balance action)", + " - One storage read to check `who` is a suspended candidate.", + " - One storage removal of the suspended candidate.", + " - Approve Logic", + " \t- One storage read to get the available pot to pay users with. O(1)", + " \t- One storage write to update the available pot. O(1)", + " \t- One storage read to get the current block number. O(1)", + " \t- One storage read to get all members. O(M)", + " \t- Up to one unreserve currency action.", + " \t- Up to two new storage writes to payouts.", + " \t- Up to one storage write with O(log M) binary search to add a member to society.", + " - Reject Logic", + " \t- Up to one repatriate reserved currency action. O(X)", + " \t- Up to one storage write to ban the vouching member from vouching again.", + " - Rebid Logic", + " \t- Storage mutate with O(log B) binary search to place the user back into bids.", + " - Up to one additional event if unvouch takes place.", + " - One storage removal.", + " - One event for the judgement.", + "", + " Total Complexity: O(M + logM + B + X)", + " # " + ] + }, + { + "name": "set_max_members", + "args": [ + { + "name": "max", + "type": "u32" + } + ], + "docs": [ + " Allows root origin to change the maximum number of members in society.", + " Max membership count must be greater than 1.", + "", + " The dispatch origin for this call must be from _ROOT_.", + "", + " Parameters:", + " - `max` - The maximum number of members for the society.", + "", + " # ", + " - One storage write to update the max. O(1)", + " - One event.", + "", + " Total Complexity: O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "Founded", + "args": [ + "AccountId" + ], + "docs": [ + " The society is founded by the given identity. \\[founder\\]" + ] + }, + { + "name": "Bid", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A membership bid just happened. The given account is the candidate's ID and their offer", + " is the second. \\[candidate_id, offer\\]" + ] + }, + { + "name": "Vouch", + "args": [ + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A membership bid just happened by vouching. The given account is the candidate's ID and", + " their offer is the second. The vouching party is the third. \\[candidate_id, offer, vouching\\]" + ] + }, + { + "name": "AutoUnbid", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (due to an excess of bids in the system)." + ] + }, + { + "name": "Unbid", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (by their request)." + ] + }, + { + "name": "Unvouch", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] was dropped (by request of who vouched for them)." + ] + }, + { + "name": "Inducted", + "args": [ + "AccountId", + "Vec" + ], + "docs": [ + " A group of candidates have been inducted. The batch's primary is the first value, the", + " batch in full is the second. \\[primary, candidates\\]" + ] + }, + { + "name": "SuspendedMemberJudgement", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A suspended member has been judged. \\[who, judged\\]" + ] + }, + { + "name": "CandidateSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[candidate\\] has been suspended" + ] + }, + { + "name": "MemberSuspended", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been suspended" + ] + }, + { + "name": "Challenged", + "args": [ + "AccountId" + ], + "docs": [ + " A \\[member\\] has been challenged" + ] + }, + { + "name": "Vote", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed \\[candidate, voter, vote\\]" + ] + }, + { + "name": "DefenderVote", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A vote has been placed for a defending member \\[voter, vote\\]" + ] + }, + { + "name": "NewMaxMembers", + "args": [ + "u32" + ], + "docs": [ + " A new \\[max\\] member count has been set" + ] + }, + { + "name": "Unfounded", + "args": [ + "AccountId" + ], + "docs": [ + " Society is unfounded. \\[founder\\]" + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds were deposited into the society account. \\[value\\]" + ] + } + ], + "constants": [ + { + "name": "CandidateDeposit", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The minimum amount of a deposit required for a bid to be made." + ] + }, + { + "name": "WrongSideDeduction", + "type": "BalanceOf", + "value": "0x0080f420e6b500000000000000000000", + "docs": [ + " The amount of the unpaid reward that gets deducted in the case that either a skeptic", + " doesn't vote or someone votes in the wrong way." + ] + }, + { + "name": "MaxStrikes", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The number of times a member may vote the wrong way (or not at all, when they are a skeptic)", + " before they become suspended." + ] + }, + { + "name": "PeriodSpend", + "type": "BalanceOf", + "value": "0x0000c52ebca2b1000000000000000000", + "docs": [ + " The amount of incentive paid within each period. Doesn't include VoterTip." + ] + }, + { + "name": "RotationPeriod", + "type": "BlockNumber", + "value": "0x00770100", + "docs": [ + " The number of blocks between candidate/membership rotation periods." + ] + }, + { + "name": "ChallengePeriod", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [ + " The number of blocks between membership challenges." + ] + }, + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f736f636965", + "docs": [ + " The societies's module id" + ] + }, + { + "name": "MaxCandidateIntake", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Maximum candidate intake per round." + ] + } + ], + "errors": [ + { + "name": "BadPosition", + "docs": [ + " An incorrect position was provided." + ] + }, + { + "name": "NotMember", + "docs": [ + " User is not a member." + ] + }, + { + "name": "AlreadyMember", + "docs": [ + " User is already a member." + ] + }, + { + "name": "Suspended", + "docs": [ + " User is suspended." + ] + }, + { + "name": "NotSuspended", + "docs": [ + " User is not suspended." + ] + }, + { + "name": "NoPayout", + "docs": [ + " Nothing to payout." + ] + }, + { + "name": "AlreadyFounded", + "docs": [ + " Society already founded." + ] + }, + { + "name": "InsufficientPot", + "docs": [ + " Not enough in pot to accept candidate." + ] + }, + { + "name": "AlreadyVouching", + "docs": [ + " Member is already vouching or banned from vouching again." + ] + }, + { + "name": "NotVouching", + "docs": [ + " Member is not vouching." + ] + }, + { + "name": "Head", + "docs": [ + " Cannot remove the head of the chain." + ] + }, + { + "name": "Founder", + "docs": [ + " Cannot remove the founder." + ] + }, + { + "name": "AlreadyBid", + "docs": [ + " User has already made a bid." + ] + }, + { + "name": "AlreadyCandidate", + "docs": [ + " User is already a candidate." + ] + }, + { + "name": "NotCandidate", + "docs": [ + " User is not a candidate." + ] + }, + { + "name": "MaxMembers", + "docs": [ + " Too many members in the society." + ] + }, + { + "name": "NotFounder", + "docs": [ + " The caller is not the founder." + ] + }, + { + "name": "NotHead", + "docs": [ + " The caller is not the head." + ] + } + ], + "index": 26 + }, + { + "name": "Recovery", + "storage": { + "prefix": "Recovery", + "items": [ + { + "name": "Recoverable", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "RecoveryConfig", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The set of recoverable accounts and their recovery configuration." + ] + }, + { + "name": "ActiveRecoveries", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "AccountId", + "value": "ActiveRecovery", + "key2Hasher": "Twox64Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Active recovery attempts.", + "", + " First account is the account to be recovered, and the second account", + " is the user trying to recover the account." + ] + }, + { + "name": "Proxy", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The list of allowed proxy accounts.", + "", + " Map from the user who can access it to the recovered account." + ] + } + ] + }, + "calls": [ + { + "name": "as_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Send a call through a recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you want to make a call on-behalf-of.", + " - `call`: The call you want to make with the recovered account.", + "", + " # ", + " - The weight of the `call` + 10,000.", + " - One storage lookup to check account is recovered by `who`. O(1)", + " # " + ] + }, + { + "name": "set_recovered", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow ROOT to bypass the recovery process and set an a rescuer account", + " for a lost account directly.", + "", + " The dispatch origin for this call must be _ROOT_.", + "", + " Parameters:", + " - `lost`: The \"lost account\" to be recovered.", + " - `rescuer`: The \"rescuer account\" which can call as the lost account.", + "", + " # ", + " - One storage write O(1)", + " - One event", + " # " + ] + }, + { + "name": "create_recovery", + "args": [ + { + "name": "friends", + "type": "Vec" + }, + { + "name": "threshold", + "type": "u16" + }, + { + "name": "delay_period", + "type": "BlockNumber" + } + ], + "docs": [ + " Create a recovery configuration for your account. This makes your account recoverable.", + "", + " Payment: `ConfigDepositBase` + `FriendDepositFactor` * #_of_friends balance", + " will be reserved for storing the recovery configuration. This deposit is returned", + " in full when the user calls `remove_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `friends`: A list of friends you trust to vouch for recovery attempts.", + " Should be ordered and contain no duplicate values.", + " - `threshold`: The number of friends that must vouch for a recovery attempt", + " before the account can be recovered. Should be less than or equal to", + " the length of the list of friends.", + " - `delay_period`: The number of blocks after a recovery attempt is initialized", + " that needs to pass before the account can be recovered.", + "", + " # ", + " - Key: F (len of friends)", + " - One storage read to check that account is not already recoverable. O(1).", + " - A check that the friends list is sorted and unique. O(F)", + " - One currency reserve operation. O(X)", + " - One storage write. O(1). Codec O(F).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "initiate_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Initiate the process for recovering a recoverable account.", + "", + " Payment: `RecoveryDeposit` balance will be reserved for initiating the", + " recovery process. This deposit will always be repatriated to the account", + " trying to be recovered. See `close_recovery`.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `account`: The lost account that you want to recover. This account", + " needs to be recoverable (i.e. have a recovery configuration).", + "", + " # ", + " - One storage read to check that account is recoverable. O(F)", + " - One storage read to check that this recovery process hasn't already started. O(1)", + " - One currency reserve operation. O(X)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1).", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "vouch_recovery", + "args": [ + { + "name": "lost", + "type": "AccountId" + }, + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " Allow a \"friend\" of a recoverable account to vouch for an active recovery", + " process for that account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"friend\"", + " for the recoverable account.", + "", + " Parameters:", + " - `lost`: The lost account that you want to recover.", + " - `rescuer`: The account trying to rescue the lost account that you", + " want to vouch for.", + "", + " The combination of these two parameters must point to an active recovery", + " process.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One binary search to confirm caller is a friend. O(logF)", + " - One binary search to confirm caller has not already vouched. O(logV)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + logF + V + logV)", + " # " + ] + }, + { + "name": "claim_recovery", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Allow a successful rescuer to claim their recovered account.", + "", + " The dispatch origin for this call must be _Signed_ and must be a \"rescuer\"", + " who has successfully completed the account recovery process: collected", + " `threshold` or more vouches, waited `delay_period` blocks since initiation.", + "", + " Parameters:", + " - `account`: The lost account that you want to claim has been successfully", + " recovered by you.", + "", + " # ", + " Key: F (len of friends in config), V (len of vouching friends)", + " - One storage read to get the recovery configuration. O(1), Codec O(F)", + " - One storage read to get the active recovery process. O(1), Codec O(V)", + " - One storage read to get the current block number. O(1)", + " - One storage write. O(1), Codec O(V).", + " - One event.", + "", + " Total Complexity: O(F + V)", + " # " + ] + }, + { + "name": "close_recovery", + "args": [ + { + "name": "rescuer", + "type": "AccountId" + } + ], + "docs": [ + " As the controller of a recoverable account, close an active recovery", + " process for your account.", + "", + " Payment: By calling this function, the recoverable account will receive", + " the recovery deposit `RecoveryDeposit` placed by the rescuer.", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account with an active recovery process for it.", + "", + " Parameters:", + " - `rescuer`: The account trying to rescue this recoverable account.", + "", + " # ", + " Key: V (len of vouching friends)", + " - One storage read/remove to get the active recovery process. O(1), Codec O(V)", + " - One balance call to repatriate reserved. O(X)", + " - One event.", + "", + " Total Complexity: O(V + X)", + " # " + ] + }, + { + "name": "remove_recovery", + "args": [], + "docs": [ + " Remove the recovery process for your account. Recovered accounts are still accessible.", + "", + " NOTE: The user must make sure to call `close_recovery` on all active", + " recovery attempts before calling this function else it will fail.", + "", + " Payment: By calling this function the recoverable account will unreserve", + " their recovery configuration deposit.", + " (`ConfigDepositBase` + `FriendDepositFactor` * #_of_friends)", + "", + " The dispatch origin for this call must be _Signed_ and must be a", + " recoverable account (i.e. has a recovery configuration).", + "", + " # ", + " Key: F (len of friends)", + " - One storage read to get the prefix iterator for active recoveries. O(1)", + " - One storage read/remove to get the recovery configuration. O(1), Codec O(F)", + " - One balance call to unreserved. O(X)", + " - One event.", + "", + " Total Complexity: O(F + X)", + " # " + ] + }, + { + "name": "cancel_recovered", + "args": [ + { + "name": "account", + "type": "AccountId" + } + ], + "docs": [ + " Cancel the ability to use `as_recovered` for `account`.", + "", + " The dispatch origin for this call must be _Signed_ and registered to", + " be able to make calls on behalf of the recovered account.", + "", + " Parameters:", + " - `account`: The recovered account you are able to call on-behalf-of.", + "", + " # ", + " - One storage mutation to check account is recovered by `who`. O(1)", + " # " + ] + } + ], + "events": [ + { + "name": "RecoveryCreated", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been set up for an \\[account\\]." + ] + }, + { + "name": "RecoveryInitiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process has been initiated for lost account by rescuer account.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "RecoveryVouched", + "args": [ + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been vouched for by sender.", + " \\[lost, rescuer, sender\\]" + ] + }, + { + "name": "RecoveryClosed", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " A recovery process for lost account by rescuer account has been closed.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "AccountRecovered", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Lost account has been successfully recovered by rescuer account.", + " \\[lost, rescuer\\]" + ] + }, + { + "name": "RecoveryRemoved", + "args": [ + "AccountId" + ], + "docs": [ + " A recovery process has been removed for an \\[account\\]." + ] + } + ], + "constants": [ + { + "name": "ConfigDepositBase", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a recovery configuration.", + "", + " This is held for an additional storage item whose value size is", + " `2 + sizeof(BlockNumber, Balance)` bytes." + ] + }, + { + "name": "FriendDepositFactor", + "type": "BalanceOf", + "value": "0x00203d88792d00000000000000000000", + "docs": [ + " The amount of currency needed per additional user when creating a recovery configuration.", + "", + " This is held for adding `sizeof(AccountId)` bytes more into a pre-existing storage value." + ] + }, + { + "name": "MaxFriends", + "type": "u16", + "value": "0x0900", + "docs": [ + " The maximum amount of friends allowed in a recovery configuration." + ] + }, + { + "name": "RecoveryDeposit", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for starting a recovery.", + "", + " This is primarily held for deterring malicious recovery attempts, and should", + " have a value large enough that a bad actor would choose not to place this", + " deposit. It also acts to fund additional storage item whose value size is", + " `sizeof(BlockNumber, Balance + T * AccountId)` bytes. Where T is a configurable", + " threshold." + ] + } + ], + "errors": [ + { + "name": "NotAllowed", + "docs": [ + " User is not allowed to make a call on behalf of this account" + ] + }, + { + "name": "ZeroThreshold", + "docs": [ + " Threshold must be greater than zero" + ] + }, + { + "name": "NotEnoughFriends", + "docs": [ + " Friends list must be greater than zero and threshold" + ] + }, + { + "name": "MaxFriends", + "docs": [ + " Friends list must be less than max friends" + ] + }, + { + "name": "NotSorted", + "docs": [ + " Friends list must be sorted and free of duplicates" + ] + }, + { + "name": "NotRecoverable", + "docs": [ + " This account is not set up for recovery" + ] + }, + { + "name": "AlreadyRecoverable", + "docs": [ + " This account is already set up for recovery" + ] + }, + { + "name": "AlreadyStarted", + "docs": [ + " A recovery process has already started for this account" + ] + }, + { + "name": "NotStarted", + "docs": [ + " A recovery process has not started for this rescuer" + ] + }, + { + "name": "NotFriend", + "docs": [ + " This account is not a friend who can vouch" + ] + }, + { + "name": "DelayPeriod", + "docs": [ + " The friend must wait until the delay period to vouch for this recovery" + ] + }, + { + "name": "AlreadyVouched", + "docs": [ + " This user has already vouched for this recovery" + ] + }, + { + "name": "Threshold", + "docs": [ + " The threshold for recovering this account has not been met" + ] + }, + { + "name": "StillActive", + "docs": [ + " There are still active recovery attempts that need to be closed" + ] + }, + { + "name": "AlreadyProxy", + "docs": [ + " This account is already set up for recovery" + ] + }, + { + "name": "BadState", + "docs": [ + " Some internal state is broken." + ] + } + ], + "index": 27 + }, + { + "name": "Vesting", + "storage": { + "prefix": "Vesting", + "items": [ + { + "name": "Vesting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AccountId", + "value": "VestingInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information regarding the vesting of a given account." + ] + } + ] + }, + "calls": [ + { + "name": "vest", + "args": [], + "docs": [ + " Unlock any vested funds of the sender account.", + "", + " The dispatch origin for this call must be _Signed_ and the sender must have funds still", + " locked under this pallet.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 2 Reads, 2 Writes", + " - Reads: Vesting Storage, Balances Locks, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, [Sender Account]", + " # " + ] + }, + { + "name": "vest_other", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Unlock any vested funds of a `target` account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account whose vested funds should be unlocked. Must have funds still", + " locked under this pallet.", + "", + " Emits either `VestingCompleted` or `VestingUpdated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account", + " - Writes: Vesting Storage, Balances Locks, Target Account", + " # " + ] + }, + { + "name": "vested_transfer", + "args": [ + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Create a vested transfer.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 3 Reads, 3 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " - Writes: Vesting Storage, Balances Locks, Target Account, [Sender Account]", + " # " + ] + }, + { + "name": "force_vested_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "schedule", + "type": "VestingInfo" + } + ], + "docs": [ + " Force a vested transfer.", + "", + " The dispatch origin for this call must be _Root_.", + "", + " - `source`: The account whose funds should be transferred.", + " - `target`: The account that should be transferred the vested funds.", + " - `amount`: The amount of funds to transfer and will be vested.", + " - `schedule`: The vesting schedule attached to the transfer.", + "", + " Emits `VestingCreated`.", + "", + " # ", + " - `O(1)`.", + " - DbWeight: 4 Reads, 4 Writes", + " - Reads: Vesting Storage, Balances Locks, Target Account, Source Account", + " - Writes: Vesting Storage, Balances Locks, Target Account, Source Account", + " # " + ] + } + ], + "events": [ + { + "name": "VestingUpdated", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " The amount vested has been updated. This could indicate more funds are available. The", + " balance given is the amount which is left unvested (and thus locked).", + " \\[account, unvested\\]" + ] + }, + { + "name": "VestingCompleted", + "args": [ + "AccountId" + ], + "docs": [ + " An \\[account\\] has become fully vested. No further vesting can happen." + ] + } + ], + "constants": [ + { + "name": "MinVestedTransfer", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount transferred to call `vested_transfer`." + ] + } + ], + "errors": [ + { + "name": "NotVesting", + "docs": [ + " The account given is not vesting." + ] + }, + { + "name": "ExistingVestingSchedule", + "docs": [ + " An existing vesting schedule already exists for this account that cannot be clobbered." + ] + }, + { + "name": "AmountLow", + "docs": [ + " Amount being transferred is too low to create a vesting schedule." + ] + } + ], + "index": 28 + }, + { + "name": "Scheduler", + "storage": { + "prefix": "Scheduler", + "items": [ + { + "name": "Agenda", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Vec>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Items to be executed, indexed by the block number that they should be executed on." + ] + }, + { + "name": "Lookup", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Bytes", + "value": "TaskAddress", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Lookup from identity to the block number and index of the task." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "Releases" + }, + "fallback": "0x00", + "docs": [ + " Storage version of the pallet.", + "", + " New networks start with last version." + ] + } + ] + }, + "calls": [ + { + "name": "schedule", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.29 + .126 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda", + " - Will use base weight of 25 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel", + "args": [ + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u32" + } + ], + "docs": [ + " Cancel an anonymously scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 22.15 + 2.869 * S µs", + " - DB Weight:", + " - Read: Agenda", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_named", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 29.6 + .159 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 35 which should be good for more than 30 scheduled calls", + " # " + ] + }, + { + "name": "cancel_named", + "args": [ + { + "name": "id", + "type": "Bytes" + } + ], + "docs": [ + " Cancel a named scheduled task.", + "", + " # ", + " - S = Number of already scheduled calls", + " - Base Weight: 24.91 + 2.907 * S µs", + " - DB Weight:", + " - Read: Agenda, Lookup", + " - Write: Agenda, Lookup", + " - Will use base weight of 100 which should be good for up to 30 scheduled calls", + " # " + ] + }, + { + "name": "schedule_after", + "args": [ + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Anonymously schedule a task after a delay.", + "", + " # ", + " Same as [`schedule`].", + " # " + ] + }, + { + "name": "schedule_named_after", + "args": [ + { + "name": "id", + "type": "Bytes" + }, + { + "name": "after", + "type": "BlockNumber" + }, + { + "name": "maybe_periodic", + "type": "Option" + }, + { + "name": "priority", + "type": "Priority" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Schedule a named task after a delay.", + "", + " # ", + " Same as [`schedule_named`](Self::schedule_named).", + " # " + ] + } + ], + "events": [ + { + "name": "Scheduled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Scheduled some task. \\[when, index\\]" + ] + }, + { + "name": "Canceled", + "args": [ + "BlockNumber", + "u32" + ], + "docs": [ + " Canceled some task. \\[when, index\\]" + ] + }, + { + "name": "Dispatched", + "args": [ + "TaskAddress", + "Option", + "DispatchResult" + ], + "docs": [ + " Dispatched some task. \\[task, id, result\\]" + ] + } + ], + "constants": [ + { + "name": "MaximumWeight", + "type": "Weight", + "value": "0x00806e8774010000", + "docs": [ + " The maximum weight that may be scheduled per block for any dispatchables of less priority", + " than `schedule::HARD_DEADLINE`." + ] + }, + { + "name": "MaxScheduledPerBlock", + "type": "u32", + "value": "0x32000000", + "docs": [ + " The maximum number of scheduled calls in the queue for a single block.", + " Not strictly enforced, but used for weight estimation." + ] + } + ], + "errors": [ + { + "name": "FailedToSchedule", + "docs": [ + " Failed to schedule a call" + ] + }, + { + "name": "NotFound", + "docs": [ + " Cannot find the scheduled call." + ] + }, + { + "name": "TargetBlockNumberInPast", + "docs": [ + " Given target block number is in the past." + ] + }, + { + "name": "RescheduleNoChange", + "docs": [ + " Reschedule failed because it does not change scheduled time." + ] + } + ], + "index": 29 + }, + { + "name": "Proxy", + "storage": { + "prefix": "Proxy", + "items": [ + { + "name": "Proxies", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The set of account proxies. Maps the account which has delegated to the accounts", + " which are being delegated to, together with the amount held on deposit." + ] + }, + { + "name": "Announcements", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(Vec,BalanceOf)", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000", + "docs": [ + " The announcements made by the proxy (key)." + ] + } + ] + }, + "calls": [ + { + "name": "proxy", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorised for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "add_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Register a proxy account for the sender that is able to make calls on its behalf.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to make a proxy.", + " - `proxy_type`: The permissions allowed for this proxy account.", + " - `delay`: The announcement period required of the initial proxy. Will generally be", + " zero.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxy", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Unregister a proxy account for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `proxy`: The account that the `caller` would like to remove as a proxy.", + " - `proxy_type`: The permissions currently enabled for the removed proxy account.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "remove_proxies", + "args": [], + "docs": [ + " Unregister all proxy accounts for the sender.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " WARNING: This may be called on accounts created by `anonymous`, however if done, then", + " the unreserved fees will be inaccessible. **All access to this account will be lost.**", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "anonymous", + "args": [ + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u16" + } + ], + "docs": [ + " Spawn a fresh new account that is guaranteed to be otherwise inaccessible, and", + " initialize it with a proxy of `proxy_type` for `origin` sender.", + "", + " Requires a `Signed` origin.", + "", + " - `proxy_type`: The type of the proxy that the sender will be registered as over the", + " new account. This will almost always be the most permissive `ProxyType` possible to", + " allow for maximum flexibility.", + " - `index`: A disambiguation index, in case this is called multiple times in the same", + " transaction (e.g. with `utility::batch`). Unless you're using `batch` you probably just", + " want to use `0`.", + " - `delay`: The announcement period required of the initial proxy. Will generally be", + " zero.", + "", + " Fails with `Duplicate` if this has already been called in this transaction, from the", + " same sender, with the same parameters.", + "", + " Fails if there are insufficient funds to pay for deposit.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # ", + " TODO: Might be over counting 1 read" + ] + }, + { + "name": "kill_anonymous", + "args": [ + { + "name": "spawner", + "type": "AccountId" + }, + { + "name": "proxy_type", + "type": "ProxyType" + }, + { + "name": "index", + "type": "u16" + }, + { + "name": "height", + "type": "Compact" + }, + { + "name": "ext_index", + "type": "Compact" + } + ], + "docs": [ + " Removes a previously spawned anonymous proxy.", + "", + " WARNING: **All access to this account will be lost.** Any funds held in it will be", + " inaccessible.", + "", + " Requires a `Signed` origin, and the sender account must have been created by a call to", + " `anonymous` with corresponding parameters.", + "", + " - `spawner`: The account that originally called `anonymous` to create this account.", + " - `index`: The disambiguation index originally passed to `anonymous`. Probably `0`.", + " - `proxy_type`: The proxy type originally passed to `anonymous`.", + " - `height`: The height of the chain when the call to `anonymous` was processed.", + " - `ext_index`: The extrinsic index in which the call to `anonymous` was processed.", + "", + " Fails with `NoPermission` in case the caller is not a previously created anonymous", + " account whose `anonymous` call has corresponding parameters.", + "", + " # ", + " Weight is a function of the number of proxies the user has (P).", + " # " + ] + }, + { + "name": "announce", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Publish the hash of a proxy-call that will be made in the future.", + "", + " This must be called some number of blocks before the corresponding `proxy` is attempted", + " if the delay associated with the proxy relationship is greater than zero.", + "", + " No more than `MaxPending` announcements may be made at any one time.", + "", + " This will take a deposit of `AnnouncementDepositFactor` as well as", + " `AnnouncementDepositBase` if there are no other pending announcements.", + "", + " The dispatch origin for this call must be _Signed_ and a proxy of `real`.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "remove_announcement", + "args": [ + { + "name": "real", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove a given announcement.", + "", + " May be called by a proxy account to remove a call they previously announced and return", + " the deposit.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `call_hash`: The hash of the call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "reject_announcement", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "call_hash", + "type": "CallHashOf" + } + ], + "docs": [ + " Remove the given announcement of a delegate.", + "", + " May be called by a target (proxied) account to remove a call that one of their delegates", + " (`delegate`) has announced they want to execute. The deposit is returned.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `delegate`: The account that previously announced the call.", + " - `call_hash`: The hash of the call to be made.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + }, + { + "name": "proxy_announced", + "args": [ + { + "name": "delegate", + "type": "AccountId" + }, + { + "name": "real", + "type": "AccountId" + }, + { + "name": "force_proxy_type", + "type": "Option" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Dispatch the given `call` from an account that the sender is authorized for through", + " `add_proxy`.", + "", + " Removes any corresponding announcement(s).", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Parameters:", + " - `real`: The account that the proxy will make a call on behalf of.", + " - `force_proxy_type`: Specify the exact proxy type to be used and checked for this call.", + " - `call`: The call to be made by the `real` account.", + "", + " # ", + " Weight is a function of:", + " - A: the number of announcements made.", + " - P: the number of proxies the user has.", + " # " + ] + } + ], + "events": [ + { + "name": "ProxyExecuted", + "args": [ + "DispatchResult" + ], + "docs": [ + " A proxy was executed correctly, with the given \\[result\\]." + ] + }, + { + "name": "AnonymousCreated", + "args": [ + "AccountId", + "AccountId", + "ProxyType", + "u16" + ], + "docs": [ + " Anonymous account has been created by new proxy with given", + " disambiguation index and proxy type. \\[anonymous, who, proxy_type, disambiguation_index\\]" + ] + }, + { + "name": "Announced", + "args": [ + "AccountId", + "AccountId", + "Hash" + ], + "docs": [ + " An announcement was placed to make a call in the future. \\[real, proxy, call_hash\\]" + ] + } + ], + "constants": [ + { + "name": "ProxyDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a proxy.", + "", + " This is held for an additional storage item whose value size is", + " `sizeof(Balance)` bytes and whose key size is `sizeof(AccountId)` bytes." + ] + }, + { + "name": "ProxyDepositFactor", + "type": "BalanceOf", + "value": "0x0060aa7714b400000000000000000000", + "docs": [ + " The amount of currency needed per proxy added.", + "", + " This is held for adding 32 bytes plus an instance of `ProxyType` more into a pre-existing", + " storage value. Thus, when configuring `ProxyDepositFactor` one should take into account", + " `32 + proxy_type.encode().len()` bytes of data." + ] + }, + { + "name": "MaxProxies", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum amount of proxies allowed for a single account." + ] + }, + { + "name": "MaxPending", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum amount of time-delayed announcements that are allowed to be pending." + ] + }, + { + "name": "AnnouncementDepositBase", + "type": "BalanceOf", + "value": "0x00f09e544c3900000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating an announcement.", + "", + " This is held when a new storage item holding a `Balance` is created (typically 16 bytes)." + ] + }, + { + "name": "AnnouncementDepositFactor", + "type": "BalanceOf", + "value": "0x00c054ef286801000000000000000000", + "docs": [ + " The amount of currency needed per announcement made.", + "", + " This is held for adding an `AccountId`, `Hash` and `BlockNumber` (typically 68 bytes)", + " into a pre-existing storage value." + ] + } + ], + "errors": [ + { + "name": "TooMany", + "docs": [ + " There are too many proxies registered or too many announcements pending." + ] + }, + { + "name": "NotFound", + "docs": [ + " Proxy registration not found." + ] + }, + { + "name": "NotProxy", + "docs": [ + " Sender is not a proxy of the account to be proxied." + ] + }, + { + "name": "Unproxyable", + "docs": [ + " A call which is incompatible with the proxy type's filter was attempted." + ] + }, + { + "name": "Duplicate", + "docs": [ + " Account is already a proxy." + ] + }, + { + "name": "NoPermission", + "docs": [ + " Call may not be made by proxy because it may escalate its privileges." + ] + }, + { + "name": "Unannounced", + "docs": [ + " Announcement, if made at all, was made too recently." + ] + }, + { + "name": "NoSelfProxy", + "docs": [ + " Cannot add self as proxy." + ] + } + ], + "index": 30 + }, + { + "name": "Multisig", + "storage": { + "prefix": "Multisig", + "items": [ + { + "name": "Multisigs", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "AccountId", + "key2": "[u8;32]", + "value": "Multisig", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " The set of open multisig operations." + ] + }, + { + "name": "Calls", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "[u8;32]", + "value": "(OpaqueCall,AccountId,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [] + } + ] + }, + "calls": [ + { + "name": "as_multi_threshold_1", + "args": [ + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Immediately dispatch a multi-signature call using a single approval from the caller.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `other_signatories`: The accounts (other than the sender) who are part of the", + " multi-signature, but do not participate in the approval process.", + " - `call`: The call to be executed.", + "", + " Result is equivalent to the dispatched result.", + "", + " # ", + " O(Z + C) where Z is the length of the call and C its execution weight.", + " -------------------------------", + " - DB Weight: None", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call", + "type": "OpaqueCall" + }, + { + "name": "store_call", + "type": "bool" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " If there are enough, then dispatch the call.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call`: The call to be executed.", + "", + " NOTE: Unless this is the final approval, you will generally want to use", + " `approve_as_multi` instead, since it only requires a hash of the call.", + "", + " Result is equivalent to the dispatched result if `threshold` is exactly `1`. Otherwise", + " on success, result is `Ok` and the result from the interior call, if it was executed,", + " may be found in the deposited `MultisigExecuted` event.", + "", + " # ", + " - `O(S + Z + Call)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One call encode & hash, both of complexity `O(Z)` where `Z` is tx-len.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - The weight of the `call`.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " -------------------------------", + " - DB Weight:", + " - Reads: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Writes: Multisig Storage, [Caller Account], Calls (if `store_call`)", + " - Plus Call Weight", + " # " + ] + }, + { + "name": "approve_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "maybe_timepoint", + "type": "Option" + }, + { + "name": "call_hash", + "type": "[u8;32]" + }, + { + "name": "max_weight", + "type": "Weight" + } + ], + "docs": [ + " Register approval for a dispatch to be made from a deterministic composite account if", + " approved by a total of `threshold - 1` of `other_signatories`.", + "", + " Payment: `DepositBase` will be reserved if this is the first approval, plus", + " `threshold` times `DepositFactor`. It is returned once this dispatch happens or", + " is cancelled.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `maybe_timepoint`: If this is the first approval, then this must be `None`. If it is", + " not the first approval, then it must be `Some`, with the timepoint (block number and", + " transaction index) of the first approval transaction.", + " - `call_hash`: The hash of the call to be executed.", + "", + " NOTE: If this is the final approval, you will want to use `as_multi` instead.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - Up to one binary search and insert (`O(logS + S)`).", + " - I/O: 1 read `O(S)`, up to 1 mutate `O(S)`. Up to one remove.", + " - One event.", + " - Storage: inserts one item, value size bounded by `MaxSignatories`, with a", + " deposit taken for its lifetime of", + " `DepositBase + threshold * DepositFactor`.", + " ----------------------------------", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account]", + " - Write: Multisig Storage, [Caller Account]", + " # " + ] + }, + { + "name": "cancel_as_multi", + "args": [ + { + "name": "threshold", + "type": "u16" + }, + { + "name": "other_signatories", + "type": "Vec" + }, + { + "name": "timepoint", + "type": "Timepoint" + }, + { + "name": "call_hash", + "type": "[u8;32]" + } + ], + "docs": [ + " Cancel a pre-existing, on-going multisig transaction. Any deposit reserved previously", + " for this operation will be unreserved on success.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " - `threshold`: The total number of approvals for this dispatch before it is executed.", + " - `other_signatories`: The accounts (other than the sender) who can approve this", + " dispatch. May not be empty.", + " - `timepoint`: The timepoint (block number and transaction index) of the first approval", + " transaction for this dispatch.", + " - `call_hash`: The hash of the call to be executed.", + "", + " # ", + " - `O(S)`.", + " - Up to one balance-reserve or unreserve operation.", + " - One passthrough operation, one insert, both `O(S)` where `S` is the number of", + " signatories. `S` is capped by `MaxSignatories`, with weight being proportional.", + " - One encode & hash, both of complexity `O(S)`.", + " - One event.", + " - I/O: 1 read `O(S)`, one remove.", + " - Storage: removes one item.", + " ----------------------------------", + " - DB Weight:", + " - Read: Multisig Storage, [Caller Account], Refund Account, Calls", + " - Write: Multisig Storage, [Caller Account], Refund Account, Calls", + " # " + ] + } + ], + "events": [ + { + "name": "NewMultisig", + "args": [ + "AccountId", + "AccountId", + "CallHash" + ], + "docs": [ + " A new multisig operation has begun. \\[approving, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigApproval", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been approved by someone.", + " \\[approving, timepoint, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigExecuted", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash", + "DispatchResult" + ], + "docs": [ + " A multisig operation has been executed. \\[approving, timepoint, multisig, call_hash\\]" + ] + }, + { + "name": "MultisigCancelled", + "args": [ + "AccountId", + "Timepoint", + "AccountId", + "CallHash" + ], + "docs": [ + " A multisig operation has been cancelled. \\[cancelling, timepoint, multisig, call_hash\\]" + ] + } + ], + "constants": [ + { + "name": "DepositBase", + "type": "BalanceOf", + "value": "0x00f01c0adbed01000000000000000000", + "docs": [ + " The base amount of currency needed to reserve for creating a multisig execution or to store", + " a dispatch call for later.", + "", + " This is held for an additional storage item whose value size is", + " `4 + sizeof((BlockNumber, Balance, AccountId))` bytes and whose key size is", + " `32 + sizeof(AccountId)` bytes." + ] + }, + { + "name": "DepositFactor", + "type": "BalanceOf", + "value": "0x0000cc7b9fae00000000000000000000", + "docs": [ + " The amount of currency needed per unit threshold when creating a multisig execution.", + "", + " This is held for adding 32 bytes more into a pre-existing storage value." + ] + }, + { + "name": "MaxSignatories", + "type": "u16", + "value": "0x6400", + "docs": [ + " The maximum amount of signatories allowed in the multisig." + ] + } + ], + "errors": [ + { + "name": "MinimumThreshold", + "docs": [ + " Threshold must be 2 or greater." + ] + }, + { + "name": "AlreadyApproved", + "docs": [ + " Call is already approved by this signatory." + ] + }, + { + "name": "NoApprovalsNeeded", + "docs": [ + " Call doesn't need any (more) approvals." + ] + }, + { + "name": "TooFewSignatories", + "docs": [ + " There are too few signatories in the list." + ] + }, + { + "name": "TooManySignatories", + "docs": [ + " There are too many signatories in the list." + ] + }, + { + "name": "SignatoriesOutOfOrder", + "docs": [ + " The signatories were provided out of order; they should be ordered." + ] + }, + { + "name": "SenderInSignatories", + "docs": [ + " The sender was contained in the other signatories; it shouldn't be." + ] + }, + { + "name": "NotFound", + "docs": [ + " Multisig operation not found when attempting to cancel." + ] + }, + { + "name": "NotOwner", + "docs": [ + " Only the account that originally created the multisig is able to cancel it." + ] + }, + { + "name": "NoTimepoint", + "docs": [ + " No timepoint was given, yet the multisig operation is already underway." + ] + }, + { + "name": "WrongTimepoint", + "docs": [ + " A different timepoint was given to the multisig operation that is underway." + ] + }, + { + "name": "UnexpectedTimepoint", + "docs": [ + " A timepoint was given, yet no multisig operation is underway." + ] + }, + { + "name": "MaxWeightTooLow", + "docs": [ + " The maximum weight information provided was too low." + ] + }, + { + "name": "AlreadyStored", + "docs": [ + " The data to be stored is already stored." + ] + } + ], + "index": 31 + }, + { + "name": "Bounties", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "BountyCount", + "modifier": "Default", + "type": { + "plain": "BountyIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of bounty proposals that have been made." + ] + }, + { + "name": "Bounties", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BountyIndex", + "value": "Bounty", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Bounties that have been made." + ] + }, + { + "name": "BountyDescriptions", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BountyIndex", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The description of each bounty." + ] + }, + { + "name": "BountyApprovals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Bounty indices that have been approved but not yet funded." + ] + } + ] + }, + "calls": [ + { + "name": "propose_bounty", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "description", + "type": "Bytes" + } + ], + "docs": [ + " Propose a new bounty.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `DataDepositPerByte` for each byte in `reason`. It will be unreserved upon approval,", + " or slashed when rejected.", + "", + " - `curator`: The curator account whom will manage this bounty.", + " - `fee`: The curator fee.", + " - `value`: The total payment amount of this bounty, curator fee included.", + " - `description`: The description of this bounty." + ] + }, + { + "name": "approve_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a bounty proposal. At a later time, the bounty will be funded and become active", + " and the original deposit will be returned.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "propose_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "curator", + "type": "LookupSource" + }, + { + "name": "fee", + "type": "Compact" + } + ], + "docs": [ + " Assign a curator to a funded bounty.", + "", + " May only be called from `T::ApproveOrigin`.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "unassign_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Unassign curator from a bounty.", + "", + " This function can only be called by the `RejectOrigin` a signed origin.", + "", + " If this function is called by the `RejectOrigin`, we assume that the curator is malicious", + " or inactive. As a result, we will slash the curator when possible.", + "", + " If the origin is the curator, we take this as a sign they are unable to do their job and", + " they willingly give up. We could slash them, but for now we allow them to recover their", + " deposit and exit without issue. (We may want to change this if it is abused.)", + "", + " Finally, the origin can be anyone if and only if the curator is \"inactive\". This allows", + " anyone in the community to call out that a curator is not doing their due diligence, and", + " we should pick a new curator. In this case the curator should also be slashed.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "accept_curator", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Accept the curator role for a bounty.", + " A deposit will be reserved from curator and refund upon successful payout.", + "", + " May only be called from the curator.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "award_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Award bounty to a beneficiary account. The beneficiary will be able to claim the funds after a delay.", + "", + " The dispatch origin for this call must be the curator of this bounty.", + "", + " - `bounty_id`: Bounty ID to award.", + " - `beneficiary`: The beneficiary account whom will receive the payout.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "claim_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Claim the payout from an awarded bounty after payout delay.", + "", + " The dispatch origin for this call must be the beneficiary of this bounty.", + "", + " - `bounty_id`: Bounty ID to claim.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "close_bounty", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + } + ], + "docs": [ + " Cancel a proposed or active bounty. All the funds will be sent to treasury and", + " the curator deposit will be unreserved if possible.", + "", + " Only `T::RejectOrigin` is able to cancel a bounty.", + "", + " - `bounty_id`: Bounty ID to cancel.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "extend_bounty_expiry", + "args": [ + { + "name": "bounty_id", + "type": "Compact" + }, + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Extend the expiry time of an active bounty.", + "", + " The dispatch origin for this call must be the curator of this bounty.", + "", + " - `bounty_id`: Bounty ID to extend.", + " - `remark`: additional information.", + "", + " # ", + " - O(1).", + " # " + ] + } + ], + "events": [ + { + "name": "BountyProposed", + "args": [ + "BountyIndex" + ], + "docs": [ + " New bounty proposal. \\[index\\]" + ] + }, + { + "name": "BountyRejected", + "args": [ + "BountyIndex", + "Balance" + ], + "docs": [ + " A bounty proposal was rejected; funds were slashed. \\[index, bond\\]" + ] + }, + { + "name": "BountyBecameActive", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty proposal is funded and became active. \\[index\\]" + ] + }, + { + "name": "BountyAwarded", + "args": [ + "BountyIndex", + "AccountId" + ], + "docs": [ + " A bounty is awarded to a beneficiary. \\[index, beneficiary\\]" + ] + }, + { + "name": "BountyClaimed", + "args": [ + "BountyIndex", + "Balance", + "AccountId" + ], + "docs": [ + " A bounty is claimed by beneficiary. \\[index, payout, beneficiary\\]" + ] + }, + { + "name": "BountyCanceled", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty is cancelled. \\[index\\]" + ] + }, + { + "name": "BountyExtended", + "args": [ + "BountyIndex" + ], + "docs": [ + " A bounty expiry is extended. \\[index\\]" + ] + } + ], + "constants": [ + { + "name": "DataDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within bounty description." + ] + }, + { + "name": "BountyDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a bounty proposal." + ] + }, + { + "name": "BountyDepositPayoutDelay", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The delay period for which a bounty beneficiary need to wait before claim the payout." + ] + }, + { + "name": "BountyUpdatePeriod", + "type": "BlockNumber", + "value": "0x00270600", + "docs": [ + " Bounty duration in blocks." + ] + }, + { + "name": "BountyCuratorDeposit", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of the curator fee that will be reserved upfront as deposit for bounty curator." + ] + }, + { + "name": "BountyValueMinimum", + "type": "BalanceOf", + "value": "0x00406352bfc601000000000000000000", + "docs": [ + " Minimum value for a bounty." + ] + }, + { + "name": "MaximumReasonLength", + "type": "u32", + "value": "0x00400000", + "docs": [ + " Maximum acceptable reason length." + ] + } + ], + "errors": [ + { + "name": "InsufficientProposersBalance", + "docs": [ + " Proposer's balance is too low." + ] + }, + { + "name": "InvalidIndex", + "docs": [ + " No proposal or bounty at that index." + ] + }, + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "UnexpectedStatus", + "docs": [ + " The bounty status is unexpected." + ] + }, + { + "name": "RequireCurator", + "docs": [ + " Require bounty curator." + ] + }, + { + "name": "InvalidValue", + "docs": [ + " Invalid bounty value." + ] + }, + { + "name": "InvalidFee", + "docs": [ + " Invalid bounty fee." + ] + }, + { + "name": "PendingPayout", + "docs": [ + " A bounty payout is pending.", + " To cancel the bounty, you must unassign and slash the curator." + ] + }, + { + "name": "Premature", + "docs": [ + " The bounties cannot be claimed/closed because it's still in the countdown period." + ] + } + ], + "index": 32 + }, + { + "name": "Tips", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "Tips", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "Hash", + "value": "OpenTip", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " TipsMap that are not yet completed. Keyed by the hash of `(reason, who)` from the value.", + " This has the insecure enumerable hash function since the key itself is already", + " guaranteed to be a secure hash." + ] + }, + { + "name": "Reasons", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "Hash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Simple preimage lookup from the reason's hash to the original data. Again, has an", + " insecure enumerable hash since the key is guaranteed to be the result of a secure hash." + ] + } + ] + }, + "calls": [ + { + "name": "report_awesome", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Report something `reason` that deserves a tip and claim any eventual the finder's fee.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " Payment: `TipReportDepositBase` will be reserved from the origin account, as well as", + " `DataDepositPerByte` for each byte in `reason`.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R)` where `R` length of `reason`.", + " - encoding and hashing of 'reason'", + " - DbReads: `Reasons`, `Tips`", + " - DbWrites: `Reasons`, `Tips`", + " # " + ] + }, + { + "name": "retract_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Retract a prior tip-report from `report_awesome`, and cancel the process of tipping.", + "", + " If successful, the original deposit will be unreserved.", + "", + " The dispatch origin for this call must be _Signed_ and the tip identified by `hash`", + " must have been reported by the signing account through `report_awesome` (and not", + " through `tip_new`).", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " Emits `TipRetracted` if successful.", + "", + " # ", + " - Complexity: `O(1)`", + " - Depends on the length of `T::Hash` which is fixed.", + " - DbReads: `Tips`, `origin account`", + " - DbWrites: `Reasons`, `Tips`, `origin account`", + " # " + ] + }, + { + "name": "tip_new", + "args": [ + { + "name": "reason", + "type": "Bytes" + }, + { + "name": "who", + "type": "AccountId" + }, + { + "name": "tip_value", + "type": "Compact" + } + ], + "docs": [ + " Give a tip for something new; no finder's fee will be taken.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `reason`: The reason for, or the thing that deserves, the tip; generally this will be", + " a UTF-8-encoded URL.", + " - `who`: The account which should be credited for the tip.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `NewTip` if successful.", + "", + " # ", + " - Complexity: `O(R + T)` where `R` length of `reason`, `T` is the number of tippers.", + " - `O(T)`: decoding `Tipper` vec of length `T`", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - `O(R)`: hashing and encoding of reason of length `R`", + " - DbReads: `Tippers`, `Reasons`", + " - DbWrites: `Reasons`, `Tips`", + " # " + ] + }, + { + "name": "tip", + "args": [ + { + "name": "hash", + "type": "Hash" + }, + { + "name": "tip_value", + "type": "Compact" + } + ], + "docs": [ + " Declare a tip value for an already-open tip.", + "", + " The dispatch origin for this call must be _Signed_ and the signing account must be a", + " member of the `Tippers` set.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the hash of the original tip `reason` and the beneficiary", + " account ID.", + " - `tip_value`: The amount of tip that the sender would like to give. The median tip", + " value of active tippers will be given to the `who`.", + "", + " Emits `TipClosing` if the threshold of tippers has been reached and the countdown period", + " has started.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`, insert tip and check closing,", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + "", + " Actually weight could be lower as it depends on how many tips are in `OpenTip` but it", + " is weighted as if almost full i.e of length `T-1`.", + " - DbReads: `Tippers`, `Tips`", + " - DbWrites: `Tips`", + " # " + ] + }, + { + "name": "close_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Close and payout a tip.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " The tip identified by `hash` must have finished its countdown period.", + "", + " - `hash`: The identity of the open tip for which a tip value is declared. This is formed", + " as the hash of the tuple of the original tip `reason` and the beneficiary account ID.", + "", + " # ", + " - Complexity: `O(T)` where `T` is the number of tippers.", + " decoding `Tipper` vec of length `T`.", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " - DbReads: `Tips`, `Tippers`, `tip finder`", + " - DbWrites: `Reasons`, `Tips`, `Tippers`, `tip finder`", + " # " + ] + }, + { + "name": "slash_tip", + "args": [ + { + "name": "hash", + "type": "Hash" + } + ], + "docs": [ + " Remove and slash an already-open tip.", + "", + " May only be called from `T::RejectOrigin`.", + "", + " As a result, the finder is slashed and the deposits are lost.", + "", + " Emits `TipSlashed` if successful.", + "", + " # ", + " `T` is charged as upper bound given by `ContainsLengthBound`.", + " The actual cost depends on the implementation of `T::Tippers`.", + " # " + ] + } + ], + "events": [ + { + "name": "NewTip", + "args": [ + "Hash" + ], + "docs": [ + " A new tip suggestion has been opened. \\[tip_hash\\]" + ] + }, + { + "name": "TipClosing", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has reached threshold and is closing. \\[tip_hash\\]" + ] + }, + { + "name": "TipClosed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been closed. \\[tip_hash, who, payout\\]" + ] + }, + { + "name": "TipRetracted", + "args": [ + "Hash" + ], + "docs": [ + " A tip suggestion has been retracted. \\[tip_hash\\]" + ] + }, + { + "name": "TipSlashed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A tip suggestion has been slashed. \\[tip_hash, finder, deposit\\]" + ] + } + ], + "constants": [ + { + "name": "TipCountdown", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " The period for which a tip remains open after is has achieved threshold tippers." + ] + }, + { + "name": "TipFindersFee", + "type": "Percent", + "value": "0x14", + "docs": [ + " The amount of the final tip which goes to the original reporter of the tip." + ] + }, + { + "name": "TipReportDepositBase", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount held on deposit for placing a tip report." + ] + }, + { + "name": "DataDepositPerByte", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount held on deposit per byte within the tip report reason." + ] + }, + { + "name": "MaximumReasonLength", + "type": "u32", + "value": "0x00400000", + "docs": [ + " Maximum acceptable reason length." + ] + } + ], + "errors": [ + { + "name": "ReasonTooBig", + "docs": [ + " The reason given is just too big." + ] + }, + { + "name": "AlreadyKnown", + "docs": [ + " The tip was already found/started." + ] + }, + { + "name": "UnknownTip", + "docs": [ + " The tip hash is unknown." + ] + }, + { + "name": "NotFinder", + "docs": [ + " The account attempting to retract the tip is not the finder of the tip." + ] + }, + { + "name": "StillOpen", + "docs": [ + " The tip cannot be claimed/closed because there are not enough tippers yet." + ] + }, + { + "name": "Premature", + "docs": [ + " The tip cannot be claimed/closed because it's still in the countdown period." + ] + } + ], + "index": 33 + }, + { + "name": "Assets", + "storage": { + "prefix": "Assets", + "items": [ + { + "name": "Asset", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AssetId", + "value": "AssetDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Details of an asset." + ] + }, + { + "name": "Account", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_128Concat", + "key1": "AssetId", + "key2": "AccountId", + "value": "AssetBalance", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00000000000000000000", + "docs": [ + " The number of units of assets held by any given account." + ] + }, + { + "name": "Approvals", + "modifier": "Optional", + "type": { + "nMap": { + "keyVec": [ + "AssetId", + "AccountId", + "AccountId" + ], + "hashers": [ + "Blake2_128Concat", + "Blake2_128Concat", + "Blake2_128Concat" + ], + "value": "AssetApproval" + } + }, + "fallback": "0x00", + "docs": [ + " Approved balance transfers. First balance is the amount approved for transfer. Second", + " is the amount of `T::Currency` reserved for storing this.", + " First key is the asset ID, second key is the owner and third key is the delegate." + ] + }, + { + "name": "Metadata", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "AssetId", + "value": "AssetMetadata", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000", + "docs": [ + " Metadata of an asset." + ] + } + ] + }, + "calls": [ + { + "name": "create", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "min_balance", + "type": "TAssetBalance" + } + ], + "docs": [ + " Issue a new class of fungible assets from a public origin.", + "", + " This new asset class has no assets initially and its owner is the origin.", + "", + " The origin must be Signed and the sender must have sufficient funds free.", + "", + " Funds of sender are reserved by `AssetDeposit`.", + "", + " Parameters:", + " - `id`: The identifier of the new asset. This must not be currently in use to identify", + " an existing asset.", + " - `admin`: The admin of this class of assets. The admin is the initial address of each", + " member of the asset class's admin team.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + "", + " Emits `Created` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_create", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "is_sufficient", + "type": "bool" + }, + { + "name": "min_balance", + "type": "Compact" + } + ], + "docs": [ + " Issue a new class of fungible assets from a privileged origin.", + "", + " This new asset class has no assets initially.", + "", + " The origin must conform to `ForceOrigin`.", + "", + " Unlike `create`, no funds are reserved.", + "", + " - `id`: The identifier of the new asset. This must not be currently in use to identify", + " an existing asset.", + " - `owner`: The owner of this class of assets. The owner has full superuser permissions", + " over this asset, but may later change and configure the permissions using `transfer_ownership`", + " and `set_team`.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + "", + " Emits `ForceCreated` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "destroy", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "witness", + "type": "AssetDestroyWitness" + } + ], + "docs": [ + " Destroy a class of fungible assets.", + "", + " The origin must conform to `ForceOrigin` or must be Signed and the sender must be the", + " owner of the asset `id`.", + "", + " - `id`: The identifier of the asset to be destroyed. This must identify an existing", + " asset.", + "", + " Emits `Destroyed` event when successful.", + "", + " NOTE: It can be helpful to first freeze an asset before destroying it so that you", + " can provide accurate witness information and prevent users from manipulating state", + " in a way that can make it harder to destroy.", + "", + " Weight: `O(c + p + a)` where:", + " - `c = (witness.accounts - witness.sufficients)`", + " - `s = witness.sufficients`", + " - `a = witness.approvals`" + ] + }, + { + "name": "mint", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Mint assets of a particular class.", + "", + " The origin must be Signed and the sender must be the Issuer of the asset `id`.", + "", + " - `id`: The identifier of the asset to have some amount minted.", + " - `beneficiary`: The account to be credited with the minted assets.", + " - `amount`: The amount of the asset to be minted.", + "", + " Emits `Issued` event when successful.", + "", + " Weight: `O(1)`", + " Modes: Pre-existing balance of `beneficiary`; Account pre-existence of `beneficiary`." + ] + }, + { + "name": "burn", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Reduce the balance of `who` by as much as possible up to `amount` assets of `id`.", + "", + " Origin must be Signed and the sender should be the Manager of the asset `id`.", + "", + " Bails with `BalanceZero` if the `who` is already dead.", + "", + " - `id`: The identifier of the asset to have some amount burned.", + " - `who`: The account to be debited from.", + " - `amount`: The maximum amount by which `who`'s balance should be reduced.", + "", + " Emits `Burned` with the actual amount burned. If this takes the balance to below the", + " minimum for the asset, then the amount burned is increased to take it to zero.", + "", + " Weight: `O(1)`", + " Modes: Post-existence of `who`; Pre & post Zombie-status of `who`." + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from the sender account to another.", + "", + " Origin must be Signed.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `target`: The account to be credited.", + " - `amount`: The amount by which the sender's balance of assets should be reduced and", + " `target`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the sender balance above zero but below", + " the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `target`; Post-existence of sender; Account pre-existence of", + " `target`." + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from the sender account to another, keeping the sender account alive.", + "", + " Origin must be Signed.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `target`: The account to be credited.", + " - `amount`: The amount by which the sender's balance of assets should be reduced and", + " `target`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the sender balance above zero but below", + " the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `target`; Post-existence of sender; Account pre-existence of", + " `target`." + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Move some assets from one account to another.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to have some amount transferred.", + " - `source`: The account to be debited.", + " - `dest`: The account to be credited.", + " - `amount`: The amount by which the `source`'s balance of assets should be reduced and", + " `dest`'s balance increased. The amount actually transferred may be slightly greater in", + " the case that the transfer would otherwise take the `source` balance above zero but", + " below the minimum balance. Must be greater than zero.", + "", + " Emits `Transferred` with the actual amount transferred. If this takes the source balance", + " to below the minimum for the asset, then the amount transferred is increased to take it", + " to zero.", + "", + " Weight: `O(1)`", + " Modes: Pre-existence of `dest`; Post-existence of `source`; Account pre-existence of", + " `dest`." + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Disallow further unprivileged transfers from an account.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `who`: The account to be frozen.", + "", + " Emits `Frozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Allow unprivileged transfers from an account again.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `who`: The account to be unfrozen.", + "", + " Emits `Thawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "freeze_asset", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Disallow further unprivileged transfers for the asset class.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + "", + " Emits `Frozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw_asset", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Allow unprivileged transfers for the asset again.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `id`.", + "", + " - `id`: The identifier of the asset to be thawed.", + "", + " Emits `Thawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "transfer_ownership", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Owner of an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The new Owner of this asset.", + "", + " Emits `OwnerChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_team", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Issuer, Admin and Freezer of an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " - `id`: The identifier of the asset to be frozen.", + " - `issuer`: The new Issuer of this asset.", + " - `admin`: The new Admin of this asset.", + " - `freezer`: The new Freezer of this asset.", + "", + " Emits `TeamChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "name", + "type": "Bytes" + }, + { + "name": "symbol", + "type": "Bytes" + }, + { + "name": "decimals", + "type": "u8" + } + ], + "docs": [ + " Set the metadata for an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " Funds of sender are reserved according to the formula:", + " `MetadataDepositBase + MetadataDepositPerByte * (name.len + symbol.len)` taking into", + " account any already reserved funds.", + "", + " - `id`: The identifier of the asset to update.", + " - `name`: The user friendly name of this asset. Limited in length by `StringLimit`.", + " - `symbol`: The exchange symbol for this asset. Limited in length by `StringLimit`.", + " - `decimals`: The number of decimals this asset uses to represent one unit.", + "", + " Emits `MetadataSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "clear_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `id`.", + "", + " Any deposit is freed for the asset owner.", + "", + " - `id`: The identifier of the asset to clear.", + "", + " Emits `MetadataCleared`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_set_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "name", + "type": "Bytes" + }, + { + "name": "symbol", + "type": "Bytes" + }, + { + "name": "decimals", + "type": "u8" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Force the metadata for an asset to some value.", + "", + " Origin must be ForceOrigin.", + "", + " Any deposit is left alone.", + "", + " - `id`: The identifier of the asset to update.", + " - `name`: The user friendly name of this asset. Limited in length by `StringLimit`.", + " - `symbol`: The exchange symbol for this asset. Limited in length by `StringLimit`.", + " - `decimals`: The number of decimals this asset uses to represent one unit.", + "", + " Emits `MetadataSet`.", + "", + " Weight: `O(N + S)` where N and S are the length of the name and symbol respectively." + ] + }, + { + "name": "force_clear_metadata", + "args": [ + { + "name": "id", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset.", + "", + " Origin must be ForceOrigin.", + "", + " Any deposit is returned.", + "", + " - `id`: The identifier of the asset to clear.", + "", + " Emits `MetadataCleared`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_asset_status", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + }, + { + "name": "min_balance", + "type": "Compact" + }, + { + "name": "is_sufficient", + "type": "bool" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Alter the attributes of a given asset.", + "", + " Origin must be `ForceOrigin`.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The new Owner of this asset.", + " - `issuer`: The new Issuer of this asset.", + " - `admin`: The new Admin of this asset.", + " - `freezer`: The new Freezer of this asset.", + " - `min_balance`: The minimum balance of this new asset that any single account must", + " have. If an account's balance is reduced below this, then it collapses to zero.", + " - `is_sufficient`: Whether a non-zero balance of this asset is deposit of sufficient", + " value to account for the state bloat associated with its balance storage. If set to", + " `true`, then non-zero balances may be stored without a `consumer` reference (and thus", + " an ED in the Balances pallet or whatever else is used to control user-account state", + " growth).", + " - `is_frozen`: Whether this asset class is frozen except for permissioned/admin", + " instructions.", + "", + " Emits `AssetStatusChanged` with the identity of the asset.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "approve_transfer", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "delegate", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Approve an amount of asset for transfer by a delegated third-party account.", + "", + " Origin must be Signed.", + "", + " Ensures that `ApprovalDeposit` worth of `Currency` is reserved from signing account", + " for the purpose of holding the approval. If some non-zero amount of assets is already", + " approved from signing account to `delegate`, then it is topped up or unreserved to", + " meet the right value.", + "", + " NOTE: The signing account does not need to own `amount` of assets at the point of", + " making this call.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account to delegate permission to transfer asset.", + " - `amount`: The amount of asset that may be transferred by `delegate`. If there is", + " already an approval in place, then this acts additively.", + "", + " Emits `ApprovedTransfer` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "cancel_approval", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "delegate", + "type": "LookupSource" + } + ], + "docs": [ + " Cancel all of some asset approved for delegated transfer by a third-party account.", + "", + " Origin must be Signed and there must be an approval in place between signer and", + " `delegate`.", + "", + " Unreserves any deposit previously reserved by `approve_transfer` for the approval.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account delegated permission to transfer asset.", + "", + " Emits `ApprovalCancelled` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_cancel_approval", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "delegate", + "type": "LookupSource" + } + ], + "docs": [ + " Cancel all of some asset approved for delegated transfer by a third-party account.", + "", + " Origin must be either ForceOrigin or Signed origin with the signer being the Admin", + " account of the asset `id`.", + "", + " Unreserves any deposit previously reserved by `approve_transfer` for the approval.", + "", + " - `id`: The identifier of the asset.", + " - `delegate`: The account delegated permission to transfer asset.", + "", + " Emits `ApprovalCancelled` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "transfer_approved", + "args": [ + { + "name": "id", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "destination", + "type": "LookupSource" + }, + { + "name": "amount", + "type": "Compact" + } + ], + "docs": [ + " Transfer some asset balance from a previously delegated account to some third-party", + " account.", + "", + " Origin must be Signed and there must be an approval in place by the `owner` to the", + " signer.", + "", + " If the entire amount approved for transfer is transferred, then any deposit previously", + " reserved by `approve_transfer` is unreserved.", + "", + " - `id`: The identifier of the asset.", + " - `owner`: The account which previously approved for a transfer of at least `amount` and", + " from which the asset balance will be withdrawn.", + " - `destination`: The account to which the asset balance of `amount` will be transferred.", + " - `amount`: The amount of assets to transfer.", + "", + " Emits `TransferredApproved` on success.", + "", + " Weight: `O(1)`" + ] + } + ], + "events": [ + { + "name": "Created", + "args": [ + "AssetId", + "AccountId", + "AccountId" + ], + "docs": [ + " Some asset class was created. \\[asset_id, creator, owner\\]" + ] + }, + { + "name": "Issued", + "args": [ + "AssetId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were issued. \\[asset_id, owner, total_supply\\]" + ] + }, + { + "name": "Transferred", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were transferred. \\[asset_id, from, to, amount\\]" + ] + }, + { + "name": "Burned", + "args": [ + "AssetId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " Some assets were destroyed. \\[asset_id, owner, balance\\]" + ] + }, + { + "name": "TeamChanged", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " The management team changed \\[asset_id, issuer, admin, freezer\\]" + ] + }, + { + "name": "OwnerChanged", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " The owner changed \\[asset_id, owner\\]" + ] + }, + { + "name": "Frozen", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some account `who` was frozen. \\[asset_id, who\\]" + ] + }, + { + "name": "Thawed", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some account `who` was thawed. \\[asset_id, who\\]" + ] + }, + { + "name": "AssetFrozen", + "args": [ + "AssetId" + ], + "docs": [ + " Some asset `asset_id` was frozen. \\[asset_id\\]" + ] + }, + { + "name": "AssetThawed", + "args": [ + "AssetId" + ], + "docs": [ + " Some asset `asset_id` was thawed. \\[asset_id\\]" + ] + }, + { + "name": "Destroyed", + "args": [ + "AssetId" + ], + "docs": [ + " An asset class was destroyed." + ] + }, + { + "name": "ForceCreated", + "args": [ + "AssetId", + "AccountId" + ], + "docs": [ + " Some asset class was force-created. \\[asset_id, owner\\]" + ] + }, + { + "name": "MetadataSet", + "args": [ + "AssetId", + "Bytes", + "Bytes", + "u8", + "bool" + ], + "docs": [ + " New metadata has been set for an asset. \\[asset_id, name, symbol, decimals, is_frozen\\]" + ] + }, + { + "name": "MetadataCleared", + "args": [ + "AssetId" + ], + "docs": [ + " Metadata has been cleared for an asset. \\[asset_id\\]" + ] + }, + { + "name": "ApprovedTransfer", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " (Additional) funds have been approved for transfer to a destination account.", + " \\[asset_id, source, delegate, amount\\]" + ] + }, + { + "name": "ApprovalCancelled", + "args": [ + "AssetId", + "AccountId", + "AccountId" + ], + "docs": [ + " An approval for account `delegate` was cancelled by `owner`.", + " \\[id, owner, delegate\\]" + ] + }, + { + "name": "TransferredApproved", + "args": [ + "AssetId", + "AccountId", + "AccountId", + "AccountId", + "TAssetBalance" + ], + "docs": [ + " An `amount` was transferred in its entirety from `owner` to `destination` by", + " the approved `delegate`.", + " \\[id, owner, delegate, destination\\]" + ] + }, + { + "name": "AssetStatusChanged", + "args": [ + "AssetId" + ], + "docs": [ + " An asset has had its attributes changed by the `Force` origin.", + " \\[id\\]" + ] + } + ], + "constants": [ + { + "name": "AssetDeposit", + "type": "DepositBalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved for an asset." + ] + }, + { + "name": "MetadataDepositBase", + "type": "DepositBalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved when adding metadata to your asset." + ] + }, + { + "name": "MetadataDepositPerByte", + "type": "DepositBalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The additional funds that must be reserved for the number of bytes you store in your", + " metadata." + ] + }, + { + "name": "ApprovalDeposit", + "type": "DepositBalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The amount of funds that must be reserved when creating a new approval." + ] + }, + { + "name": "StringLimit", + "type": "u32", + "value": "0x32000000", + "docs": [ + " The maximum length of a name or symbol stored on-chain." + ] + } + ], + "errors": [ + { + "name": "BalanceLow", + "docs": [ + " Account balance must be greater than or equal to the transfer amount." + ] + }, + { + "name": "BalanceZero", + "docs": [ + " Balance should be non-zero." + ] + }, + { + "name": "NoPermission", + "docs": [ + " The signing account has no permission to do the operation." + ] + }, + { + "name": "Unknown", + "docs": [ + " The given asset ID is unknown." + ] + }, + { + "name": "Frozen", + "docs": [ + " The origin account is frozen." + ] + }, + { + "name": "InUse", + "docs": [ + " The asset ID is already taken." + ] + }, + { + "name": "BadWitness", + "docs": [ + " Invalid witness data given." + ] + }, + { + "name": "MinBalanceZero", + "docs": [ + " Minimum balance should be non-zero." + ] + }, + { + "name": "NoProvider", + "docs": [ + " No provider reference exists to allow a non-zero balance of a non-self-sufficient asset." + ] + }, + { + "name": "BadMetadata", + "docs": [ + " Invalid metadata given." + ] + }, + { + "name": "Unapproved", + "docs": [ + " No approval exists that would allow the transfer." + ] + }, + { + "name": "WouldDie", + "docs": [ + " The source account would not survive the transfer and it needs to stay alive." + ] + } + ], + "index": 34 + }, + { + "name": "Mmr", + "storage": { + "prefix": "Mmr", + "items": [ + { + "name": "RootHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Latest MMR Root hash." + ] + }, + { + "name": "NumberOfLeaves", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current size of the MMR (number of leaves)." + ] + }, + { + "name": "Nodes", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Identity", + "key": "u64", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Hashes of the nodes in the MMR.", + "", + " Note this collection only contains MMR peaks, the inner nodes (and leaves)", + " are pruned and only stored in the Offchain DB." + ] + } + ] + }, + "calls": null, + "events": null, + "constants": [], + "errors": [], + "index": 35 + }, + { + "name": "Lottery", + "storage": { + "prefix": "Lottery", + "items": [ + { + "name": "LotteryIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [] + }, + { + "name": "Lottery", + "modifier": "Optional", + "type": { + "plain": "LotteryConfig" + }, + "fallback": "0x00", + "docs": [ + " The configuration for the current lottery." + ] + }, + { + "name": "Participants", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "AccountId", + "value": "(u32,Vec)", + "linked": false + } + }, + "fallback": "0x0000000000", + "docs": [ + " Users who have purchased a ticket. (Lottery Index, Tickets Purchased)" + ] + }, + { + "name": "TicketsCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Total number of tickets sold." + ] + }, + { + "name": "Tickets", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "u32", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Each ticket's owner.", + "", + " May have residual storage from previous lotteries. Use `TicketsCount` to see which ones", + " are actually valid ticket mappings." + ] + }, + { + "name": "CallIndices", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The calls stored in this pallet to be used in an active lottery if configured", + " by `Config::ValidateCall`." + ] + } + ] + }, + "calls": [ + { + "name": "buy_ticket", + "args": [ + { + "name": "call", + "type": "Call" + } + ], + "docs": [ + " Buy a ticket to enter the lottery.", + "", + " This extrinsic acts as a passthrough function for `call`. In all", + " situations where `call` alone would succeed, this extrinsic should", + " succeed.", + "", + " If `call` is successful, then we will attempt to purchase a ticket,", + " which may fail silently. To detect success of a ticket purchase, you", + " should listen for the `TicketBought` event.", + "", + " This extrinsic must be called by a signed origin." + ] + }, + { + "name": "set_calls", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Set calls in storage which can be used to purchase a lottery ticket.", + "", + " This function only matters if you use the `ValidateCall` implementation", + " provided by this pallet, which uses storage to determine the valid calls.", + "", + " This extrinsic must be called by the Manager origin." + ] + }, + { + "name": "start_lottery", + "args": [ + { + "name": "price", + "type": "BalanceOf" + }, + { + "name": "length", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + }, + { + "name": "repeat", + "type": "bool" + } + ], + "docs": [ + " Start a lottery using the provided configuration.", + "", + " This extrinsic must be called by the `ManagerOrigin`.", + "", + " Parameters:", + "", + " * `price`: The cost of a single ticket.", + " * `length`: How long the lottery should run for starting at the current block.", + " * `delay`: How long after the lottery end we should wait before picking a winner.", + " * `repeat`: If the lottery should repeat when completed." + ] + }, + { + "name": "stop_repeat", + "args": [], + "docs": [ + " If a lottery is repeating, you can use this to stop the repeat.", + " The lottery will continue to run to completion.", + "", + " This extrinsic must be called by the `ManagerOrigin`." + ] + } + ], + "events": [ + { + "name": "LotteryStarted", + "args": [], + "docs": [ + " A lottery has been started!" + ] + }, + { + "name": "CallsUpdated", + "args": [], + "docs": [ + " A new set of calls have been set!" + ] + }, + { + "name": "Winner", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A winner has been chosen!" + ] + }, + { + "name": "TicketBought", + "args": [ + "AccountId", + "CallIndex" + ], + "docs": [ + " A ticket has been bought!" + ] + } + ], + "constants": [ + { + "name": "PalletId", + "type": "PalletId", + "value": "0x70792f6c6f74746f", + "docs": [ + " The Lottery's pallet id" + ] + }, + { + "name": "MaxCalls", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The max number of calls available in a single lottery." + ] + }, + { + "name": "MaxGenerateRandom", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " Number of time we should try to generate a random number that has no modulo bias.", + " The larger this number, the more potential computation is used for picking the winner,", + " but also the more likely that the chosen winner is done fairly." + ] + } + ], + "errors": [ + { + "name": "NotConfigured", + "docs": [ + " A lottery has not been configured." + ] + }, + { + "name": "InProgress", + "docs": [ + " A lottery is already in progress." + ] + }, + { + "name": "AlreadyEnded", + "docs": [ + " A lottery has already ended." + ] + }, + { + "name": "InvalidCall", + "docs": [ + " The call is not valid for an open lottery." + ] + }, + { + "name": "AlreadyParticipating", + "docs": [ + " You are already participating in the lottery with this call." + ] + }, + { + "name": "TooManyCalls", + "docs": [ + " Too many calls for a single lottery." + ] + }, + { + "name": "EncodingFailed", + "docs": [ + " Failed to encode calls" + ] + } + ], + "index": 36 + }, + { + "name": "Gilt", + "storage": { + "prefix": "Gilt", + "items": [ + { + "name": "QueueTotals", + "modifier": "Default", + "type": { + "plain": "Vec<(u32,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The totals of items and balances within each queue. Saves a lot of storage reads in the", + " case of sparsely packed queues.", + "", + " The vector is indexed by duration in `Period`s, offset by one, so information on the queue", + " whose duration is one `Period` would be storage `0`." + ] + }, + { + "name": "Queues", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "u32", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The queues of bids ready to become gilts. Indexed by duration (in `Period`s)." + ] + }, + { + "name": "ActiveTotal", + "modifier": "Default", + "type": { + "plain": "ActiveGiltsTotal" + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Information relating to the gilts currently active." + ] + }, + { + "name": "Active", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "ActiveIndex", + "value": "ActiveGilt", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The currently active gilts, indexed according to the order of creation." + ] + } + ] + }, + "calls": [ + { + "name": "place_bid", + "args": [ + { + "name": "amount", + "type": "Compact" + }, + { + "name": "duration", + "type": "u32" + } + ], + "docs": [ + " Place a bid for a gilt to be issued.", + "", + " Origin must be Signed, and account must have at least `amount` in free balance.", + "", + " - `amount`: The amount of the bid; these funds will be reserved. If the bid is", + " successfully elevated into an issued gilt, then these funds will continue to be", + " reserved until the gilt expires. Must be at least `MinFreeze`.", + " - `duration`: The number of periods for which the funds will be locked if the gilt is", + " issued. It will expire only after this period has elapsed after the point of issuance.", + " Must be greater than 1 and no more than `QueueCount`.", + "", + " Complexities:", + " - `Queues[duration].len()` (just take max)." + ] + }, + { + "name": "retract_bid", + "args": [ + { + "name": "amount", + "type": "Compact" + }, + { + "name": "duration", + "type": "u32" + } + ], + "docs": [ + " Retract a previously placed bid.", + "", + " Origin must be Signed, and the account should have previously issued a still-active bid", + " of `amount` for `duration`.", + "", + " - `amount`: The amount of the previous bid.", + " - `duration`: The duration of the previous bid." + ] + }, + { + "name": "set_target", + "args": [ + { + "name": "target", + "type": "Compact" + } + ], + "docs": [ + " Set target proportion of gilt-funds.", + "", + " Origin must be `AdminOrigin`.", + "", + " - `target`: The target proportion of effective issued funds that should be under gilts", + " at any one time." + ] + }, + { + "name": "thaw", + "args": [ + { + "name": "index", + "type": "Compact" + } + ], + "docs": [ + " Remove an active but expired gilt. Reserved funds under gilt are freed and balance is", + " adjusted to ensure that the funds grow or shrink to maintain the equivalent proportion", + " of effective total issued funds.", + "", + " Origin must be Signed and the account must be the owner of the gilt of the given index.", + "", + " - `index`: The index of the gilt to be thawed." + ] + } + ], + "events": [ + { + "name": "BidPlaced", + "args": [ + "AccountId", + "BalanceOf", + "u32" + ], + "docs": [ + " A bid was successfully placed.", + " \\[ who, amount, duration \\]" + ] + }, + { + "name": "BidRetracted", + "args": [ + "AccountId", + "BalanceOf", + "u32" + ], + "docs": [ + " A bid was successfully removed (before being accepted as a gilt).", + " \\[ who, amount, duration \\]" + ] + }, + { + "name": "GiltIssued", + "args": [ + "ActiveIndex", + "BlockNumber", + "AccountId", + "BalanceOf" + ], + "docs": [ + " A bid was accepted as a gilt. The balance may not be released until expiry.", + " \\[ index, expiry, who, amount \\]" + ] + }, + { + "name": "GiltThawed", + "args": [ + "ActiveIndex", + "AccountId", + "BalanceOf", + "BalanceOf" + ], + "docs": [ + " An expired gilt has been thawed.", + " \\[ index, who, original_amount, additional_amount \\]" + ] + } + ], + "constants": [ + { + "name": "IgnoredIssuance", + "type": "BalanceOf", + "value": "0x00000000000000000000000000000000", + "docs": [ + " The issuance to ignore. This is subtracted from the `Currency`'s `total_issuance` to get", + " the issuance by which we inflate or deflate the gilt." + ] + }, + { + "name": "QueueCount", + "type": "u32", + "value": "0x2c010000", + "docs": [ + " Number of duration queues in total. This sets the maximum duration supported, which is", + " this value multiplied by `Period`." + ] + }, + { + "name": "MaxQueueLen", + "type": "u32", + "value": "0xe8030000", + "docs": [ + " Maximum number of items that may be in each duration queue." + ] + }, + { + "name": "FifoQueueLen", + "type": "u32", + "value": "0xf4010000", + "docs": [ + " Portion of the queue which is free from ordering and just a FIFO.", + "", + " Must be no greater than `MaxQueueLen`." + ] + }, + { + "name": "Period", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The base period for the duration queues. This is the common multiple across all", + " supported freezing durations that can be bid upon." + ] + }, + { + "name": "MinFreeze", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount of funds that may be offered to freeze for a gilt. Note that this", + " does not actually limit the amount which may be frozen in a gilt since gilts may be", + " split up in order to satisfy the desired amount of funds under gilts.", + "", + " It should be at least big enough to ensure that there is no possible storage spam attack", + " or queue-filling attack." + ] + }, + { + "name": "IntakePeriod", + "type": "BlockNumber", + "value": "0x0a000000", + "docs": [ + " The number of blocks between consecutive attempts to issue more gilts in an effort to", + " get to the target amount to be frozen.", + "", + " A larger value results in fewer storage hits each block, but a slower period to get to", + " the target." + ] + }, + { + "name": "MaxIntakeBids", + "type": "u32", + "value": "0x0a000000", + "docs": [ + " The maximum amount of bids that can be turned into issued gilts each block. A larger", + " value here means less of the block available for transactions should there be a glut of", + " bids to make into gilts to reach the target." + ] + } + ], + "errors": [ + { + "name": "DurationTooSmall", + "docs": [ + " The duration of the bid is less than one." + ] + }, + { + "name": "DurationTooBig", + "docs": [ + " The duration is the bid is greater than the number of queues." + ] + }, + { + "name": "AmountTooSmall", + "docs": [ + " The amount of the bid is less than the minimum allowed." + ] + }, + { + "name": "BidTooLow", + "docs": [ + " The queue for the bid's duration is full and the amount bid is too low to get in through", + " replacing an existing bid." + ] + }, + { + "name": "Unknown", + "docs": [ + " Gilt index is unknown." + ] + }, + { + "name": "NotOwner", + "docs": [ + " Not the owner of the gilt." + ] + }, + { + "name": "NotExpired", + "docs": [ + " Gilt not yet at expiry date." + ] + }, + { + "name": "NotFound", + "docs": [ + " The given bid for retraction is not found." + ] + } + ], + "index": 37 + }, + { + "name": "Uniques", + "storage": { + "prefix": "Uniques", + "items": [ + { + "name": "Class", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "ClassId", + "value": "ClassDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Details of an asset class." + ] + }, + { + "name": "Account", + "modifier": "Optional", + "type": { + "nMap": { + "keyVec": [ + "AccountId", + "ClassId", + "InstanceId" + ], + "hashers": [ + "Blake2_128Concat", + "Blake2_128Concat", + "Blake2_128Concat" + ], + "value": "()" + } + }, + "fallback": "0x00", + "docs": [ + " The assets held by any given account; set out this way so that assets owned by a single", + " account can be enumerated." + ] + }, + { + "name": "Asset", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_128Concat", + "key1": "ClassId", + "key2": "InstanceId", + "value": "InstanceDetails", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " The assets in existence and their ownership details." + ] + }, + { + "name": "ClassMetadataOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "ClassId", + "value": "ClassMetadata", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Metadata of an asset class." + ] + }, + { + "name": "InstanceMetadataOf", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_128Concat", + "key1": "ClassId", + "key2": "InstanceId", + "value": "InstanceMetadata", + "key2Hasher": "Blake2_128Concat" + } + }, + "fallback": "0x00", + "docs": [ + " Metadata of an asset instance." + ] + }, + { + "name": "Attribute", + "modifier": "Optional", + "type": { + "nMap": { + "keyVec": [ + "ClassId", + "Option", + "Bytes" + ], + "hashers": [ + "Blake2_128Concat", + "Blake2_128Concat", + "Blake2_128Concat" + ], + "value": "(Bytes,DepositBalanceOf)" + } + }, + "fallback": "0x00", + "docs": [ + " Metadata of an asset class." + ] + } + ] + }, + "calls": [ + { + "name": "create", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "admin", + "type": "LookupSource" + } + ], + "docs": [ + " Issue a new class of non-fungible assets from a public origin.", + "", + " This new asset class has no assets initially and its owner is the origin.", + "", + " The origin must be Signed and the sender must have sufficient funds free.", + "", + " `AssetDeposit` funds of sender are reserved.", + "", + " Parameters:", + " - `class`: The identifier of the new asset class. This must not be currently in use.", + " - `admin`: The admin of this class of assets. The admin is the initial address of each", + " member of the asset class's admin team.", + "", + " Emits `Created` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_create", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "free_holding", + "type": "bool" + } + ], + "docs": [ + " Issue a new class of non-fungible assets from a privileged origin.", + "", + " This new asset class has no assets initially.", + "", + " The origin must conform to `ForceOrigin`.", + "", + " Unlike `create`, no funds are reserved.", + "", + " - `class`: The identifier of the new asset. This must not be currently in use.", + " - `owner`: The owner of this class of assets. The owner has full superuser permissions", + " over this asset, but may later change and configure the permissions using", + " `transfer_ownership` and `set_team`.", + "", + " Emits `ForceCreated` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "destroy", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "witness", + "type": "DestroyWitness" + } + ], + "docs": [ + " Destroy a class of fungible assets.", + "", + " The origin must conform to `ForceOrigin` or must be `Signed` and the sender must be the", + " owner of the asset `class`.", + "", + " - `class`: The identifier of the asset class to be destroyed.", + " - `witness`: Information on the instances minted in the asset class. This must be", + " correct.", + "", + " Emits `Destroyed` event when successful.", + "", + " Weight: `O(n + m)` where:", + " - `n = witness.instances`", + " - `m = witness.instance_metadatas`", + " - `a = witness.attributes`" + ] + }, + { + "name": "mint", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + } + ], + "docs": [ + " Mint an asset instance of a particular class.", + "", + " The origin must be Signed and the sender must be the Issuer of the asset `class`.", + "", + " - `class`: The class of the asset to be minted.", + " - `instance`: The instance value of the asset to be minted.", + " - `beneficiary`: The initial owner of the minted asset.", + "", + " Emits `Issued` event when successful.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "burn", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "check_owner", + "type": "Option" + } + ], + "docs": [ + " Destroy a single asset instance.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `class`.", + "", + " - `class`: The class of the asset to be burned.", + " - `instance`: The instance of the asset to be burned.", + " - `check_owner`: If `Some` then the operation will fail with `WrongOwner` unless the", + " asset is owned by this value.", + "", + " Emits `Burned` with the actual amount burned.", + "", + " Weight: `O(1)`", + " Modes: `check_owner.is_some()`." + ] + }, + { + "name": "transfer", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "dest", + "type": "LookupSource" + } + ], + "docs": [ + " Move an asset from the sender account to another.", + "", + " Origin must be Signed and the signing account must be either:", + " - the Admin of the asset `class`;", + " - the Owner of the asset `instance`;", + " - the approved delegate for the asset `instance` (in this case, the approval is reset).", + "", + " Arguments:", + " - `class`: The class of the asset to be transferred.", + " - `instance`: The instance of the asset to be transferred.", + " - `dest`: The account to receive ownership of the asset.", + "", + " Emits `Transferred`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "redeposit", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instances", + "type": "Vec" + } + ], + "docs": [ + " Reevaluate the deposits on some assets.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `class`.", + "", + " - `class`: The class of the asset to be frozen.", + " - `instances`: The instances of the asset class whose deposits will be reevaluated.", + "", + " NOTE: This exists as a best-effort function. Any asset instances which are unknown or", + " in the case that the owner account does not have reservable funds to pay for a", + " deposit increase are ignored. Generally the owner isn't going to call this on instances", + " whose existing deposit is less than the refreshed deposit as it would only cost them,", + " so it's of little consequence.", + "", + " It will still return an error in the case that the class is unknown of the signer is", + " not permitted to call it.", + "", + " Weight: `O(instances.len())`" + ] + }, + { + "name": "freeze", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + } + ], + "docs": [ + " Disallow further unprivileged transfer of an asset instance.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `class`.", + "", + " - `class`: The class of the asset to be frozen.", + " - `instance`: The instance of the asset to be frozen.", + "", + " Emits `Frozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + } + ], + "docs": [ + " Re-allow unprivileged transfer of an asset instance.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `class`.", + "", + " - `class`: The class of the asset to be thawed.", + " - `instance`: The instance of the asset to be thawed.", + "", + " Emits `Thawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "freeze_class", + "args": [ + { + "name": "class", + "type": "Compact" + } + ], + "docs": [ + " Disallow further unprivileged transfers for a whole asset class.", + "", + " Origin must be Signed and the sender should be the Freezer of the asset `class`.", + "", + " - `class`: The asset class to be frozen.", + "", + " Emits `ClassFrozen`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "thaw_class", + "args": [ + { + "name": "class", + "type": "Compact" + } + ], + "docs": [ + " Re-allow unprivileged transfers for a whole asset class.", + "", + " Origin must be Signed and the sender should be the Admin of the asset `class`.", + "", + " - `class`: The class to be thawed.", + "", + " Emits `ClassThawed`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "transfer_ownership", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Owner of an asset class.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `class`.", + "", + " - `class`: The asset class whose owner should be changed.", + " - `owner`: The new Owner of this asset class.", + "", + " Emits `OwnerChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_team", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + } + ], + "docs": [ + " Change the Issuer, Admin and Freezer of an asset class.", + "", + " Origin must be Signed and the sender should be the Owner of the asset `class`.", + "", + " - `class`: The asset class whose team should be changed.", + " - `issuer`: The new Issuer of this asset class.", + " - `admin`: The new Admin of this asset class.", + " - `freezer`: The new Freezer of this asset class.", + "", + " Emits `TeamChanged`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "approve_transfer", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "delegate", + "type": "LookupSource" + } + ], + "docs": [ + " Approve an instance to be transferred by a delegated third-party account.", + "", + " Origin must be Signed and must be the owner of the asset `instance`.", + "", + " - `class`: The class of the asset to be approved for delegated transfer.", + " - `instance`: The instance of the asset to be approved for delegated transfer.", + " - `delegate`: The account to delegate permission to transfer the asset.", + "", + " Emits `ApprovedTransfer` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "cancel_approval", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "maybe_check_delegate", + "type": "Option" + } + ], + "docs": [ + " Cancel the prior approval for the transfer of an asset by a delegate.", + "", + " Origin must be either:", + " - the `Force` origin;", + " - `Signed` with the signer being the Admin of the asset `class`;", + " - `Signed` with the signer being the Owner of the asset `instance`;", + "", + " Arguments:", + " - `class`: The class of the asset of whose approval will be cancelled.", + " - `instance`: The instance of the asset of whose approval will be cancelled.", + " - `maybe_check_delegate`: If `Some` will ensure that the given account is the one to", + " which permission of transfer is delegated.", + "", + " Emits `ApprovalCancelled` on success.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "force_asset_status", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "owner", + "type": "LookupSource" + }, + { + "name": "issuer", + "type": "LookupSource" + }, + { + "name": "admin", + "type": "LookupSource" + }, + { + "name": "freezer", + "type": "LookupSource" + }, + { + "name": "free_holding", + "type": "bool" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Alter the attributes of a given asset.", + "", + " Origin must be `ForceOrigin`.", + "", + " - `class`: The identifier of the asset.", + " - `owner`: The new Owner of this asset.", + " - `issuer`: The new Issuer of this asset.", + " - `admin`: The new Admin of this asset.", + " - `freezer`: The new Freezer of this asset.", + " - `free_holding`: Whether a deposit is taken for holding an instance of this asset", + " class.", + " - `is_frozen`: Whether this asset class is frozen except for permissioned/admin", + " instructions.", + "", + " Emits `AssetStatusChanged` with the identity of the asset.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_attribute", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "maybe_instance", + "type": "Option" + }, + { + "name": "key", + "type": "Bytes" + }, + { + "name": "value", + "type": "Bytes" + } + ], + "docs": [ + " Set an attribute for an asset class or instance.", + "", + " Origin must be either `ForceOrigin` or Signed and the sender should be the Owner of the", + " asset `class`.", + "", + " If the origin is Signed, then funds of signer are reserved according to the formula:", + " `MetadataDepositBase + DepositPerByte * (key.len + value.len)` taking into", + " account any already reserved funds.", + "", + " - `class`: The identifier of the asset class whose instance's metadata to set.", + " - `maybe_instance`: The identifier of the asset instance whose metadata to set.", + " - `key`: The key of the attribute.", + " - `value`: The value to which to set the attribute.", + "", + " Emits `AttributeSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "clear_attribute", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "maybe_instance", + "type": "Option" + }, + { + "name": "key", + "type": "Bytes" + } + ], + "docs": [ + " Set an attribute for an asset class or instance.", + "", + " Origin must be either `ForceOrigin` or Signed and the sender should be the Owner of the", + " asset `class`.", + "", + " If the origin is Signed, then funds of signer are reserved according to the formula:", + " `MetadataDepositBase + DepositPerByte * (key.len + value.len)` taking into", + " account any already reserved funds.", + "", + " - `class`: The identifier of the asset class whose instance's metadata to set.", + " - `instance`: The identifier of the asset instance whose metadata to set.", + " - `key`: The key of the attribute.", + " - `value`: The value to which to set the attribute.", + "", + " Emits `AttributeSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_metadata", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Set the metadata for an asset instance.", + "", + " Origin must be either `ForceOrigin` or Signed and the sender should be the Owner of the", + " asset `class`.", + "", + " If the origin is Signed, then funds of signer are reserved according to the formula:", + " `MetadataDepositBase + DepositPerByte * data.len` taking into", + " account any already reserved funds.", + "", + " - `class`: The identifier of the asset class whose instance's metadata to set.", + " - `instance`: The identifier of the asset instance whose metadata to set.", + " - `data`: The general information of this asset. Limited in length by `StringLimit`.", + " - `is_frozen`: Whether the metadata should be frozen against further changes.", + "", + " Emits `MetadataSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "clear_metadata", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "instance", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset instance.", + "", + " Origin must be either `ForceOrigin` or Signed and the sender should be the Owner of the", + " asset `instance`.", + "", + " Any deposit is freed for the asset class owner.", + "", + " - `class`: The identifier of the asset class whose instance's metadata to clear.", + " - `instance`: The identifier of the asset instance whose metadata to clear.", + "", + " Emits `MetadataCleared`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "set_class_metadata", + "args": [ + { + "name": "class", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + }, + { + "name": "is_frozen", + "type": "bool" + } + ], + "docs": [ + " Set the metadata for an asset class.", + "", + " Origin must be either `ForceOrigin` or `Signed` and the sender should be the Owner of", + " the asset `class`.", + "", + " If the origin is `Signed`, then funds of signer are reserved according to the formula:", + " `MetadataDepositBase + DepositPerByte * data.len` taking into", + " account any already reserved funds.", + "", + " - `class`: The identifier of the asset whose metadata to update.", + " - `data`: The general information of this asset. Limited in length by `StringLimit`.", + " - `is_frozen`: Whether the metadata should be frozen against further changes.", + "", + " Emits `ClassMetadataSet`.", + "", + " Weight: `O(1)`" + ] + }, + { + "name": "clear_class_metadata", + "args": [ + { + "name": "class", + "type": "Compact" + } + ], + "docs": [ + " Clear the metadata for an asset class.", + "", + " Origin must be either `ForceOrigin` or `Signed` and the sender should be the Owner of", + " the asset `class`.", + "", + " Any deposit is freed for the asset class owner.", + "", + " - `class`: The identifier of the asset class whose metadata to clear.", + "", + " Emits `ClassMetadataCleared`.", + "", + " Weight: `O(1)`" + ] + } + ], + "events": [ + { + "name": "Created", + "args": [ + "ClassId", + "AccountId", + "AccountId" + ], + "docs": [ + " An asset class was created. \\[ class, creator, owner \\]" + ] + }, + { + "name": "ForceCreated", + "args": [ + "ClassId", + "AccountId" + ], + "docs": [ + " An asset class was force-created. \\[ class, owner \\]" + ] + }, + { + "name": "Destroyed", + "args": [ + "ClassId" + ], + "docs": [ + " An asset `class` was destroyed. \\[ class \\]" + ] + }, + { + "name": "Issued", + "args": [ + "ClassId", + "InstanceId", + "AccountId" + ], + "docs": [ + " An asset `instace` was issued. \\[ class, instance, owner \\]" + ] + }, + { + "name": "Transferred", + "args": [ + "ClassId", + "InstanceId", + "AccountId", + "AccountId" + ], + "docs": [ + " An asset `instace` was transferred. \\[ class, instance, from, to \\]" + ] + }, + { + "name": "Burned", + "args": [ + "ClassId", + "InstanceId", + "AccountId" + ], + "docs": [ + " An asset `instance` was destroyed. \\[ class, instance, owner \\]" + ] + }, + { + "name": "Frozen", + "args": [ + "ClassId", + "InstanceId" + ], + "docs": [ + " Some asset `instance` was frozen. \\[ class, instance \\]" + ] + }, + { + "name": "Thawed", + "args": [ + "ClassId", + "InstanceId" + ], + "docs": [ + " Some asset `instance` was thawed. \\[ class, instance \\]" + ] + }, + { + "name": "ClassFrozen", + "args": [ + "ClassId" + ], + "docs": [ + " Some asset `class` was frozen. \\[ class \\]" + ] + }, + { + "name": "ClassThawed", + "args": [ + "ClassId" + ], + "docs": [ + " Some asset `class` was thawed. \\[ class \\]" + ] + }, + { + "name": "OwnerChanged", + "args": [ + "ClassId", + "AccountId" + ], + "docs": [ + " The owner changed \\[ class, new_owner \\]" + ] + }, + { + "name": "TeamChanged", + "args": [ + "ClassId", + "AccountId", + "AccountId", + "AccountId" + ], + "docs": [ + " The management team changed \\[ class, issuer, admin, freezer \\]" + ] + }, + { + "name": "ApprovedTransfer", + "args": [ + "ClassId", + "InstanceId", + "AccountId", + "AccountId" + ], + "docs": [ + " An `instance` of an asset `class` has been approved by the `owner` for transfer by a", + " `delegate`.", + " \\[ class, instance, owner, delegate \\]" + ] + }, + { + "name": "ApprovalCancelled", + "args": [ + "ClassId", + "InstanceId", + "AccountId", + "AccountId" + ], + "docs": [ + " An approval for a `delegate` account to transfer the `instance` of an asset `class` was", + " cancelled by its `owner`.", + " \\[ class, instance, owner, delegate \\]" + ] + }, + { + "name": "AssetStatusChanged", + "args": [ + "ClassId" + ], + "docs": [ + " An asset `class` has had its attributes changed by the `Force` origin.", + " \\[ class \\]" + ] + }, + { + "name": "ClassMetadataSet", + "args": [ + "ClassId", + "Bytes", + "bool" + ], + "docs": [ + " New metadata has been set for an asset class. \\[ class, data, is_frozen \\]" + ] + }, + { + "name": "ClassMetadataCleared", + "args": [ + "ClassId" + ], + "docs": [ + " Metadata has been cleared for an asset class. \\[ class \\]" + ] + }, + { + "name": "MetadataSet", + "args": [ + "ClassId", + "InstanceId", + "Bytes", + "bool" + ], + "docs": [ + " New metadata has been set for an asset instance.", + " \\[ class, instance, data, is_frozen \\]" + ] + }, + { + "name": "MetadataCleared", + "args": [ + "ClassId", + "InstanceId" + ], + "docs": [ + " Metadata has been cleared for an asset instance. \\[ class, instance \\]" + ] + }, + { + "name": "Redeposited", + "args": [ + "ClassId", + "Vec" + ], + "docs": [ + " Metadata has been cleared for an asset instance. \\[ class, successful_instances \\]" + ] + }, + { + "name": "AttributeSet", + "args": [ + "ClassId", + "Option", + "Bytes", + "Bytes" + ], + "docs": [ + " New attribute metadata has been set for an asset class or instance.", + " \\[ class, maybe_instance, key, value \\]" + ] + }, + { + "name": "AttributeCleared", + "args": [ + "ClassId", + "Option", + "Bytes" + ], + "docs": [ + " Attribute metadata has been cleared for an asset class or instance.", + " \\[ class, maybe_instance, key, maybe_value \\]" + ] + } + ], + "constants": [ + { + "name": "ClassDeposit", + "type": "DepositBalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved for an asset class." + ] + }, + { + "name": "InstanceDeposit", + "type": "DepositBalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved for an asset instance." + ] + }, + { + "name": "MetadataDepositBase", + "type": "DepositBalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved when adding metadata to your asset." + ] + }, + { + "name": "AttributeDepositBase", + "type": "DepositBalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [ + " The basic amount of funds that must be reserved when adding an attribute to an asset." + ] + }, + { + "name": "DepositPerByte", + "type": "DepositBalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The additional funds that must be reserved for the number of bytes store in metadata,", + " either \"normal\" metadata or attribute metadata." + ] + }, + { + "name": "StringLimit", + "type": "u32", + "value": "0x32000000", + "docs": [ + " The maximum length of data stored on-chain." + ] + }, + { + "name": "KeyLimit", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum length of an attribute key." + ] + }, + { + "name": "ValueLimit", + "type": "u32", + "value": "0x00010000", + "docs": [ + " The maximum length of an attribute value." + ] + } + ], + "errors": [ + { + "name": "NoPermission", + "docs": [ + " The signing account has no permission to do the operation." + ] + }, + { + "name": "Unknown", + "docs": [ + " The given asset ID is unknown." + ] + }, + { + "name": "AlreadyExists", + "docs": [ + " The asset instance ID has already been used for an asset." + ] + }, + { + "name": "WrongOwner", + "docs": [ + " The owner turned out to be different to what was expected." + ] + }, + { + "name": "BadWitness", + "docs": [ + " Invalid witness data given." + ] + }, + { + "name": "InUse", + "docs": [ + " The asset ID is already taken." + ] + }, + { + "name": "Frozen", + "docs": [ + " The asset instance or class is frozen." + ] + }, + { + "name": "WrongDelegate", + "docs": [ + " The delegate turned out to be different to what was expected." + ] + }, + { + "name": "NoDelegate", + "docs": [ + " There is no delegate approved." + ] + }, + { + "name": "Unapproved", + "docs": [ + " No approval exists that would allow the transfer." + ] + } + ], + "index": 38 + }, + { + "name": "TransactionStorage", + "storage": { + "prefix": "TransactionStorage", + "items": [ + { + "name": "Transactions", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "BlockNumber", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Collection of transaction metadata by block number." + ] + }, + { + "name": "ChunkCount", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_128Concat", + "key": "BlockNumber", + "value": "u32", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " Count indexed chunks for each block." + ] + }, + { + "name": "ByteFee", + "modifier": "Optional", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00", + "docs": [ + " Storage fee per byte." + ] + }, + { + "name": "EntryFee", + "modifier": "Optional", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00", + "docs": [ + " Storage fee per transaction." + ] + }, + { + "name": "MaxTransactionSize", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Maximum data set in a single transaction in bytes." + ] + }, + { + "name": "MaxBlockTransactions", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Maximum number of indexed transactions in the block." + ] + }, + { + "name": "StoragePeriod", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " Storage period for data in blocks. Should match `sp_storage_proof::DEFAULT_STORAGE_PERIOD`", + " for block authoring." + ] + }, + { + "name": "BlockTransactions", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [] + }, + { + "name": "ProofChecked", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Was the proof checked in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "store", + "args": [ + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Index and store data on chain. Minimum data size is 1 bytes, maximum is `MaxTransactionSize`.", + " Data will be removed after `STORAGE_PERIOD` blocks, unless `renew` is called.", + " # ", + " - n*log(n) of data size, as all data is pushed to an in-memory trie.", + " Additionally contains a DB write.", + " # " + ] + }, + { + "name": "renew", + "args": [ + { + "name": "block", + "type": "BlockNumber" + }, + { + "name": "index", + "type": "u32" + } + ], + "docs": [ + " Renew previously stored data. Parameters are the block number that contains", + " previous `store` or `renew` call and transaction index within that block.", + " Transaction index is emitted in the `Stored` or `Renewed` event.", + " Applies same fees as `store`.", + " # ", + " - Constant.", + " # " + ] + }, + { + "name": "check_proof", + "args": [ + { + "name": "proof", + "type": "TransactionStorageProof" + } + ], + "docs": [ + " Check storage proof for block number `block_number() - StoragePeriod`.", + " If such block does not exist the proof is expected to be `None`.", + " # ", + " - Linear w.r.t the number of indexed transactions in the proved block for random probing.", + " There's a DB read for each transaction.", + " Here we assume a maximum of 100 probed transactions.", + " # " + ] + } + ], + "events": [ + { + "name": "Stored", + "args": [ + "u32" + ], + "docs": [ + " Stored data under specified index." + ] + }, + { + "name": "Renewed", + "args": [ + "u32" + ], + "docs": [ + " Renewed data under specified index." + ] + }, + { + "name": "ProofChecked", + "args": [], + "docs": [ + " Storage proof was successfully checked." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "InsufficientFunds", + "docs": [ + " Insufficient account balance." + ] + }, + { + "name": "NotConfigured", + "docs": [ + " Invalid configuration." + ] + }, + { + "name": "RenewedNotFound", + "docs": [ + " Renewed extrinsic is not found." + ] + }, + { + "name": "EmptyTransaction", + "docs": [ + " Attempting to store empty transaction" + ] + }, + { + "name": "UnexpectedProof", + "docs": [ + " Proof was not expected in this block." + ] + }, + { + "name": "InvalidProof", + "docs": [ + " Proof failed verification." + ] + }, + { + "name": "MissingProof", + "docs": [ + " Missing storage proof." + ] + }, + { + "name": "MissingStateData", + "docs": [ + " Unable to verify proof becasue state data is missing." + ] + }, + { + "name": "DoubleCheck", + "docs": [ + " Double proof check in the block." + ] + }, + { + "name": "ProofNotChecked", + "docs": [ + " Storage proof was not checked in the block." + ] + }, + { + "name": "TransactionTooLarge", + "docs": [ + " Transaction is too large." + ] + }, + { + "name": "TooManyTransactions", + "docs": [ + " Too many transactions in the block." + ] + }, + { + "name": "BadContext", + "docs": [ + " Attempted to call `store` outside of block execution." + ] + } + ], + "index": 39 + } + ], + "extrinsic": { + "version": 4, + "signedExtensions": [ + "CheckSpecVersion", + "CheckTxVersion", + "CheckGenesis", + "CheckMortality", + "CheckNonce", + "CheckWeight", + "ChargeTransactionPayment" + ] + } + } + } +} \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v9.hex b/packages/polkadot/tests/meta/v9.hex new file mode 100644 index 00000000..d3dd6bf3 --- /dev/null +++ b/packages/polkadot/tests/meta/v9.hex @@ -0,0 +1 @@ +0x6d65746109641853797374656d011853797374656d34304163636f756e744e6f6e636501010130543a3a4163636f756e74496420543a3a496e646578001000000000047c2045787472696e73696373206e6f6e636520666f72206163636f756e74732e3845787472696e736963436f756e7400000c753332040004b820546f74616c2065787472696e7369637320636f756e7420666f72207468652063757272656e7420626c6f636b2e4c416c6c45787472696e73696373576569676874000018576569676874040004150120546f74616c2077656967687420666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e40416c6c45787472696e736963734c656e00000c753332040004410120546f74616c206c656e6774682028696e2062797465732920666f7220616c6c2065787472696e736963732070757420746f6765746865722c20666f72207468652063757272656e7420626c6f636b2e24426c6f636b4861736801010138543a3a426c6f636b4e756d6265721c543a3a48617368008000000000000000000000000000000000000000000000000000000000000000000498204d6170206f6620626c6f636b206e756d6265727320746f20626c6f636b206861736865732e3445787472696e736963446174610101010c7533321c5665633c75383e000400043d012045787472696e73696373206461746120666f72207468652063757272656e7420626c6f636b20286d61707320616e2065787472696e736963277320696e64657820746f206974732064617461292e184e756d626572010038543a3a426c6f636b4e756d6265721000000000040901205468652063757272656e7420626c6f636b206e756d626572206265696e672070726f6365737365642e205365742062792060657865637574655f626c6f636b602e28506172656e744861736801001c543a3a4861736880000000000000000000000000000000000000000000000000000000000000000004702048617368206f66207468652070726576696f757320626c6f636b2e3845787472696e73696373526f6f7401001c543a3a486173688000000000000000000000000000000000000000000000000000000000000000000415012045787472696e7369637320726f6f74206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e1844696765737401002c4469676573744f663c543e040004f020446967657374206f66207468652063757272656e7420626c6f636b2c20616c736f2070617274206f662074686520626c6f636b206865616465722e184576656e747301008c5665633c4576656e745265636f72643c543a3a4576656e742c20543a3a486173683e3e040004a0204576656e7473206465706f736974656420666f72207468652063757272656e7420626c6f636b2e284576656e74436f756e740100284576656e74496e646578100000000004b820546865206e756d626572206f66206576656e747320696e2074686520604576656e74733c543e60206c6973742e2c4576656e74546f706963730102010828291c543a3a48617368845665633c28543a3a426c6f636b4e756d6265722c204576656e74496e646578293e010400342501204d617070696e67206265747765656e206120746f7069632028726570726573656e74656420627920543a3a486173682920616e64206120766563746f72206f6620696e646578657394206f66206576656e747320696e2074686520603c4576656e74733c543e3e60206c6973742e002d0120546865206669727374206b657920736572766573206e6f20707572706f73652e2054686973206669656c64206973206465636c6172656420617320646f75626c655f6d6170206a757374a820666f7220636f6e76656e69656e6365206f66207573696e67206072656d6f76655f707265666978602e00510120416c6c20746f70696320766563746f727320686176652064657465726d696e69737469632073746f72616765206c6f636174696f6e7320646570656e64696e67206f6e2074686520746f7069632e2054686973450120616c6c6f7773206c696768742d636c69656e747320746f206c6576657261676520746865206368616e67657320747269652073746f7261676520747261636b696e67206d656368616e69736d20616e64e420696e2063617365206f66206368616e67657320666574636820746865206c697374206f66206576656e7473206f6620696e7465726573742e004d01205468652076616c756520686173207468652074797065206028543a3a426c6f636b4e756d6265722c204576656e74496e646578296020626563617573652069662077652075736564206f6e6c79206a7573744d012074686520604576656e74496e64657860207468656e20696e20636173652069662074686520746f70696320686173207468652073616d6520636f6e74656e7473206f6e20746865206e65787420626c6f636b0101206e6f206e6f74696669636174696f6e2077696c6c20626520747269676765726564207468757320746865206576656e74206d69676874206265206c6f73742e011c2866696c6c5f626c6f636b0004210120412062696720646973706174636820746861742077696c6c20646973616c6c6f7720616e79206f74686572207472616e73616374696f6e20746f20626520696e636c756465642e1872656d61726b041c5f72656d61726b1c5665633c75383e046c204d616b6520736f6d65206f6e2d636861696e2072656d61726b2e387365745f686561705f7061676573041470616765730c75363404fc2053657420746865206e756d626572206f6620706167657320696e2074686520576562417373656d626c7920656e7669726f6e6d656e74277320686561702e207365745f636f6465040c6e65771c5665633c75383e04482053657420746865206e657720636f64652e2c7365745f73746f7261676504146974656d73345665633c4b657956616c75653e046c2053657420736f6d65206974656d73206f662073746f726167652e306b696c6c5f73746f7261676504106b657973205665633c4b65793e0478204b696c6c20736f6d65206974656d732066726f6d2073746f726167652e2c6b696c6c5f70726566697804187072656669780c4b6579041501204b696c6c20616c6c2073746f72616765206974656d7320776974682061206b657920746861742073746172747320776974682074686520676976656e207072656669782e01084045787472696e7369635375636365737304304469737061746368496e666f049420416e2065787472696e73696320636f6d706c65746564207375636365737366756c6c792e3c45787472696e7369634661696c6564083444697370617463684572726f72304469737061746368496e666f045420416e2065787472696e736963206661696c65642e000c4c526571756972655369676e65644f726967696e004452657175697265526f6f744f726967696e003c526571756972654e6f4f726967696e001c5574696c697479000104146261746368041463616c6c735c5665633c3c542061732054726169743e3a3a43616c6c3e04b02053656e642061206261746368206f662064697370617463682063616c6c7320286f6e6c7920726f6f74292e0104344261746368457865637574656404785665633c526573756c743c28292c2044697370617463684572726f723e3e0000001042616265011042616265242845706f6368496e64657801000c75363420000000000000000004542043757272656e742065706f636820696e6465782e2c417574686f72697469657301009c5665633c28417574686f7269747949642c2042616265417574686f72697479576569676874293e0400046c2043757272656e742065706f636820617574686f7269746965732e2c47656e65736973536c6f7401000c75363420000000000000000008f82054686520736c6f74206174207768696368207468652066697273742065706f63682061637475616c6c7920737461727465642e205468697320697320309020756e74696c2074686520666972737420626c6f636b206f662074686520636861696e2e2c43757272656e74536c6f7401000c75363420000000000000000004542043757272656e7420736c6f74206e756d6265722e2852616e646f6d6e6573730100205b75383b2033325d80000000000000000000000000000000000000000000000000000000000000000028b8205468652065706f63682072616e646f6d6e65737320666f7220746865202a63757272656e742a2065706f63682e002c20232053656375726974790005012054686973204d555354204e4f54206265207573656420666f722067616d626c696e672c2061732069742063616e20626520696e666c75656e6365642062792061f8206d616c6963696f75732076616c696461746f7220696e207468652073686f7274207465726d2e204974204d4159206265207573656420696e206d616e7915012063727970746f677261706869632070726f746f636f6c732c20686f77657665722c20736f206c6f6e67206173206f6e652072656d656d6265727320746861742074686973150120286c696b652065766572797468696e6720656c7365206f6e2d636861696e29206974206973207075626c69632e20466f72206578616d706c652c2069742063616e206265050120757365642077686572652061206e756d626572206973206e656564656420746861742063616e6e6f742068617665206265656e2063686f73656e20627920616e0d01206164766572736172792c20666f7220707572706f7365732073756368206173207075626c69632d636f696e207a65726f2d6b6e6f776c656467652070726f6f66732e384e65787452616e646f6d6e6573730100205b75383b2033325d800000000000000000000000000000000000000000000000000000000000000000045c204e6578742065706f63682072616e646f6d6e6573732e305365676d656e74496e64657801000c7533321000000000247c2052616e646f6d6e65737320756e64657220636f6e737472756374696f6e2e00f4205765206d616b6520612074726164656f6666206265747765656e2073746f7261676520616363657373657320616e64206c697374206c656e6774682e01012057652073746f72652074686520756e6465722d636f6e737472756374696f6e2072616e646f6d6e65737320696e207365676d656e7473206f6620757020746f942060554e4445525f434f4e535452554354494f4e5f5345474d454e545f4c454e475448602e00ec204f6e63652061207365676d656e7420726561636865732074686973206c656e6774682c20776520626567696e20746865206e657874206f6e652e090120576520726573657420616c6c207365676d656e747320616e642072657475726e20746f206030602061742074686520626567696e6e696e67206f662065766572791c2065706f63682e44556e646572436f6e737472756374696f6e0101010c753332345665633c5b75383b2033325d3e000400002c496e697469616c697a65640000204d6179626556726604000801012054656d706f726172792076616c75652028636c656172656420617420626c6f636b2066696e616c697a6174696f6e292077686963682069732060536f6d65601d01206966207065722d626c6f636b20696e697469616c697a6174696f6e2068617320616c7265616479206265656e2063616c6c656420666f722063757272656e7420626c6f636b2e010000083445706f63684475726174696f6e0c75363420c800000000000000080d0120546865206e756d626572206f66202a2a736c6f74732a2a207468617420616e2065706f63682074616b65732e20576520636f75706c652073657373696f6e7320746ffc2065706f6368732c20692e652e2077652073746172742061206e65772073657373696f6e206f6e636520746865206e65772065706f636820626567696e732e444578706563746564426c6f636b54696d6524543a3a4d6f6d656e7420b80b00000000000014050120546865206578706563746564206176657261676520626c6f636b2074696d6520617420776869636820424142452073686f756c64206265206372656174696e67110120626c6f636b732e2053696e636520424142452069732070726f626162696c6973746963206974206973206e6f74207472697669616c20746f20666967757265206f75740501207768617420746865206578706563746564206176657261676520626c6f636b2074696d652073686f756c64206265206261736564206f6e2074686520736c6f740901206475726174696f6e20616e642074686520736563757269747920706172616d657465722060636020287768657265206031202d20636020726570726573656e7473a0207468652070726f626162696c697479206f66206120736c6f74206265696e6720656d707479292e002454696d657374616d70012454696d657374616d70080c4e6f77010024543a3a4d6f6d656e7420000000000000000004902043757272656e742074696d6520666f72207468652063757272656e7420626c6f636b2e24446964557064617465010010626f6f6c040004b420446964207468652074696d657374616d7020676574207570646174656420696e207468697320626c6f636b3f01040c736574040c6e6f7748436f6d706163743c543a3a4d6f6d656e743e245820536574207468652063757272656e742074696d652e00590120546869732063616c6c2073686f756c6420626520696e766f6b65642065786163746c79206f6e63652070657220626c6f636b2e2049742077696c6c2070616e6963206174207468652066696e616c697a6174696f6ed82070686173652c20696620746869732063616c6c206861736e2774206265656e20696e766f6b656420627920746861742074696d652e004501205468652074696d657374616d702073686f756c642062652067726561746572207468616e207468652070726576696f7573206f6e652062792074686520616d6f756e74207370656369666965642062794420604d696e696d756d506572696f64602e00d820546865206469737061746368206f726967696e20666f7220746869732063616c6c206d7573742062652060496e686572656e74602e0004344d696e696d756d506572696f6424543a3a4d6f6d656e7420dc0500000000000010690120546865206d696e696d756d20706572696f64206265747765656e20626c6f636b732e204265776172652074686174207468697320697320646966666572656e7420746f20746865202a65787065637465642a20706572696f64690120746861742074686520626c6f636b2070726f64756374696f6e206170706172617475732070726f76696465732e20596f75722063686f73656e20636f6e73656e7375732073797374656d2077696c6c2067656e6572616c6c79650120776f726b2077697468207468697320746f2064657465726d696e6520612073656e7369626c6520626c6f636b2074696d652e20652e672e20466f7220417572612c2069742077696c6c20626520646f75626c6520746869737020706572696f64206f6e2064656661756c742073657474696e67732e0028417574686f72736869700128417574686f72736869700c18556e636c65730100e85665633c556e636c65456e7472794974656d3c543a3a426c6f636b4e756d6265722c20543a3a486173682c20543a3a4163636f756e7449643e3e0400041c20556e636c657318417574686f72000030543a3a4163636f756e7449640400046420417574686f72206f662063757272656e7420626c6f636b2e30446964536574556e636c6573010010626f6f6c040004bc205768657468657220756e636c6573207765726520616c72656164792073657420696e207468697320626c6f636b2e0104287365745f756e636c657304286e65775f756e636c6573385665633c543a3a4865616465723e04642050726f76696465206120736574206f6620756e636c65732e0000001c496e6469636573011c496e6469636573082c4e657874456e756d53657401003c543a3a4163636f756e74496e6465781000000000047c20546865206e657874206672656520656e756d65726174696f6e207365742e1c456e756d5365740101013c543a3a4163636f756e74496e646578445665633c543a3a4163636f756e7449643e00040004582054686520656e756d65726174696f6e20736574732e010001043c4e65774163636f756e74496e64657808244163636f756e744964304163636f756e74496e64657810882041206e6577206163636f756e7420696e646578207761732061737369676e65642e0005012054686973206576656e74206973206e6f7420747269676765726564207768656e20616e206578697374696e6720696e64657820697320726561737369676e65646020746f20616e6f7468657220604163636f756e744964602e00002042616c616e636573012042616c616e6365731434546f74616c49737375616e6365010028543a3a42616c616e6365400000000000000000000000000000000004982054686520746f74616c20756e6974732069737375656420696e207468652073797374656d2e1c56657374696e6700010130543a3a4163636f756e744964ac56657374696e675363686564756c653c543a3a42616c616e63652c20543a3a426c6f636b4e756d6265723e00040004d820496e666f726d6174696f6e20726567617264696e67207468652076657374696e67206f66206120676976656e206163636f756e742e2c4672656542616c616e636501010130543a3a4163636f756e74496428543a3a42616c616e63650040000000000000000000000000000000002c9c20546865202766726565272062616c616e6365206f66206120676976656e206163636f756e742e004101205468697320697320746865206f6e6c792062616c616e63652074686174206d61747465727320696e207465726d73206f66206d6f7374206f7065726174696f6e73206f6e20746f6b656e732e204974750120616c6f6e65206973207573656420746f2064657465726d696e65207468652062616c616e6365207768656e20696e2074686520636f6e747261637420657865637574696f6e20656e7669726f6e6d656e742e205768656e207468697355012062616c616e63652066616c6c732062656c6f77207468652076616c7565206f6620604578697374656e7469616c4465706f736974602c207468656e20746865202763757272656e74206163636f756e74272069733d012064656c657465643a207370656369666963616c6c7920604672656542616c616e6365602e20467572746865722c2074686520604f6e4672656542616c616e63655a65726f602063616c6c6261636b450120697320696e766f6b65642c20676976696e672061206368616e636520746f2065787465726e616c206d6f64756c657320746f20636c65616e2075702064617461206173736f636961746564207769746854207468652064656c65746564206163636f756e742e005d01206073797374656d3a3a4163636f756e744e6f6e63656020697320616c736f2064656c657465642069662060526573657276656442616c616e63656020697320616c736f207a65726f2028697420616c736f2067657473150120636f6c6c617073656420746f207a65726f2069662069742065766572206265636f6d6573206c657373207468616e20604578697374656e7469616c4465706f736974602e3c526573657276656442616c616e636501010130543a3a4163636f756e74496428543a3a42616c616e63650040000000000000000000000000000000002c75012054686520616d6f756e74206f66207468652062616c616e6365206f66206120676976656e206163636f756e7420746861742069732065787465726e616c6c792072657365727665643b20746869732063616e207374696c6c206765749c20736c61736865642c20627574206765747320736c6173686564206c617374206f6620616c6c2e006d0120546869732062616c616e63652069732061202772657365727665272062616c616e63652074686174206f746865722073756273797374656d732075736520696e206f7264657220746f2073657420617369646520746f6b656e732501207468617420617265207374696c6c20276f776e65642720627920746865206163636f756e7420686f6c6465722c20627574207768696368206172652073757370656e6461626c652e007501205768656e20746869732062616c616e63652066616c6c732062656c6f77207468652076616c7565206f6620604578697374656e7469616c4465706f736974602c207468656e2074686973202772657365727665206163636f756e7427b42069732064656c657465643a207370656369666963616c6c792c2060526573657276656442616c616e6365602e004d01206073797374656d3a3a4163636f756e744e6f6e63656020697320616c736f2064656c6574656420696620604672656542616c616e63656020697320616c736f207a65726f2028697420616c736f2067657473190120636f6c6c617073656420746f207a65726f2069662069742065766572206265636f6d6573206c657373207468616e20604578697374656e7469616c4465706f736974602e29144c6f636b7301010130543a3a4163636f756e744964b05665633c42616c616e63654c6f636b3c543a3a42616c616e63652c20543a3a426c6f636b4e756d6265723e3e00040004b820416e79206c6971756964697479206c6f636b73206f6e20736f6d65206163636f756e742062616c616e6365732e0110207472616e736665720810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e64d8205472616e7366657220736f6d65206c697175696420667265652062616c616e636520746f20616e6f74686572206163636f756e742e00090120607472616e73666572602077696c6c207365742074686520604672656542616c616e636560206f66207468652073656e64657220616e642072656365697665722e21012049742077696c6c2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d2062792074686520605472616e73666572466565602e1501204966207468652073656e6465722773206163636f756e742069732062656c6f7720746865206578697374656e7469616c206465706f736974206173206120726573756c74b4206f6620746865207472616e736665722c20746865206163636f756e742077696c6c206265207265617065642e00190120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d75737420626520605369676e65646020627920746865207472616e736163746f722e002c2023203c7765696768743e3101202d20446570656e64656e74206f6e20617267756d656e747320627574206e6f7420637269746963616c2c20676976656e2070726f70657220696d706c656d656e746174696f6e7320666f72cc202020696e70757420636f6e6669672074797065732e205365652072656c617465642066756e6374696f6e732062656c6f772e6901202d20497420636f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e642077726974657320696e7465726e616c6c7920616e64206e6f20636f6d706c657820636f6d7075746174696f6e2e004c2052656c617465642066756e6374696f6e733a0051012020202d2060656e737572655f63616e5f77697468647261776020697320616c776179732063616c6c656420696e7465726e616c6c792062757420686173206120626f756e64656420636f6d706c65786974792e2d012020202d205472616e7366657272696e672062616c616e63657320746f206163636f756e7473207468617420646964206e6f74206578697374206265666f72652077696c6c206361757365d420202020202060543a3a4f6e4e65774163636f756e743a3a6f6e5f6e65775f6163636f756e746020746f2062652063616c6c65642edc2020202d2052656d6f76696e6720656e6f7567682066756e64732066726f6d20616e206163636f756e742077696c6c20747269676765725901202020202060543a3a4475737452656d6f76616c3a3a6f6e5f756e62616c616e6365646020616e642060543a3a4f6e4672656542616c616e63655a65726f3a3a6f6e5f667265655f62616c616e63655f7a65726f602e49012020202d20607472616e736665725f6b6565705f616c6976656020776f726b73207468652073616d652077617920617320607472616e73666572602c206275742068617320616e206164646974696f6e616cf82020202020636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c20746865206f726967696e206163636f756e742e00302023203c2f7765696768743e2c7365745f62616c616e63650c0c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365206e65775f667265654c436f6d706163743c543a3a42616c616e63653e306e65775f72657365727665644c436f6d706163743c543a3a42616c616e63653e349420536574207468652062616c616e636573206f66206120676976656e206163636f756e742e00210120546869732077696c6c20616c74657220604672656542616c616e63656020616e642060526573657276656442616c616e63656020696e2073746f726167652e2069742077696c6c090120616c736f2064656372656173652074686520746f74616c2069737375616e6365206f66207468652073797374656d202860546f74616c49737375616e636560292e190120496620746865206e65772066726565206f722072657365727665642062616c616e63652069732062656c6f7720746865206578697374656e7469616c206465706f7369742ce82069742077696c6c20726573657420746865206163636f756e74206e6f6e636520286073797374656d3a3a4163636f756e744e6f6e636560292e00b420546865206469737061746368206f726967696e20666f7220746869732063616c6c2069732060726f6f74602e002c2023203c7765696768743e80202d20496e646570656e64656e74206f662074686520617267756d656e74732ec4202d20436f6e7461696e732061206c696d69746564206e756d626572206f6620726561647320616e64207772697465732e302023203c2f7765696768743e38666f7263655f7472616e736665720c18736f757263658c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636510646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e0851012045786163746c7920617320607472616e73666572602c2065786365707420746865206f726967696e206d75737420626520726f6f7420616e642074686520736f75726365206163636f756e74206d61792062652c207370656369666965642e4c7472616e736665725f6b6565705f616c6976650810646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c75654c436f6d706163743c543a3a42616c616e63653e1851012053616d6520617320746865205b607472616e73666572605d2063616c6c2c206275742077697468206120636865636b207468617420746865207472616e736665722077696c6c206e6f74206b696c6c2074686540206f726967696e206163636f756e742e00bc20393925206f66207468652074696d6520796f752077616e74205b607472616e73666572605d20696e73746561642e00c4205b607472616e73666572605d3a207374727563742e4d6f64756c652e68746d6c236d6574686f642e7472616e73666572010c284e65774163636f756e7408244163636f756e7449641c42616c616e6365046c2041206e6577206163636f756e742077617320637265617465642e345265617065644163636f756e7404244163636f756e744964045c20416e206163636f756e7420776173207265617065642e205472616e7366657210244163636f756e744964244163636f756e7449641c42616c616e63651c42616c616e636504b0205472616e7366657220737563636565646564202866726f6d2c20746f2c2076616c75652c2066656573292e0c484578697374656e7469616c4465706f73697428543a3a42616c616e63654000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f206b65657020616e206163636f756e74206f70656e2e2c5472616e7366657246656528543a3a42616c616e6365400010a5d4e800000000000000000000000494205468652066656520726571756972656420746f206d616b652061207472616e736665722e2c4372656174696f6e46656528543a3a42616c616e6365400010a5d4e80000000000000000000000049c205468652066656520726571756972656420746f2063726561746520616e206163636f756e742e00485472616e73616374696f6e5061796d656e74012042616c616e63657304444e6578744665654d756c7469706c6965720100284d756c7469706c69657220000000000000000000000008485472616e73616374696f6e426173654665653042616c616e63654f663c543e400010a5d4e8000000000000000000000004dc205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b2074686520626173652e485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e001c5374616b696e67011c5374616b696e67683856616c696461746f72436f756e7401000c753332100000000004a82054686520696465616c206e756d626572206f66207374616b696e67207061727469636970616e74732e544d696e696d756d56616c696461746f72436f756e7401000c7533321004000000044101204d696e696d756d206e756d626572206f66207374616b696e67207061727469636970616e7473206265666f726520656d657267656e637920636f6e646974696f6e732061726520696d706f7365642e34496e76756c6e657261626c65730100445665633c543a3a4163636f756e7449643e04000c590120416e792076616c696461746f72732074686174206d6179206e6576657220626520736c6173686564206f7220666f726369626c79206b69636b65642e20497427732061205665632073696e636520746865792772654d01206561737920746f20696e697469616c697a6520616e642074686520706572666f726d616e636520686974206973206d696e696d616c2028776520657870656374206e6f206d6f7265207468616e20666f7572ac20696e76756c6e657261626c65732920616e64207265737472696374656420746f20746573746e6574732e18426f6e64656400010130543a3a4163636f756e74496430543a3a4163636f756e744964000400040101204d61702066726f6d20616c6c206c6f636b65642022737461736822206163636f756e747320746f2074686520636f6e74726f6c6c6572206163636f756e742e184c656467657200010130543a3a4163636f756e744964a45374616b696e674c65646765723c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400044501204d61702066726f6d20616c6c2028756e6c6f636b6564292022636f6e74726f6c6c657222206163636f756e747320746f2074686520696e666f20726567617264696e6720746865207374616b696e672e14506179656501010130543a3a4163636f756e7449644452657761726444657374696e6174696f6e00040004e42057686572652074686520726577617264207061796d656e742073686f756c64206265206d6164652e204b657965642062792073746173682e2856616c696461746f727301010130543a3a4163636f756e7449643856616c696461746f72507265667301040004450120546865206d61702066726f6d202877616e6e616265292076616c696461746f72207374617368206b657920746f2074686520707265666572656e636573206f6620746861742076616c696461746f722e284e6f6d696e61746f727300010130543a3a4163636f756e744964644e6f6d696e6174696f6e733c543a3a4163636f756e7449643e01040010650120546865206d61702066726f6d206e6f6d696e61746f72207374617368206b657920746f2074686520736574206f66207374617368206b657973206f6620616c6c2076616c696461746f727320746f206e6f6d696e6174652e003501204e4f54453a206973207072697661746520736f20746861742077652063616e20656e73757265207570677261646564206265666f726520616c6c207479706963616c2061636365737365732ed8204469726563742073746f7261676520415049732063616e207374696c6c2062797061737320746869732070726f74656374696f6e2e1c5374616b65727301010130543a3a4163636f756e744964904578706f737572653c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000c000000104d01204e6f6d696e61746f727320666f72206120706172746963756c6172206163636f756e74207468617420697320696e20616374696f6e207269676874206e6f772e20596f752063616e277420697465726174651901207468726f7567682076616c696461746f727320686572652c2062757420796f752063616e2066696e64207468656d20696e207468652053657373696f6e206d6f64756c652e00902054686973206973206b6579656420627920746865207374617368206163636f756e742e3843757272656e74456c65637465640100445665633c543a3a4163636f756e7449643e040004fc205468652063757272656e746c7920656c65637465642076616c696461746f7220736574206b65796564206279207374617368206163636f756e742049442e2843757272656e74457261010020457261496e6465781000000000045c205468652063757272656e742065726120696e6465782e3c43757272656e74457261537461727401002c4d6f6d656e744f663c543e200000000000000000047820546865207374617274206f66207468652063757272656e74206572612e6c43757272656e74457261537461727453657373696f6e496e64657801003053657373696f6e496e646578100000000004d0205468652073657373696f6e20696e646578206174207768696368207468652063757272656e742065726120737461727465642e5843757272656e74457261506f696e74734561726e6564010024457261506f696e7473140000000000040d01205265776172647320666f72207468652063757272656e74206572612e205573696e6720696e6469636573206f662063757272656e7420656c6563746564207365742e24536c6f745374616b6501003042616c616e63654f663c543e40000000000000000000000000000000000c31012054686520616d6f756e74206f662062616c616e6365206163746976656c79206174207374616b6520666f7220656163682076616c696461746f7220736c6f742c2063757272656e746c792e00c02054686973206973207573656420746f20646572697665207265776172647320616e642070756e6973686d656e74732e20466f72636545726101001c466f7263696e670400041d01205472756520696620746865206e6578742073657373696f6e206368616e67652077696c6c2062652061206e657720657261207265676172646c657373206f6620696e6465782e4c536c6173685265776172644672616374696f6e01001c50657262696c6c10000000000cf8205468652070657263656e74616765206f662074686520736c617368207468617420697320646973747269627574656420746f207265706f72746572732e00e4205468652072657374206f662074686520736c61736865642076616c75652069732068616e646c6564206279207468652060536c617368602e4c43616e63656c6564536c6173685061796f757401003042616c616e63654f663c543e40000000000000000000000000000000000815012054686520616d6f756e74206f662063757272656e637920676976656e20746f207265706f7274657273206f66206120736c617368206576656e7420776869636820776173ec2063616e63656c65642062792065787472616f7264696e6172792063697263756d7374616e6365732028652e672e20676f7665726e616e6365292e40556e6170706c696564536c617368657301010120457261496e646578bc5665633c556e6170706c696564536c6173683c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e3e00040004c420416c6c20756e6170706c69656420736c61736865732074686174206172652071756575656420666f72206c617465722e28426f6e646564457261730100745665633c28457261496e6465782c2053657373696f6e496e646578293e04000425012041206d617070696e672066726f6d207374696c6c2d626f6e646564206572617320746f207468652066697273742073657373696f6e20696e646578206f662074686174206572612e4c56616c696461746f72536c617368496e45726100020120457261496e64657830543a3a4163636f756e7449645c2850657262696c6c2c2042616c616e63654f663c543e2902040008450120416c6c20736c617368696e67206576656e7473206f6e2076616c696461746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682070726f706f7274696f6e7020616e6420736c6173682076616c7565206f6620746865206572612e4c4e6f6d696e61746f72536c617368496e45726100020120457261496e64657830543a3a4163636f756e7449643042616c616e63654f663c543e02040004610120416c6c20736c617368696e67206576656e7473206f6e206e6f6d696e61746f72732c206d61707065642062792065726120746f20746865206869676865737420736c6173682076616c7565206f6620746865206572612e34536c617368696e675370616e7300010130543a3a4163636f756e7449645c736c617368696e673a3a536c617368696e675370616e73000400048c20536c617368696e67207370616e7320666f72207374617368206163636f756e74732e245370616e536c6173680101018c28543a3a4163636f756e7449642c20736c617368696e673a3a5370616e496e6465782988736c617368696e673a3a5370616e5265636f72643c42616c616e63654f663c543e3e00800000000000000000000000000000000000000000000000000000000000000000083d01205265636f72647320696e666f726d6174696f6e2061626f757420746865206d6178696d756d20736c617368206f6620612073746173682077697468696e206120736c617368696e67207370616e2cb82061732077656c6c20617320686f77206d7563682072657761726420686173206265656e2070616964206f75742e584561726c69657374556e6170706c696564536c617368000020457261496e646578040004fc20546865206561726c696573742065726120666f72207768696368207765206861766520612070656e64696e672c20756e6170706c69656420736c6173682e3853746f7261676556657273696f6e01000c75333210000000000490205468652076657273696f6e206f662073746f7261676520666f7220757067726164652e014010626f6e640c28636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e1470617965654452657761726444657374696e6174696f6e3c65012054616b6520746865206f726967696e206163636f756e74206173206120737461736820616e64206c6f636b207570206076616c756560206f66206974732062616c616e63652e2060636f6e74726f6c6c6572602077696c6c8420626520746865206163636f756e74207468617420636f6e74726f6c732069742e003101206076616c756560206d757374206265206d6f7265207468616e2074686520606d696e696d756d5f62616c616e636560207370656369666965642062792060543a3a43757272656e6379602e00250120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f20627920746865207374617368206163636f756e742e002c2023203c7765696768743ed4202d20496e646570656e64656e74206f662074686520617267756d656e74732e204d6f64657261746520636f6d706c65786974792e20202d204f2831292e68202d20546872656520657874726120444220656e74726965732e006d01204e4f54453a2054776f206f66207468652073746f726167652077726974657320286053656c663a3a626f6e646564602c206053656c663a3a7061796565602920617265205f6e657665725f20636c65616e656420756e6c65737325012074686520606f726967696e602066616c6c732062656c6f77205f6578697374656e7469616c206465706f7369745f20616e6420676574732072656d6f76656420617320647573742e302023203c2f7765696768743e28626f6e645f657874726104386d61785f6164646974696f6e616c54436f6d706163743c42616c616e63654f663c543e3e3865012041646420736f6d6520657874726120616d6f756e742074686174206861766520617070656172656420696e207468652073746173682060667265655f62616c616e63656020696e746f207468652062616c616e63652075703420666f72207374616b696e672e00510120557365207468697320696620746865726520617265206164646974696f6e616c2066756e647320696e20796f7572207374617368206163636f756e74207468617420796f75207769736820746f20626f6e642e650120556e6c696b65205b60626f6e64605d206f72205b60756e626f6e64605d20746869732066756e6374696f6e20646f6573206e6f7420696d706f736520616e79206c696d69746174696f6e206f6e2074686520616d6f756e744c20746861742063616e2062652061646465642e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e20202d204f2831292e40202d204f6e6520444220656e7472792e302023203c2f7765696768743e18756e626f6e64041476616c756554436f6d706163743c42616c616e63654f663c543e3e5c5501205363686564756c65206120706f7274696f6e206f662074686520737461736820746f20626520756e6c6f636b656420726561647920666f72207472616e73666572206f75742061667465722074686520626f6e64010120706572696f6420656e64732e2049662074686973206c656176657320616e20616d6f756e74206163746976656c7920626f6e646564206c657373207468616e250120543a3a43757272656e63793a3a6d696e696d756d5f62616c616e636528292c207468656e20697420697320696e6372656173656420746f207468652066756c6c20616d6f756e742e004901204f6e63652074686520756e6c6f636b20706572696f6420697320646f6e652c20796f752063616e2063616c6c206077697468647261775f756e626f6e6465646020746f2061637475616c6c79206d6f7665c0207468652066756e6473206f7574206f66206d616e6167656d656e7420726561647920666f72207472616e736665722e003d01204e6f206d6f7265207468616e2061206c696d69746564206e756d626572206f6620756e6c6f636b696e67206368756e6b73202873656520604d41585f554e4c4f434b494e475f4348554e4b5360293d012063616e20636f2d657869737473206174207468652073616d652074696d652e20496e207468617420636173652c205b6043616c6c3a3a77697468647261775f756e626f6e646564605d206e656564fc20746f2062652063616c6c656420666972737420746f2072656d6f766520736f6d65206f6620746865206368756e6b732028696620706f737369626c65292e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e00982053656520616c736f205b6043616c6c3a3a77697468647261775f756e626f6e646564605d2e002c2023203c7765696768743e4101202d20496e646570656e64656e74206f662074686520617267756d656e74732e204c696d697465642062757420706f74656e7469616c6c79206578706c6f697461626c6520636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732e6501202d20456163682063616c6c20287265717569726573207468652072656d61696e646572206f662074686520626f6e6465642062616c616e636520746f2062652061626f766520606d696e696d756d5f62616c616e63656029710120202077696c6c2063617573652061206e657720656e74727920746f20626520696e73657274656420696e746f206120766563746f722028604c65646765722e756e6c6f636b696e676029206b65707420696e2073746f726167652ea501202020546865206f6e6c792077617920746f20636c65616e207468652061666f72656d656e74696f6e65642073746f72616765206974656d20697320616c736f20757365722d636f6e74726f6c6c656420766961206077697468647261775f756e626f6e646564602e40202d204f6e6520444220656e7472792e28203c2f7765696768743e4477697468647261775f756e626f6e64656400402d012052656d6f766520616e7920756e6c6f636b6564206368756e6b732066726f6d207468652060756e6c6f636b696e67602071756575652066726f6d206f7572206d616e6167656d656e742e003501205468697320657373656e7469616c6c7920667265657320757020746861742062616c616e636520746f206265207573656420627920746865207374617368206163636f756e7420746f20646f4c2077686174657665722069742077616e74732e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e006c2053656520616c736f205b6043616c6c3a3a756e626f6e64605d2e002c2023203c7765696768743e5501202d20436f756c6420626520646570656e64656e74206f6e2074686520606f726967696e6020617267756d656e7420616e6420686f77206d7563682060756e6c6f636b696e6760206368756e6b732065786973742e45012020497420696d706c6965732060636f6e736f6c69646174655f756e6c6f636b656460207768696368206c6f6f7073206f76657220604c65646765722e756e6c6f636b696e67602c207768696368206973f42020696e6469726563746c7920757365722d636f6e74726f6c6c65642e20536565205b60756e626f6e64605d20666f72206d6f72652064657461696c2e7901202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732c20796574207468652073697a65206f6620776869636820636f756c64206265206c61726765206261736564206f6e20606c6564676572602ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e2076616c6964617465041470726566733856616c696461746f7250726566732ce8204465636c617265207468652064657369726520746f2076616c696461746520666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e206e6f6d696e617465041c74617267657473a05665633c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263653e2c1101204465636c617265207468652064657369726520746f206e6f6d696e6174652060746172676574736020666f7220746865206f726967696e20636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743e2501202d20546865207472616e73616374696f6e277320636f6d706c65786974792069732070726f706f7274696f6e616c20746f207468652073697a65206f66206074617267657473602c982077686963682069732063617070656420617420604d41585f4e4f4d494e4154494f4e53602ed8202d20426f74682074686520726561647320616e642077726974657320666f6c6c6f7720612073696d696c6172207061747465726e2e302023203c2f7765696768743e146368696c6c002cc8204465636c617265206e6f2064657369726520746f206569746865722076616c6964617465206f72206e6f6d696e6174652e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e54202d20436f6e7461696e73206f6e6520726561642ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e247365745f7061796565041470617965654452657761726444657374696e6174696f6e2cb8202852652d2973657420746865207061796d656e742074617267657420666f72206120636f6e74726f6c6c65722e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2062792074686520636f6e74726f6c6c65722c206e6f74207468652073746173682e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e387365745f636f6e74726f6c6c65720428636f6e74726f6c6c65728c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652c90202852652d297365742074686520636f6e74726f6c6c6572206f6620612073746173682e00dc20456666656374732077696c6c2062652066656c742061742074686520626567696e6e696e67206f6620746865206e657874206572612e00550120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f206279207468652073746173682c206e6f742074686520636f6e74726f6c6c65722e002c2023203c7765696768743ee8202d20496e646570656e64656e74206f662074686520617267756d656e74732e20496e7369676e69666963616e7420636f6d706c65786974792e98202d20436f6e7461696e732061206c696d69746564206e756d626572206f662072656164732ec8202d2057726974657320617265206c696d6974656420746f2074686520606f726967696e60206163636f756e74206b65792e302023203c2f7765696768743e4c7365745f76616c696461746f725f636f756e74040c6e657730436f6d706163743c7533323e04802054686520696465616c206e756d626572206f662076616c696461746f72732e34666f7263655f6e6f5f657261730014b020466f72636520746865726520746f206265206e6f206e6577206572617320696e646566696e6974656c792e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e302023203c2f7765696768743e34666f7263655f6e65775f65726100184d0120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f6620746865206e6578742073657373696f6e2e20416674657220746869732c2069742077696c6c206265a020726573657420746f206e6f726d616c20286e6f6e2d666f7263656429206265686176696f75722e002c2023203c7765696768743e40202d204e6f20617267756d656e74732e302023203c2f7765696768743e447365745f696e76756c6e657261626c6573042876616c696461746f7273445665633c543a3a4163636f756e7449643e04cc20536574207468652076616c696461746f72732077686f2063616e6e6f7420626520736c61736865642028696620616e79292e34666f7263655f756e7374616b650414737461736830543a3a4163636f756e744964040d0120466f72636520612063757272656e74207374616b657220746f206265636f6d6520636f6d706c6574656c7920756e7374616b65642c20696d6d6564696174656c792e50666f7263655f6e65775f6572615f616c776179730014050120466f72636520746865726520746f2062652061206e6577206572612061742074686520656e64206f662073657373696f6e7320696e646566696e6974656c792e002c2023203c7765696768743e50202d204f6e652073746f72616765207772697465302023203c2f7765696768743e5463616e63656c5f64656665727265645f736c617368080c65726120457261496e64657834736c6173685f696e6469636573205665633c7533323e1c45012043616e63656c20656e6163746d656e74206f66206120646566657272656420736c6173682e2043616e2062652063616c6c6564206279206569746865722074686520726f6f74206f726967696e206f7270207468652060543a3a536c61736843616e63656c4f726967696e602e05012070617373696e67207468652065726120616e6420696e6469636573206f662074686520736c617368657320666f7220746861742065726120746f206b696c6c2e002c2023203c7765696768743e54202d204f6e652073746f726167652077726974652e302023203c2f7765696768743e010c18526577617264081c42616c616e63651c42616c616e636508510120416c6c2076616c696461746f72732068617665206265656e207265776172646564206279207468652066697273742062616c616e63653b20746865207365636f6e64206973207468652072656d61696e6465728c2066726f6d20746865206d6178696d756d20616d6f756e74206f66207265776172642e14536c61736808244163636f756e7449641c42616c616e6365042501204f6e652076616c696461746f722028616e6420697473206e6f6d696e61746f72732920686173206265656e20736c61736865642062792074686520676976656e20616d6f756e742e684f6c64536c617368696e675265706f7274446973636172646564043053657373696f6e496e646578081d0120416e206f6c6420736c617368696e67207265706f72742066726f6d2061207072696f72206572612077617320646973636172646564206265636175736520697420636f756c6448206e6f742062652070726f6365737365642e083853657373696f6e735065724572613053657373696f6e496e64657810060000000470204e756d626572206f662073657373696f6e7320706572206572612e3c426f6e64696e674475726174696f6e20457261496e64657810a002000004e4204e756d626572206f6620657261732074686174207374616b65642066756e6473206d7573742072656d61696e20626f6e64656420666f722e001c53657373696f6e011c53657373696f6e1c2856616c696461746f727301004c5665633c543a3a56616c696461746f7249643e0400047c205468652063757272656e7420736574206f662076616c696461746f72732e3043757272656e74496e64657801003053657373696f6e496e646578100000000004782043757272656e7420696e646578206f66207468652073657373696f6e2e345175657565644368616e676564010010626f6f6c040008390120547275652069662074686520756e6465726c79696e672065636f6e6f6d6963206964656e746974696573206f7220776569676874696e6720626568696e64207468652076616c696461746f7273a420686173206368616e67656420696e20746865207175657565642076616c696461746f72207365742e285175657565644b6579730100785665633c28543a3a56616c696461746f7249642c20543a3a4b657973293e0400083d012054686520717565756564206b65797320666f7220746865206e6578742073657373696f6e2e205768656e20746865206e6578742073657373696f6e20626567696e732c207468657365206b657973e02077696c6c206265207573656420746f2064657465726d696e65207468652076616c696461746f7227732073657373696f6e206b6579732e4844697361626c656456616c696461746f72730100205665633c7533323e04000c8020496e6469636573206f662064697361626c65642076616c696461746f72732e003501205468652073657420697320636c6561726564207768656e20606f6e5f73657373696f6e5f656e64696e67602072657475726e732061206e657720736574206f66206964656e7469746965732e204e6578744b6579730002041c5665633c75383e38543a3a56616c696461746f7249641c543a3a4b657973010400109c20546865206e6578742073657373696f6e206b65797320666f7220612076616c696461746f722e00590120546865206669727374206b657920697320616c77617973206044454455505f4b45595f5052454649586020746f206861766520616c6c20746865206461746120696e207468652073616d65206272616e6368206f6661012074686520747269652e20486176696e6720616c6c206461746120696e207468652073616d65206272616e63682073686f756c642070726576656e7420736c6f77696e6720646f776e206f7468657220717565726965732e204b65794f776e65720002041c5665633c75383e50284b65795479706549642c205665633c75383e2938543a3a56616c696461746f72496401040010250120546865206f776e6572206f662061206b65792e20546865207365636f6e64206b65792069732074686520604b657954797065496460202b2074686520656e636f646564206b65792e00590120546865206669727374206b657920697320616c77617973206044454455505f4b45595f5052454649586020746f206861766520616c6c20746865206461746120696e207468652073616d65206272616e6368206f6661012074686520747269652e20486176696e6720616c6c206461746120696e207468652073616d65206272616e63682073686f756c642070726576656e7420736c6f77696e6720646f776e206f7468657220717565726965732e0104207365745f6b65797308106b6579731c543a3a4b6579731470726f6f661c5665633c75383e28e42053657473207468652073657373696f6e206b6579287329206f66207468652066756e6374696f6e2063616c6c657220746f20606b6579602e210120416c6c6f777320616e206163636f756e7420746f20736574206974732073657373696f6e206b6579207072696f7220746f206265636f6d696e6720612076616c696461746f722ec4205468697320646f65736e27742074616b652065666665637420756e74696c20746865206e6578742073657373696f6e2e00d420546865206469737061746368206f726967696e206f6620746869732066756e6374696f6e206d757374206265207369676e65642e002c2023203c7765696768743e88202d204f286c6f67206e2920696e206e756d626572206f66206163636f756e74732e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e0104284e657753657373696f6e043053657373696f6e496e646578085501204e65772073657373696f6e206861732068617070656e65642e204e6f746520746861742074686520617267756d656e74206973207468652073657373696f6e20696e6465782c206e6f742074686520626c6f636b88206e756d626572206173207468652074797065206d6967687420737567676573742e044044454455505f4b45595f50524546495814265b75385d38343a73657373696f6e3a6b6579730865012055736564206173206669727374206b657920666f7220604e6578744b6579736020616e6420604b65794f776e65726020746f2070757420616c6c20746865206461746120696e746f207468652073616d65206272616e636834206f662074686520747269652e002444656d6f6372616379012444656d6f6372616379403c5075626c696350726f70436f756e7401002450726f70496e646578100000000004f420546865206e756d626572206f6620287075626c6963292070726f706f73616c7320746861742068617665206265656e206d61646520736f206661722e2c5075626c696350726f707301009c5665633c2850726f70496e6465782c20543a3a486173682c20543a3a4163636f756e744964293e040004210120546865207075626c69632070726f706f73616c732e20556e736f727465642e20546865207365636f6e64206974656d206973207468652070726f706f73616c277320686173682e24507265696d616765730001011c543a3a48617368d4285665633c75383e2c20543a3a4163636f756e7449642c2042616c616e63654f663c543e2c20543a3a426c6f636b4e756d62657229000400086101204d6170206f662068617368657320746f207468652070726f706f73616c20707265696d6167652c20616c6f6e6720776974682077686f207265676973746572656420697420616e64207468656972206465706f7369742ee42054686520626c6f636b206e756d6265722069732074686520626c6f636b20617420776869636820697420776173206465706f73697465642e244465706f7369744f660001012450726f70496e646578842842616c616e63654f663c543e2c205665633c543a3a4163636f756e7449643e2900040004842054686f73652077686f2068617665206c6f636b65642061206465706f7369742e3c5265666572656e64756d436f756e7401003c5265666572656e64756d496e646578100000000004310120546865206e6578742066726565207265666572656e64756d20696e6465782c20616b6120746865206e756d626572206f66207265666572656e6461207374617274656420736f206661722e244e65787454616c6c7901003c5265666572656e64756d496e646578100000000004c820546865206e657874207265666572656e64756d20696e64657820746861742073686f756c642062652074616c6c6965642e405265666572656e64756d496e666f4f660001013c5265666572656e64756d496e646578a4285265666572656e64756d496e666f3c543a3a426c6f636b4e756d6265722c20543a3a486173683e2900040004b420496e666f726d6174696f6e20636f6e6365726e696e6720616e7920676976656e207265666572656e64756d2e344469737061746368517565756501010438543a3a426c6f636b4e756d6265729c5665633c4f7074696f6e3c28543a3a486173682c205265666572656e64756d496e646578293e3e00040004c0205175657565206f66207375636365737366756c207265666572656e646120746f20626520646973706174636865642e24566f74657273466f720101013c5265666572656e64756d496e646578445665633c543a3a4163636f756e7449643e00040004a4204765742074686520766f7465727320666f72207468652063757272656e742070726f706f73616c2e18566f74654f660101017c285265666572656e64756d496e6465782c20543a3a4163636f756e7449642910566f7465000400106101204765742074686520766f746520696e206120676976656e207265666572656e64756d206f66206120706172746963756c617220766f7465722e2054686520726573756c74206973206d65616e696e6766756c206f6e6c794d012069662060766f746572735f666f726020696e636c756465732074686520766f746572207768656e2063616c6c6564207769746820746865207265666572656e64756d2028796f75276c6c20676574207468655d012064656661756c742060566f7465602076616c7565206f7468657277697365292e20496620796f7520646f6e27742077616e7420746f20636865636b2060766f746572735f666f72602c207468656e20796f752063616ef420616c736f20636865636b20666f722073696d706c65206578697374656e636520776974682060566f74654f663a3a657869737473602066697273742e1450726f787900010130543a3a4163636f756e74496430543a3a4163636f756e7449640004000831012057686f2069732061626c6520746f20766f746520666f722077686f6d2e2056616c7565206973207468652066756e642d686f6c64696e67206163636f756e742c206b6579206973207468658820766f74652d7472616e73616374696f6e2d73656e64696e67206163636f756e742e2c44656c65676174696f6e7301010130543a3a4163636f756e7449646828543a3a4163636f756e7449642c20436f6e76696374696f6e2901840000000000000000000000000000000000000000000000000000000000000000000441012047657420746865206163636f756e742028616e64206c6f636b20706572696f64732920746f20776869636820616e6f74686572206163636f756e742069732064656c65676174696e6720766f74652e544c6173745461626c656457617345787465726e616c010010626f6f6c0400085901205472756520696620746865206c617374207265666572656e64756d207461626c656420776173207375626d69747465642065787465726e616c6c792e2046616c7365206966206974207761732061207075626c6963282070726f706f73616c2e304e65787445787465726e616c00006028543a3a486173682c20566f74655468726573686f6c6429040010590120546865207265666572656e64756d20746f206265207461626c6564207768656e6576657220697420776f756c642062652076616c696420746f207461626c6520616e2065787465726e616c2070726f706f73616c2e550120546869732068617070656e73207768656e2061207265666572656e64756d206e6565647320746f206265207461626c656420616e64206f6e65206f662074776f20636f6e646974696f6e7320617265206d65743aa4202d20604c6173745461626c656457617345787465726e616c60206973206066616c7365603b206f7268202d20605075626c696350726f70736020697320656d7074792e24426c61636b6c6973740001011c543a3a486173688c28543a3a426c6f636b4e756d6265722c205665633c543a3a4163636f756e7449643e290004000851012041207265636f7264206f662077686f207665746f656420776861742e204d6170732070726f706f73616c206861736820746f206120706f737369626c65206578697374656e7420626c6f636b206e756d626572e82028756e74696c207768656e206974206d6179206e6f742062652072657375626d69747465642920616e642077686f207665746f65642069742e3443616e63656c6c6174696f6e730101011c543a3a4861736810626f6f6c000400042901205265636f7264206f6620616c6c2070726f706f73616c7320746861742068617665206265656e207375626a65637420746f20656d657267656e63792063616e63656c6c6174696f6e2e01541c70726f706f7365083470726f706f73616c5f686173681c543a3a486173681476616c756554436f6d706163743c42616c616e63654f663c543e3e18a02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e002c2023203c7765696768743e20202d204f2831292e80202d2054776f204442206368616e6765732c206f6e6520444220656e7472792e302023203c2f7765696768743e187365636f6e64042070726f706f73616c48436f6d706163743c50726f70496e6465783e18a02050726f706f736520612073656e73697469766520616374696f6e20746f2062652074616b656e2e002c2023203c7765696768743e20202d204f2831292e40202d204f6e6520444220656e7472792e302023203c2f7765696768743e10766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f746510566f74651c350120566f746520696e2061207265666572656e64756d2e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374207468652070726f706f73616c3bbc206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e002c2023203c7765696768743e20202d204f2831292e7c202d204f6e65204442206368616e67652c206f6e6520444220656e7472792e302023203c2f7765696768743e2870726f78795f766f746508247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e10766f746510566f74651c510120566f746520696e2061207265666572656e64756d206f6e20626568616c66206f6620612073746173682e2049662060766f74652e69735f6179652829602c2074686520766f746520697320746f20656e616374f8207468652070726f706f73616c3b20206f7468657277697365206974206973206120766f746520746f206b65657020746865207374617475732071756f2e002c2023203c7765696768743e20202d204f2831292e7c202d204f6e65204442206368616e67652c206f6e6520444220656e7472792e302023203c2f7765696768743e40656d657267656e63795f63616e63656c04247265665f696e6465783c5265666572656e64756d496e646578085101205363686564756c6520616e20656d657267656e63792063616e63656c6c6174696f6e206f662061207265666572656e64756d2e2043616e6e6f742068617070656e20747769636520746f207468652073616d6530207265666572656e64756d2e4065787465726e616c5f70726f706f7365043470726f706f73616c5f686173681c543a3a48617368083101205363686564756c652061207265666572656e64756d20746f206265207461626c6564206f6e6365206974206973206c6567616c20746f207363686564756c6520616e2065787465726e616c30207265666572656e64756d2e6465787465726e616c5f70726f706f73655f6d616a6f72697479043470726f706f73616c5f686173681c543a3a48617368145901205363686564756c652061206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f207363686564756c656020616e2065787465726e616c207265666572656e64756d2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e6065787465726e616c5f70726f706f73655f64656661756c74043470726f706f73616c5f686173681c543a3a48617368144901205363686564756c652061206e656761746976652d7475726e6f75742d62696173207265666572656e64756d20746f206265207461626c6564206e657874206f6e6365206974206973206c6567616c20746f84207363686564756c6520616e2065787465726e616c207265666572656e64756d2e004d0120556e6c696b65206065787465726e616c5f70726f706f7365602c20626c61636b6c697374696e6720686173206e6f20656666656374206f6e207468697320616e64206974206d6179207265706c61636520619c207072652d7363686564756c6564206065787465726e616c5f70726f706f7365602063616c6c2e28666173745f747261636b0c3470726f706f73616c5f686173681c543a3a4861736834766f74696e675f706572696f6438543a3a426c6f636b4e756d6265721464656c617938543a3a426c6f636b4e756d626572245101205363686564756c65207468652063757272656e746c792065787465726e616c6c792d70726f706f736564206d616a6f726974792d63617272696573207265666572656e64756d20746f206265207461626c6564650120696d6d6564696174656c792e204966207468657265206973206e6f2065787465726e616c6c792d70726f706f736564207265666572656e64756d2063757272656e746c792c206f72206966207468657265206973206f6e65ec20627574206974206973206e6f742061206d616a6f726974792d63617272696573207265666572656e64756d207468656e206974206661696c732e00f8202d206070726f706f73616c5f68617368603a205468652068617368206f66207468652063757272656e742065787465726e616c2070726f706f73616c2e6101202d2060766f74696e675f706572696f64603a2054686520706572696f64207468617420697320616c6c6f77656420666f7220766f74696e67206f6e20746869732070726f706f73616c2e20496e6372656173656420746f9820202060456d657267656e6379566f74696e67506572696f646020696620746f6f206c6f772e5501202d206064656c6179603a20546865206e756d626572206f6620626c6f636b20616674657220766f74696e672068617320656e64656420696e20617070726f76616c20616e6420746869732073686f756c64206265bc202020656e61637465642e205468697320646f65736e277420686176652061206d696e696d756d20616d6f756e742e347665746f5f65787465726e616c043470726f706f73616c5f686173681c543a3a4861736804bc205665746f20616e6420626c61636b6c697374207468652065787465726e616c2070726f706f73616c20686173682e4463616e63656c5f7265666572656e64756d04247265665f696e64657860436f6d706163743c5265666572656e64756d496e6465783e04542052656d6f76652061207265666572656e64756d2e3463616e63656c5f7175657565640c107768656e5c436f6d706163743c543a3a426c6f636b4e756d6265723e14776869636830436f6d706163743c7533323e107768617460436f6d706163743c5265666572656e64756d496e6465783e04a02043616e63656c20612070726f706f73616c2071756575656420666f7220656e6163746d656e742e247365745f70726f7879041470726f787930543a3a4163636f756e7449641498205370656369667920612070726f78792e2043616c6c6564206279207468652073746173682e002c2023203c7765696768743e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e3072657369676e5f70726f787900149820436c656172207468652070726f78792e2043616c6c6564206279207468652070726f78792e002c2023203c7765696768743e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e3072656d6f76655f70726f7879041470726f787930543a3a4163636f756e744964149820436c656172207468652070726f78792e2043616c6c6564206279207468652073746173682e002c2023203c7765696768743e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e2064656c65676174650808746f30543a3a4163636f756e74496428636f6e76696374696f6e28436f6e76696374696f6e143c2044656c656761746520766f74652e002c2023203c7765696768743e58202d204f6e6520657874726120444220656e7472792e302023203c2f7765696768743e28756e64656c656761746500144420556e64656c656761746520766f74652e002c2023203c7765696768743e20202d204f2831292e302023203c2f7765696768743e58636c6561725f7075626c69635f70726f706f73616c7300040101205665746f20616e6420626c61636b6c697374207468652070726f706f73616c20686173682e204d7573742062652066726f6d20526f6f74206f726967696e2e346e6f74655f707265696d6167650440656e636f6465645f70726f706f73616c1c5665633c75383e0861012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e205468697320646f65736e27742072657175697265207468652070726f706f73616c20746f206265250120696e207468652064697370617463682071756575652062757420646f657320726571756972652061206465706f7369742c2072657475726e6564206f6e636520656e61637465642e586e6f74655f696d6d696e656e745f707265696d6167650c40656e636f6465645f70726f706f73616c1c5665633c75383e107768656e38543a3a426c6f636b4e756d6265721477686963680c7533320845012052656769737465722074686520707265696d61676520666f7220616e207570636f6d696e672070726f706f73616c2e2054686973207265717569726573207468652070726f706f73616c20746f206265b420696e207468652064697370617463682071756575652e204e6f206465706f736974206973206e65656465642e34726561705f707265696d616765043470726f706f73616c5f686173681c543a3a4861736804f42052656d6f766520616e20657870697265642070726f706f73616c20707265696d61676520616e6420636f6c6c65637420746865206465706f7369742e01402050726f706f736564082450726f70496e6465781c42616c616e636504c02041206d6f74696f6e20686173206265656e2070726f706f7365642062792061207075626c6963206163636f756e742e185461626c65640c2450726f70496e6465781c42616c616e6365385665633c4163636f756e7449643e04dc2041207075626c69632070726f706f73616c20686173206265656e207461626c656420666f72207265666572656e64756d20766f74652e3845787465726e616c5461626c656400049820416e2065787465726e616c2070726f706f73616c20686173206265656e207461626c65642e1c53746172746564083c5265666572656e64756d496e64657834566f74655468726573686f6c6404602041207265666572656e64756d2068617320626567756e2e18506173736564043c5265666572656e64756d496e64657804b020412070726f706f73616c20686173206265656e20617070726f766564206279207265666572656e64756d2e244e6f74506173736564043c5265666572656e64756d496e64657804b020412070726f706f73616c20686173206265656e2072656a6563746564206279207265666572656e64756d2e2443616e63656c6c6564043c5265666572656e64756d496e64657804842041207265666572656e64756d20686173206265656e2063616e63656c6c65642e204578656375746564083c5265666572656e64756d496e64657810626f6f6c047420412070726f706f73616c20686173206265656e20656e61637465642e2444656c65676174656408244163636f756e744964244163636f756e74496404e020416e206163636f756e74206861732064656c65676174656420746865697220766f746520746f20616e6f74686572206163636f756e742e2c556e64656c65676174656404244163636f756e74496404e820416e206163636f756e74206861732063616e63656c6c656420612070726576696f75732064656c65676174696f6e206f7065726174696f6e2e185665746f65640c244163636f756e74496410486173682c426c6f636b4e756d626572049820416e2065787465726e616c2070726f706f73616c20686173206265656e207665746f65642e34507265696d6167654e6f7465640c1048617368244163636f756e7449641c42616c616e636504e020412070726f706f73616c277320707265696d61676520776173206e6f7465642c20616e6420746865206465706f7369742074616b656e2e30507265696d616765557365640c1048617368244163636f756e7449641c42616c616e636504150120412070726f706f73616c20707265696d616765207761732072656d6f76656420616e6420757365642028746865206465706f736974207761732072657475726e6564292e3c507265696d616765496e76616c69640810486173683c5265666572656e64756d496e646578040d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d6167652077617320696e76616c69642e3c507265696d6167654d697373696e670810486173683c5265666572656e64756d496e646578040d0120412070726f706f73616c20636f756c64206e6f7420626520657865637574656420626563617573652069747320707265696d61676520776173206d697373696e672e38507265696d616765526561706564101048617368244163636f756e7449641c42616c616e6365244163636f756e744964045d012041207265676973746572656420707265696d616765207761732072656d6f76656420616e6420746865206465706f73697420636f6c6c6563746564206279207468652072656170657220286c617374206974656d292e1c3c456e6163746d656e74506572696f6438543a3a426c6f636b4e756d62657210002f0d0014710120546865206d696e696d756d20706572696f64206f66206c6f636b696e6720616e642074686520706572696f64206265747765656e20612070726f706f73616c206265696e6720617070726f76656420616e6420656e61637465642e0031012049742073686f756c642067656e6572616c6c792062652061206c6974746c65206d6f7265207468616e2074686520756e7374616b6520706572696f6420746f20656e737572652074686174690120766f74696e67207374616b657273206861766520616e206f70706f7274756e69747920746f2072656d6f7665207468656d73656c7665732066726f6d207468652073797374656d20696e2074686520636173652077686572659c207468657920617265206f6e20746865206c6f73696e672073696465206f66206120766f74652e304c61756e6368506572696f6438543a3a426c6f636b4e756d62657210004e0c0004e420486f77206f6674656e2028696e20626c6f636b7329206e6577207075626c6963207265666572656e646120617265206c61756e636865642e30566f74696e67506572696f6438543a3a426c6f636b4e756d62657210004e0c0004b820486f77206f6674656e2028696e20626c6f636b732920746f20636865636b20666f72206e657720766f7465732e384d696e696d756d4465706f7369743042616c616e63654f663c543e400000c16ff2862300000000000000000004350120546865206d696e696d756d20616d6f756e7420746f20626520757365642061732061206465706f73697420666f722061207075626c6963207265666572656e64756d2070726f706f73616c2e54456d657267656e6379566f74696e67506572696f6438543a3a426c6f636b4e756d626572108051010004ec204d696e696d756d20766f74696e6720706572696f6420616c6c6f77656420666f7220616e20656d657267656e6379207265666572656e64756d2e34436f6f6c6f6666506572696f6438543a3a426c6f636b4e756d62657210004e0c0004610120506572696f6420696e20626c6f636b7320776865726520616e2065787465726e616c2070726f706f73616c206d6179206e6f742062652072652d7375626d6974746564206166746572206265696e67207665746f65642e4c507265696d616765427974654465706f7369743042616c616e63654f663c543e400010a5d4e800000000000000000000000429012054686520616d6f756e74206f662062616c616e63652074686174206d757374206265206465706f7369746564207065722062797465206f6620707265696d6167652073746f7265642e001c436f756e63696c014c496e7374616e636531436f6c6c656374697665142450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001011c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001011c543a3a486173684c566f7465733c543a3a4163636f756e7449643e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e01102c7365745f6d656d62657273042c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e105101205365742074686520636f6c6c6563746976652773206d656d62657273686970206d616e75616c6c7920746f20606e65775f6d656d62657273602e204265206e69636520746f2074686520636861696e20616e645c2070726f76696465206974207072652d736f727465642e005820526571756972657320726f6f74206f726967696e2e1c65786563757465042070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e0cf420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e1c70726f706f736508247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e102c2023203c7765696768743e90202d20426f756e6465642073746f7261676520726561647320616e64207772697465732eb8202d20417267756d656e7420607468726573686f6c6460206861732062656172696e67206f6e207765696768742e302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c102c2023203c7765696768743e8c202d20426f756e6465642073746f72616765207265616420616e64207772697465732e5501202d2057696c6c20626520736c696768746c792068656176696572206966207468652070726f706f73616c20697320617070726f766564202f20646973617070726f7665642061667465722074686520766f74652e302023203c2f7765696768743e01182050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e74084d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292e14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740809012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292e20417070726f76656404104861736804c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e2c446973617070726f76656404104861736804d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e20457865637574656408104861736810626f6f6c0405012041206d6f74696f6e207761732065786563757465643b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e384d656d626572457865637574656408104861736810626f6f6c042d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e000048546563686e6963616c436f6d6d6974746565014c496e7374616e636532436f6c6c656374697665142450726f706f73616c730100305665633c543a3a486173683e040004902054686520686173686573206f6620746865206163746976652070726f706f73616c732e2850726f706f73616c4f660001011c543a3a48617368643c542061732054726169743c493e3e3a3a50726f706f73616c00040004cc2041637475616c2070726f706f73616c20666f72206120676976656e20686173682c20696620697427732063757272656e742e18566f74696e670001011c543a3a486173684c566f7465733c543a3a4163636f756e7449643e00040004b420566f746573206f6e206120676976656e2070726f706f73616c2c206966206974206973206f6e676f696e672e3450726f706f73616c436f756e7401000c753332100000000004482050726f706f73616c7320736f206661722e1c4d656d626572730100445665633c543a3a4163636f756e7449643e0400043901205468652063757272656e74206d656d62657273206f662074686520636f6c6c6563746976652e20546869732069732073746f72656420736f7274656420286a7573742062792076616c7565292e01102c7365745f6d656d62657273042c6e65775f6d656d62657273445665633c543a3a4163636f756e7449643e105101205365742074686520636f6c6c6563746976652773206d656d62657273686970206d616e75616c6c7920746f20606e65775f6d656d62657273602e204265206e69636520746f2074686520636861696e20616e645c2070726f76696465206974207072652d736f727465642e005820526571756972657320726f6f74206f726967696e2e1c65786563757465042070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e0cf420446973706174636820612070726f706f73616c2066726f6d2061206d656d626572207573696e672074686520604d656d62657260206f726967696e2e00ac204f726967696e206d7573742062652061206d656d626572206f662074686520636f6c6c6563746976652e1c70726f706f736508247468726573686f6c6450436f6d706163743c4d656d626572436f756e743e2070726f706f73616c78426f783c3c542061732054726169743c493e3e3a3a50726f706f73616c3e102c2023203c7765696768743e90202d20426f756e6465642073746f7261676520726561647320616e64207772697465732eb8202d20417267756d656e7420607468726573686f6c6460206861732062656172696e67206f6e207765696768742e302023203c2f7765696768743e10766f74650c2070726f706f73616c1c543a3a4861736814696e64657858436f6d706163743c50726f706f73616c496e6465783e1c617070726f766510626f6f6c102c2023203c7765696768743e8c202d20426f756e6465642073746f72616765207265616420616e64207772697465732e5501202d2057696c6c20626520736c696768746c792068656176696572206966207468652070726f706f73616c20697320617070726f766564202f20646973617070726f7665642061667465722074686520766f74652e302023203c2f7765696768743e01182050726f706f73656410244163636f756e7449643450726f706f73616c496e64657810486173682c4d656d626572436f756e74084d012041206d6f74696f6e2028676976656e20686173682920686173206265656e2070726f706f7365642028627920676976656e206163636f756e742920776974682061207468726573686f6c642028676976656e4020604d656d626572436f756e7460292e14566f74656414244163636f756e744964104861736810626f6f6c2c4d656d626572436f756e742c4d656d626572436f756e740809012041206d6f74696f6e2028676976656e20686173682920686173206265656e20766f746564206f6e20627920676976656e206163636f756e742c206c656176696e67190120612074616c6c79202879657320766f74657320616e64206e6f20766f74657320676976656e20726573706563746976656c7920617320604d656d626572436f756e7460292e20417070726f76656404104861736804c42041206d6f74696f6e2077617320617070726f76656420627920746865207265717569726564207468726573686f6c642e2c446973617070726f76656404104861736804d42041206d6f74696f6e20776173206e6f7420617070726f76656420627920746865207265717569726564207468726573686f6c642e20457865637574656408104861736810626f6f6c0405012041206d6f74696f6e207761732065786563757465643b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e384d656d626572457865637574656408104861736810626f6f6c042d0120412073696e676c65206d656d6265722064696420736f6d6520616374696f6e3b2060626f6f6c6020697320747275652069662072657475726e656420776974686f7574206572726f722e000024456c656374696f6e73014050687261676d656e456c656374696f6e181c4d656d626572730100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e040004f0205468652063757272656e7420656c6563746564206d656d626572736869702e20536f72746564206261736564206f6e206163636f756e742069642e2452756e6e65727355700100845665633c28543a3a4163636f756e7449642c2042616c616e63654f663c543e293e0400044901205468652063757272656e742072756e6e6572735f75702e20536f72746564206261736564206f6e206c6f7720746f2068696768206d657269742028776f72736520746f20626573742072756e6e6572292e38456c656374696f6e526f756e647301000c75333210000000000441012054686520746f74616c206e756d626572206f6620766f746520726f756e6473207468617420686176652068617070656e65642c206578636c7564696e6720746865207570636f6d696e67206f6e652e1c566f7465734f6601010130543a3a4163636f756e744964445665633c543a3a4163636f756e7449643e01040004010120566f746573206f66206120706172746963756c617220766f7465722c20776974682074686520726f756e6420696e646578206f662074686520766f7465732e1c5374616b654f6601010130543a3a4163636f756e7449643042616c616e63654f663c543e0040000000000000000000000000000000000464204c6f636b6564207374616b65206f66206120766f7465722e2843616e646964617465730100445665633c543a3a4163636f756e7449643e0400086501205468652070726573656e742063616e646964617465206c6973742e20536f72746564206261736564206f6e206163636f756e742069642e20412063757272656e74206d656d6265722063616e206e6576657220656e7465720101207468697320766563746f7220616e6420697320616c7761797320696d706c696369746c7920617373756d656420746f20626520612063616e6469646174652e011810766f74650814766f746573445665633c543a3a4163636f756e7449643e1476616c756554436f6d706163743c42616c616e63654f663c543e3e3c050120566f746520666f72206120736574206f662063616e6469646174657320666f7220746865207570636f6d696e6720726f756e64206f6620656c656374696f6e2e0050205468652060766f746573602073686f756c643a482020202d206e6f7420626520656d7074792eac2020202d206265206c657373207468616e20746865206e756d626572206f662063616e646964617465732e005d012055706f6e20766f74696e672c206076616c75656020756e697473206f66206077686f6027732062616c616e6365206973206c6f636b656420616e64206120626f6e6420616d6f756e742069732072657365727665642e5d012049742069732074686520726573706f6e736962696c697479206f66207468652063616c6c657220746f206e6f7420706c61636520616c6c206f662074686569722062616c616e636520696e746f20746865206c6f636ba020616e64206b65657020736f6d6520666f722066757274686572207472616e73616374696f6e732e002c2023203c7765696768743e2c2023232323205374617465302052656164733a204f283129c8205772697465733a204f28562920676976656e2060566020766f7465732e205620697320626f756e6465642062792031362e302023203c2f7765696768743e3072656d6f76655f766f746572001c21012052656d6f766520606f726967696e60206173206120766f7465722e20546869732072656d6f76657320746865206c6f636b20616e642072657475726e732074686520626f6e642e002c2023203c7765696768743e2c2023232323205374617465302052656164733a204f28312934205772697465733a204f283129302023203c2f7765696768743e507265706f72745f646566756e63745f766f74657204187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365345d01205265706f727420607461726765746020666f72206265696e6720616e20646566756e637420766f7465722e20496e2063617365206f6620612076616c6964207265706f72742c20746865207265706f727465722069735d012072657761726465642062792074686520626f6e6420616d6f756e74206f662060746172676574602e204f74686572776973652c20746865207265706f7274657220697473656c662069732072656d6f76656420616e645c20746865697220626f6e6420697320736c61736865642e0088204120646566756e637420766f74657220697320646566696e656420746f2062653a4d012020202d206120766f7465722077686f73652063757272656e74207375626d697474656420766f7465732061726520616c6c20696e76616c69642e20692e652e20616c6c206f66207468656d20617265206e6fb420202020206c6f6e67657220612063616e646964617465206e6f7220616e20616374697665206d656d6265722e002c2023203c7765696768743e2c202323232320537461746515012052656164733a204f284e4c6f674d2920676976656e204d2063757272656e742063616e6469646174657320616e64204e20766f74657320666f722060746172676574602e34205772697465733a204f283129302023203c2f7765696768743e407375626d69745f63616e646964616379003478205375626d6974206f6e6573656c6620666f722063616e6469646163792e006420412063616e6469646174652077696c6c206569746865723aec2020202d204c6f73652061742074686520656e64206f6620746865207465726d20616e6420666f7266656974207468656972206465706f7369742e2d012020202d2057696e20616e64206265636f6d652061206d656d6265722e204d656d626572732077696c6c206576656e7475616c6c7920676574207468656972207374617368206261636b2e55012020202d204265636f6d6520612072756e6e65722d75702e2052756e6e6572732d75707320617265207265736572766564206d656d6265727320696e2063617365206f6e65206765747320666f72636566756c6c7934202020202072656d6f7665642e002c2023203c7765696768743e2c20232323232053746174658c2052656164733a204f284c6f674e2920476976656e204e2063616e646964617465732e34205772697465733a204f283129302023203c2f7765696768743e4872656e6f756e63655f63616e646964616379002451012052656e6f756e6365206f6e65277320696e74656e74696f6e20746f20626520612063616e64696461746520666f7220746865206e65787420656c656374696f6e20726f756e642e203320706f74656e7469616c40206f7574636f6d65732065786973743a4101202d20606f726967696e6020697320612063616e64696461746520616e64206e6f7420656c656374656420696e20616e79207365742e20496e207468697320636173652c2074686520626f6e64206973f4202020756e72657365727665642c2072657475726e656420616e64206f726967696e2069732072656d6f76656420617320612063616e6469646174652e5901202d20606f726967696e6020697320612063757272656e742072756e6e65722075702e20496e207468697320636173652c2074686520626f6e6420697320756e72657365727665642c2072657475726e656420616e64842020206f726967696e2069732072656d6f76656420617320612072756e6e65722e4d01202d20606f726967696e6020697320612063757272656e74206d656d6265722e20496e207468697320636173652c2074686520626f6e6420697320756e726573657276656420616e64206f726967696e206973590120202072656d6f7665642061732061206d656d6265722c20636f6e73657175656e746c79206e6f74206265696e6720612063616e64696461746520666f7220746865206e65787420726f756e6420616e796d6f72652e650120202053696d696c617220746f205b6072656d6f76655f766f746572605d2c206966207265706c6163656d656e742072756e6e657273206578697374732c20746865792061726520696d6d6564696174656c7920757365642e3472656d6f76655f6d656d626572040c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365345d012052656d6f7665206120706172746963756c6172206d656d6265722066726f6d20746865207365742e20546869732069732065666665637469766520696d6d6564696174656c7920616e642074686520626f6e64206f668020746865206f7574676f696e67206d656d62657220697320736c61736865642e00590120496620612072756e6e65722d757020697320617661696c61626c652c207468656e2074686520626573742072756e6e65722d75702077696c6c2062652072656d6f76656420616e64207265706c6163657320746865f4206f7574676f696e67206d656d6265722e204f74686572776973652c2061206e65772070687261676d656e20726f756e6420697320737461727465642e004501204e6f74652074686174207468697320646f6573206e6f7420616666656374207468652064657369676e6174656420626c6f636b206e756d626572206f6620746865206e65787420656c656374696f6e2e002c2023203c7765696768743e2c2023232323205374617465582052656164733a204f28646f5f70687261676d656e295c205772697465733a204f28646f5f70687261676d656e29302023203c2f7765696768743e01141c4e65775465726d04645665633c284163636f756e7449642c2042616c616e6365293e0855012041206e6577207465726d2077697468206e6577206d656d626572732e205468697320696e64696361746573207468617420656e6f7567682063616e6469646174657320657869737465642c206e6f742074686174450120656e6f756768206861766520686173206265656e20656c65637465642e2054686520696e6e65722076616c7565206d757374206265206578616d696e656420666f72207468697320707572706f73652e24456d7074795465726d0004d8204e6f20286f72206e6f7420656e6f756768292063616e64696461746573206578697374656420666f72207468697320726f756e642e304d656d6265724b69636b656404244163636f756e7449640845012041206d656d62657220686173206265656e2072656d6f7665642e20546869732073686f756c6420616c7761797320626520666f6c6c6f7765642062792065697468657220604e65775465726d60206f74342060456d7074795465726d602e3c4d656d62657252656e6f756e63656404244163636f756e74496404a02041206d656d626572206861732072656e6f756e6365642074686569722063616e6469646163792e34566f7465725265706f727465640c244163636f756e744964244163636f756e74496410626f6f6c086101204120766f7465722028666972737420656c656d656e742920776173207265706f72746564202862797420746865207365636f6e6420656c656d656e742920776974682074686520746865207265706f7274206265696e678c207375636365737366756c206f72206e6f742028746869726420656c656d656e74292e143443616e646964616379426f6e643042616c616e63654f663c543e400080c6a47e8d030000000000000000000028566f74696e67426f6e643042616c616e63654f663c543e4000407a10f35a000000000000000000000038446573697265644d656d626572730c753332100d00000000404465736972656452756e6e65727355700c753332100700000000305465726d4475726174696f6e38543a3a426c6f636b4e756d626572108013030000004c546563686e6963616c4d656d62657273686970014c496e7374616e6365314d656d62657273686970041c4d656d626572730100445665633c543a3a4163636f756e7449643e040004c8205468652063757272656e74206d656d626572736869702c2073746f72656420617320616e206f726465726564205665632e0114286164645f6d656d626572040c77686f30543a3a4163636f756e7449640c7c204164642061206d656d626572206077686f6020746f20746865207365742e00b4204d6179206f6e6c792062652063616c6c65642066726f6d20604164644f726967696e60206f7220726f6f742e3472656d6f76655f6d656d626572040c77686f30543a3a4163636f756e7449640c902052656d6f76652061206d656d626572206077686f602066726f6d20746865207365742e00c0204d6179206f6e6c792062652063616c6c65642066726f6d206052656d6f76654f726967696e60206f7220726f6f742e2c737761705f6d656d626572081872656d6f766530543a3a4163636f756e7449640c61646430543a3a4163636f756e7449640cc02053776170206f7574206f6e65206d656d626572206072656d6f76656020666f7220616e6f746865722060616464602e00b8204d6179206f6e6c792062652063616c6c65642066726f6d2060537761704f726967696e60206f7220726f6f742e3472657365745f6d656d62657273041c6d656d62657273445665633c543a3a4163636f756e7449643e105901204368616e676520746865206d656d6265727368697020746f2061206e6577207365742c20646973726567617264696e6720746865206578697374696e67206d656d626572736869702e204265206e69636520616e646c207061737320606d656d6265727360207072652d736f727465642e00bc204d6179206f6e6c792062652063616c6c65642066726f6d206052657365744f726967696e60206f7220726f6f742e286368616e67655f6b6579040c6e657730543a3a4163636f756e7449640cd82053776170206f7574207468652073656e64696e67206d656d62657220666f7220736f6d65206f74686572206b657920606e6577602e00f4204d6179206f6e6c792062652063616c6c65642066726f6d20605369676e656460206f726967696e206f6620612063757272656e74206d656d6265722e01182c4d656d62657241646465640004e42054686520676976656e206d656d626572207761732061646465643b2073656520746865207472616e73616374696f6e20666f722077686f2e344d656d62657252656d6f7665640004ec2054686520676976656e206d656d626572207761732072656d6f7665643b2073656520746865207472616e73616374696f6e20666f722077686f2e384d656d62657273537761707065640004dc2054776f206d656d62657273207765726520737761707065643b2073656520746865207472616e73616374696f6e20666f722077686f2e304d656d6265727352657365740004190120546865206d656d62657273686970207761732072657365743b2073656520746865207472616e73616374696f6e20666f722077686f20746865206e6577207365742069732e284b65794368616e676564000488204f6e65206f6620746865206d656d6265727327206b657973206368616e6765642e1444756d6d7904b4727374643a3a6d61726b65723a3a5068616e746f6d446174613c284163636f756e7449642c204576656e74293e0470205068616e746f6d206d656d6265722c206e6576657220757365642e00003c46696e616c697479547261636b65720001042866696e616c5f68696e74041068696e745c436f6d706163743c543a3a426c6f636b4e756d6265723e08f42048696e7420746861742074686520617574686f72206f66207468697320626c6f636b207468696e6b732074686520626573742066696e616c697a65646c20626c6f636b2069732074686520676976656e206e756d6265722e00082857696e646f7753697a6538543a3a426c6f636b4e756d626572106500000004190120546865206e756d626572206f6620726563656e742073616d706c657320746f206b6565702066726f6d207468697320636861696e2e2044656661756c74206973203130312e345265706f72744c6174656e637938543a3a426c6f636b4e756d62657210e8030000041d01205468652064656c617920616674657220776869636820706f696e74207468696e6773206265636f6d6520737573706963696f75732e2044656661756c7420697320313030302e001c4772616e647061013c4772616e64706146696e616c6974791c2c417574686f726974696573010034417574686f726974794c6973740400102c20444550524543415445440061012054686973207573656420746f2073746f7265207468652063757272656e7420617574686f72697479207365742c20776869636820686173206265656e206d6967726174656420746f207468652077656c6c2d6b6e6f776e94204752414e4450415f415554484f52495445535f4b455920756e686173686564206b65792e14537461746501006c53746f72656453746174653c543a3a426c6f636b4e756d6265723e04000490205374617465206f66207468652063757272656e7420617574686f72697479207365742e3450656e64696e674368616e676500008c53746f72656450656e64696e674368616e67653c543a3a426c6f636b4e756d6265723e040004c42050656e64696e67206368616e67653a20287369676e616c65642061742c207363686564756c6564206368616e6765292e284e657874466f72636564000038543a3a426c6f636b4e756d626572040004bc206e65787420626c6f636b206e756d6265722077686572652077652063616e20666f7263652061206368616e67652e1c5374616c6c656400008028543a3a426c6f636b4e756d6265722c20543a3a426c6f636b4e756d626572290400049020607472756560206966207765206172652063757272656e746c79207374616c6c65642e3043757272656e7453657449640100145365744964200000000000000000085d0120546865206e756d626572206f66206368616e6765732028626f746820696e207465726d73206f66206b65797320616e6420756e6465726c79696e672065636f6e6f6d696320726573706f6e736962696c697469657329c420696e20746865202273657422206f66204772616e6470612076616c696461746f72732066726f6d2067656e657369732e30536574496453657373696f6e0001011453657449643053657373696f6e496e64657800040004c1012041206d617070696e672066726f6d206772616e6470612073657420494420746f2074686520696e646578206f6620746865202a6d6f737420726563656e742a2073657373696f6e20666f7220776869636820697473206d656d62657273207765726520726573706f6e7369626c652e0104487265706f72745f6d69736265686176696f72041c5f7265706f72741c5665633c75383e0464205265706f727420736f6d65206d69736265686176696f722e010c384e6577417574686f7269746965730434417574686f726974794c6973740490204e657720617574686f726974792073657420686173206265656e206170706c6965642e1850617573656400049c2043757272656e7420617574686f726974792073657420686173206265656e207061757365642e1c526573756d65640004a02043757272656e7420617574686f726974792073657420686173206265656e20726573756d65642e0000205472656173757279012054726561737572790c3450726f706f73616c436f756e7401003450726f706f73616c496e646578100000000004a4204e756d626572206f662070726f706f73616c7320746861742068617665206265656e206d6164652e2450726f706f73616c730001013450726f706f73616c496e6465789050726f706f73616c3c543a3a4163636f756e7449642c2042616c616e63654f663c543e3e000400047c2050726f706f73616c7320746861742068617665206265656e206d6164652e24417070726f76616c730100485665633c50726f706f73616c496e6465783e040004f82050726f706f73616c20696e646963657320746861742068617665206265656e20617070726f76656420627574206e6f742079657420617761726465642e010c3470726f706f73655f7370656e64081476616c756554436f6d706163743c42616c616e63654f663c543e3e2c62656e65666963696172798c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365242d012050757420666f727761726420612073756767657374696f6e20666f72207370656e64696e672e2041206465706f7369742070726f706f7274696f6e616c20746f207468652076616c7565350120697320726573657276656420616e6420736c6173686564206966207468652070726f706f73616c2069732072656a65637465642e2049742069732072657475726e6564206f6e636520746865542070726f706f73616c20697320617761726465642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e94202d204f6e65204442206368616e67652c206f6e6520657874726120444220656e7472792e302023203c2f7765696768743e3c72656a6563745f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e1cfc2052656a65637420612070726f706f736564207370656e642e20546865206f726967696e616c206465706f7369742077696c6c20626520736c61736865642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e40202d204f6e6520444220636c6561722e302023203c2f7765696768743e40617070726f76655f70726f706f73616c042c70726f706f73616c5f696458436f6d706163743c50726f706f73616c496e6465783e205d0120417070726f766520612070726f706f73616c2e2041742061206c617465722074696d652c207468652070726f706f73616c2077696c6c20626520616c6c6f636174656420746f207468652062656e6566696369617279ac20616e6420746865206f726967696e616c206465706f7369742077696c6c2062652072657475726e65642e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e01182050726f706f736564043450726f706f73616c496e6465780438204e65772070726f706f73616c2e205370656e64696e67041c42616c616e636504e8205765206861766520656e6465642061207370656e6420706572696f6420616e642077696c6c206e6f7720616c6c6f636174652066756e64732e1c417761726465640c3450726f706f73616c496e6465781c42616c616e6365244163636f756e744964048020536f6d652066756e64732068617665206265656e20616c6c6f63617465642e144275726e74041c42616c616e6365048c20536f6d65206f66206f75722066756e64732068617665206265656e206275726e742e20526f6c6c6f766572041c42616c616e6365043101205370656e64696e67206861732066696e69736865643b20746869732069732074686520616d6f756e74207468617420726f6c6c73206f76657220756e74696c206e657874207370656e642e1c4465706f736974041c42616c616e6365048020536f6d652066756e64732068617665206265656e206465706f73697465642e103050726f706f73616c426f6e641c5065726d696c6c1050c30000085501204672616374696f6e206f6620612070726f706f73616c27732076616c756520746861742073686f756c6420626520626f6e64656420696e206f7264657220746f20706c616365207468652070726f706f73616c2e110120416e2061636365707465642070726f706f73616c2067657473207468657365206261636b2e20412072656a65637465642070726f706f73616c20646f6573206e6f742e4c50726f706f73616c426f6e644d696e696d756d3042616c616e63654f663c543e4000407a10f35a00000000000000000000044901204d696e696d756d20616d6f756e74206f662066756e647320746861742073686f756c6420626520706c6163656420696e2061206465706f73697420666f72206d616b696e6720612070726f706f73616c2e2c5370656e64506572696f6438543a3a426c6f636b4e756d6265721080700000048820506572696f64206265747765656e2073756363657373697665207370656e64732e104275726e1c5065726d696c6c1020a107000411012050657263656e74616765206f662073706172652066756e64732028696620616e7929207468617420617265206275726e7420706572207370656e6420706572696f642e0024436f6e7472616374730120436f6e74726163741c204761735370656e7401000c476173200000000000000000048020476173207370656e7420736f2066617220696e207468697320626c6f636b2e3c43757272656e745363686564756c650100205363686564756c65c5010000000001000000000000000100000000000000010000000000000001000000000000000100000000000000010000000000000001000000000000008700000000000000af000000000000000100000000000000010000000000000004000000000001001000000000400000002000000004942043757272656e7420636f7374207363686564756c6520666f7220636f6e7472616374732e305072697374696e65436f64650001012c436f6465486173683c543e1c5665633c75383e0004000465012041206d617070696e672066726f6d20616e206f726967696e616c20636f6465206861736820746f20746865206f726967696e616c20636f64652c20756e746f756368656420627920696e737472756d656e746174696f6e2e2c436f646553746f726167650001012c436f6465486173683c543e587761736d3a3a5072656661625761736d4d6f64756c650004000465012041206d617070696e67206265747765656e20616e206f726967696e616c20636f6465206861736820616e6420696e737472756d656e746564207761736d20636f64652c20726561647920666f7220657865637574696f6e2e384163636f756e74436f756e74657201000c753634200000000000000000045420546865207375627472696520636f756e7465722e38436f6e7472616374496e666f4f6600010130543a3a4163636f756e7449643c436f6e7472616374496e666f3c543e00040004a82054686520636f6465206173736f6369617465642077697468206120676976656e206163636f756e742e20476173507269636501003042616c616e63654f663c543e4001000000000000000000000000000000047820546865207072696365206f66206f6e6520756e6974206f66206761732e01143c7570646174655f7363686564756c6504207363686564756c65205363686564756c650cb4205570646174657320746865207363686564756c6520666f72206d65746572696e6720636f6e7472616374732e000d0120546865207363686564756c65206d7573742068617665206120677265617465722076657273696f6e207468616e207468652073746f726564207363686564756c652e207075745f636f646508246761735f6c696d697430436f6d706163743c4761733e10636f64651c5665633c75383e085d012053746f7265732074686520676976656e2062696e617279205761736d20636f646520696e746f2074686520636861696e27732073746f7261676520616e642072657475726e73206974732060636f646568617368602ed420596f752063616e20696e7374616e746961746520636f6e747261637473206f6e6c7920776974682073746f72656420636f64652e1063616c6c1010646573748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263651476616c756554436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e10646174611c5665633c75383e1c0901204d616b657320612063616c6c20746f20616e206163636f756e742c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e002901202a20496620746865206163636f756e74206973206120736d6172742d636f6e7472616374206163636f756e742c20746865206173736f63696174656420636f64652077696c6c206265b020657865637574656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e1901202a20496620746865206163636f756e74206973206120726567756c6172206163636f756e742c20616e792076616c75652077696c6c206265207472616e736665727265642e4901202a204966206e6f206163636f756e742065786973747320616e64207468652063616c6c2076616c7565206973206e6f74206c657373207468616e20606578697374656e7469616c5f6465706f736974602c1501206120726567756c6172206163636f756e742077696c6c206265206372656174656420616e6420616e792076616c75652077696c6c206265207472616e736665727265642e2c696e7374616e74696174651024656e646f776d656e7454436f6d706163743c42616c616e63654f663c543e3e246761735f6c696d697430436f6d706163743c4761733e24636f64655f686173682c436f6465486173683c543e10646174611c5665633c75383e28bd0120496e7374616e7469617465732061206e657720636f6e74726163742066726f6d207468652060636f646568617368602067656e65726174656420627920607075745f636f6465602c206f7074696f6e616c6c79207472616e7366657272696e6720736f6d652062616c616e63652e009820496e7374616e74696174696f6e20697320657865637574656420617320666f6c6c6f77733a004101202d205468652064657374696e6174696f6e206164647265737320697320636f6d7075746564206261736564206f6e207468652073656e64657220616e642068617368206f662074686520636f64652e0501202d2054686520736d6172742d636f6e7472616374206163636f756e7420697320637265617465642061742074686520636f6d707574656420616464726573732e6d01202d20546865206063746f725f636f64656020697320657865637574656420696e2074686520636f6e74657874206f6620746865206e65776c792d63726561746564206163636f756e742e204275666665722072657475726e65645d0120202061667465722074686520657865637574696f6e206973207361766564206173207468652060636f646560206f6620746865206163636f756e742e205468617420636f64652077696c6c20626520696e766f6b6564a820202075706f6e20616e792063616c6c2072656365697665642062792074686973206163636f756e742e7c202d2054686520636f6e747261637420697320696e697469616c697a65642e3c636c61696d5f73757263686172676508106465737430543a3a4163636f756e744964286175785f73656e646572504f7074696f6e3c543a3a4163636f756e7449643e14710120416c6c6f777320626c6f636b2070726f64756365727320746f20636c61696d206120736d616c6c2072657761726420666f72206576696374696e67206120636f6e74726163742e204966206120626c6f636b2070726f64756365721501206661696c7320746f20646f20736f2c206120726567756c61722075736572732077696c6c20626520616c6c6f77656420746f20636c61696d20746865207265776172642e00390120496620636f6e7472616374206973206e6f742065766963746564206173206120726573756c74206f6620746869732063616c6c2c206e6f20616374696f6e73206172652074616b656e20616e64ac207468652073656e646572206973206e6f7420656c696769626c6520666f7220746865207265776172642e0118205472616e736665720c244163636f756e744964244163636f756e7449641c42616c616e6365046901205472616e736665722068617070656e6564206066726f6d6020746f2060746f60207769746820676976656e206076616c7565602061732070617274206f662061206063616c6c60206f722060696e7374616e7469617465602e30496e7374616e74696174656408244163636f756e744964244163636f756e74496404dc20436f6e7472616374206465706c6f7965642062792061646472657373206174207468652073706563696669656420616464726573732e28436f646553746f72656404104861736804b820436f646520776974682074686520737065636966696564206861736820686173206265656e2073746f7265642e3c5363686564756c6555706461746564040c75333204c020547269676765726564207768656e207468652063757272656e74207363686564756c6520697320757064617465642e284469737061746368656408244163636f756e74496410626f6f6c08390120412063616c6c2077617320646973706174636865642066726f6d2074686520676976656e206163636f756e742e2054686520626f6f6c207369676e616c7320776865746865722069742077617374207375636365737366756c20657865637574696f6e206f72206e6f742e20436f6e747261637408244163636f756e7449641c5665633c75383e048c20416e206576656e742066726f6d20636f6e7472616374206f66206163636f756e742e404c5369676e6564436c61696d48616e646963617038543a3a426c6f636b4e756d626572100200000010e0204e756d626572206f6620626c6f636b2064656c617920616e2065787472696e73696320636c61696d20737572636861726765206861732e000d01205768656e20636c61696d207375726368617267652069732063616c6c656420627920616e2065787472696e736963207468652072656e7420697320636865636b65646820666f722063757272656e745f626c6f636b202d2064656c617940546f6d6273746f6e654465706f7369743042616c616e63654f663c543e4000407a10f35a0000000000000000000004d420546865206d696e696d756d20616d6f756e7420726571756972656420746f2067656e6572617465206120746f6d6273746f6e652e4453746f7261676553697a654f66667365740c75333210080000000851012053697a65206f66206120636f6e7472616374206174207468652074696d65206f6620696e7374616e746961696f6e2e205468697320697320612073696d706c652077617920746f20656e737572652074686174a420656d70747920636f6e747261637473206576656e7475616c6c7920676574732064656c657465642e2c52656e74427974654665653042616c616e63654f663c543e4000407a10f35a00000000000000000000043501205072696365206f6620612062797465206f662073746f7261676520706572206f6e6520626c6f636b20696e74657276616c2e2053686f756c642062652067726561746572207468616e20302e4452656e744465706f7369744f66667365743042616c616e63654f663c543e4000008a5d7845630100000000000000001c05012054686520616d6f756e74206f662066756e6473206120636f6e74726163742073686f756c64206465706f73697420696e206f7264657220746f206f6666736574582074686520636f7374206f66206f6e6520627974652e006901204c6574277320737570706f736520746865206465706f73697420697320312c303030204255202862616c616e636520756e697473292f6279746520616e64207468652072656e7420697320312042552f627974652f6461792c5901207468656e206120636f6e7472616374207769746820312c3030302c3030302042552074686174207573657320312c303030206279746573206f662073746f7261676520776f756c6420706179206e6f2072656e742e4d0120427574206966207468652062616c616e6365207265647563656420746f203530302c30303020425520616e64207468652073746f7261676520737461796564207468652073616d6520617420312c3030302c78207468656e20697420776f756c6420706179203530302042552f6461792e3c5375726368617267655265776172643042616c616e63654f663c543e400080a1a76b4a3500000000000000000008e4205265776172642074686174206973207265636569766564206279207468652070617274792077686f736520746f75636820686173206c65646820746f2072656d6f76616c206f66206120636f6e74726163742e2c5472616e736665724665653042616c616e63654f663c543e400010a5d4e800000000000000000000000494205468652066656520726571756972656420746f206d616b652061207472616e736665722e2c4372656174696f6e4665653042616c616e63654f663c543e400010a5d4e80000000000000000000000049c205468652066656520726571756972656420746f2063726561746520616e206163636f756e742e485472616e73616374696f6e426173654665653042616c616e63654f663c543e400010a5d4e8000000000000000000000004dc205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b2074686520626173652e485472616e73616374696f6e427974654665653042616c616e63654f663c543e4000e40b54020000000000000000000000040d01205468652066656520746f206265207061696420666f72206d616b696e672061207472616e73616374696f6e3b20746865207065722d6279746520706f7274696f6e2e2c436f6e74726163744665653042616c616e63654f663c543e400010a5d4e80000000000000000000000084101205468652066656520726571756972656420746f20696e7374616e7469617465206120636f6e747261637420696e7374616e63652e204120726561736f6e61626c652064656661756c742076616c75651c2069732032312e2c43616c6c426173654665650c47617320e803000000000000081d0120546865206261736520666565206368617267656420666f722063616c6c696e6720696e746f206120636f6e74726163742e204120726561736f6e61626c652064656661756c74382076616c7565206973203133352e48496e7374616e7469617465426173654665650c47617320e80300000000000008390120546865206261736520666565206368617267656420666f7220696e7374616e74696174696e67206120636f6e74726163742e204120726561736f6e61626c652064656661756c742076616c756520206973203137352e204d617844657074680c753332102000000008310120546865206d6178696d756d206e657374696e67206c6576656c206f6620612063616c6c2f696e7374616e746961746520737461636b2e204120726561736f6e61626c652064656661756c74382076616c7565206973203130302e304d617856616c756553697a650c753332100040000004390120546865206d6178696d756d2073697a65206f6620612073746f726167652076616c756520696e2062797465732e204120726561736f6e61626c652064656661756c74206973203136204b69422e34426c6f636b4761734c696d69740c47617320809698000000000008250120546865206d6178696d756d20616d6f756e74206f6620676173207468617420636f756c6420626520657870656e6465642070657220626c6f636b2e204120726561736f6e61626c65742064656661756c742076616c75652069732031305f3030305f3030302e00105375646f01105375646f040c4b6579010030543a3a4163636f756e74496480000000000000000000000000000000000000000000000000000000000000000004842054686520604163636f756e74496460206f6620746865207375646f206b65792e010c107375646f042070726f706f73616c40426f783c543a3a50726f706f73616c3e2839012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c20776974682060526f6f7460206f726967696e2e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ed4202d20556e6b6e6f776e20776569676874206f662064657269766174697665206070726f706f73616c6020657865637574696f6e2e302023203c2f7765696768743e1c7365745f6b6579040c6e65778c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652475012041757468656e74696361746573207468652063757272656e74207375646f206b657920616e6420736574732074686520676976656e204163636f756e7449642028606e6577602920617320746865206e6577207375646f206b65792e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e44202d204f6e65204442206368616e67652e302023203c2f7765696768743e1c7375646f5f6173080c77686f8c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f757263652070726f706f73616c40426f783c543a3a50726f706f73616c3e2c51012041757468656e7469636174657320746865207375646f206b657920616e64206469737061746368657320612066756e6374696f6e2063616c6c207769746820605369676e656460206f726967696e2066726f6d44206120676976656e206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204c696d697465642073746f726167652072656164732e60202d204f6e6520444220777269746520286576656e74292ed4202d20556e6b6e6f776e20776569676874206f662064657269766174697665206070726f706f73616c6020657865637574696f6e2e302023203c2f7765696768743e010c1453756469640410626f6f6c04602041207375646f206a75737420746f6f6b20706c6163652e284b65794368616e67656404244163636f756e74496404f020546865207375646f6572206a757374207377697463686564206964656e746974793b20746865206f6c64206b657920697320737570706c6965642e285375646f4173446f6e650410626f6f6c04602041207375646f206a75737420746f6f6b20706c6163652e000020496d4f6e6c696e650120496d4f6e6c696e651020476f737369704174010038543a3a426c6f636b4e756d626572100000000004a02054686520626c6f636b206e756d626572207768656e2077652073686f756c6420676f737369702e104b65797301004c5665633c543a3a417574686f7269747949643e040004d0205468652063757272656e7420736574206f66206b6579732074686174206d61792069737375652061206865617274626561742e485265636569766564486561727462656174730002013053657373696f6e496e6465782441757468496e6465781c5665633c75383e01040008e420466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f66206041757468496e646578608c20746f20606f6666636861696e3a3a4f70617175654e6574776f726b5374617465602e38417574686f726564426c6f636b730102013053657373696f6e496e64657838543a3a56616c696461746f7249640c75333201100000000008150120466f7220656163682073657373696f6e20696e6465782c207765206b6565702061206d617070696e67206f662060543a3a56616c696461746f7249646020746f20746865c8206e756d626572206f6620626c6f636b7320617574686f7265642062792074686520676976656e20617574686f726974792e0104246865617274626561740824686561727462656174644865617274626561743c543a3a426c6f636b4e756d6265723e285f7369676e6174757265bc3c543a3a417574686f7269747949642061732052756e74696d654170705075626c69633e3a3a5369676e617475726500010c444865617274626561745265636569766564042c417574686f72697479496404c02041206e657720686561727462656174207761732072656365697665642066726f6d2060417574686f726974794964601c416c6c476f6f640004d42041742074686520656e64206f66207468652073657373696f6e2c206e6f206f6666656e63652077617320636f6d6d69747465642e2c536f6d654f66666c696e6504605665633c4964656e74696669636174696f6e5475706c653e0431012041742074686520656e64206f66207468652073657373696f6e2c206174206c65617374206f6e63652076616c696461746f722077617320666f756e6420746f206265206f66666c696e652e000048417574686f72697479446973636f76657279000100000000204f6666656e63657301204f6666656e6365730c1c5265706f727473000101345265706f727449644f663c543ed04f6666656e636544657461696c733c543a3a4163636f756e7449642c20543a3a4964656e74696669636174696f6e5475706c653e00040004490120546865207072696d61727920737472756374757265207468617420686f6c647320616c6c206f6666656e6365207265636f726473206b65796564206279207265706f7274206964656e746966696572732e58436f6e63757272656e745265706f727473496e646578010201104b696e64384f706171756554696d65536c6f74485665633c5265706f727449644f663c543e3e010400042901204120766563746f72206f66207265706f727473206f66207468652073616d65206b696e6420746861742068617070656e6564206174207468652073616d652074696d6520736c6f742e485265706f72747342794b696e64496e646578010101104b696e641c5665633c75383e00040018110120456e756d65726174657320616c6c207265706f727473206f662061206b696e6420616c6f6e672077697468207468652074696d6520746865792068617070656e65642e00bc20416c6c207265706f7274732061726520736f72746564206279207468652074696d65206f66206f6666656e63652e004901204e6f74652074686174207468652061637475616c2074797065206f662074686973206d617070696e6720697320605665633c75383e602c207468697320697320626563617573652076616c756573206f66690120646966666572656e7420747970657320617265206e6f7420737570706f7274656420617420746865206d6f6d656e7420736f2077652061726520646f696e6720746865206d616e75616c2073657269616c697a6174696f6e2e010001041c4f6666656e636508104b696e64384f706171756554696d65536c6f7408550120546865726520697320616e206f6666656e6365207265706f72746564206f662074686520676976656e20606b696e64602068617070656e656420617420746865206073657373696f6e5f696e6465786020616e64390120286b696e642d7370656369666963292074696d6520736c6f742e2054686973206576656e74206973206e6f74206465706f736974656420666f72206475706c696361746520736c61736865732e00006052616e646f6d6e657373436f6c6c656374697665466c6970016052616e646f6d6e657373436f6c6c656374697665466c6970043852616e646f6d4d6174657269616c0100305665633c543a3a486173683e04000c610120536572696573206f6620626c6f636b20686561646572732066726f6d20746865206c61737420383120626c6f636b73207468617420616374732061732072616e646f6d2073656564206d6174657269616c2e2054686973610120697320617272616e67656420617320612072696e672062756666657220776974682060626c6f636b5f6e756d626572202520383160206265696e672074686520696e64657820696e746f20746865206056656360206f664420746865206f6c6465737420686173682e0100000000144e69636b7301105375646f04184e616d654f6600010130543a3a4163636f756e7449645c285665633c75383e2c2042616c616e63654f663c543e29000400047020546865206c6f6f6b7570207461626c6520666f72206e616d65732e0110207365745f6e616d6504106e616d651c5665633c75383e405d012053657420616e206163636f756e742773206e616d652e20546865206e616d652073686f756c642062652061205554462d382d656e636f64656420737472696e6720627920636f6e76656e74696f6e2c2074686f7567684c20776520646f6e277420636865636b2069742e00610120546865206e616d65206d6179206e6f74206265206d6f7265207468616e2060543a3a4d61784c656e677468602062797465732c206e6f72206c657373207468616e2060543a3a4d696e4c656e677468602062797465732e005d0120496620746865206163636f756e7420646f65736e277420616c726561647920686176652061206e616d652c207468656e206120666565206f6620605265736572766174696f6e466565602069732072657365727665644020696e20746865206163636f756e742e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e84202d204174206d6f7374206f6e652062616c616e6365206f7065726174696f6e2e68202d204f6e652073746f7261676520726561642f77726974652e34202d204f6e65206576656e742e302023203c2f7765696768743e28636c6561725f6e616d650028510120436c65617220616e206163636f756e742773206e616d6520616e642072657475726e20746865206465706f7369742e204661696c7320696620746865206163636f756e7420776173206e6f74206e616d65642e00d020546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f5369676e65645f2e002c2023203c7765696768743e20202d204f2831292e64202d204f6e652062616c616e6365206f7065726174696f6e2e68202d204f6e652073746f7261676520726561642f77726974652e34202d204f6e65206576656e742e302023203c2f7765696768743e246b696c6c5f6e616d6504187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f7572636534e42052656d6f766520616e206163636f756e742773206e616d6520616e642074616b6520636861726765206f6620746865206465706f7369742e004901204661696c73206966206077686f6020686173206e6f74206265656e206e616d65642e20546865206465706f736974206973206465616c742077697468207468726f7567682060543a3a536c6173686564604c20696d62616c616e63652068616e646c65722e00310120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f206f72206d617463682060543a3a466f7263654f726967696e602e002c2023203c7765696768743e20202d204f2831292edc202d204f6e6520756e62616c616e6365642068616e646c6572202870726f6261626c7920612062616c616e6365207472616e736665722968202d204f6e652073746f7261676520726561642f77726974652e34202d204f6e65206576656e742e302023203c2f7765696768743e28666f7263655f6e616d6508187461726765748c3c543a3a4c6f6f6b7570206173205374617469634c6f6f6b75703e3a3a536f75726365106e616d651c5665633c75383e30c82053657420612074686972642d7061727479206163636f756e742773206e616d652077697468206e6f206465706f7369742e00a0204e6f206c656e67746820636865636b696e6720697320646f6e65206f6e20746865206e616d652e00310120546865206469737061746368206f726967696e20666f7220746869732063616c6c206d757374206265205f526f6f745f206f72206d617463682060543a3a466f7263654f726967696e602e002c2023203c7765696768743e20202d204f2831292e84202d204174206d6f7374206f6e652062616c616e6365206f7065726174696f6e2e68202d204f6e652073746f7261676520726561642f77726974652e34202d204f6e65206576656e742e302023203c2f7765696768743e01141c4e616d6553657404244163636f756e74496404402041206e616d6520776173207365742e284e616d65466f7263656404244163636f756e74496404642041206e616d652077617320666f726369626c79207365742e2c4e616d654368616e67656404244163636f756e74496404502041206e616d6520776173206368616e6765642e2c4e616d65436c656172656408244163636f756e7449641c42616c616e636504d02041206e616d652077617320636c65617265642c20616e642074686520676976656e2062616c616e63652072657475726e65642e284e616d654b696c6c656408244163636f756e7449641c42616c616e636504c82041206e616d65207761732072656d6f76656420616e642074686520676976656e2062616c616e636520736c61736865642e0c385265736572766174696f6e4665653042616c616e63654f663c543e4000407a10f35a000000000000000000000444205265736572766174696f6e206665652e244d696e4c656e6774680c7533321003000000048820546865206d696e696d756d206c656e6774682061206e616d65206d61792062652e244d61784c656e6774680c7533321010000000048820546865206d6178696d756d206c656e6774682061206e616d65206d61792062652e00 \ No newline at end of file diff --git a/packages/polkadot/tests/meta/v9.json b/packages/polkadot/tests/meta/v9.json new file mode 100644 index 00000000..d58dc108 --- /dev/null +++ b/packages/polkadot/tests/meta/v9.json @@ -0,0 +1,4896 @@ +{ + "magicNumber": 1635018093, + "metadata": { + "v9": { + "modules": [ + { + "name": "System", + "storage": { + "prefix": "System", + "items": [ + { + "name": "AccountNonce", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Index", + "linked": false + } + }, + "fallback": "0x00000000", + "docs": [ + " Extrinsics nonce for accounts." + ] + }, + { + "name": "ExtrinsicCount", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total extrinsics count for the current block." + ] + }, + { + "name": "AllExtrinsicsWeight", + "modifier": "Optional", + "type": { + "plain": "Weight" + }, + "fallback": "0x00", + "docs": [ + " Total weight for all extrinsics put together, for the current block." + ] + }, + { + "name": "AllExtrinsicsLen", + "modifier": "Optional", + "type": { + "plain": "u32" + }, + "fallback": "0x00", + "docs": [ + " Total length (in bytes) for all extrinsics put together, for the current block." + ] + }, + { + "name": "BlockHash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "BlockNumber", + "value": "Hash", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Map of block numbers to block hashes." + ] + }, + { + "name": "ExtrinsicData", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "u32", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Extrinsics data for the current block (maps an extrinsic's index to its data)." + ] + }, + { + "name": "Number", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The current block number being processed. Set by `execute_block`." + ] + }, + { + "name": "ParentHash", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Hash of the previous block." + ] + }, + { + "name": "ExtrinsicsRoot", + "modifier": "Default", + "type": { + "plain": "Hash" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Extrinsics root of the current block, also part of the block header." + ] + }, + { + "name": "Digest", + "modifier": "Default", + "type": { + "plain": "DigestOf" + }, + "fallback": "0x00", + "docs": [ + " Digest of the current block, also part of the block header." + ] + }, + { + "name": "Events", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Events deposited for the current block." + ] + }, + { + "name": "EventCount", + "modifier": "Default", + "type": { + "plain": "EventIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of events in the `Events` list." + ] + }, + { + "name": "EventTopics", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "()", + "key2": "Hash", + "value": "Vec<(BlockNumber,EventIndex)>", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " Mapping between a topic (represented by T::Hash) and a vector of indexes", + " of events in the `>` list.", + "", + " The first key serves no purpose. This field is declared as double_map just", + " for convenience of using `remove_prefix`.", + "", + " All topic vectors have deterministic storage locations depending on the topic. This", + " allows light-clients to leverage the changes trie storage tracking mechanism and", + " in case of changes fetch the list of events of interest.", + "", + " The value has the type `(T::BlockNumber, EventIndex)` because if we used only just", + " the `EventIndex` then in case if the topic has the same contents on the next block", + " no notification will be triggered thus the event might be lost." + ] + } + ] + }, + "calls": [ + { + "name": "fill_block", + "args": [], + "docs": [ + " A big dispatch that will disallow any other transaction to be included." + ] + }, + { + "name": "remark", + "args": [ + { + "name": "_remark", + "type": "Bytes" + } + ], + "docs": [ + " Make some on-chain remark." + ] + }, + { + "name": "set_heap_pages", + "args": [ + { + "name": "pages", + "type": "u64" + } + ], + "docs": [ + " Set the number of pages in the WebAssembly environment's heap." + ] + }, + { + "name": "set_code", + "args": [ + { + "name": "new", + "type": "Bytes" + } + ], + "docs": [ + " Set the new code." + ] + }, + { + "name": "set_storage", + "args": [ + { + "name": "items", + "type": "Vec" + } + ], + "docs": [ + " Set some items of storage." + ] + }, + { + "name": "kill_storage", + "args": [ + { + "name": "keys", + "type": "Vec" + } + ], + "docs": [ + " Kill some items from storage." + ] + }, + { + "name": "kill_prefix", + "args": [ + { + "name": "prefix", + "type": "Key" + } + ], + "docs": [ + " Kill all storage items with a key that starts with the given prefix." + ] + } + ], + "events": [ + { + "name": "ExtrinsicSuccess", + "args": [ + "DispatchInfo" + ], + "docs": [ + " An extrinsic completed successfully." + ] + }, + { + "name": "ExtrinsicFailed", + "args": [ + "DispatchError", + "DispatchInfo" + ], + "docs": [ + " An extrinsic failed." + ] + } + ], + "constants": [], + "errors": [ + { + "name": "RequireSignedOrigin", + "docs": [] + }, + { + "name": "RequireRootOrigin", + "docs": [] + }, + { + "name": "RequireNoOrigin", + "docs": [] + } + ] + }, + { + "name": "Utility", + "storage": null, + "calls": [ + { + "name": "batch", + "args": [ + { + "name": "calls", + "type": "Vec" + } + ], + "docs": [ + " Send a batch of dispatch calls (only root)." + ] + } + ], + "events": [ + { + "name": "BatchExecuted", + "args": [ + "Vec>" + ], + "docs": [] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Babe", + "storage": { + "prefix": "Babe", + "items": [ + { + "name": "EpochIndex", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current epoch index." + ] + }, + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "Vec<(AuthorityId,BabeAuthorityWeight)>" + }, + "fallback": "0x00", + "docs": [ + " Current epoch authorities." + ] + }, + { + "name": "GenesisSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The slot at which the first epoch actually started. This is 0", + " until the first block of the chain." + ] + }, + { + "name": "CurrentSlot", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current slot number." + ] + }, + { + "name": "Randomness", + "modifier": "Default", + "type": { + "plain": "[u8;32]" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The epoch randomness for the *current* epoch.", + "", + " # Security", + "", + " This MUST NOT be used for gambling, as it can be influenced by a", + " malicious validator in the short term. It MAY be used in many", + " cryptographic protocols, however, so long as one remembers that this", + " (like everything else on-chain) it is public. For example, it can be", + " used where a number is needed that cannot have been chosen by an", + " adversary, for purposes such as public-coin zero-knowledge proofs." + ] + }, + { + "name": "NextRandomness", + "modifier": "Default", + "type": { + "plain": "[u8;32]" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Next epoch randomness." + ] + }, + { + "name": "SegmentIndex", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Randomness under construction.", + "", + " We make a tradeoff between storage accesses and list length.", + " We store the under-construction randomness in segments of up to", + " `UNDER_CONSTRUCTION_SEGMENT_LENGTH`.", + "", + " Once a segment reaches this length, we begin the next one.", + " We reset all segments and return to `0` at the beginning of every", + " epoch." + ] + }, + { + "name": "UnderConstruction", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "u32", + "value": "Vec<[u8;32]>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [] + }, + { + "name": "Initialized", + "modifier": "Optional", + "type": { + "plain": "MaybeVrf" + }, + "fallback": "0x00", + "docs": [ + " Temporary value (cleared at block finalization) which is `Some`", + " if per-block initialization has already been called for current block." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [ + { + "name": "EpochDuration", + "type": "u64", + "value": "0xc800000000000000", + "docs": [ + " The number of **slots** that an epoch takes. We couple sessions to", + " epochs, i.e. we start a new session once the new epoch begins." + ] + }, + { + "name": "ExpectedBlockTime", + "type": "Moment", + "value": "0xb80b000000000000", + "docs": [ + " The expected average block time at which BABE should be creating", + " blocks. Since BABE is probabilistic it is not trivial to figure out", + " what the expected average block time should be based on the slot", + " duration and the security parameter `c` (where `1 - c` represents", + " the probability of a slot being empty)." + ] + } + ], + "errors": [] + }, + { + "name": "Timestamp", + "storage": { + "prefix": "Timestamp", + "items": [ + { + "name": "Now", + "modifier": "Default", + "type": { + "plain": "Moment" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Current time for the current block." + ] + }, + { + "name": "DidUpdate", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Did the timestamp get updated in this block?" + ] + } + ] + }, + "calls": [ + { + "name": "set", + "args": [ + { + "name": "now", + "type": "Compact" + } + ], + "docs": [ + " Set the current time.", + "", + " This call should be invoked exactly once per block. It will panic at the finalization", + " phase, if this call hasn't been invoked by that time.", + "", + " The timestamp should be greater than the previous one by the amount specified by", + " `MinimumPeriod`.", + "", + " The dispatch origin for this call must be `Inherent`." + ] + } + ], + "events": null, + "constants": [ + { + "name": "MinimumPeriod", + "type": "Moment", + "value": "0xdc05000000000000", + "docs": [ + " The minimum period between blocks. Beware that this is different to the *expected* period", + " that the block production apparatus provides. Your chosen consensus system will generally", + " work with this to determine a sensible block time. e.g. For Aura, it will be double this", + " period on default settings." + ] + } + ], + "errors": [] + }, + { + "name": "Authorship", + "storage": { + "prefix": "Authorship", + "items": [ + { + "name": "Uncles", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Uncles" + ] + }, + { + "name": "Author", + "modifier": "Optional", + "type": { + "plain": "AccountId" + }, + "fallback": "0x00", + "docs": [ + " Author of current block." + ] + }, + { + "name": "DidSetUncles", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " Whether uncles were already set in this block." + ] + } + ] + }, + "calls": [ + { + "name": "set_uncles", + "args": [ + { + "name": "new_uncles", + "type": "Vec
" + } + ], + "docs": [ + " Provide a set of uncles." + ] + } + ], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Indices", + "storage": { + "prefix": "Indices", + "items": [ + { + "name": "NextEnumSet", + "modifier": "Default", + "type": { + "plain": "AccountIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free enumeration set." + ] + }, + { + "name": "EnumSet", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The enumeration sets." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "NewAccountIndex", + "args": [ + "AccountId", + "AccountIndex" + ], + "docs": [ + " A new account index was assigned.", + "", + " This event is not triggered when an existing index is reassigned", + " to another `AccountId`." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Balances", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "TotalIssuance", + "modifier": "Default", + "type": { + "plain": "Balance" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The total units issued in the system." + ] + }, + { + "name": "Vesting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "VestingSchedule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information regarding the vesting of a given account." + ] + }, + { + "name": "FreeBalance", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Balance", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The 'free' balance of a given account.", + "", + " This is the only balance that matters in terms of most operations on tokens. It", + " alone is used to determine the balance when in the contract execution environment. When this", + " balance falls below the value of `ExistentialDeposit`, then the 'current account' is", + " deleted: specifically `FreeBalance`. Further, the `OnFreeBalanceZero` callback", + " is invoked, giving a chance to external modules to clean up data associated with", + " the deleted account.", + "", + " `system::AccountNonce` is also deleted if `ReservedBalance` is also zero (it also gets", + " collapsed to zero if it ever becomes less than `ExistentialDeposit`." + ] + }, + { + "name": "ReservedBalance", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Balance", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of the balance of a given account that is externally reserved; this can still get", + " slashed, but gets slashed last of all.", + "", + " This balance is a 'reserve' balance that other subsystems use in order to set aside tokens", + " that are still 'owned' by the account holder, but which are suspendable.", + "", + " When this balance falls below the value of `ExistentialDeposit`, then this 'reserve account'", + " is deleted: specifically, `ReservedBalance`.", + "", + " `system::AccountNonce` is also deleted if `FreeBalance` is also zero (it also gets", + " collapsed to zero if it ever becomes less than `ExistentialDeposit`.)" + ] + }, + { + "name": "Locks", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Any liquidity locks on some account balances." + ] + } + ] + }, + "calls": [ + { + "name": "transfer", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Transfer some liquid free balance to another account.", + "", + " `transfer` will set the `FreeBalance` of the sender and receiver.", + " It will decrease the total issuance of the system by the `TransferFee`.", + " If the sender's account is below the existential deposit as a result", + " of the transfer, the account will be reaped.", + "", + " The dispatch origin for this call must be `Signed` by the transactor.", + "", + " # ", + " - Dependent on arguments but not critical, given proper implementations for", + " input config types. See related functions below.", + " - It contains a limited number of reads and writes internally and no complex computation.", + "", + " Related functions:", + "", + " - `ensure_can_withdraw` is always called internally but has a bounded complexity.", + " - Transferring balances to accounts that did not exist before will cause", + " `T::OnNewAccount::on_new_account` to be called.", + " - Removing enough funds from an account will trigger", + " `T::DustRemoval::on_unbalanced` and `T::OnFreeBalanceZero::on_free_balance_zero`.", + " - `transfer_keep_alive` works the same way as `transfer`, but has an additional", + " check that the transfer will not kill the origin account.", + "", + " # " + ] + }, + { + "name": "set_balance", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "new_free", + "type": "Compact" + }, + { + "name": "new_reserved", + "type": "Compact" + } + ], + "docs": [ + " Set the balances of a given account.", + "", + " This will alter `FreeBalance` and `ReservedBalance` in storage. it will", + " also decrease the total issuance of the system (`TotalIssuance`).", + " If the new free or reserved balance is below the existential deposit,", + " it will reset the account nonce (`system::AccountNonce`).", + "", + " The dispatch origin for this call is `root`.", + "", + " # ", + " - Independent of the arguments.", + " - Contains a limited number of reads and writes.", + " # " + ] + }, + { + "name": "force_transfer", + "args": [ + { + "name": "source", + "type": "LookupSource" + }, + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Exactly as `transfer`, except the origin must be root and the source account may be", + " specified." + ] + }, + { + "name": "transfer_keep_alive", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Same as the [`transfer`] call, but with a check that the transfer will not kill the", + " origin account.", + "", + " 99% of the time you want [`transfer`] instead.", + "", + " [`transfer`]: struct.Module.html#method.transfer" + ] + } + ], + "events": [ + { + "name": "NewAccount", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A new account was created." + ] + }, + { + "name": "ReapedAccount", + "args": [ + "AccountId" + ], + "docs": [ + " An account was reaped." + ] + }, + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance", + "Balance" + ], + "docs": [ + " Transfer succeeded (from, to, value, fees)." + ] + } + ], + "constants": [ + { + "name": "ExistentialDeposit", + "type": "Balance", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to keep an account open." + ] + }, + { + "name": "TransferFee", + "type": "Balance", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to make a transfer." + ] + }, + { + "name": "CreationFee", + "type": "Balance", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to create an account." + ] + } + ], + "errors": [] + }, + { + "name": "TransactionPayment", + "storage": { + "prefix": "Balances", + "items": [ + { + "name": "NextFeeMultiplier", + "modifier": "Default", + "type": { + "plain": "Multiplier" + }, + "fallback": "0x0000000000000000", + "docs": [] + } + ] + }, + "calls": null, + "events": null, + "constants": [ + { + "name": "TransactionBaseFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the base." + ] + }, + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + } + ], + "errors": [] + }, + { + "name": "Staking", + "storage": { + "prefix": "Staking", + "items": [ + { + "name": "ValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The ideal number of staking participants." + ] + }, + { + "name": "MinimumValidatorCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x04000000", + "docs": [ + " Minimum number of staking participants before emergency conditions are imposed." + ] + }, + { + "name": "Invulnerables", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Any validators that may never be slashed or forcibly kicked. It's a Vec since they're", + " easy to initialize and the performance hit is minimal (we expect no more than four", + " invulnerables) and restricted to testnets." + ] + }, + { + "name": "Bonded", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all locked \"stash\" accounts to the controller account." + ] + }, + { + "name": "Ledger", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "StakingLedger", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map from all (unlocked) \"controller\" accounts to the info regarding the staking." + ] + }, + { + "name": "Payee", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "RewardDestination", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Where the reward payment should be made. Keyed by stash." + ] + }, + { + "name": "Validators", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "ValidatorPrefs", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " The map from (wannabe) validator stash key to the preferences of that validator." + ] + }, + { + "name": "Nominators", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Nominations", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " The map from nominator stash key to the set of stash keys of all validators to nominate.", + "", + " NOTE: is private so that we can ensure upgraded before all typical accesses.", + " Direct storage APIs can still bypass this protection." + ] + }, + { + "name": "Stakers", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Exposure", + "linked": false + } + }, + "fallback": "0x000000", + "docs": [ + " Nominators for a particular account that is in action right now. You can't iterate", + " through validators here, but you can find them in the Session module.", + "", + " This is keyed by the stash account." + ] + }, + { + "name": "CurrentElected", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The currently elected validator set keyed by stash account ID." + ] + }, + { + "name": "CurrentEra", + "modifier": "Default", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The current era index." + ] + }, + { + "name": "CurrentEraStart", + "modifier": "Default", + "type": { + "plain": "MomentOf" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The start of the current era." + ] + }, + { + "name": "CurrentEraStartSessionIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The session index at which the current era started." + ] + }, + { + "name": "CurrentEraPointsEarned", + "modifier": "Default", + "type": { + "plain": "EraPoints" + }, + "fallback": "0x0000000000", + "docs": [ + " Rewards for the current era. Using indices of current elected set." + ] + }, + { + "name": "SlotStake", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of balance actively at stake for each validator slot, currently.", + "", + " This is used to derive rewards and punishments." + ] + }, + { + "name": "ForceEra", + "modifier": "Default", + "type": { + "plain": "Forcing" + }, + "fallback": "0x00", + "docs": [ + " True if the next session change will be a new era regardless of index." + ] + }, + { + "name": "SlashRewardFraction", + "modifier": "Default", + "type": { + "plain": "Perbill" + }, + "fallback": "0x00000000", + "docs": [ + " The percentage of the slash that is distributed to reporters.", + "", + " The rest of the slashed value is handled by the `Slash`." + ] + }, + { + "name": "CanceledSlashPayout", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " The amount of currency given to reporters of a slash event which was", + " canceled by extraordinary circumstances (e.g. governance)." + ] + }, + { + "name": "UnappliedSlashes", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "EraIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " All unapplied slashes that are queued for later." + ] + }, + { + "name": "BondedEras", + "modifier": "Default", + "type": { + "plain": "Vec<(EraIndex,SessionIndex)>" + }, + "fallback": "0x00", + "docs": [ + " A mapping from still-bonded eras to the first session index of that era." + ] + }, + { + "name": "ValidatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "EraIndex", + "key2": "AccountId", + "value": "(Perbill,BalanceOf)", + "key2Hasher": "Twox128" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on validators, mapped by era to the highest slash proportion", + " and slash value of the era." + ] + }, + { + "name": "NominatorSlashInEra", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "EraIndex", + "key2": "AccountId", + "value": "BalanceOf", + "key2Hasher": "Twox128" + } + }, + "fallback": "0x00", + "docs": [ + " All slashing events on nominators, mapped by era to the highest slash value of the era." + ] + }, + { + "name": "SlashingSpans", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "SlashingSpans", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Slashing spans for stash accounts." + ] + }, + { + "name": "SpanSlash", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "(AccountId,SpanIndex)", + "value": "SpanRecord", + "linked": false + } + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Records information about the maximum slash of a stash within a slashing span,", + " as well as how much reward has been paid out." + ] + }, + { + "name": "EarliestUnappliedSlash", + "modifier": "Optional", + "type": { + "plain": "EraIndex" + }, + "fallback": "0x00", + "docs": [ + " The earliest era for which we have a pending, unapplied slash." + ] + }, + { + "name": "StorageVersion", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The version of storage for upgrade." + ] + } + ] + }, + "calls": [ + { + "name": "bond", + "args": [ + { + "name": "controller", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " Take the origin account as a stash and lock up `value` of its balance. `controller` will", + " be the account that controls it.", + "", + " `value` must be more than the `minimum_balance` specified by `T::Currency`.", + "", + " The dispatch origin for this call must be _Signed_ by the stash account.", + "", + " # ", + " - Independent of the arguments. Moderate complexity.", + " - O(1).", + " - Three extra DB entries.", + "", + " NOTE: Two of the storage writes (`Self::bonded`, `Self::payee`) are _never_ cleaned unless", + " the `origin` falls below _existential deposit_ and gets removed as dust.", + " # " + ] + }, + { + "name": "bond_extra", + "args": [ + { + "name": "max_additional", + "type": "Compact" + } + ], + "docs": [ + " Add some extra amount that have appeared in the stash `free_balance` into the balance up", + " for staking.", + "", + " Use this if there are additional funds in your stash account that you wish to bond.", + " Unlike [`bond`] or [`unbond`] this function does not impose any limitation on the amount", + " that can be added.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - O(1).", + " - One DB entry.", + " # " + ] + }, + { + "name": "unbond", + "args": [ + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Schedule a portion of the stash to be unlocked ready for transfer out after the bond", + " period ends. If this leaves an amount actively bonded less than", + " T::Currency::minimum_balance(), then it is increased to the full amount.", + "", + " Once the unlock period is done, you can call `withdraw_unbonded` to actually move", + " the funds out of management ready for transfer.", + "", + " No more than a limited number of unlocking chunks (see `MAX_UNLOCKING_CHUNKS`)", + " can co-exists at the same time. In that case, [`Call::withdraw_unbonded`] need", + " to be called first to remove some of the chunks (if possible).", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " See also [`Call::withdraw_unbonded`].", + "", + " # ", + " - Independent of the arguments. Limited but potentially exploitable complexity.", + " - Contains a limited number of reads.", + " - Each call (requires the remainder of the bonded balance to be above `minimum_balance`)", + " will cause a new entry to be inserted into a vector (`Ledger.unlocking`) kept in storage.", + " The only way to clean the aforementioned storage item is also user-controlled via `withdraw_unbonded`.", + " - One DB entry.", + " " + ] + }, + { + "name": "withdraw_unbonded", + "args": [], + "docs": [ + " Remove any unlocked chunks from the `unlocking` queue from our management.", + "", + " This essentially frees up that balance to be used by the stash account to do", + " whatever it wants.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " See also [`Call::unbond`].", + "", + " # ", + " - Could be dependent on the `origin` argument and how much `unlocking` chunks exist.", + " It implies `consolidate_unlocked` which loops over `Ledger.unlocking`, which is", + " indirectly user-controlled. See [`unbond`] for more detail.", + " - Contains a limited number of reads, yet the size of which could be large based on `ledger`.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "validate", + "args": [ + { + "name": "prefs", + "type": "ValidatorPrefs" + } + ], + "docs": [ + " Declare the desire to validate for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "nominate", + "args": [ + { + "name": "targets", + "type": "Vec" + } + ], + "docs": [ + " Declare the desire to nominate `targets` for the origin controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - The transaction's complexity is proportional to the size of `targets`,", + " which is capped at `MAX_NOMINATIONS`.", + " - Both the reads and writes follow a similar pattern.", + " # " + ] + }, + { + "name": "chill", + "args": [], + "docs": [ + " Declare no desire to either validate or nominate.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains one read.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_payee", + "args": [ + { + "name": "payee", + "type": "RewardDestination" + } + ], + "docs": [ + " (Re-)set the payment target for a controller.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the controller, not the stash.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_controller", + "args": [ + { + "name": "controller", + "type": "LookupSource" + } + ], + "docs": [ + " (Re-)set the controller of a stash.", + "", + " Effects will be felt at the beginning of the next era.", + "", + " The dispatch origin for this call must be _Signed_ by the stash, not the controller.", + "", + " # ", + " - Independent of the arguments. Insignificant complexity.", + " - Contains a limited number of reads.", + " - Writes are limited to the `origin` account key.", + " # " + ] + }, + { + "name": "set_validator_count", + "args": [ + { + "name": "new", + "type": "Compact" + } + ], + "docs": [ + " The ideal number of validators." + ] + }, + { + "name": "force_no_eras", + "args": [], + "docs": [ + " Force there to be no new eras indefinitely.", + "", + " # ", + " - No arguments.", + " # " + ] + }, + { + "name": "force_new_era", + "args": [], + "docs": [ + " Force there to be a new era at the end of the next session. After this, it will be", + " reset to normal (non-forced) behaviour.", + "", + " # ", + " - No arguments.", + " # " + ] + }, + { + "name": "set_invulnerables", + "args": [ + { + "name": "validators", + "type": "Vec" + } + ], + "docs": [ + " Set the validators who cannot be slashed (if any)." + ] + }, + { + "name": "force_unstake", + "args": [ + { + "name": "stash", + "type": "AccountId" + } + ], + "docs": [ + " Force a current staker to become completely unstaked, immediately." + ] + }, + { + "name": "force_new_era_always", + "args": [], + "docs": [ + " Force there to be a new era at the end of sessions indefinitely.", + "", + " # ", + " - One storage write", + " # " + ] + }, + { + "name": "cancel_deferred_slash", + "args": [ + { + "name": "era", + "type": "EraIndex" + }, + { + "name": "slash_indices", + "type": "Vec" + } + ], + "docs": [ + " Cancel enactment of a deferred slash. Can be called by either the root origin or", + " the `T::SlashCancelOrigin`.", + " passing the era and indices of the slashes for that era to kill.", + "", + " # ", + " - One storage write.", + " # " + ] + } + ], + "events": [ + { + "name": "Reward", + "args": [ + "Balance", + "Balance" + ], + "docs": [ + " All validators have been rewarded by the first balance; the second is the remainder", + " from the maximum amount of reward." + ] + }, + { + "name": "Slash", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " One validator (and its nominators) has been slashed by the given amount." + ] + }, + { + "name": "OldSlashingReportDiscarded", + "args": [ + "SessionIndex" + ], + "docs": [ + " An old slashing report from a prior era was discarded because it could", + " not be processed." + ] + } + ], + "constants": [ + { + "name": "SessionsPerEra", + "type": "SessionIndex", + "value": "0x06000000", + "docs": [ + " Number of sessions per era." + ] + }, + { + "name": "BondingDuration", + "type": "EraIndex", + "value": "0xa0020000", + "docs": [ + " Number of eras that staked funds must remain bonded for." + ] + } + ], + "errors": [] + }, + { + "name": "Session", + "storage": { + "prefix": "Session", + "items": [ + { + "name": "Validators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of validators." + ] + }, + { + "name": "CurrentIndex", + "modifier": "Default", + "type": { + "plain": "SessionIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Current index of the session." + ] + }, + { + "name": "QueuedChanged", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the underlying economic identities or weighting behind the validators", + " has changed in the queued validator set." + ] + }, + { + "name": "QueuedKeys", + "modifier": "Default", + "type": { + "plain": "Vec<(ValidatorId,Keys)>" + }, + "fallback": "0x00", + "docs": [ + " The queued keys for the next session. When the next session begins, these keys", + " will be used to determine the validator's session keys." + ] + }, + { + "name": "DisabledValidators", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Indices of disabled validators.", + "", + " The set is cleared when `on_session_ending` returns a new set of identities." + ] + }, + { + "name": "NextKeys", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Bytes", + "key2": "ValidatorId", + "value": "Keys", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " The next session keys for a validator.", + "", + " The first key is always `DEDUP_KEY_PREFIX` to have all the data in the same branch of", + " the trie. Having all data in the same branch should prevent slowing down other queries." + ] + }, + { + "name": "KeyOwner", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Twox64Concat", + "key1": "Bytes", + "key2": "(KeyTypeId,Bytes)", + "value": "ValidatorId", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " The owner of a key. The second key is the `KeyTypeId` + the encoded key.", + "", + " The first key is always `DEDUP_KEY_PREFIX` to have all the data in the same branch of", + " the trie. Having all data in the same branch should prevent slowing down other queries." + ] + } + ] + }, + "calls": [ + { + "name": "set_keys", + "args": [ + { + "name": "keys", + "type": "Keys" + }, + { + "name": "proof", + "type": "Bytes" + } + ], + "docs": [ + " Sets the session key(s) of the function caller to `key`.", + " Allows an account to set its session key prior to becoming a validator.", + " This doesn't take effect until the next session.", + "", + " The dispatch origin of this function must be signed.", + "", + " # ", + " - O(log n) in number of accounts.", + " - One extra DB entry.", + " # " + ] + } + ], + "events": [ + { + "name": "NewSession", + "args": [ + "SessionIndex" + ], + "docs": [ + " New session has happened. Note that the argument is the session index, not the block", + " number as the type might suggest." + ] + } + ], + "constants": [ + { + "name": "DEDUP_KEY_PREFIX", + "type": "Bytes", + "value": "0x343a73657373696f6e3a6b657973", + "docs": [ + " Used as first key for `NextKeys` and `KeyOwner` to put all the data into the same branch", + " of the trie." + ] + } + ], + "errors": [] + }, + { + "name": "Democracy", + "storage": { + "prefix": "Democracy", + "items": [ + { + "name": "PublicPropCount", + "modifier": "Default", + "type": { + "plain": "PropIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The number of (public) proposals that have been made so far." + ] + }, + { + "name": "PublicProps", + "modifier": "Default", + "type": { + "plain": "Vec<(PropIndex,Hash,AccountId)>" + }, + "fallback": "0x00", + "docs": [ + " The public proposals. Unsorted. The second item is the proposal's hash." + ] + }, + { + "name": "Preimages", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "(Bytes,AccountId,BalanceOf,BlockNumber)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Map of hashes to the proposal preimage, along with who registered it and their deposit.", + " The block number is the block at which it was deposited." + ] + }, + { + "name": "DepositOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "PropIndex", + "value": "(BalanceOf,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Those who have locked a deposit." + ] + }, + { + "name": "ReferendumCount", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next free referendum index, aka the number of referenda started so far." + ] + }, + { + "name": "NextTally", + "modifier": "Default", + "type": { + "plain": "ReferendumIndex" + }, + "fallback": "0x00000000", + "docs": [ + " The next referendum index that should be tallied." + ] + }, + { + "name": "ReferendumInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReferendumIndex", + "value": "ReferendumInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Information concerning any given referendum." + ] + }, + { + "name": "DispatchQueue", + "modifier": "Default", + "type": { + "map": { + "hasher": "Twox64Concat", + "key": "BlockNumber", + "value": "Vec>", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Queue of successful referenda to be dispatched." + ] + }, + { + "name": "VotersFor", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReferendumIndex", + "value": "Vec", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Get the voters for the current proposal." + ] + }, + { + "name": "VoteOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "(ReferendumIndex,AccountId)", + "value": "Vote", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Get the vote in a given referendum of a particular voter. The result is meaningful only", + " if `voters_for` includes the voter when called with the referendum (you'll get the", + " default `Vote` value otherwise). If you don't want to check `voters_for`, then you can", + " also check for simple existence with `VoteOf::exists` first." + ] + }, + { + "name": "Proxy", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "AccountId", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Who is able to vote for whom. Value is the fund-holding account, key is the", + " vote-transaction-sending account." + ] + }, + { + "name": "Delegations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(AccountId,Conviction)", + "linked": true + } + }, + "fallback": "0x000000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " Get the account (and lock periods) to which another account is delegating vote." + ] + }, + { + "name": "LastTabledWasExternal", + "modifier": "Default", + "type": { + "plain": "bool" + }, + "fallback": "0x00", + "docs": [ + " True if the last referendum tabled was submitted externally. False if it was a public", + " proposal." + ] + }, + { + "name": "NextExternal", + "modifier": "Optional", + "type": { + "plain": "(Hash,VoteThreshold)" + }, + "fallback": "0x00", + "docs": [ + " The referendum to be tabled whenever it would be valid to table an external proposal.", + " This happens when a referendum needs to be tabled and one of two conditions are met:", + " - `LastTabledWasExternal` is `false`; or", + " - `PublicProps` is empty." + ] + }, + { + "name": "Blacklist", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "(BlockNumber,Vec)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A record of who vetoed what. Maps proposal hash to a possible existent block number", + " (until when it may not be resubmitted) and who vetoed it." + ] + }, + { + "name": "Cancellations", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "bool", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Record of all proposals that have been subject to emergency cancellation." + ] + } + ] + }, + "calls": [ + { + "name": "propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " # ", + " - O(1).", + " - Two DB changes, one DB entry.", + " # " + ] + }, + { + "name": "second", + "args": [ + { + "name": "proposal", + "type": "Compact" + } + ], + "docs": [ + " Propose a sensitive action to be taken.", + "", + " # ", + " - O(1).", + " - One DB entry.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "Vote" + } + ], + "docs": [ + " Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;", + " otherwise it is a vote to keep the status quo.", + "", + " # ", + " - O(1).", + " - One DB change, one DB entry.", + " # " + ] + }, + { + "name": "proxy_vote", + "args": [ + { + "name": "ref_index", + "type": "Compact" + }, + { + "name": "vote", + "type": "Vote" + } + ], + "docs": [ + " Vote in a referendum on behalf of a stash. If `vote.is_aye()`, the vote is to enact", + " the proposal; otherwise it is a vote to keep the status quo.", + "", + " # ", + " - O(1).", + " - One DB change, one DB entry.", + " # " + ] + }, + { + "name": "emergency_cancel", + "args": [ + { + "name": "ref_index", + "type": "ReferendumIndex" + } + ], + "docs": [ + " Schedule an emergency cancellation of a referendum. Cannot happen twice to the same", + " referendum." + ] + }, + { + "name": "external_propose", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a referendum to be tabled once it is legal to schedule an external", + " referendum." + ] + }, + { + "name": "external_propose_majority", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a majority-carries referendum to be tabled next once it is legal to schedule", + " an external referendum.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call." + ] + }, + { + "name": "external_propose_default", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Schedule a negative-turnout-bias referendum to be tabled next once it is legal to", + " schedule an external referendum.", + "", + " Unlike `external_propose`, blacklisting has no effect on this and it may replace a", + " pre-scheduled `external_propose` call." + ] + }, + { + "name": "fast_track", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + }, + { + "name": "voting_period", + "type": "BlockNumber" + }, + { + "name": "delay", + "type": "BlockNumber" + } + ], + "docs": [ + " Schedule the currently externally-proposed majority-carries referendum to be tabled", + " immediately. If there is no externally-proposed referendum currently, or if there is one", + " but it is not a majority-carries referendum then it fails.", + "", + " - `proposal_hash`: The hash of the current external proposal.", + " - `voting_period`: The period that is allowed for voting on this proposal. Increased to", + " `EmergencyVotingPeriod` if too low.", + " - `delay`: The number of block after voting has ended in approval and this should be", + " enacted. This doesn't have a minimum amount." + ] + }, + { + "name": "veto_external", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Veto and blacklist the external proposal hash." + ] + }, + { + "name": "cancel_referendum", + "args": [ + { + "name": "ref_index", + "type": "Compact" + } + ], + "docs": [ + " Remove a referendum." + ] + }, + { + "name": "cancel_queued", + "args": [ + { + "name": "when", + "type": "Compact" + }, + { + "name": "which", + "type": "Compact" + }, + { + "name": "what", + "type": "Compact" + } + ], + "docs": [ + " Cancel a proposal queued for enactment." + ] + }, + { + "name": "set_proxy", + "args": [ + { + "name": "proxy", + "type": "AccountId" + } + ], + "docs": [ + " Specify a proxy. Called by the stash.", + "", + " # ", + " - One extra DB entry.", + " # " + ] + }, + { + "name": "resign_proxy", + "args": [], + "docs": [ + " Clear the proxy. Called by the proxy.", + "", + " # ", + " - One DB clear.", + " # " + ] + }, + { + "name": "remove_proxy", + "args": [ + { + "name": "proxy", + "type": "AccountId" + } + ], + "docs": [ + " Clear the proxy. Called by the stash.", + "", + " # ", + " - One DB clear.", + " # " + ] + }, + { + "name": "delegate", + "args": [ + { + "name": "to", + "type": "AccountId" + }, + { + "name": "conviction", + "type": "Conviction" + } + ], + "docs": [ + " Delegate vote.", + "", + " # ", + " - One extra DB entry.", + " # " + ] + }, + { + "name": "undelegate", + "args": [], + "docs": [ + " Undelegate vote.", + "", + " # ", + " - O(1).", + " # " + ] + }, + { + "name": "clear_public_proposals", + "args": [], + "docs": [ + " Veto and blacklist the proposal hash. Must be from Root origin." + ] + }, + { + "name": "note_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This doesn't require the proposal to be", + " in the dispatch queue but does require a deposit, returned once enacted." + ] + }, + { + "name": "note_imminent_preimage", + "args": [ + { + "name": "encoded_proposal", + "type": "Bytes" + }, + { + "name": "when", + "type": "BlockNumber" + }, + { + "name": "which", + "type": "u32" + } + ], + "docs": [ + " Register the preimage for an upcoming proposal. This requires the proposal to be", + " in the dispatch queue. No deposit is needed." + ] + }, + { + "name": "reap_preimage", + "args": [ + { + "name": "proposal_hash", + "type": "Hash" + } + ], + "docs": [ + " Remove an expired proposal preimage and collect the deposit." + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "PropIndex", + "Balance" + ], + "docs": [ + " A motion has been proposed by a public account." + ] + }, + { + "name": "Tabled", + "args": [ + "PropIndex", + "Balance", + "Vec" + ], + "docs": [ + " A public proposal has been tabled for referendum vote." + ] + }, + { + "name": "ExternalTabled", + "args": [], + "docs": [ + " An external proposal has been tabled." + ] + }, + { + "name": "Started", + "args": [ + "ReferendumIndex", + "VoteThreshold" + ], + "docs": [ + " A referendum has begun." + ] + }, + { + "name": "Passed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been approved by referendum." + ] + }, + { + "name": "NotPassed", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A proposal has been rejected by referendum." + ] + }, + { + "name": "Cancelled", + "args": [ + "ReferendumIndex" + ], + "docs": [ + " A referendum has been cancelled." + ] + }, + { + "name": "Executed", + "args": [ + "ReferendumIndex", + "bool" + ], + "docs": [ + " A proposal has been enacted." + ] + }, + { + "name": "Delegated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " An account has delegated their vote to another account." + ] + }, + { + "name": "Undelegated", + "args": [ + "AccountId" + ], + "docs": [ + " An account has cancelled a previous delegation operation." + ] + }, + { + "name": "Vetoed", + "args": [ + "AccountId", + "Hash", + "BlockNumber" + ], + "docs": [ + " An external proposal has been vetoed." + ] + }, + { + "name": "PreimageNoted", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal's preimage was noted, and the deposit taken." + ] + }, + { + "name": "PreimageUsed", + "args": [ + "Hash", + "AccountId", + "Balance" + ], + "docs": [ + " A proposal preimage was removed and used (the deposit was returned)." + ] + }, + { + "name": "PreimageInvalid", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was invalid." + ] + }, + { + "name": "PreimageMissing", + "args": [ + "Hash", + "ReferendumIndex" + ], + "docs": [ + " A proposal could not be executed because its preimage was missing." + ] + }, + { + "name": "PreimageReaped", + "args": [ + "Hash", + "AccountId", + "Balance", + "AccountId" + ], + "docs": [ + " A registered preimage was removed and the deposit collected by the reaper (last item)." + ] + } + ], + "constants": [ + { + "name": "EnactmentPeriod", + "type": "BlockNumber", + "value": "0x002f0d00", + "docs": [ + " The minimum period of locking and the period between a proposal being approved and enacted.", + "", + " It should generally be a little more than the unstake period to ensure that", + " voting stakers have an opportunity to remove themselves from the system in the case where", + " they are on the losing side of a vote." + ] + }, + { + "name": "LaunchPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) new public referenda are launched." + ] + }, + { + "name": "VotingPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " How often (in blocks) to check for new votes." + ] + }, + { + "name": "MinimumDeposit", + "type": "BalanceOf", + "value": "0x0000c16ff28623000000000000000000", + "docs": [ + " The minimum amount to be used as a deposit for a public referendum proposal." + ] + }, + { + "name": "EmergencyVotingPeriod", + "type": "BlockNumber", + "value": "0x80510100", + "docs": [ + " Minimum voting period allowed for an emergency referendum." + ] + }, + { + "name": "CooloffPeriod", + "type": "BlockNumber", + "value": "0x004e0c00", + "docs": [ + " Period in blocks where an external proposal may not be re-submitted after being vetoed." + ] + }, + { + "name": "PreimageByteDeposit", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The amount of balance that must be deposited per byte of preimage stored." + ] + } + ], + "errors": [] + }, + { + "name": "Council", + "storage": { + "prefix": "Instance1Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + } + ], + "docs": [ + " Set the collective's membership manually to `new_members`. Be nice to the chain and", + " provide it pre-sorted.", + "", + " Requires root origin." + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective." + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " # ", + " - Bounded storage reads and writes.", + " - Argument `threshold` has bearing on weight.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " # ", + " - Bounded storage read and writes.", + " - Will be slightly heavier if the proposal is approved / disapproved after the vote.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`)." + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`)." + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold." + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold." + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A motion was executed; `bool` is true if returned without error." + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A single member did some action; `bool` is true if returned without error." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "TechnicalCommittee", + "storage": { + "prefix": "Instance2Collective", + "items": [ + { + "name": "Proposals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The hashes of the active proposals." + ] + }, + { + "name": "ProposalOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Proposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Actual proposal for a given hash, if it's current." + ] + }, + { + "name": "Voting", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Hash", + "value": "Votes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Votes on a given proposal, if it is ongoing." + ] + }, + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " Proposals so far." + ] + }, + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current members of the collective. This is stored sorted (just by value)." + ] + } + ] + }, + "calls": [ + { + "name": "set_members", + "args": [ + { + "name": "new_members", + "type": "Vec" + } + ], + "docs": [ + " Set the collective's membership manually to `new_members`. Be nice to the chain and", + " provide it pre-sorted.", + "", + " Requires root origin." + ] + }, + { + "name": "execute", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Dispatch a proposal from a member using the `Member` origin.", + "", + " Origin must be a member of the collective." + ] + }, + { + "name": "propose", + "args": [ + { + "name": "threshold", + "type": "Compact" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " # ", + " - Bounded storage reads and writes.", + " - Argument `threshold` has bearing on weight.", + " # " + ] + }, + { + "name": "vote", + "args": [ + { + "name": "proposal", + "type": "Hash" + }, + { + "name": "index", + "type": "Compact" + }, + { + "name": "approve", + "type": "bool" + } + ], + "docs": [ + " # ", + " - Bounded storage read and writes.", + " - Will be slightly heavier if the proposal is approved / disapproved after the vote.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "AccountId", + "ProposalIndex", + "Hash", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been proposed (by given account) with a threshold (given", + " `MemberCount`)." + ] + }, + { + "name": "Voted", + "args": [ + "AccountId", + "Hash", + "bool", + "MemberCount", + "MemberCount" + ], + "docs": [ + " A motion (given hash) has been voted on by given account, leaving", + " a tally (yes votes and no votes given respectively as `MemberCount`)." + ] + }, + { + "name": "Approved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was approved by the required threshold." + ] + }, + { + "name": "Disapproved", + "args": [ + "Hash" + ], + "docs": [ + " A motion was not approved by the required threshold." + ] + }, + { + "name": "Executed", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A motion was executed; `bool` is true if returned without error." + ] + }, + { + "name": "MemberExecuted", + "args": [ + "Hash", + "bool" + ], + "docs": [ + " A single member did some action; `bool` is true if returned without error." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Elections", + "storage": { + "prefix": "PhragmenElection", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current elected membership. Sorted based on account id." + ] + }, + { + "name": "RunnersUp", + "modifier": "Default", + "type": { + "plain": "Vec<(AccountId,BalanceOf)>" + }, + "fallback": "0x00", + "docs": [ + " The current runners_up. Sorted based on low to high merit (worse to best runner)." + ] + }, + { + "name": "ElectionRounds", + "modifier": "Default", + "type": { + "plain": "u32" + }, + "fallback": "0x00000000", + "docs": [ + " The total number of vote rounds that have happened, excluding the upcoming one." + ] + }, + { + "name": "VotesOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "Vec", + "linked": true + } + }, + "fallback": "0x00", + "docs": [ + " Votes of a particular voter, with the round index of the votes." + ] + }, + { + "name": "StakeOf", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "BalanceOf", + "linked": false + } + }, + "fallback": "0x00000000000000000000000000000000", + "docs": [ + " Locked stake of a voter." + ] + }, + { + "name": "Candidates", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The present candidate list. Sorted based on account id. A current member can never enter", + " this vector and is always implicitly assumed to be a candidate." + ] + } + ] + }, + "calls": [ + { + "name": "vote", + "args": [ + { + "name": "votes", + "type": "Vec" + }, + { + "name": "value", + "type": "Compact" + } + ], + "docs": [ + " Vote for a set of candidates for the upcoming round of election.", + "", + " The `votes` should:", + " - not be empty.", + " - be less than the number of candidates.", + "", + " Upon voting, `value` units of `who`'s balance is locked and a bond amount is reserved.", + " It is the responsibility of the caller to not place all of their balance into the lock", + " and keep some for further transactions.", + "", + " # ", + " #### State", + " Reads: O(1)", + " Writes: O(V) given `V` votes. V is bounded by 16.", + " # " + ] + }, + { + "name": "remove_voter", + "args": [], + "docs": [ + " Remove `origin` as a voter. This removes the lock and returns the bond.", + "", + " # ", + " #### State", + " Reads: O(1)", + " Writes: O(1)", + " # " + ] + }, + { + "name": "report_defunct_voter", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Report `target` for being an defunct voter. In case of a valid report, the reporter is", + " rewarded by the bond amount of `target`. Otherwise, the reporter itself is removed and", + " their bond is slashed.", + "", + " A defunct voter is defined to be:", + " - a voter whose current submitted votes are all invalid. i.e. all of them are no", + " longer a candidate nor an active member.", + "", + " # ", + " #### State", + " Reads: O(NLogM) given M current candidates and N votes for `target`.", + " Writes: O(1)", + " # " + ] + }, + { + "name": "submit_candidacy", + "args": [], + "docs": [ + " Submit oneself for candidacy.", + "", + " A candidate will either:", + " - Lose at the end of the term and forfeit their deposit.", + " - Win and become a member. Members will eventually get their stash back.", + " - Become a runner-up. Runners-ups are reserved members in case one gets forcefully", + " removed.", + "", + " # ", + " #### State", + " Reads: O(LogN) Given N candidates.", + " Writes: O(1)", + " # " + ] + }, + { + "name": "renounce_candidacy", + "args": [], + "docs": [ + " Renounce one's intention to be a candidate for the next election round. 3 potential", + " outcomes exist:", + " - `origin` is a candidate and not elected in any set. In this case, the bond is", + " unreserved, returned and origin is removed as a candidate.", + " - `origin` is a current runner up. In this case, the bond is unreserved, returned and", + " origin is removed as a runner.", + " - `origin` is a current member. In this case, the bond is unreserved and origin is", + " removed as a member, consequently not being a candidate for the next round anymore.", + " Similar to [`remove_voter`], if replacement runners exists, they are immediately used." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "LookupSource" + } + ], + "docs": [ + " Remove a particular member from the set. This is effective immediately and the bond of", + " the outgoing member is slashed.", + "", + " If a runner-up is available, then the best runner-up will be removed and replaces the", + " outgoing member. Otherwise, a new phragmen round is started.", + "", + " Note that this does not affect the designated block number of the next election.", + "", + " # ", + " #### State", + " Reads: O(do_phragmen)", + " Writes: O(do_phragmen)", + " # " + ] + } + ], + "events": [ + { + "name": "NewTerm", + "args": [ + "Vec<(AccountId,Balance)>" + ], + "docs": [ + " A new term with new members. This indicates that enough candidates existed, not that", + " enough have has been elected. The inner value must be examined for this purpose." + ] + }, + { + "name": "EmptyTerm", + "args": [], + "docs": [ + " No (or not enough) candidates existed for this round." + ] + }, + { + "name": "MemberKicked", + "args": [ + "AccountId" + ], + "docs": [ + " A member has been removed. This should always be followed by either `NewTerm` ot", + " `EmptyTerm`." + ] + }, + { + "name": "MemberRenounced", + "args": [ + "AccountId" + ], + "docs": [ + " A member has renounced their candidacy." + ] + }, + { + "name": "VoterReported", + "args": [ + "AccountId", + "AccountId", + "bool" + ], + "docs": [ + " A voter (first element) was reported (byt the second element) with the the report being", + " successful or not (third element)." + ] + } + ], + "constants": [ + { + "name": "CandidacyBond", + "type": "BalanceOf", + "value": "0x0080c6a47e8d03000000000000000000", + "docs": [] + }, + { + "name": "VotingBond", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [] + }, + { + "name": "DesiredMembers", + "type": "u32", + "value": "0x0d000000", + "docs": [] + }, + { + "name": "DesiredRunnersUp", + "type": "u32", + "value": "0x07000000", + "docs": [] + }, + { + "name": "TermDuration", + "type": "BlockNumber", + "value": "0x80130300", + "docs": [] + } + ], + "errors": [] + }, + { + "name": "TechnicalMembership", + "storage": { + "prefix": "Instance1Membership", + "items": [ + { + "name": "Members", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current membership, stored as an ordered Vec." + ] + } + ] + }, + "calls": [ + { + "name": "add_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Add a member `who` to the set.", + "", + " May only be called from `AddOrigin` or root." + ] + }, + { + "name": "remove_member", + "args": [ + { + "name": "who", + "type": "AccountId" + } + ], + "docs": [ + " Remove a member `who` from the set.", + "", + " May only be called from `RemoveOrigin` or root." + ] + }, + { + "name": "swap_member", + "args": [ + { + "name": "remove", + "type": "AccountId" + }, + { + "name": "add", + "type": "AccountId" + } + ], + "docs": [ + " Swap out one member `remove` for another `add`.", + "", + " May only be called from `SwapOrigin` or root." + ] + }, + { + "name": "reset_members", + "args": [ + { + "name": "members", + "type": "Vec" + } + ], + "docs": [ + " Change the membership to a new set, disregarding the existing membership. Be nice and", + " pass `members` pre-sorted.", + "", + " May only be called from `ResetOrigin` or root." + ] + }, + { + "name": "change_key", + "args": [ + { + "name": "new", + "type": "AccountId" + } + ], + "docs": [ + " Swap out the sending member for some other key `new`.", + "", + " May only be called from `Signed` origin of a current member." + ] + } + ], + "events": [ + { + "name": "MemberAdded", + "args": [], + "docs": [ + " The given member was added; see the transaction for who." + ] + }, + { + "name": "MemberRemoved", + "args": [], + "docs": [ + " The given member was removed; see the transaction for who." + ] + }, + { + "name": "MembersSwapped", + "args": [], + "docs": [ + " Two members were swapped; see the transaction for who." + ] + }, + { + "name": "MembersReset", + "args": [], + "docs": [ + " The membership was reset; see the transaction for who the new set is." + ] + }, + { + "name": "KeyChanged", + "args": [], + "docs": [ + " One of the members' keys changed." + ] + }, + { + "name": "Dummy", + "args": [ + "PhantomData" + ], + "docs": [ + " Phantom member, never used." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "FinalityTracker", + "storage": null, + "calls": [ + { + "name": "final_hint", + "args": [ + { + "name": "hint", + "type": "Compact" + } + ], + "docs": [ + " Hint that the author of this block thinks the best finalized", + " block is the given number." + ] + } + ], + "events": null, + "constants": [ + { + "name": "WindowSize", + "type": "BlockNumber", + "value": "0x65000000", + "docs": [ + " The number of recent samples to keep from this chain. Default is 101." + ] + }, + { + "name": "ReportLatency", + "type": "BlockNumber", + "value": "0xe8030000", + "docs": [ + " The delay after which point things become suspicious. Default is 1000." + ] + } + ], + "errors": [] + }, + { + "name": "Grandpa", + "storage": { + "prefix": "GrandpaFinality", + "items": [ + { + "name": "Authorities", + "modifier": "Default", + "type": { + "plain": "AuthorityList" + }, + "fallback": "0x00", + "docs": [ + " DEPRECATED", + "", + " This used to store the current authority set, which has been migrated to the well-known", + " GRANDPA_AUTHORITES_KEY unhashed key." + ] + }, + { + "name": "State", + "modifier": "Default", + "type": { + "plain": "StoredState" + }, + "fallback": "0x00", + "docs": [ + " State of the current authority set." + ] + }, + { + "name": "PendingChange", + "modifier": "Optional", + "type": { + "plain": "StoredPendingChange" + }, + "fallback": "0x00", + "docs": [ + " Pending change: (signaled at, scheduled change)." + ] + }, + { + "name": "NextForced", + "modifier": "Optional", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00", + "docs": [ + " next block number where we can force a change." + ] + }, + { + "name": "Stalled", + "modifier": "Optional", + "type": { + "plain": "(BlockNumber,BlockNumber)" + }, + "fallback": "0x00", + "docs": [ + " `true` if we are currently stalled." + ] + }, + { + "name": "CurrentSetId", + "modifier": "Default", + "type": { + "plain": "SetId" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The number of changes (both in terms of keys and underlying economic responsibilities)", + " in the \"set\" of Grandpa validators from genesis." + ] + }, + { + "name": "SetIdSession", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "SetId", + "value": "SessionIndex", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from grandpa set ID to the index of the *most recent* session for which its members were responsible." + ] + } + ] + }, + "calls": [ + { + "name": "report_misbehavior", + "args": [ + { + "name": "_report", + "type": "Bytes" + } + ], + "docs": [ + " Report some misbehavior." + ] + } + ], + "events": [ + { + "name": "NewAuthorities", + "args": [ + "AuthorityList" + ], + "docs": [ + " New authority set has been applied." + ] + }, + { + "name": "Paused", + "args": [], + "docs": [ + " Current authority set has been paused." + ] + }, + { + "name": "Resumed", + "args": [], + "docs": [ + " Current authority set has been resumed." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "Treasury", + "storage": { + "prefix": "Treasury", + "items": [ + { + "name": "ProposalCount", + "modifier": "Default", + "type": { + "plain": "ProposalIndex" + }, + "fallback": "0x00000000", + "docs": [ + " Number of proposals that have been made." + ] + }, + { + "name": "Proposals", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ProposalIndex", + "value": "TreasuryProposal", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Proposals that have been made." + ] + }, + { + "name": "Approvals", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Proposal indices that have been approved but not yet awarded." + ] + } + ] + }, + "calls": [ + { + "name": "propose_spend", + "args": [ + { + "name": "value", + "type": "Compact" + }, + { + "name": "beneficiary", + "type": "LookupSource" + } + ], + "docs": [ + " Put forward a suggestion for spending. A deposit proportional to the value", + " is reserved and slashed if the proposal is rejected. It is returned once the", + " proposal is awarded.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change, one extra DB entry.", + " # " + ] + }, + { + "name": "reject_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Reject a proposed spend. The original deposit will be slashed.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB clear.", + " # " + ] + }, + { + "name": "approve_proposal", + "args": [ + { + "name": "proposal_id", + "type": "Compact" + } + ], + "docs": [ + " Approve a proposal. At a later time, the proposal will be allocated to the beneficiary", + " and the original deposit will be returned.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + } + ], + "events": [ + { + "name": "Proposed", + "args": [ + "ProposalIndex" + ], + "docs": [ + " New proposal." + ] + }, + { + "name": "Spending", + "args": [ + "Balance" + ], + "docs": [ + " We have ended a spend period and will now allocate funds." + ] + }, + { + "name": "Awarded", + "args": [ + "ProposalIndex", + "Balance", + "AccountId" + ], + "docs": [ + " Some funds have been allocated." + ] + }, + { + "name": "Burnt", + "args": [ + "Balance" + ], + "docs": [ + " Some of our funds have been burnt." + ] + }, + { + "name": "Rollover", + "args": [ + "Balance" + ], + "docs": [ + " Spending has finished; this is the amount that rolls over until next spend." + ] + }, + { + "name": "Deposit", + "args": [ + "Balance" + ], + "docs": [ + " Some funds have been deposited." + ] + } + ], + "constants": [ + { + "name": "ProposalBond", + "type": "Permill", + "value": "0x50c30000", + "docs": [ + " Fraction of a proposal's value that should be bonded in order to place the proposal.", + " An accepted proposal gets these back. A rejected proposal does not." + ] + }, + { + "name": "ProposalBondMinimum", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Minimum amount of funds that should be placed in a deposit for making a proposal." + ] + }, + { + "name": "SpendPeriod", + "type": "BlockNumber", + "value": "0x80700000", + "docs": [ + " Period between successive spends." + ] + }, + { + "name": "Burn", + "type": "Permill", + "value": "0x20a10700", + "docs": [ + " Percentage of spare funds (if any) that are burnt per spend period." + ] + } + ], + "errors": [] + }, + { + "name": "Contracts", + "storage": { + "prefix": "Contract", + "items": [ + { + "name": "GasSpent", + "modifier": "Default", + "type": { + "plain": "Gas" + }, + "fallback": "0x0000000000000000", + "docs": [ + " Gas spent so far in this block." + ] + }, + { + "name": "CurrentSchedule", + "modifier": "Default", + "type": { + "plain": "Schedule" + }, + "fallback": "0x0000000001000000000000000100000000000000010000000000000001000000000000000100000000000000010000000000000001000000000000008700000000000000af0000000000000001000000000000000100000000000000040000000000010010000000004000000020000000", + "docs": [ + " Current cost schedule for contracts." + ] + }, + { + "name": "PristineCode", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "CodeHash", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping from an original code hash to the original code, untouched by instrumentation." + ] + }, + { + "name": "CodeStorage", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "CodeHash", + "value": "PrefabWasmModule", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " A mapping between an original code hash and instrumented wasm code, ready for execution." + ] + }, + { + "name": "AccountCounter", + "modifier": "Default", + "type": { + "plain": "u64" + }, + "fallback": "0x0000000000000000", + "docs": [ + " The subtrie counter." + ] + }, + { + "name": "ContractInfoOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "ContractInfo", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The code associated with a given account." + ] + }, + { + "name": "GasPrice", + "modifier": "Default", + "type": { + "plain": "BalanceOf" + }, + "fallback": "0x01000000000000000000000000000000", + "docs": [ + " The price of one unit of gas." + ] + } + ] + }, + "calls": [ + { + "name": "update_schedule", + "args": [ + { + "name": "schedule", + "type": "Schedule" + } + ], + "docs": [ + " Updates the schedule for metering contracts.", + "", + " The schedule must have a greater version than the stored schedule." + ] + }, + { + "name": "put_code", + "args": [ + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code", + "type": "Bytes" + } + ], + "docs": [ + " Stores the given binary Wasm code into the chain's storage and returns its `codehash`.", + " You can instantiate contracts only with stored code." + ] + }, + { + "name": "call", + "args": [ + { + "name": "dest", + "type": "LookupSource" + }, + { + "name": "value", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Makes a call to an account, optionally transferring some balance.", + "", + " * If the account is a smart-contract account, the associated code will be", + " executed and any value will be transferred.", + " * If the account is a regular account, any value will be transferred.", + " * If no account exists and the call value is not less than `existential_deposit`,", + " a regular account will be created and any value will be transferred." + ] + }, + { + "name": "instantiate", + "args": [ + { + "name": "endowment", + "type": "Compact" + }, + { + "name": "gas_limit", + "type": "Compact" + }, + { + "name": "code_hash", + "type": "CodeHash" + }, + { + "name": "data", + "type": "Bytes" + } + ], + "docs": [ + " Instantiates a new contract from the `codehash` generated by `put_code`, optionally transferring some balance.", + "", + " Instantiation is executed as follows:", + "", + " - The destination address is computed based on the sender and hash of the code.", + " - The smart-contract account is created at the computed address.", + " - The `ctor_code` is executed in the context of the newly-created account. Buffer returned", + " after the execution is saved as the `code` of the account. That code will be invoked", + " upon any call received by this account.", + " - The contract is initialized." + ] + }, + { + "name": "claim_surcharge", + "args": [ + { + "name": "dest", + "type": "AccountId" + }, + { + "name": "aux_sender", + "type": "Option" + } + ], + "docs": [ + " Allows block producers to claim a small reward for evicting a contract. If a block producer", + " fails to do so, a regular users will be allowed to claim the reward.", + "", + " If contract is not evicted as a result of this call, no actions are taken and", + " the sender is not eligible for the reward." + ] + } + ], + "events": [ + { + "name": "Transfer", + "args": [ + "AccountId", + "AccountId", + "Balance" + ], + "docs": [ + " Transfer happened `from` to `to` with given `value` as part of a `call` or `instantiate`." + ] + }, + { + "name": "Instantiated", + "args": [ + "AccountId", + "AccountId" + ], + "docs": [ + " Contract deployed by address at the specified address." + ] + }, + { + "name": "CodeStored", + "args": [ + "Hash" + ], + "docs": [ + " Code with the specified hash has been stored." + ] + }, + { + "name": "ScheduleUpdated", + "args": [ + "u32" + ], + "docs": [ + " Triggered when the current schedule is updated." + ] + }, + { + "name": "Dispatched", + "args": [ + "AccountId", + "bool" + ], + "docs": [ + " A call was dispatched from the given account. The bool signals whether it was", + " successful execution or not." + ] + }, + { + "name": "Contract", + "args": [ + "AccountId", + "Bytes" + ], + "docs": [ + " An event from contract of account." + ] + } + ], + "constants": [ + { + "name": "SignedClaimHandicap", + "type": "BlockNumber", + "value": "0x02000000", + "docs": [ + " Number of block delay an extrinsic claim surcharge has.", + "", + " When claim surcharge is called by an extrinsic the rent is checked", + " for current_block - delay" + ] + }, + { + "name": "TombstoneDeposit", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " The minimum amount required to generate a tombstone." + ] + }, + { + "name": "StorageSizeOffset", + "type": "u32", + "value": "0x08000000", + "docs": [ + " Size of a contract at the time of instantiaion. This is a simple way to ensure that", + " empty contracts eventually gets deleted." + ] + }, + { + "name": "RentByteFee", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Price of a byte of storage per one block interval. Should be greater than 0." + ] + }, + { + "name": "RentDepositOffset", + "type": "BalanceOf", + "value": "0x00008a5d784563010000000000000000", + "docs": [ + " The amount of funds a contract should deposit in order to offset", + " the cost of one byte.", + "", + " Let's suppose the deposit is 1,000 BU (balance units)/byte and the rent is 1 BU/byte/day,", + " then a contract with 1,000,000 BU that uses 1,000 bytes of storage would pay no rent.", + " But if the balance reduced to 500,000 BU and the storage stayed the same at 1,000,", + " then it would pay 500 BU/day." + ] + }, + { + "name": "SurchargeReward", + "type": "BalanceOf", + "value": "0x0080a1a76b4a35000000000000000000", + "docs": [ + " Reward that is received by the party whose touch has led", + " to removal of a contract." + ] + }, + { + "name": "TransferFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to make a transfer." + ] + }, + { + "name": "CreationFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to create an account." + ] + }, + { + "name": "TransactionBaseFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the base." + ] + }, + { + "name": "TransactionByteFee", + "type": "BalanceOf", + "value": "0x00e40b54020000000000000000000000", + "docs": [ + " The fee to be paid for making a transaction; the per-byte portion." + ] + }, + { + "name": "ContractFee", + "type": "BalanceOf", + "value": "0x0010a5d4e80000000000000000000000", + "docs": [ + " The fee required to instantiate a contract instance. A reasonable default value", + " is 21." + ] + }, + { + "name": "CallBaseFee", + "type": "Gas", + "value": "0xe803000000000000", + "docs": [ + " The base fee charged for calling into a contract. A reasonable default", + " value is 135." + ] + }, + { + "name": "InstantiateBaseFee", + "type": "Gas", + "value": "0xe803000000000000", + "docs": [ + " The base fee charged for instantiating a contract. A reasonable default value", + " is 175." + ] + }, + { + "name": "MaxDepth", + "type": "u32", + "value": "0x20000000", + "docs": [ + " The maximum nesting level of a call/instantiate stack. A reasonable default", + " value is 100." + ] + }, + { + "name": "MaxValueSize", + "type": "u32", + "value": "0x00400000", + "docs": [ + " The maximum size of a storage value in bytes. A reasonable default is 16 KiB." + ] + }, + { + "name": "BlockGasLimit", + "type": "Gas", + "value": "0x8096980000000000", + "docs": [ + " The maximum amount of gas that could be expended per block. A reasonable", + " default value is 10_000_000." + ] + } + ], + "errors": [] + }, + { + "name": "Sudo", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "Key", + "modifier": "Default", + "type": { + "plain": "AccountId" + }, + "fallback": "0x0000000000000000000000000000000000000000000000000000000000000000", + "docs": [ + " The `AccountId` of the sudo key." + ] + } + ] + }, + "calls": [ + { + "name": "sudo", + "args": [ + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Root` origin.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Unknown weight of derivative `proposal` execution.", + " # " + ] + }, + { + "name": "set_key", + "args": [ + { + "name": "new", + "type": "LookupSource" + } + ], + "docs": [ + " Authenticates the current sudo key and sets the given AccountId (`new`) as the new sudo key.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB change.", + " # " + ] + }, + { + "name": "sudo_as", + "args": [ + { + "name": "who", + "type": "LookupSource" + }, + { + "name": "proposal", + "type": "Proposal" + } + ], + "docs": [ + " Authenticates the sudo key and dispatches a function call with `Signed` origin from", + " a given account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - Limited storage reads.", + " - One DB write (event).", + " - Unknown weight of derivative `proposal` execution.", + " # " + ] + } + ], + "events": [ + { + "name": "Sudid", + "args": [ + "bool" + ], + "docs": [ + " A sudo just took place." + ] + }, + { + "name": "KeyChanged", + "args": [ + "AccountId" + ], + "docs": [ + " The sudoer just switched identity; the old key is supplied." + ] + }, + { + "name": "SudoAsDone", + "args": [ + "bool" + ], + "docs": [ + " A sudo just took place." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "ImOnline", + "storage": { + "prefix": "ImOnline", + "items": [ + { + "name": "GossipAt", + "modifier": "Default", + "type": { + "plain": "BlockNumber" + }, + "fallback": "0x00000000", + "docs": [ + " The block number when we should gossip." + ] + }, + { + "name": "Keys", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " The current set of keys that may issue a heartbeat." + ] + }, + { + "name": "ReceivedHeartbeats", + "modifier": "Optional", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "SessionIndex", + "key2": "AuthIndex", + "value": "Bytes", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " For each session index, we keep a mapping of `AuthIndex`", + " to `offchain::OpaqueNetworkState`." + ] + }, + { + "name": "AuthoredBlocks", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "SessionIndex", + "key2": "ValidatorId", + "value": "u32", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00000000", + "docs": [ + " For each session index, we keep a mapping of `T::ValidatorId` to the", + " number of blocks authored by the given authority." + ] + } + ] + }, + "calls": [ + { + "name": "heartbeat", + "args": [ + { + "name": "heartbeat", + "type": "Heartbeat" + }, + { + "name": "_signature", + "type": "Signature" + } + ], + "docs": [] + } + ], + "events": [ + { + "name": "HeartbeatReceived", + "args": [ + "AuthorityId" + ], + "docs": [ + " A new heartbeat was received from `AuthorityId`" + ] + }, + { + "name": "AllGood", + "args": [], + "docs": [ + " At the end of the session, no offence was committed." + ] + }, + { + "name": "SomeOffline", + "args": [ + "Vec" + ], + "docs": [ + " At the end of the session, at least once validator was found to be offline." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "AuthorityDiscovery", + "storage": null, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Offences", + "storage": { + "prefix": "Offences", + "items": [ + { + "name": "Reports", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "ReportIdOf", + "value": "OffenceDetails", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The primary structure that holds all offence records keyed by report identifiers." + ] + }, + { + "name": "ConcurrentReportsIndex", + "modifier": "Default", + "type": { + "doubleMap": { + "hasher": "Blake2_256", + "key1": "Kind", + "key2": "OpaqueTimeSlot", + "value": "Vec", + "key2Hasher": "Blake2_256" + } + }, + "fallback": "0x00", + "docs": [ + " A vector of reports of the same kind that happened at the same time slot." + ] + }, + { + "name": "ReportsByKindIndex", + "modifier": "Default", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "Kind", + "value": "Bytes", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " Enumerates all reports of a kind along with the time they happened.", + "", + " All reports are sorted by the time of offence.", + "", + " Note that the actual type of this mapping is `Vec`, this is because values of", + " different types are not supported at the moment so we are doing the manual serialization." + ] + } + ] + }, + "calls": [], + "events": [ + { + "name": "Offence", + "args": [ + "Kind", + "OpaqueTimeSlot" + ], + "docs": [ + " There is an offence reported of the given `kind` happened at the `session_index` and", + " (kind-specific) time slot. This event is not deposited for duplicate slashes." + ] + } + ], + "constants": [], + "errors": [] + }, + { + "name": "RandomnessCollectiveFlip", + "storage": { + "prefix": "RandomnessCollectiveFlip", + "items": [ + { + "name": "RandomMaterial", + "modifier": "Default", + "type": { + "plain": "Vec" + }, + "fallback": "0x00", + "docs": [ + " Series of block headers from the last 81 blocks that acts as random seed material. This", + " is arranged as a ring buffer with `block_number % 81` being the index into the `Vec` of", + " the oldest hash." + ] + } + ] + }, + "calls": [], + "events": null, + "constants": [], + "errors": [] + }, + { + "name": "Nicks", + "storage": { + "prefix": "Sudo", + "items": [ + { + "name": "NameOf", + "modifier": "Optional", + "type": { + "map": { + "hasher": "Blake2_256", + "key": "AccountId", + "value": "(Bytes,BalanceOf)", + "linked": false + } + }, + "fallback": "0x00", + "docs": [ + " The lookup table for names." + ] + } + ] + }, + "calls": [ + { + "name": "set_name", + "args": [ + { + "name": "name", + "type": "Bytes" + } + ], + "docs": [ + " Set an account's name. The name should be a UTF-8-encoded string by convention, though", + " we don't check it.", + "", + " The name may not be more than `T::MaxLength` bytes, nor less than `T::MinLength` bytes.", + "", + " If the account doesn't already have a name, then a fee of `ReservationFee` is reserved", + " in the account.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - At most one balance operation.", + " - One storage read/write.", + " - One event.", + " # " + ] + }, + { + "name": "clear_name", + "args": [], + "docs": [ + " Clear an account's name and return the deposit. Fails if the account was not named.", + "", + " The dispatch origin for this call must be _Signed_.", + "", + " # ", + " - O(1).", + " - One balance operation.", + " - One storage read/write.", + " - One event.", + " # " + ] + }, + { + "name": "kill_name", + "args": [ + { + "name": "target", + "type": "LookupSource" + } + ], + "docs": [ + " Remove an account's name and take charge of the deposit.", + "", + " Fails if `who` has not been named. The deposit is dealt with through `T::Slashed`", + " imbalance handler.", + "", + " The dispatch origin for this call must be _Root_ or match `T::ForceOrigin`.", + "", + " # ", + " - O(1).", + " - One unbalanced handler (probably a balance transfer)", + " - One storage read/write.", + " - One event.", + " # " + ] + }, + { + "name": "force_name", + "args": [ + { + "name": "target", + "type": "LookupSource" + }, + { + "name": "name", + "type": "Bytes" + } + ], + "docs": [ + " Set a third-party account's name with no deposit.", + "", + " No length checking is done on the name.", + "", + " The dispatch origin for this call must be _Root_ or match `T::ForceOrigin`.", + "", + " # ", + " - O(1).", + " - At most one balance operation.", + " - One storage read/write.", + " - One event.", + " # " + ] + } + ], + "events": [ + { + "name": "NameSet", + "args": [ + "AccountId" + ], + "docs": [ + " A name was set." + ] + }, + { + "name": "NameForced", + "args": [ + "AccountId" + ], + "docs": [ + " A name was forcibly set." + ] + }, + { + "name": "NameChanged", + "args": [ + "AccountId" + ], + "docs": [ + " A name was changed." + ] + }, + { + "name": "NameCleared", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was cleared, and the given balance returned." + ] + }, + { + "name": "NameKilled", + "args": [ + "AccountId", + "Balance" + ], + "docs": [ + " A name was removed and the given balance slashed." + ] + } + ], + "constants": [ + { + "name": "ReservationFee", + "type": "BalanceOf", + "value": "0x00407a10f35a00000000000000000000", + "docs": [ + " Reservation fee." + ] + }, + { + "name": "MinLength", + "type": "u32", + "value": "0x03000000", + "docs": [ + " The minimum length a name may be." + ] + }, + { + "name": "MaxLength", + "type": "u32", + "value": "0x10000000", + "docs": [ + " The maximum length a name may be." + ] + } + ], + "errors": [] + } + ] + } + } +} diff --git a/packages/polkadot/web3-polkadot.cabal b/packages/polkadot/web3-polkadot.cabal new file mode 100644 index 00000000..eb003468 --- /dev/null +++ b/packages/polkadot/web3-polkadot.cabal @@ -0,0 +1,187 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-polkadot +version: 1.1.0.1 +synopsis: Polkadot support for Haskell Web3 library. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple +data-files: + tests/meta/v10.hex + tests/meta/v11.hex + tests/meta/v12.hex + tests/meta/v13.hex + tests/meta/v9.hex + tests/meta/v10.json + tests/meta/v11.json + tests/meta/v12.json + tests/meta/v13.json + tests/meta/v9.json + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Network.Polkadot + Network.Polkadot.Account + Network.Polkadot.Call + Network.Polkadot.Crypto + Network.Polkadot.Extrinsic + Network.Polkadot.Extrinsic.Era + Network.Polkadot.Extrinsic.Payload + Network.Polkadot.Extrinsic.SignedExtension + Network.Polkadot.Extrinsic.SignedExtension.System + Network.Polkadot.Extrinsic.SignedExtension.TransactionPayment + Network.Polkadot.Extrinsic.Unchecked + Network.Polkadot.Metadata + Network.Polkadot.Metadata.MagicNumber + Network.Polkadot.Metadata.Type + Network.Polkadot.Metadata.Type.Ast + Network.Polkadot.Metadata.Type.Discovery + Network.Polkadot.Metadata.Type.Parser + Network.Polkadot.Metadata.Type.ParserCombinators + Network.Polkadot.Metadata.V10 + Network.Polkadot.Metadata.V11 + Network.Polkadot.Metadata.V12 + Network.Polkadot.Metadata.V13 + Network.Polkadot.Metadata.V9 + Network.Polkadot.Primitives + Network.Polkadot.Query + Network.Polkadot.Rpc.Account + Network.Polkadot.Rpc.Author + Network.Polkadot.Rpc.Babe + Network.Polkadot.Rpc.Chain + Network.Polkadot.Rpc.Childstate + Network.Polkadot.Rpc.Contracts + Network.Polkadot.Rpc.Engine + Network.Polkadot.Rpc.Grandpa + Network.Polkadot.Rpc.Offchain + Network.Polkadot.Rpc.Payment + Network.Polkadot.Rpc.Rpc + Network.Polkadot.Rpc.State + Network.Polkadot.Rpc.System + Network.Polkadot.Rpc.Types + Network.Polkadot.Storage + Network.Polkadot.Storage.Key + other-modules: + Paths_web3_polkadot + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , base58-bytestring ==0.1.* + , bytestring >=0.10 && <0.13 + , cases ==0.1.* + , containers >=0.6 && <0.8 + , crypton >=0.30 && <1.1 + , generics-sop >=0.3 && <0.6 + , jsonrpc-tinyclient >=1.0 && <1.2 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , microlens-mtl ==0.2.* + , microlens-th ==0.4.* + , mtl >=2.2 && <2.4 + , parsec >=3.0 && <3.2 + , scale >=1.0 && <1.2 + , text >=1.2 && <2.2 + , web3-bignum >=1.0 && <1.2 + , web3-crypto >=1.0 && <1.2 + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Network.Polkadot.Test.AccountSpec + Network.Polkadot.Test.ExtrinsicSpec + Network.Polkadot.Test.MetadataSpec + Network.Polkadot.Test.StorageSpec + Network.Polkadot + Network.Polkadot.Account + Network.Polkadot.Call + Network.Polkadot.Crypto + Network.Polkadot.Extrinsic + Network.Polkadot.Extrinsic.Era + Network.Polkadot.Extrinsic.Payload + Network.Polkadot.Extrinsic.SignedExtension + Network.Polkadot.Extrinsic.SignedExtension.System + Network.Polkadot.Extrinsic.SignedExtension.TransactionPayment + Network.Polkadot.Extrinsic.Unchecked + Network.Polkadot.Metadata + Network.Polkadot.Metadata.MagicNumber + Network.Polkadot.Metadata.Type + Network.Polkadot.Metadata.Type.Ast + Network.Polkadot.Metadata.Type.Discovery + Network.Polkadot.Metadata.Type.Parser + Network.Polkadot.Metadata.Type.ParserCombinators + Network.Polkadot.Metadata.V10 + Network.Polkadot.Metadata.V11 + Network.Polkadot.Metadata.V12 + Network.Polkadot.Metadata.V13 + Network.Polkadot.Metadata.V9 + Network.Polkadot.Primitives + Network.Polkadot.Query + Network.Polkadot.Rpc.Account + Network.Polkadot.Rpc.Author + Network.Polkadot.Rpc.Babe + Network.Polkadot.Rpc.Chain + Network.Polkadot.Rpc.Childstate + Network.Polkadot.Rpc.Contracts + Network.Polkadot.Rpc.Engine + Network.Polkadot.Rpc.Grandpa + Network.Polkadot.Rpc.Offchain + Network.Polkadot.Rpc.Payment + Network.Polkadot.Rpc.Rpc + Network.Polkadot.Rpc.State + Network.Polkadot.Rpc.System + Network.Polkadot.Rpc.Types + Network.Polkadot.Storage + Network.Polkadot.Storage.Key + Paths_web3_polkadot + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , base58-bytestring ==0.1.* + , bytestring >=0.10 && <0.13 + , cases ==0.1.* + , containers >=0.6 && <0.8 + , crypton >=0.30 && <1.1 + , generics-sop >=0.3 && <0.6 + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , hspec-expectations-json >=1.0.0 && <1.1 + , jsonrpc-tinyclient >=1.0 && <1.2 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , microlens-mtl ==0.2.* + , microlens-th ==0.4.* + , mtl >=2.2 && <2.4 + , parsec >=3.0 && <3.2 + , scale >=1.0 && <1.2 + , text >=1.2 && <2.2 + , web3-bignum >=1.0 && <1.2 + , web3-crypto >=1.0 && <1.2 + default-language: Haskell2010 diff --git a/packages/provider/LICENSE b/packages/provider/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/provider/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/provider/Setup.hs b/packages/provider/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/provider/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/provider/package.yaml b/packages/provider/package.yaml new file mode 100644 index 00000000..f119d2d3 --- /dev/null +++ b/packages/provider/package.yaml @@ -0,0 +1,51 @@ +name: web3-provider +version: 1.1.0.0 +synopsis: Node connection provider for Haskell Web3 library. +description: This package contains general Web3 node adapters and connection helpers. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- mtl >=2.2 && <2.4 +- text >=1.2 && <2.2 +- async >=2.1 && <2.3 +- network >=2.5 && <3.3 +- websockets >=0.10 && <0.14 +- exceptions >=0.8 && <0.11 +- http-client >=0.5 && <0.8 +- data-default >=0.7 && <0.9 +- transformers >=0.5 && <0.7 +- jsonrpc-tinyclient >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src diff --git a/packages/provider/src/Network/Web3/Provider.hs b/packages/provider/src/Network/Web3/Provider.hs new file mode 100644 index 00000000..d5ad00fd --- /dev/null +++ b/packages/provider/src/Network/Web3/Provider.hs @@ -0,0 +1,132 @@ +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} + +-- | +-- Module : Network.Web3.Provider +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : portable +-- +-- Web3 service provider. +-- + +module Network.Web3.Provider where + +import Control.Concurrent.Async (Async, async) +import Control.Exception (Exception, try) +import Control.Monad.Catch (MonadThrow) +import Control.Monad.Fail (MonadFail) +import Control.Monad.IO.Class (MonadIO (..)) +import Control.Monad.State (MonadState (..)) +import Control.Monad.Trans.State (StateT, evalStateT, withStateT) +import Data.Default (Default (..)) +import Data.Text (Text) +import GHC.Generics (Generic) +import Network.HTTP.Client (Manager) +import Network.JsonRpc.TinyClient (JsonRpc, JsonRpcClient (..), + defaultSettings, jsonRpcManager) +import qualified Network.Socket as S +import qualified Network.WebSockets as WS (Connection, + defaultConnectionOptions, + newClientConnection, + sendClose) +import qualified Network.WebSockets.Stream as Stream + +-- | Any communication with node wrapped with 'Web3' monad +newtype Web3 a = Web3 { unWeb3 :: StateT JsonRpcClient IO a } + deriving (Functor, Applicative, Monad, MonadIO, MonadThrow, MonadFail, MonadState JsonRpcClient) + +instance JsonRpc Web3 + +-- | Some piece of error response +data Web3Error = JsonRpcFail !String + | ParserFail !String + | UserFail !String + deriving (Show, Eq, Generic) + +instance Exception Web3Error + +--TODO: Change to `HttpProvider ServerUri | IpcProvider FilePath` to support IPC +-- | Web3 Provider +data Provider = HttpProvider String + | WsProvider String Int + deriving (Show, Eq, Generic) + +-- | Default Provider URI +instance Default Provider where + def = HttpProvider "http://localhost:8545" + +-- | 'Web3' monad runner, using the supplied Manager +runWeb3With :: MonadIO m + => Manager + -> Provider + -> Web3 a + -> m (Either Web3Error a) +runWeb3With manager provider f = do + runWeb3' provider Web3 { unWeb3 = withStateT changeManager $ unWeb3 f} + where + changeManager jRpcClient = case jRpcClient of + JsonRpcHttpClient{..} -> jRpcClient { jsonRpcManager = manager } + JsonRpcWsClient{..} -> jRpcClient + +-- | 'Web3' monad runner +runWeb3' :: MonadIO m + => Provider + -> Web3 a + -> m (Either Web3Error a) +runWeb3' (HttpProvider uri) f = do + cfg <- defaultSettings uri + liftIO . try . flip evalStateT cfg . unWeb3 $ f + +runWeb3' (WsProvider host port) f = do + connection <- liftIO $ getConnection host port "/" + let currentClient = JsonRpcWsClient { jsonRpcWsConnection = connection } + response <- liftIO $ try . flip evalStateT currentClient . unWeb3 $ f + liftIO $ WS.sendClose connection ("Bye-" :: Text) + return response + +-- | 'Web3' runner for default Http provider +runWeb3 :: MonadIO m + => Web3 a + -> m (Either Web3Error a) +{-# INLINE runWeb3 #-} +runWeb3 = runWeb3' def + +-- | Fork 'Web3' with the same 'Provider' and 'Manager' +forkWeb3 :: Web3 a -> Web3 (Async a) +forkWeb3 f = liftIO . async . evalStateT (unWeb3 f) =<< get + +-- | Returns a WebSocket Connection Instance +getConnection :: String -- ^ Host + -> Int -- ^ Port + -> String -- ^ Path + -> IO WS.Connection +{-# INLINE getConnection #-} +getConnection host port path = do + -- Create and connect socket + let hints = S.defaultHints + {S.addrSocketType = S.Stream} + + -- Correct host and path. + fullHost = if port == 80 then host else (host ++ ":" ++ show port) + path0 = if null path then "/" else path + + addr:_ <- S.getAddrInfo (Just hints) (Just host) (Just $ show port) + sock <- S.socket (S.addrFamily addr) S.Stream S.defaultProtocol + S.setSocketOption sock S.NoDelay 1 + + -- Connect WebSocket and run client + + res <- ( S.connect sock (S.addrAddress addr) >> + Stream.makeSocketStream sock) >>= + (\stream -> + WS.newClientConnection stream fullHost + path0 WS.defaultConnectionOptions [] ) + return res diff --git a/packages/provider/web3-provider.cabal b/packages/provider/web3-provider.cabal new file mode 100644 index 00000000..067a42ce --- /dev/null +++ b/packages/provider/web3-provider.cabal @@ -0,0 +1,45 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-provider +version: 1.1.0.0 +synopsis: Node connection provider for Haskell Web3 library. +description: This package contains general Web3 node adapters and connection helpers. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Network.Web3.Provider + other-modules: + Paths_web3_provider + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + async >=2.1 && <2.3 + , base >=4.11 && <4.21 + , data-default >=0.7 && <0.9 + , exceptions >=0.8 && <0.11 + , http-client >=0.5 && <0.8 + , jsonrpc-tinyclient >=1.0 && <1.2 + , mtl >=2.2 && <2.4 + , network >=2.5 && <3.3 + , text >=1.2 && <2.2 + , transformers >=0.5 && <0.7 + , websockets >=0.10 && <0.14 + default-language: Haskell2010 diff --git a/packages/scale/LICENSE b/packages/scale/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/scale/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/scale/Setup.hs b/packages/scale/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/scale/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/scale/package.yaml b/packages/scale/package.yaml new file mode 100644 index 00000000..ea64f066 --- /dev/null +++ b/packages/scale/package.yaml @@ -0,0 +1,66 @@ +name: scale +version: 1.1.0.0 +synopsis: SCALE v2.0 codec for Haskell Web3 library. +description: Client library for Third Generation of Web. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- cereal >=0.5 && <0.6 +- bitvec >=1.0 && <1.2 +- vector >=0.12 && <0.14 +- memory >=0.14 && <0.19 +- bytestring >=0.10 && <0.13 +- generics-sop >=0.3 && <0.6 +- data-default >=0.7 && <0.9 +- template-haskell >=2.11 && <2.23 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + dependencies: + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/packages/scale/scale.cabal b/packages/scale/scale.cabal new file mode 100644 index 00000000..212e4629 --- /dev/null +++ b/packages/scale/scale.cabal @@ -0,0 +1,88 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: scale +version: 1.1.0.0 +synopsis: SCALE v2.0 codec for Haskell Web3 library. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Codec.Scale + Codec.Scale.Class + Codec.Scale.Compact + Codec.Scale.Core + Codec.Scale.Generic + Codec.Scale.SingletonEnum + Codec.Scale.Skip + Codec.Scale.TH + other-modules: + Paths_scale + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + base >=4.11 && <4.21 + , bitvec >=1.0 && <1.2 + , bytestring >=0.10 && <0.13 + , cereal ==0.5.* + , data-default >=0.7 && <0.9 + , generics-sop >=0.3 && <0.6 + , memory >=0.14 && <0.19 + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , vector >=0.12 && <0.14 + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Codec.Scale.Test.CoreSpec + Codec.Scale.Test.SingleFieldStructSpec + Codec.Scale.Test.SkipSpec + Codec.Scale + Codec.Scale.Class + Codec.Scale.Compact + Codec.Scale.Core + Codec.Scale.Generic + Codec.Scale.SingletonEnum + Codec.Scale.Skip + Codec.Scale.TH + Paths_scale + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + base >=4.11 && <4.21 + , bitvec >=1.0 && <1.2 + , bytestring >=0.10 && <0.13 + , cereal ==0.5.* + , data-default >=0.7 && <0.9 + , generics-sop >=0.3 && <0.6 + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , memory >=0.14 && <0.19 + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , vector >=0.12 && <0.14 + default-language: Haskell2010 diff --git a/packages/scale/src/Codec/Scale.hs b/packages/scale/src/Codec/Scale.hs new file mode 100644 index 00000000..d325dd47 --- /dev/null +++ b/packages/scale/src/Codec/Scale.hs @@ -0,0 +1,73 @@ +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Codec.Scale.Class +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- The SCALE (Simple Concatenated Aggregate Little-Endian) Codec is +-- a lightweight, efficient, binary serialization and deserialization codec. +-- +-- It is designed for high-performance, copy-free encoding and decoding of data in +-- resource-constrained execution contexts, like the Substrate runtime. It is not +-- self-describing in any way and assumes the decoding context has all type +-- knowledge about the encoded data. +-- + +module Codec.Scale + ( encode + , decode + , encode' + , decode' + , Encode + , Decode + , Generic + , module Core + ) where + +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) +import Data.Serialize (runGet, runPut) +import Generics.SOP (Generic, Rep, from, to) + +import Codec.Scale.Class (Decode (..), Encode (..), GDecode (..), + GEncode (..)) +import Codec.Scale.Core as Core + +-- | Encode datatype to SCALE format. +encode :: (Encode a, ByteArray ba) + => a + -> ba +{-# INLINE encode #-} +encode = convert . runPut . put + +-- | Generic driven version of 'encode' +encode' :: (Generic a, + Rep a ~ rep, + GEncode rep, + ByteArray ba) + => a + -> ba +{-# INLINE encode' #-} +encode' = convert . runPut . gPut . from + +-- | Decode datatype from SCALE format. +decode :: (ByteArrayAccess ba, Decode a) + => ba + -> Either String a +{-# INLINE decode #-} +decode = runGet get . convert + +-- | Generic driven version of 'decode' +decode' :: (Generic a, + Rep a ~ rep, + GDecode rep, + ByteArrayAccess ba) + => ba + -> Either String a +{-# INLINE decode' #-} +decode' = runGet (to <$> gGet) . convert diff --git a/packages/scale/src/Codec/Scale/Class.hs b/packages/scale/src/Codec/Scale/Class.hs new file mode 100644 index 00000000..7c268398 --- /dev/null +++ b/packages/scale/src/Codec/Scale/Class.hs @@ -0,0 +1,61 @@ +{-# LANGUAGE DefaultSignatures #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Codec.Scale.Class +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- +-- + +module Codec.Scale.Class where + +import Data.Serialize (Get, Putter) +import Generics.SOP (Generic, Rep, from, to) + +-- | A class for encoding datatypes to SCALE format. +-- +-- If your compiler has support for the @DeriveGeneric@ and +-- @DefaultSignatures@ language extensions (@ghc >= 7.2.1@), +-- the 'put' method will have default generic implementations. +-- +-- To use this option, simply add a @deriving 'Generic'@ clause +-- to your datatype and declare a 'Encode' instance for it without +-- giving a definition for 'put'. +-- +class Encode a where + put :: Putter a + + default put :: (Generic a, Rep a ~ rep, GEncode rep) => Putter a + put = gPut . from + +-- | A class for encoding generically composed datatypes to SCALE format. +class GEncode a where + gPut :: Putter a + +-- | A class for decoding datatypes from SCALE format. +-- +-- If your compiler has support for the @DeriveGeneric@ and +-- @DefaultSignatures@ language extensions (@ghc >= 7.2.1@), +-- the 'get' method will have default generic implementations. +-- +-- To use this option, simply add a @deriving 'Generic'@ clause +-- to your datatype and declare a 'Decode' instance for it without +-- giving a definition for 'get'. +-- +class Decode a where + get :: Get a + + default get :: (Generic a, Rep a ~ rep, GDecode rep) => Get a + get = to <$> gGet + +-- | A class for decoding generically composed datatypes from SCALE format. +class GDecode a where + gGet :: Get a diff --git a/packages/scale/src/Codec/Scale/Compact.hs b/packages/scale/src/Codec/Scale/Compact.hs new file mode 100644 index 00000000..7268a455 --- /dev/null +++ b/packages/scale/src/Codec/Scale/Compact.hs @@ -0,0 +1,70 @@ +-- | +-- Module : Codec.Scale.Compact +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Efficient general integer codec. +-- + +module Codec.Scale.Compact (Compact(..)) where + +import Control.Monad (replicateM) +import Data.Bits (shiftL, shiftR, (.&.), (.|.)) +import Data.List (unfoldr) +import Data.Serialize.Get (getWord16le, getWord32le, getWord8, + lookAhead) +import Data.Serialize.Put (putWord16le, putWord32le, putWord8) + +import Codec.Scale.Class (Decode (..), Encode (..)) + +-- | A "compact" or general integer encoding is sufficient for encoding +-- large integers (up to 2**536) and is more efficient at encoding most +-- values than the fixed-width version. +newtype Compact a = Compact { unCompact :: a } + deriving (Eq, Ord) + +instance Show a => Show (Compact a) where + show = ("Compact " ++) . show . unCompact + +instance Integral a => Encode (Compact a) where + put (Compact x) + | n < 0 = error "negatives not supported by compact codec" + | n < 64 = singleByteMode + | n < 2^14 = twoByteMode + | n < 2^30 = fourByteMode + | n < 2^536 = bigIntegerMode + | otherwise = error $ "unable to encode " ++ show n ++ " as compact" + where + n = toInteger x + singleByteMode = putWord8 (fromIntegral x `shiftL` 2) + twoByteMode = putWord16le (fromIntegral x `shiftL` 2 .|. 1) + fourByteMode = putWord32le (fromIntegral x `shiftL` 2 .|. 2) + bigIntegerMode = do + let step 0 = Nothing + step i = Just (fromIntegral i, i `shiftR` 8) + unroll = unfoldr step n + putWord8 (fromIntegral (length unroll - 4) `shiftL` 2 .|. 3) + mapM_ putWord8 unroll + +instance Integral a => Decode (Compact a) where + get = do + mode <- lookAhead ((3 .&.) <$> getWord8) + Compact <$> case mode of + 0 -> fromIntegral <$> singleByteMode + 1 -> fromIntegral <$> twoByteMode + 2 -> fromIntegral <$> fourByteMode + 3 -> bigIntegerMode + _ -> fail "unexpected prefix decoding compact number" + where + singleByteMode = flip shiftR 2 <$> getWord8 + twoByteMode = flip shiftR 2 <$> getWord16le + fourByteMode = flip shiftR 2 <$> getWord32le + bigIntegerMode = do + let unstep b a = a `shiftL` 8 .|. fromIntegral b + roll = fromInteger . foldr unstep 0 + len <- ((+4) . flip shiftR 2) <$> getWord8 + roll <$> replicateM (fromIntegral len) getWord8 diff --git a/packages/scale/src/Codec/Scale/Core.hs b/packages/scale/src/Codec/Scale/Core.hs new file mode 100644 index 00000000..79aeb9d0 --- /dev/null +++ b/packages/scale/src/Codec/Scale/Core.hs @@ -0,0 +1,237 @@ +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Codec.Scale.Core +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Particular core type instances. +-- + +module Codec.Scale.Core (Compact(..)) where + +import Control.Monad (replicateM) +import Data.Bit (Bit, castFromWords8, cloneToWords8) +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS (length) +import Data.Int (Int16, Int32, Int64, Int8) +import Data.Serialize.Get (getByteString, getInt16le, getInt32le, + getInt64le, getInt8, getWord16le, + getWord32le, getWord64le, getWord8) +import Data.Serialize.Put (putByteString, putInt16le, putInt32le, + putInt64le, putInt8, putWord16le, + putWord32le, putWord64le, putWord8) +import Data.Text (Text) +import Data.Text.Encoding (decodeUtf8', encodeUtf8) +import Data.Vector.Unboxed (Unbox, Vector) +import qualified Data.Vector.Unboxed as V +import Data.Word (Word16, Word32, Word64, Word8) +import Generics.SOP () + +import Codec.Scale.Class (Decode (..), Encode (..)) +import Codec.Scale.Compact (Compact (..)) +import Codec.Scale.Generic () +import Codec.Scale.TH (tupleInstances) + +-- +-- Empty instance. +-- + +instance Encode () where + put = return + +instance Decode () where + get = return () + +-- +-- Boolean instance. +-- + +instance Encode Bool where + put False = putWord8 0 + put True = putWord8 1 + +instance Decode Bool where + get = do x <- getWord8 + case x of + 0 -> return False + 1 -> return True + _ -> fail "invalid boolean representation" + +-- +-- Integer instances. +-- + +instance Encode Word8 where + put = putWord8 + +instance Decode Word8 where + get = getWord8 + +instance Encode Word16 where + put = putWord16le + +instance Decode Word16 where + get = getWord16le + +instance Encode Word32 where + put = putWord32le + +instance Decode Word32 where + get = getWord32le + +instance Encode Word64 where + put = putWord64le + +instance Decode Word64 where + get = getWord64le + +instance Encode Int8 where + put = putInt8 + +instance Decode Int8 where + get = getInt8 + +instance Encode Int16 where + put = putInt16le + +instance Decode Int16 where + get = getInt16le + +instance Encode Int32 where + put = putInt32le + +instance Decode Int32 where + get = getInt32le + +instance Encode Int64 where + put = putInt64le + +instance Decode Int64 where + get = getInt64le + +-- +-- Option type instances. +-- + +-- Let's map `Maybe a` type to Rust `Option`: Just -> Some, Nothing -> None + +instance Encode a => Encode (Maybe a) where + put (Just a) = putWord8 1 >> put a + put Nothing = putWord8 0 + +instance Decode a => Decode (Maybe a) where + get = do + x <- getWord8 + case x of + 0 -> return Nothing + 1 -> Just <$> get + _ -> fail "unexpecded first byte decoding Option" + +-- Option is exception and it is always one byte + +instance {-# OVERLAPPING #-} Encode (Maybe Bool) where + put Nothing = putWord8 0 + put (Just False) = putWord8 1 + put (Just True) = putWord8 2 + +instance {-# OVERLAPPING #-} Decode (Maybe Bool) where + get = do + x <- getWord8 + case x of + 0 -> return Nothing + 1 -> return (Just False) + 2 -> return (Just True) + _ -> fail "unexpecded first byte decoding OptionBool" + +-- +-- Result type isntances. +-- + +-- Let's map `Ether a b` type to Rust `Result`: Left -> Error, Right -> Ok + +instance (Encode a, Encode b) => Encode (Either a b) where + put (Right a) = putWord8 0 >> put a + put (Left a) = putWord8 1 >> put a + +instance (Decode a, Decode b) => Decode (Either a b) where + get = do + x <- getWord8 + case x of + 0 -> Right <$> get + 1 -> Left <$> get + _ -> fail "unexpected first byte decoding Result" + + +-- +-- Tuple type instances. +-- + +$(concat <$> mapM tupleInstances [2..20]) + +-- +-- Vector type instances. +-- + +instance Encode a => Encode [a] where + put list = do + put (Compact $ length list) + mapM_ put list + +instance Decode a => Decode [a] where + get = do + len <- get + replicateM (unCompact len) get + +instance (Encode a, Unbox a) => Encode (Vector a) where + put vec = do + put (Compact $ V.length vec) + V.mapM_ put vec + +instance (Decode a, Unbox a) => Decode (Vector a) where + get = do + len <- get + V.replicateM (unCompact len) get + +instance {-# OVERLAPPING #-} Encode (Vector Bit) where + put vec = do + let encoded = cloneToWords8 vec + put (Compact $ V.length encoded) + V.mapM_ put encoded + +instance {-# OVERLAPPING #-} Decode (Vector Bit) where + get = do + len <- get + castFromWords8 <$> V.replicateM (unCompact len) get + +instance Encode ByteString where + put bs = do + put (Compact $ BS.length bs) + putByteString bs + +instance Decode ByteString where + get = do + len <- get + getByteString (unCompact len) + +-- +-- Text type instances. +-- + +instance Encode Text where + put str = do + let encoded = encodeUtf8 str + put (Compact $ BS.length encoded) + putByteString encoded + +instance Decode Text where + get = do + len <- get + str <- getByteString (unCompact len) + either (fail . show) return (decodeUtf8' str) diff --git a/packages/scale/src/Codec/Scale/Generic.hs b/packages/scale/src/Codec/Scale/Generic.hs new file mode 100644 index 00000000..9e927f15 --- /dev/null +++ b/packages/scale/src/Codec/Scale/Generic.hs @@ -0,0 +1,89 @@ +{-# LANGUAGE BangPatterns #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE RankNTypes #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeInType #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Codec.Scale.Generic +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- This module defines generic codec instances for data structures (including tuples) +-- and enums (tagged-unions in Rust). +-- + +module Codec.Scale.Generic () where + +import Data.Serialize.Get (Get, getWord8) +import Data.Serialize.Put (PutM, putWord8) +import Data.Word (Word8) +import Generics.SOP (All, Compose, I (..), NP (..), NS (..), + SOP (..), unSOP, unZ) + +import Codec.Scale.Class (Decode (..), Encode (..), GDecode (..), + GEncode (..)) + +-- Enum has multiple sum types. +instance ( GEncode (NP f xs) + , GEncode (NP f ys) + , All (GEncode `Compose` NP f) xss + ) => GEncode (SOP f (xs ': ys ': xss)) where + gPut = go 0 . unSOP + where + go :: forall f as . All (GEncode `Compose` f) as => Word8 -> NS f as -> PutM () + go !acc (Z x) = putWord8 acc >> gPut x + go !acc (S x) = go (acc + 1) x + +-- Structures has only one sum type. +instance GEncode (NP f xs) => GEncode (SOP f '[xs]) where + gPut = gPut . unZ . unSOP + +-- Product serialization is just encode each field step by step. +instance (Encode a, GEncode (NP I as)) => GEncode (NP I (a ': as)) where + gPut (I a :* as) = put a >> gPut as + +-- Finish when all fields handled. +instance GEncode (NP I '[]) where + gPut _ = mempty + +-- | Enum parser definition. +-- +-- The index of sum type to parse given as an argument. +class EnumParser xs where + enumParser :: All (GDecode `Compose` NP f) xs => Word8 -> Get (NS (NP f) xs) + +-- Enumerate enum index, zero means that we reach the goal. +instance EnumParser as => EnumParser (a ': as) where + enumParser !i | i > 0 = S <$> enumParser (i - 1) + | otherwise = Z <$> gGet + +-- When index out of type scope raise the error. +instance EnumParser '[] where + enumParser i = fail ("index out of enum constructors count: " ++ show i) + +-- Decode enum when multiple sum types. +instance ( GDecode (NP f xs) + , GDecode (NP f ys) + , All (GDecode `Compose` NP f) xss + , EnumParser xss + ) => GDecode (SOP f (xs ': ys ': xss)) where + gGet = SOP <$> (enumParser =<< getWord8) + +-- Decode plain structure when only one sum type. +instance GDecode (NP f as) => GDecode (SOP f '[as]) where + gGet = SOP . Z <$> gGet + +-- Decode each field in sequence. +instance (Decode a, GDecode (NP I as)) => GDecode (NP I (a ': as)) where + gGet = (:*) <$> (I <$> get) <*> gGet + +-- Finish decoding when empty. +instance GDecode (NP I '[]) where + gGet = return Nil diff --git a/packages/scale/src/Codec/Scale/SingletonEnum.hs b/packages/scale/src/Codec/Scale/SingletonEnum.hs new file mode 100644 index 00000000..e53f0b83 --- /dev/null +++ b/packages/scale/src/Codec/Scale/SingletonEnum.hs @@ -0,0 +1,30 @@ +-- | +-- Module : Codec.Scale.SingletonEnum +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- This type helps to encode/decode singleton Rust enums like: +-- `enum Enum { Data { some_data: u32 } }` +-- + +module Codec.Scale.SingletonEnum (SingletonEnum(..)) where + +import Data.Serialize.Get (getWord8) +import Data.Serialize.Put (putWord8) + +import Codec.Scale.Class (Decode (..), Encode (..)) + +-- | Haskell don't permit to make Rust-like enum type with only one element. +-- For this reason it is impossible to make generic parser for singleton enum type. +-- This type helps to parse Rust encoded singleton enums. +newtype SingletonEnum a = SingletonEnum { unSingletonEnum :: a } + +instance Encode a => Encode (SingletonEnum a) where + put (SingletonEnum x) = putWord8 0 >> put x + +instance Decode a => Decode (SingletonEnum a) where + get = getWord8 >> (SingletonEnum <$> get) diff --git a/packages/scale/src/Codec/Scale/Skip.hs b/packages/scale/src/Codec/Scale/Skip.hs new file mode 100644 index 00000000..33f842d5 --- /dev/null +++ b/packages/scale/src/Codec/Scale/Skip.hs @@ -0,0 +1,32 @@ +-- | +-- Module : Codec.Scale.Skip +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- This type helps to skip fields in encoded data type. +-- + +module Codec.Scale.Skip (Skip(..)) where + +import Data.Default (Default (..)) + +import Codec.Scale.Class (Decode (..), Encode (..)) + +-- | This type hide filed from encoding context. +-- It's useful in cases when serialization impossible or not needed. +-- For decoding wrapped type should have 'Default' instance. +newtype Skip a = Skip { unSkip :: a } + deriving (Eq, Ord, Show) + +instance Encode (Skip a) where + put _ = return () + +instance Default a => Decode (Skip a) where + get = return def + +instance Default a => Default (Skip a) where + def = Skip def diff --git a/packages/scale/src/Codec/Scale/TH.hs b/packages/scale/src/Codec/Scale/TH.hs new file mode 100644 index 00000000..7f24ec75 --- /dev/null +++ b/packages/scale/src/Codec/Scale/TH.hs @@ -0,0 +1,31 @@ +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Codec.Scale.TH +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- It contains template haskell SCALE helper functions. +-- + +module Codec.Scale.TH where + + +import Control.Monad (replicateM) +import Language.Haskell.TH (DecsQ, Type (VarT), appT, conT, cxt, + instanceD, newName, tupleT) + +import Codec.Scale.Class (Decode, Encode) + +tupleInstances :: Int -> DecsQ +tupleInstances n = do + vars <- replicateM n $ newName "a" + let types = fmap (pure . VarT) vars + sequence $ + [ instanceD (cxt $ map (appT $ conT ''Decode) types) (appT (conT ''Decode) (foldl appT (tupleT n) types)) [] + , instanceD (cxt $ map (appT $ conT ''Encode) types) (appT (conT ''Encode) (foldl appT (tupleT n) types)) [] + ] diff --git a/packages/scale/tests/Codec/Scale/Test/CoreSpec.hs b/packages/scale/tests/Codec/Scale/Test/CoreSpec.hs new file mode 100644 index 00000000..ed7272f7 --- /dev/null +++ b/packages/scale/tests/Codec/Scale/Test/CoreSpec.hs @@ -0,0 +1,258 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Codec.Scale.Test.CoreSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ported to Haskell rust test spec: +-- https://github.com/paritytech/parity-scale-codec/blob/master/tests/single_field_struct_encoding.rs +-- + +module Codec.Scale.Test.CoreSpec where + +import Control.Monad (forM_) +import Data.Bit (castFromWords8) +import Data.Bits (bit) +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS (length, pack, unpack) +import Data.Int (Int16, Int32, Int64, Int8) +import qualified Data.Text as T (pack) +import Data.Vector.Unboxed (Vector) +import qualified Data.Vector.Unboxed as V (fromList) +import Data.Word (Word16, Word32, Word64, Word8) +import qualified GHC.Generics as GHC (Generic) +import Test.Hspec +import Test.Hspec.QuickCheck + +import Codec.Scale + +data Unit = Unit + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data Indexed = Indexed Word32 Word64 + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data Struct a b c = Struct + { _a :: a + , _b :: b + , _c :: c + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data StructWithPhantom a = StructWithPhantom + { a1 :: Word32 + , b1 :: Word64 + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +type TestType = Struct Word32 Word64 (Vector Word8); + +data EnumType = A + | B Word32 Word64 + | C + { a2 :: Word32 + , b2 :: Word64 + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data TestHasCompact a = TestHasCompact + { bar1 :: Compact a + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data TestHasCompactEnum a = Unnamed (Compact a) + | Named + { bar2 :: Compact a + } + | UnnamedCompact (Compact a) + | NamedCompact + { bar3 :: Compact a + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data TestGenericEnum = UnnamedGenericEnum (Compact Integer) (Vector Word16) + | NamedGenericEnum + { bar5 :: Compact Word64 + , bar6 :: Word32 + } + deriving (Eq, Show, GHC.Generic, Generic) + +data RecursiveVariant1 a = RecursiveVariant1 + { payload1 :: a + , other1 :: [RecursiveVariant1 a] + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +data RecursiveVariant2 a b n = RecursiveVariant2 + { payload2 :: n + , other2 :: [Struct a b (RecursiveVariant1 n)] + } + deriving (Eq, Show, GHC.Generic, Generic, Encode, Decode) + +spec :: Spec +spec = parallel $ do + describe "Regular types" $ do + prop "Bool" $ \(v :: Bool) -> decode (encode v :: ByteString) == Right v + + prop "Option" $ \(v :: Maybe Bool) -> decode (encode v :: ByteString) == Right v + + prop "Result>" $ \v vec -> do + let success = Right v :: Either (Vector Word8) Bool + failure = Left (V.fromList vec) :: Either (Vector Word8) Bool + decode (encode success :: ByteString) == Right success + && decode (encode failure :: ByteString) == Right failure + + prop "u64" $ \(v :: Word64) -> decode (encode v :: ByteString) == Right v + prop "u32" $ \(v :: Word32) -> decode (encode v :: ByteString) == Right v + prop "u16" $ \(v :: Word16) -> decode (encode v :: ByteString) == Right v + prop "u8" $ \(v :: Word8) -> decode (encode v :: ByteString) == Right v + + prop "i64" $ \(v :: Int64) -> decode (encode v :: ByteString) == Right v + prop "i32" $ \(v :: Int32) -> decode (encode v :: ByteString) == Right v + prop "i16" $ \(v :: Int16) -> decode (encode v :: ByteString) == Right v + prop "i8" $ \(v :: Int8) -> decode (encode v :: ByteString) == Right v + + prop "Compact" $ \(v :: Integer) -> decode (encode (Compact $ abs v) :: ByteString) == Right (Compact $ abs v) + prop "Compact" $ \(v :: Word64) -> decode (encode (Compact v) :: ByteString) == Right (Compact v) + prop "Compact" $ \(v :: Word32) -> decode (encode (Compact v) :: ByteString) == Right (Compact v) + prop "Compact" $ \(v :: Word16) -> decode (encode (Compact v) :: ByteString) == Right (Compact v) + prop "Compact" $ \(v :: Word8) -> decode (encode (Compact v) :: ByteString) == Right (Compact v) + + prop "Vector" $ \(v :: [Word64]) -> decode (encode (V.fromList v) :: ByteString) == Right v + prop "Vector" $ \(v :: [Word32]) -> decode (encode (V.fromList v) :: ByteString) == Right v + prop "Vector" $ \(v :: [Word16]) -> decode (encode (V.fromList v) :: ByteString) == Right v + prop "Vector" $ \(v :: [Word8]) -> decode (encode (V.fromList v) :: ByteString) == Right v + + prop "BitVec" $ \(v :: [Word8]) -> decode (encode $ castFromWords8 $ V.fromList v :: ByteString) == Right v + + prop "ByteString" $ \(v :: [Word8]) -> decode (encode (BS.pack v) :: ByteString) == Right (BS.pack v) + + prop "Text" $ \(v :: String) -> decode (encode (T.pack v) :: ByteString) == Right (T.pack v) + + prop "List" $ \(v :: [Word64]) -> decode (encode v :: ByteString) == Right v + prop "List" $ \(v :: [Word32]) -> decode (encode v :: ByteString) == Right v + prop "List" $ \(v :: [Word16]) -> decode (encode v :: ByteString) == Right v + prop "List" $ \(v :: [Word8]) -> decode (encode v :: ByteString) == Right v + + describe "Generic types" $ do + prop "unamed_enum" $ \v vec -> + let e = UnnamedGenericEnum (Compact $ abs v) (V.fromList vec) + in decode' (encode' e :: ByteString) == Right e + prop "named_struct_enum" $ \a b -> + let e = NamedGenericEnum (Compact a) b + in decode' (encode' e :: ByteString) == Right e + + describe "Recursive types" $ do + prop "variant_1" $ \(n :: Word32) -> + let v = RecursiveVariant1 n [RecursiveVariant1 (n+1) []] + in decode (encode v :: ByteString) == Right v + + prop "variant_2" $ \(a :: Word8) (b :: Word16) (n :: Word32) -> + let v = RecursiveVariant2 n [Struct a b (RecursiveVariant1 (n+1) [])] + in decode (encode v :: ByteString) == Right v + + describe "SCALE Rust core tests" $ do + it "option_excheption_works" $ do + encode (Nothing :: Maybe Bool) `shouldBe` ("\0" :: ByteString) + encode (Just False) `shouldBe` ("\x01" :: ByteString) + encode (Just True) `shouldBe` ("\x02" :: ByteString) + + it "should_work_for_simple_enum" $ do + -- Index modificator isn't support yet, skip codec test for A + let sb = B 1 2 + sc = C 1 2 + encoded_b = "\x01\x01\0\0\0\x02\0\0\0\0\0\0\0" :: ByteString + encoded_c = "\x02\x01\0\0\0\x02\0\0\0\0\0\0\0" :: ByteString + + encode sc `shouldBe` encoded_c + encode sb `shouldBe` encoded_b + + decode encoded_b `shouldBe` Right sb + decode encoded_c `shouldBe` Right sc + decode ("\x0a" :: ByteString) `shouldBe` (Left "Failed reading: index out of enum constructors count: 7\nEmpty call stack\n" :: Either String EnumType) + + it "should_derive_encode" $ do + let v :: TestType + v = Struct 15 9 (V.fromList $ BS.unpack "Hello world") + v_encoded :: ByteString + v_encoded = "\x0f\0\0\0\x09\0\0\0\0\0\0\0\x2cHello world" + encode v `shouldBe` v_encoded + Right v `shouldBe` decode v_encoded + + it "should_work_for_unit" $ do + encode Unit `shouldBe` ("" :: ByteString) + decode ("" :: ByteString) `shouldBe` Right Unit + + it "should_work_for_indexed" $ do + let v = Indexed 1 2 + v_encoded :: ByteString + v_encoded = "\x01\0\0\0\x02\0\0\0\0\0\0\0" + encode v `shouldBe` v_encoded + Right v `shouldBe` decode v_encoded + + it "correct_error_for_indexed_0" $ do + let wrong = "\x08" :: ByteString + decode wrong `shouldBe` (Left "too few bytes\nFrom:\tdemandInput\n\n" :: Either String Indexed) + + it "correct_error_for_indexed_1" $ do + let wrong = "\0\0\0\0\x01" :: ByteString + decode wrong `shouldBe` (Left "too few bytes\nFrom:\tdemandInput\n\n" :: Either String Indexed) + + it "correct_error_for_enumtype" $ do + let wrong = "\x01" :: ByteString + decode wrong `shouldBe` (Left "too few bytes\nFrom:\tdemandInput\n\n" :: Either String EnumType) + + it "correct_error_for_named_struct_1" $ do + let wrong = "\x01" :: ByteString + decode wrong `shouldBe` (Left "too few bytes\nFrom:\tdemandInput\n\n" :: Either String TestType) + + it "correct_error_for_named_struct_2" $ do + let wrong = "\0\0\0\0\x01" :: ByteString + decode wrong `shouldBe` (Left "too few bytes\nFrom:\tdemandInput\n\n" :: Either String TestType) + + let u64_TEST_COMPACT_VALUES :: [(Word64, Int)] + u64_TEST_COMPACT_VALUES = + [ (0, 1), (63, 1), (64, 2), (16383, 2) + , (16384, 4), (1073741823, 4), (1073741824, 5) + , (bit 32 - 1, 5), (bit 32, 6), (bit 40, 7) + , (bit 48, 8), (bit 56 - 1, 8), (bit 56, 9) + , (maxBound, 9) + ] + + it "compact_works" $ forM_ u64_TEST_COMPACT_VALUES $ \(n, l) -> do + let encoded = encode (TestHasCompact $ Compact n) + BS.length encoded `shouldBe` l + decode encoded `shouldBe` Right (Compact n) + + let u64_TEST_COMPACT_VALUES_FOR_ENUM :: [(Word64, Int)] + u64_TEST_COMPACT_VALUES_FOR_ENUM = + [ (0, 2), (63, 2), (64, 3), (16383, 3), (16384, 5) + , (1073741823, 5), (1073741824, 6), (bit 32 - 1, 6) + , (bit 32, 7), (bit 40, 8), (bit 48, 9), (bit 56 - 1, 9) + , (bit 56, 10), (maxBound, 10) + ] + + it "enum_compact_works" $ forM_ u64_TEST_COMPACT_VALUES_FOR_ENUM $ \(x, l) -> do + let u = encode $ Unnamed (Compact x) + BS.length u `shouldBe` l + decode u `shouldBe` Right (Unnamed $ Compact x) + + let n = encode $ Named (Compact x) + BS.length n `shouldBe` l + decode n `shouldBe` Right (Named $ Compact x) + + let uc = encode $ UnnamedCompact (Compact x) + BS.length uc `shouldBe` l + decode uc `shouldBe` Right (UnnamedCompact $ Compact x) + + let nc = encode $ NamedCompact (Compact x) + BS.length nc `shouldBe` l + decode nc `shouldBe` Right (NamedCompact $ Compact x) diff --git a/packages/scale/tests/Codec/Scale/Test/SingleFieldStructSpec.hs b/packages/scale/tests/Codec/Scale/Test/SingleFieldStructSpec.hs new file mode 100644 index 00000000..fce4e88e --- /dev/null +++ b/packages/scale/tests/Codec/Scale/Test/SingleFieldStructSpec.hs @@ -0,0 +1,105 @@ +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Codec.Scale.Test.SingleFieldStructSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ported to Haskell rust test spec: +-- https://github.com/paritytech/parity-scale-codec/blob/master/tests/single_field_struct_encoding.rs +-- + +module Codec.Scale.Test.SingleFieldStructSpec where + +import Data.ByteString as BS (pack) +import Data.Default (def) +import Data.Word (Word32, Word64) +import qualified GHC.Generics as GHC (Generic) +import Test.Hspec + +import Codec.Scale +import Codec.Scale.Skip + +newtype S = S { x1 :: Word32 } + deriving (Eq, Ord, Show, Encode, Decode) + +data SSkip = SSkip + { s1 :: Skip Word32 + , x2 :: Word32 + , s2 :: Skip Word32 + } + deriving (Eq, Ord, Show, GHC.Generic) + +instance Generic SSkip +instance Encode SSkip +instance Decode SSkip + +newtype Sc = Sc { x3 :: Compact Word32 } + deriving (Eq, Ord, Show, Encode, Decode) + +newtype U = U Word32 + deriving (Eq, Ord, Show, Enum, Num, Real, Integral, Encode, Decode) + +newtype U2 = U2 { a :: Word64 } + deriving (Eq, Ord, Show, Encode, Decode) + +data USkip = USkip (Skip Word32) Word32 (Skip Word32) + deriving (Eq, Ord, Show, GHC.Generic) + +instance Generic USkip +instance Encode USkip +instance Decode USkip + +newtype Uc = Uc (Compact Word32) + deriving (Eq, Ord, Show, Encode, Decode) + +newtype Ucas = Ucas (Compact U) + deriving (Eq, Ord, Show, Encode, Decode) + +spec :: Spec +spec = parallel $ do + describe "Single field struct encoding" $ do + let x = 3 + s = S x + s_skip = SSkip def x def + sc = Sc (Compact x) + u = U x + u_skip = USkip def x def + uc = Uc (Compact x) + ucom = Compact u + ucas = Ucas (Compact u) + + s_encoded = BS.pack [3, 0, 0, 0] + s_skip_encoded = BS.pack [3, 0, 0, 0] + sc_encoded = BS.pack [12] + u_encoded = BS.pack [3, 0, 0, 0] + u_skip_encoded = BS.pack [3, 0, 0, 0] + uc_encoded = BS.pack [12] + ucom_encoded = BS.pack [12] + ucas_encoded = BS.pack [12] + + it "encoding" $ do + encode s `shouldBe` s_encoded + encode s_skip `shouldBe` s_skip_encoded + encode sc `shouldBe` sc_encoded + encode u `shouldBe` u_encoded + encode u_skip `shouldBe` u_skip_encoded + encode uc `shouldBe` uc_encoded + encode ucom `shouldBe` ucom_encoded + encode ucas `shouldBe` ucas_encoded + + it "decoding" $ do + Right s `shouldBe` decode s_encoded + Right s_skip `shouldBe` decode s_skip_encoded + Right sc `shouldBe` decode sc_encoded + Right u `shouldBe` decode u_encoded + Right u_skip `shouldBe` decode u_skip_encoded + Right uc `shouldBe` decode uc_encoded + Right ucom `shouldBe` decode ucom_encoded + Right ucas `shouldBe` decode ucas_encoded diff --git a/packages/scale/tests/Codec/Scale/Test/SkipSpec.hs b/packages/scale/tests/Codec/Scale/Test/SkipSpec.hs new file mode 100644 index 00000000..4d7dab0a --- /dev/null +++ b/packages/scale/tests/Codec/Scale/Test/SkipSpec.hs @@ -0,0 +1,80 @@ +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Codec.Scale.Test.SkipSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : BSD3 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Ported to Haskell rust test spec: +-- https://github.com/paritytech/parity-scale-codec/blob/master/tests/skip.rs +-- + +module Codec.Scale.Test.SkipSpec where + +import Data.ByteString (ByteString, pack) +import Data.Default (Default) +import Data.Word (Word32) +import qualified GHC.Generics as GHC (Generic) +import Test.Hspec + +import Codec.Scale +import Codec.Scale.SingletonEnum +import Codec.Scale.Skip + +data UncodecType = UncodecType + deriving (Eq, Ord, Show, GHC.Generic, Default) + +-- Implementing A constructor is impossible +data EnumType = B + { _b1 :: Skip UncodecType + , b2 :: Word32 + } + | C (Skip UncodecType) Word32 + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + + +data StructNamed = StructNamed + { a :: Skip UncodecType + , b :: Word32 + } + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +data StructUnnamed = StructUnnamed (Skip UncodecType) Word32 + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +data NamedStruct = NamedStruct + { some_named :: Word32 + , ignore :: Skip (Maybe Word32) + } + deriving (Eq, Ord, Show, GHC.Generic, Generic, Encode, Decode) + +spec :: Spec +spec = parallel $ do + describe "Type encoding modificators" $ do + it "enum_struct_test" $ do + let eb = B { _b1 = Skip UncodecType, b2 = 1 } + ec = C (Skip UncodecType) 1 + sn = StructNamed { a = Skip UncodecType, b = 1 } + su = StructUnnamed (Skip UncodecType) 1 + + let eb_encoded = encode eb :: ByteString + let ec_encoded = encode ec :: ByteString + let sn_encoded = encode sn :: ByteString + let su_encoded = encode su :: ByteString + + decode eb_encoded `shouldBe` Right eb + decode ec_encoded `shouldBe` Right ec + decode sn_encoded `shouldBe` Right sn + decode su_encoded `shouldBe` Right su + + it "skip_enum_struct_inner_variant" $ do + let struct = NamedStruct { some_named = 1, ignore = Skip (Just 1) } + single = SingletonEnum struct + encoded = pack [0x00, 0x01, 0x00, 0x00, 0x00] + encode single `shouldBe` encoded diff --git a/packages/scale/tests/Spec.hs b/packages/scale/tests/Spec.hs new file mode 100644 index 00000000..a824f8c3 --- /dev/null +++ b/packages/scale/tests/Spec.hs @@ -0,0 +1 @@ +{-# OPTIONS_GHC -F -pgmF hspec-discover #-} diff --git a/packages/solidity/LICENSE b/packages/solidity/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/solidity/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/solidity/Setup.hs b/packages/solidity/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/solidity/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/solidity/package.yaml b/packages/solidity/package.yaml new file mode 100644 index 00000000..d90bc160 --- /dev/null +++ b/packages/solidity/package.yaml @@ -0,0 +1,72 @@ +name: web3-solidity +version: 1.1.0.0 +synopsis: Solidity language for Haskell Web3 library. +description: This package contains Solidity parsec-based parser and primitive types. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- text >=1.2 && <2.2 +- aeson >=1.2 && <2.3 +- cereal >=0.5 && <0.6 +- memory >=0.14 && <0.19 +- memory-hexstring >=1.0 && <1.2 +- tagged >=0.8 && <0.9 +- parsec >=3.1 && <3.2 +- basement >=0.0 && <0.1 +- OneTuple >=0.2 && <0.5 +- microlens >=0.4 && <0.5 +- bytestring >=0.10 && <0.13 +- generics-sop >=0.3 && <0.6 +- data-default >=0.7 && <0.9 +- template-haskell >=2.11 && <2.23 +- web3-crypto >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src + +tests: + tests: + main: Spec.hs + source-dirs: + - tests + - src + dependencies: + - hspec-expectations >=0.8.2 && <0.9 + - hspec-discover >=2.4.4 && <2.12 + - hspec-contrib >=0.4.0 && <0.6 + - hspec >=2.4.4 && <2.12 + ghc-options: + - -threaded + - -rtsopts + - -with-rtsopts=-N diff --git a/src/Network/Ethereum/ABI/Class.hs b/packages/solidity/src/Data/Solidity/Abi.hs similarity index 61% rename from src/Network/Ethereum/ABI/Class.hs rename to packages/solidity/src/Data/Solidity/Abi.hs index 9735183f..402175d3 100644 --- a/src/Network/Ethereum/ABI/Class.hs +++ b/packages/solidity/src/Data/Solidity/Abi.hs @@ -1,33 +1,31 @@ {-# LANGUAGE DefaultSignatures #-} {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} -- | --- Module : Network.Ethereum.ABI.Class --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 +-- Module : Data.Solidity.Abi +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental -- Portability : noportable -- --- Ethereum ABI encoding base type classes. +-- The Application Binary Interface is the standard way to interact with contracts +-- in the Ethereum ecosystem, both from outside the blockchain and for contract-to-contract +-- interaction. Data is encoded according to its type, as described in this specification. +-- The encoding is not self describing and thus requires a schema in order to decode. -- -module Network.Ethereum.ABI.Class ( - ABIType(..) - , ABIPut(..) - , ABIGet(..) - , GenericABIPut(..) - , GenericABIGet(..) - ) where +module Data.Solidity.Abi where import Data.Proxy (Proxy) import Data.Serialize (Get, Putter) import Generics.SOP (Generic, Rep, from, to) -- | A class for abi encoding datatype descriptions -class ABIType a where +class AbiType a where isDynamic :: Proxy a -> Bool -- | A class for encoding datatypes to their abi encoding @@ -37,17 +35,17 @@ class ABIType a where -- the 'abiPut' method will have default generic implementations. -- -- To use this option, simply add a @deriving 'Generic'@ clause --- to your datatype and declare a 'ABIPut' instance for it without +-- to your datatype and declare a 'AbiPut' instance for it without -- giving a definition for 'abiPut'. -- -class ABIType a => ABIPut a where +class AbiType a => AbiPut a where abiPut :: Putter a - default abiPut :: (Generic a, Rep a ~ rep, GenericABIPut rep) => Putter a + default abiPut :: (Generic a, Rep a ~ rep, GenericAbiPut rep) => Putter a abiPut = gAbiPut . from -- | A class for encoding generically composed datatypes to their abi encoding -class GenericABIPut a where +class GenericAbiPut a where gAbiPut :: Putter a -- | A class for decoding datatypes from their abi encoding @@ -57,15 +55,15 @@ class GenericABIPut a where -- the 'abiGet' method will have default generic implementations. -- -- To use this option, simply add a @deriving 'Generic'@ clause --- to your datatype and declare a 'ABIGet' instance for it without +-- to your datatype and declare a 'AbiGet' instance for it without -- giving a definition for 'abiGet'. -- -class ABIType a => ABIGet a where +class AbiType a => AbiGet a where abiGet :: Get a - default abiGet :: (Generic a, Rep a ~ rep, GenericABIGet rep) => Get a + default abiGet :: (Generic a, Rep a ~ rep, GenericAbiGet rep) => Get a abiGet = to <$> gAbiGet -- | A class for decoding generically composed datatypes from their abi encoding -class GenericABIGet a where +class GenericAbiGet a where gAbiGet :: Get a diff --git a/packages/solidity/src/Data/Solidity/Abi/Codec.hs b/packages/solidity/src/Data/Solidity/Abi/Codec.hs new file mode 100644 index 00000000..13e3346f --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Abi/Codec.hs @@ -0,0 +1,71 @@ +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Data.Solidity.Abi.Codec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Solidity contract ABI encoding functions. +-- + +module Data.Solidity.Abi.Codec + ( + -- * @AbiPut@/@AbiGet@ type class encoding + encode + , decode + + -- * Generic encoding + , encode' + , decode' + + -- * Generic type re-export + , Generic + ) where + +import Data.ByteArray (ByteArray, ByteArrayAccess, convert) +import Data.Serialize (runGet, runPut) +import Generics.SOP (Generic, Rep, from, to) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), + GenericAbiGet (..), + GenericAbiPut (..)) +import Data.Solidity.Abi.Generic () + +-- | Encode datatype to Ethereum Abi-encoding +encode :: (AbiPut a, ByteArray ba) + => a + -> ba +{-# INLINE encode #-} +encode = convert . runPut . abiPut + +-- | Generic driven version of 'encode' +encode' :: (Generic a, + Rep a ~ rep, + GenericAbiPut rep, + ByteArray ba) + => a + -> ba +{-# INLINE encode' #-} +encode' = convert . runPut . gAbiPut . from + +-- | Decode datatype from Ethereum Abi-encoding +decode :: (ByteArrayAccess ba, AbiGet a) + => ba + -> Either String a +{-# INLINE decode #-} +decode = runGet abiGet . convert + +-- | Generic driven version of 'decode' +decode' :: (Generic a, + Rep a ~ rep, + GenericAbiGet rep, + ByteArrayAccess ba) + => ba + -> Either String a +{-# INLINE decode' #-} +decode' = runGet (to <$> gAbiGet) . convert diff --git a/packages/solidity/src/Data/Solidity/Abi/Generic.hs b/packages/solidity/src/Data/Solidity/Abi/Generic.hs new file mode 100644 index 00000000..4b3f9b9a --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Abi/Generic.hs @@ -0,0 +1,134 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeInType #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Data.Solidity.Abi.Generic +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- This module is internal, the purpose is to define helper classes and functions +-- to assist in encoding and decoding Solidity types for function calls and events. +-- The user of this library should have no need to use this directly in application code. +-- + +module Data.Solidity.Abi.Generic () where + +import qualified Data.ByteString.Lazy as LBS +import Data.Int (Int64) +import qualified Data.List as L +import Data.Proxy (Proxy (..)) +import Data.Serialize (Get, Put) +import Data.Serialize.Get (bytesRead, lookAheadE, skip) +import Data.Serialize.Put (runPutLazy) +import Generics.SOP (I (..), NP (..), NS (..), SOP (..)) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), AbiType (..), + GenericAbiGet (..), GenericAbiPut (..)) +import Data.Solidity.Prim.Int (getWord256, putWord256) + +data EncodedValue = EncodedValue + { evOrder :: Int64 + , evIsDynamic :: Bool + , evEncoding :: Put + , evEncodingLengthInBytes :: Int64 -- cache + } + +instance Eq EncodedValue where + ev1 == ev2 = evOrder ev1 == evOrder ev2 + +instance Ord EncodedValue where + compare ev1 ev2 = evOrder ev1 `compare` evOrder ev2 + +-- from https://docs.soliditylang.org/en/v0.8.12/abi-spec.html#examples +-- +-- if Ti is static: +-- head(X(i)) = enc(X(i)) and tail(X(i)) = "" (the empty string) +-- otherwise, i.e. if Ti is dynamic: +-- head(X(i)) = enc(len( head(X(1)) ... head(X(k)) tail(X(1)) ... tail(X(i-1)) )) tail(X(i)) = enc(X(i)) +combineEncodedValues :: [EncodedValue] -> Put +combineEncodedValues encodings = + let sortedEncodings = L.sort encodings + + wordLengthInBytes :: Int64 + wordLengthInBytes = 32 + + headsOffsetInBytes :: Int64 + headsOffsetInBytes = foldl (+) 0 $ map (\EncodedValue{..} -> if evIsDynamic then wordLengthInBytes else evEncodingLengthInBytes) encodings + + heads = fst $ foldl + (\(accumulator, lengthOfPreviousDynamicValues) EncodedValue{..} -> if evIsDynamic + then ( accumulator <> putWord256 (fromIntegral $ headsOffsetInBytes + lengthOfPreviousDynamicValues) + , lengthOfPreviousDynamicValues + evEncodingLengthInBytes + ) + else ( accumulator <> evEncoding + , lengthOfPreviousDynamicValues + ) + ) + (mempty, 0) + sortedEncodings + tails = foldMap + (\EncodedValue{..} -> if evIsDynamic + then evEncoding + else mempty + ) + sortedEncodings + in heads <> tails + where + +-- aIsDynamic is a variable because of https://github.com/airalab/hs-web3/pull/129#issuecomment-1074045478 +-- TODO: call the `isDynamic` function in the `mkEncodedValue` function +mkEncodedValue :: (AbiType a, AbiPut a) => [EncodedValue] -> a -> Bool -> EncodedValue +mkEncodedValue otherEncodedArray a aIsDynamic = + let encoding = abiPut a + in EncodedValue + { evEncoding = encoding + , evOrder = fromInteger . toInteger . L.length $ otherEncodedArray + , evIsDynamic = aIsDynamic + , evEncodingLengthInBytes = lengthInBytes encoding + } + where + lengthInBytes :: Put -> Int64 + lengthInBytes e = LBS.length . runPutLazy $ e + +class AbiData a where + _serialize :: [EncodedValue] -> a -> [EncodedValue] + +instance AbiData (NP f '[]) where + _serialize encoded _ = encoded + +instance (AbiType b, AbiPut b, AbiData (NP I as)) => AbiData (NP I (b : as)) where + _serialize encoded (I b :* a) = _serialize (mkEncodedValue encoded b (isDynamic (Proxy :: Proxy b)) : encoded) a + +instance AbiData (NP f as) => GenericAbiPut (SOP f '[as]) where + gAbiPut (SOP (Z a)) = combineEncodedValues $ _serialize [] a + gAbiPut _ = error "Impossible branch" + +instance GenericAbiGet (NP f '[]) where + gAbiGet = return Nil + +instance (AbiGet a, GenericAbiGet (NP I as)) => GenericAbiGet (NP I (a : as)) where + gAbiGet = (:*) <$> (I <$> factorParser) <*> gAbiGet + +instance GenericAbiGet (NP f as) => GenericAbiGet (SOP f '[as]) where + gAbiGet = SOP . Z <$> gAbiGet + +factorParser :: forall a . AbiGet a => Get a +factorParser + | not $ isDynamic (Proxy :: Proxy a) = abiGet + | otherwise = do + dataOffset <- fromIntegral <$> getWord256 + currentOffset <- bytesRead + Left x <- lookAheadE $ do + skip (dataOffset - currentOffset) + Left <$> abiGet + return x diff --git a/src/Network/Ethereum/ABI/Event.hs b/packages/solidity/src/Data/Solidity/Event.hs similarity index 70% rename from src/Network/Ethereum/ABI/Event.hs rename to packages/solidity/src/Data/Solidity/Event.hs index e8a026b2..82520bbe 100644 --- a/src/Network/Ethereum/ABI/Event.hs +++ b/packages/solidity/src/Data/Solidity/Event.hs @@ -2,7 +2,6 @@ {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE FunctionalDependencies #-} -{-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE PolyKinds #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE TypeFamilies #-} @@ -10,9 +9,9 @@ {-# LANGUAGE UndecidableInstances #-} -- | --- Module : Network.Ethereum.Web3.Encoding.Event --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 +-- Module : Data.Solidity.Event +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental @@ -24,21 +23,20 @@ -- this directly in application code. -- -module Network.Ethereum.ABI.Event( - DecodeEvent(..) - , IndexedEvent(..) - ) where +module Data.Solidity.Event + ( + DecodeEvent(..) + , IndexedEvent(..) + ) where -import Data.ByteArray (ByteArrayAccess) -import Data.Proxy (Proxy (..)) -import Generics.SOP (Generic, I (..), NP (..), - NS (..), Rep, SOP (..), - from, to) +import Data.ByteArray (ByteArrayAccess) +import Data.Proxy (Proxy (..)) +import Generics.SOP (Generic, I (..), NP (..), + NS (..), Rep, SOP (..), from, to) -import Network.Ethereum.ABI.Class (GenericABIGet) -import Network.Ethereum.ABI.Codec (decode') -import Network.Ethereum.ABI.Event.Internal -import Network.Ethereum.Web3.Types (Change (..)) +import Data.Solidity.Abi (AbiGet) +import Data.Solidity.Abi.Codec (decode) +import Data.Solidity.Event.Internal -- | Indexed event args come back in as a list of encoded values. 'ArrayParser' -- | is used to decode these values so that they can be used to reconstruct the @@ -51,11 +49,11 @@ class ArrayParser a where instance ArrayParser (NP f '[]) where arrayParser _ = Right Nil -instance (ArrayParser (NP I as), Generic a, Rep a ~ rep, GenericABIGet rep) +instance (ArrayParser (NP I as), AbiGet a) => ArrayParser (NP I (a : as)) where arrayParser [] = Left "Empty" arrayParser (a : as) = do - a' <- decode' a + a' <- decode a as' <- arrayParser as return $ I a' :* as' @@ -81,20 +79,21 @@ data Event i ni = Event i ni parseChange :: ( Generic i , Rep i ~ irep , ArrayParser irep - , Generic ni - , Rep ni ~ nirep - , GenericABIGet nirep + , AbiGet ni + , ByteArrayAccess ba ) - => Change + => [ba] + -- ^ event change topics + -> ba + -- ^ event change data -> Bool -- ^ is anonymous event -> Either String (Event i ni) -parseChange change anonymous = - Event <$> genericArrayParser topics <*> decode' data_ +parseChange topics data_ anonymous = + Event <$> genericArrayParser topics' <*> decode data_ where - topics | anonymous = changeTopics change - | otherwise = tail (changeTopics change) - data_ = changeData change + topics' | anonymous = topics + | otherwise = tail topics class IndexedEvent i ni e | e -> i ni where isAnonymous :: Proxy e -> Bool @@ -125,20 +124,20 @@ instance ( Generic i in to . fromHList $ hle class DecodeEvent i ni e | e -> i ni where - decodeEvent :: Change -> Either String e + decodeEvent :: ByteArrayAccess ba => [ba] -> ba -> Either String e instance ( IndexedEvent i ni e , Generic i , Rep i ~ SOP I '[hli] + , AbiGet ni , Generic ni , Rep ni ~ SOP I '[hlni] , Generic e , Rep e ~ SOP I '[hle] , CombineChange i ni e - , GenericABIGet (SOP I '[hlni]) , ArrayParser (SOP I '[hli]) ) => DecodeEvent i ni e where - decodeEvent change = do + decodeEvent topics data_ = do let anonymous = isAnonymous (Proxy :: Proxy e) - (Event i ni :: Event i ni) <- parseChange change anonymous + (Event i ni :: Event i ni) <- parseChange topics data_ anonymous return $ combineChange i ni diff --git a/src/Network/Ethereum/ABI/Event/Internal.hs b/packages/solidity/src/Data/Solidity/Event/Internal.hs similarity index 95% rename from src/Network/Ethereum/ABI/Event/Internal.hs rename to packages/solidity/src/Data/Solidity/Event/Internal.hs index d98fe668..31246d3e 100644 --- a/src/Network/Ethereum/ABI/Event/Internal.hs +++ b/packages/solidity/src/Data/Solidity/Event/Internal.hs @@ -3,7 +3,6 @@ {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE FunctionalDependencies #-} {-# LANGUAGE GADTs #-} -{-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE PolyKinds #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE TypeFamilies #-} @@ -12,9 +11,9 @@ {-# LANGUAGE UndecidableInstances #-} -- | --- Module : Network.Ethereum.ABI.Event.Internal --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 +-- Module : Data.Solidity.Event.Internal +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 -- -- Maintainer : mail@akru.me -- Stability : experimental @@ -25,7 +24,7 @@ -- this directly in application code. -- -module Network.Ethereum.ABI.Event.Internal where +module Data.Solidity.Event.Internal where import Data.Kind (Type) import Data.Proxy (Proxy (..)) diff --git a/packages/solidity/src/Data/Solidity/Prim.hs b/packages/solidity/src/Data/Solidity/Prim.hs new file mode 100644 index 00000000..3185bd7b --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim.hs @@ -0,0 +1,30 @@ +-- | +-- Module : Data.Solidity.Prim +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Solidity primitive data types. +-- + +module Data.Solidity.Prim + ( + Address + , Bytes + , BytesN + , IntN + , UIntN + , ListN + ) where + +import Data.Solidity.Prim.Address (Address) +import Data.Solidity.Prim.Bool () +import Data.Solidity.Prim.Bytes (Bytes, BytesN) +import Data.Solidity.Prim.Int (IntN, UIntN) +import Data.Solidity.Prim.List (ListN) +import Data.Solidity.Prim.String () +import Data.Solidity.Prim.Tagged () +import Data.Solidity.Prim.Tuple () diff --git a/packages/solidity/src/Data/Solidity/Prim/Address.hs b/packages/solidity/src/Data/Solidity/Prim/Address.hs new file mode 100644 index 00000000..934d0e1d --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Address.hs @@ -0,0 +1,123 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.Solidity.Prim.Address +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethreum account address. +-- + +module Data.Solidity.Prim.Address + ( + -- * The @Address@ type + Address + + -- * Hex string encoding + , toHexString + , fromHexString + + -- * Derive address from public key + , fromPubKey + + -- * EIP55 Mix-case checksum address encoding + , toChecksum + , verifyChecksum + ) where + +import Control.Monad ((<=<)) +import Crypto.Ethereum (PublicKey) +import Data.Aeson (FromJSON (..), ToJSON (..)) +import Data.Bits ((.&.)) +import Data.Bool (bool) +import Data.ByteArray (zero) +import qualified Data.ByteArray as BA (drop) +import Data.ByteString (ByteString) +import qualified Data.ByteString as BS (take, unpack) +import qualified Data.ByteString.Char8 as C8 (drop, length, pack, unpack) +import qualified Data.Char as C (toLower, toUpper) +import Data.Default (Default (..)) +import Data.String (IsString (..)) +import Data.Text.Encoding as T (encodeUtf8) +import Generics.SOP (Generic) +import qualified GHC.Generics as GHC (Generic) + +import Crypto.Ecdsa.Utils (exportPubKey) +import Crypto.Ethereum.Utils (keccak256) +import Data.ByteArray.HexString (HexString, fromBytes, toBytes, + toText) +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), + AbiType (..)) +import Data.Solidity.Abi.Codec (decode, encode) +import Data.Solidity.Prim.Int (UIntN) + +-- | Ethereum account address +newtype Address = Address { unAddress :: UIntN 160 } + deriving (Eq, Ord, GHC.Generic) + +instance Generic Address + +instance Default Address where + def = Address 0 + +instance Show Address where + show = show . toChecksum . T.encodeUtf8 . toText . toHexString + +instance IsString Address where + fromString = either error id . fromHexString . fromString + +instance AbiType Address where + isDynamic _ = False + +instance AbiGet Address where + abiGet = Address <$> abiGet + +instance AbiPut Address where + abiPut = abiPut . unAddress + +instance FromJSON Address where + parseJSON = (either fail pure . fromHexString) <=< parseJSON + +instance ToJSON Address where + toJSON = toJSON . toHexString + +-- | Derive address from secp256k1 public key +fromPubKey :: PublicKey -> Address +fromPubKey key = + case decode $ zero 12 <> toAddress (exportPubKey key) of + Right a -> a + Left e -> error $ "Impossible error: " ++ e + where + toAddress :: HexString -> HexString + toAddress = BA.drop 12 . keccak256 + +-- | Decode address from hex string +fromHexString :: HexString -> Either String Address +fromHexString bs + | bslen == 20 = decode (zero 12 <> toBytes bs :: ByteString) + | otherwise = Left $ "Incorrect address length: " ++ show bslen + where bslen = C8.length (toBytes bs) + +-- | Encode address to hex string +toHexString :: Address -> HexString +toHexString = fromBytes . C8.drop 12 . encode + +-- | Encode address with mixed-case checksum +-- https://github.com/ethereum/EIPs/blob/master/EIPS/eip-55.md +toChecksum :: ByteString -> ByteString +toChecksum addr = ("0x" <>) . C8.pack $ zipWith ($) upcaseVector lower + where + upcaseVector = (>>= fourthBits) . BS.unpack . BS.take 20 $ keccak256 (C8.pack lower) + fourthBits n = bool id C.toUpper <$> [n .&. 0x80 /= 0, n .&. 0x08 /= 0] + lower = drop 2 . fmap C.toLower . C8.unpack $ addr + +-- | Verify mixed-case address checksum +-- https://github.com/ethereum/EIPs/blob/master/EIPS/eip-55.md +verifyChecksum :: ByteString -> Bool +verifyChecksum = toChecksum >>= (==) diff --git a/packages/solidity/src/Data/Solidity/Prim/Bool.hs b/packages/solidity/src/Data/Solidity/Prim/Bool.hs new file mode 100644 index 00000000..17464a64 --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Bool.hs @@ -0,0 +1,25 @@ +-- | +-- Module : Data.Solidity.Prim.Bool +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethereum Abi boolean type. +-- + +module Data.Solidity.Prim.Bool () where + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), AbiType (..)) +import Data.Solidity.Prim.Int (getWord256, putWord256) + +instance AbiType Bool where + isDynamic _ = False + +instance AbiGet Bool where + abiGet = toEnum . fromIntegral <$> getWord256 + +instance AbiPut Bool where + abiPut = putWord256 . fromIntegral . fromEnum diff --git a/packages/solidity/src/Data/Solidity/Prim/Bytes.hs b/packages/solidity/src/Data/Solidity/Prim/Bytes.hs new file mode 100644 index 00000000..96684d24 --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Bytes.hs @@ -0,0 +1,130 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} +{-# LANGUAGE UndecidableInstances #-} + +-- | +-- Module : Data.Solidity.Prim.Bytes +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Bytes and BytesN primitive types. +-- + +module Data.Solidity.Prim.Bytes + ( + -- * The dynamic length @Bytes@ type + Bytes + + -- * The fixed length @BytesN@ type + , BytesN + ) where + +import Control.Monad (unless, void) +import Data.Aeson (FromJSON (..), ToJSON (..), + Value (String)) +import Data.ByteArray (Bytes, convert, length, zero) +import Data.ByteArray.Encoding (Base (Base16), convertFromBase, + convertToBase) +import Data.ByteArray.Sized (SizedByteArray, unSizedByteArray, + unsafeFromByteArrayAccess) +import qualified Data.ByteArray.Sized as S (take) +import Data.ByteString (ByteString) +import qualified Data.ByteString.Char8 as C8 +import Data.Proxy (Proxy (..)) +import Data.Serialize (Get, Putter, getBytes, putByteString) +import Data.String (IsString (..)) +import qualified Data.Text as T (append, drop, take) +import Data.Text.Encoding (decodeUtf8, encodeUtf8) +import GHC.TypeLits +import Prelude hiding (length) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), + AbiType (..)) +import Data.Solidity.Prim.Int (getWord256, putWord256) + +instance AbiType ByteString where + isDynamic _ = True + +instance AbiGet ByteString where + abiGet = abiGetByteString + +instance AbiPut ByteString where + abiPut = abiPutByteString + +instance AbiType Bytes where + isDynamic _ = True + +instance AbiGet Bytes where + abiGet = convert <$> abiGetByteString + +instance AbiPut Bytes where + abiPut = abiPutByteString . convert + +instance IsString Bytes where + fromString ('0' : 'x' : hex) = either error id $ convertFromBase Base16 (C8.pack hex) + fromString str = convert (C8.pack str) + +instance FromJSON Bytes where + parseJSON (String hex) + | T.take 2 hex == "0x" = + either fail pure $ convertFromBase Base16 $ encodeUtf8 $ T.drop 2 hex + | otherwise = fail "Hex string should have '0x' prefix" + parseJSON _ = fail "Bytes should be encoded as hex string" + +instance ToJSON Bytes where + toJSON = toJSON . T.append "0x" . decodeUtf8 . convertToBase Base16 + +-- | Sized byte array with fixed length in bytes +type BytesN n = SizedByteArray n Bytes + +instance KnownNat n => AbiType (BytesN n) where + isDynamic _ = False + +instance (KnownNat n, n <= 32) => AbiGet (BytesN n) where + abiGet = do + ba <- unsafeFromByteArrayAccess <$> getBytes 32 + return $ S.take (ba :: BytesN 32) + +instance KnownNat n => AbiPut (BytesN n) where + abiPut ba = putByteString $ convert ba <> zero (32 - len) + where len = fromIntegral $ natVal (Proxy :: Proxy n) + +instance KnownNat n => IsString (BytesN n) where + fromString s = unsafeFromByteArrayAccess padded + where bytes = fromString s :: Bytes + len = fromIntegral $ natVal (Proxy :: Proxy n) + padded = bytes <> zero (len - length bytes) + +instance KnownNat n => FromJSON (BytesN n) where + parseJSON v = do ba <- parseJSON v + return $ unsafeFromByteArrayAccess (ba :: Bytes) + +instance KnownNat n => ToJSON (BytesN n) where + toJSON ba = toJSON (unSizedByteArray ba :: Bytes) + +abiGetByteString :: Get ByteString +abiGetByteString = do + len <- fromIntegral <$> getWord256 + res <- getBytes len + let remainder = len `mod` 32 + unless (remainder == 0) $ + void $ getBytes (32 - remainder) + pure res + +abiPutByteString :: Putter ByteString +abiPutByteString bs = do + putWord256 $ fromIntegral len + putByteString bs + unless (remainder == 0) $ + putByteString $ zero (32 - remainder) + where len = length bs + remainder = len `mod` 32 diff --git a/packages/solidity/src/Data/Solidity/Prim/Int.hs b/packages/solidity/src/Data/Solidity/Prim/Int.hs new file mode 100644 index 00000000..a4de0dec --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Int.hs @@ -0,0 +1,147 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Data.Solidity.Prim.Int +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethereum Abi intN and uintN types. +-- + +module Data.Solidity.Prim.Int + ( + -- * The @IntN@ type + IntN + + -- * The @UIntN@ type + , UIntN + + -- * @Word256@ serializers + , getWord256 + , putWord256 + ) where + +import qualified Basement.Numerical.Number as Basement (toInteger) +import Basement.Types.Word256 (Word256 (Word256)) +import qualified Basement.Types.Word256 as Basement (quot, rem) +import Data.Aeson (ToJSON (..)) +import Data.Bits (Bits (testBit), (.&.)) +import Data.Proxy (Proxy (..)) +import Data.Serialize (Get, Putter, Serialize (get, put)) +import GHC.Generics (Generic) +import GHC.TypeLits + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), + AbiType (..)) + +instance Real Word256 where + toRational = toRational . toInteger + +instance Integral Word256 where + toInteger = Basement.toInteger + quotRem a b = (Basement.quot a b, Basement.rem a b) + +-- | Unsigned integer with fixed length in bits. +newtype UIntN (n :: Nat) = UIntN { unUIntN :: Word256 } + deriving (Eq, Ord, Enum, Bits, Generic) + +instance KnownNat n => Num (UIntN n) where + a + b = fromInteger (toInteger a + toInteger b) + a - b = fromInteger (toInteger a - toInteger b) + a * b = fromInteger (toInteger a * toInteger b) + abs = fromInteger . abs . toInteger + negate = fromInteger . negate . toInteger + signum = fromInteger . signum . toInteger + fromInteger x + | x >= 0 = mask $ UIntN (fromInteger x) + | otherwise = mask $ UIntN (fromInteger $ 2 ^ 256 + x) + where + mask = (maxBound .&.) :: UIntN n -> UIntN n + +instance KnownNat n => Show (UIntN n) where + show = show . unUIntN + +instance KnownNat n => Bounded (UIntN n) where + minBound = UIntN 0 + maxBound = UIntN $ 2 ^ natVal (Proxy :: Proxy n) - 1 + +instance KnownNat n => Real (UIntN n) where + toRational = toRational . toInteger + +instance KnownNat n => Integral (UIntN n) where + toInteger = toInteger . unUIntN + quotRem (UIntN a) (UIntN b) = (UIntN $ quot a b, UIntN $ rem a b) + +instance KnownNat n => AbiType (UIntN n) where + isDynamic _ = False + +instance KnownNat n => AbiGet (UIntN n) where + abiGet = UIntN <$> getWord256 + +instance KnownNat n => AbiPut (UIntN n) where + abiPut = putWord256 . unUIntN + +instance KnownNat n => ToJSON (UIntN n) where + toJSON = toJSON . toInteger + +-- | Signed integer with fixed length in bits. +newtype IntN (n :: Nat) = IntN { unIntN :: Word256 } + deriving (Eq, Ord, Enum, Bits, Generic) + +instance KnownNat n => Show (IntN n) where + show = show . toInteger + +instance KnownNat n => Bounded (IntN n) where + minBound = IntN $ negate $ 2 ^ (natVal (Proxy :: Proxy (n :: Nat)) - 1) + maxBound = IntN $ 2 ^ (natVal (Proxy :: Proxy (n :: Nat)) - 1) - 1 + +instance KnownNat n => Num (IntN n) where + a + b = fromInteger (toInteger a + toInteger b) + a - b = fromInteger (toInteger a - toInteger b) + a * b = fromInteger (toInteger a * toInteger b) + abs = fromInteger . abs . toInteger + negate = fromInteger . negate . toInteger + signum = fromInteger . signum . toInteger + fromInteger x + | x >= 0 = IntN (fromInteger x) + | otherwise = IntN (fromInteger $ 2 ^ 256 + x) + +instance KnownNat n => Real (IntN n) where + toRational = toRational . toInteger + +instance KnownNat n => Integral (IntN n) where + quotRem (IntN a) (IntN b) = (IntN $ quot a b, IntN $ rem a b) + toInteger x + | testBit x 255 = toInteger (unIntN x) - 2 ^ 256 + | otherwise = toInteger $ unIntN x + +instance KnownNat n => AbiType (IntN n) where + isDynamic _ = False + +instance KnownNat n => AbiGet (IntN n) where + abiGet = IntN <$> getWord256 + +instance KnownNat n => AbiPut (IntN n) where + abiPut = putWord256 . unIntN + +instance KnownNat n => ToJSON (IntN n) where + toJSON = toJSON . toInteger + +-- | Serialize 256 bit unsigned integer. +putWord256 :: Putter Word256 +putWord256 (Word256 a3 a2 a1 a0) = + put a3 >> put a2 >> put a1 >> put a0 + +-- | Deserialize 256 bit unsigned integer. +getWord256 :: Get Word256 +getWord256 = Word256 <$> get <*> get <*> get <*> get diff --git a/packages/solidity/src/Data/Solidity/Prim/List.hs b/packages/solidity/src/Data/Solidity/Prim/List.hs new file mode 100644 index 00000000..eff1f6df --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/List.hs @@ -0,0 +1,96 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE TypeOperators #-} +{-# LANGUAGE UndecidableInstances #-} + +-- | +-- Module : Data.Solidity.Prim.List +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethereum Abi dynamic and static size vectors based on linked lists. +-- + +module Data.Solidity.Prim.List + ( + -- * Fixed size linked list + ListN + ) where + +import Basement.Nat (NatWithinBound) +import Basement.Sized.List (ListN, toListN_, unListN) +import qualified Basement.Sized.List as SL (init, map, mapM, mapM_, + replicateM, scanl') +import Basement.Types.Word256 (Word256) +import Control.Monad (forM, replicateM) +import qualified Data.ByteString as B +import Data.List (scanl') +import Data.Proxy (Proxy (..)) +import Data.Serialize.Get (lookAhead, skip) +import Data.Serialize.Put (putByteString, runPut) +import GHC.Exts (IsList (..)) +import GHC.TypeLits (KnownNat, natVal, type (+), type (<=)) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), AbiType (..)) +import Data.Solidity.Prim.Int (getWord256, putWord256) + +instance AbiType [a] where + isDynamic _ = True + +instance AbiPut a => AbiPut [a] where + abiPut l = do putWord256 $ fromIntegral (length l) + if isDynamic (Proxy :: Proxy a) then do + let encs = map (runPut . abiPut) l + lengths = map ((fromIntegral :: Int -> Word256) . B.length) encs + offsets = init $ scanl' (+) (fromIntegral (0x20 * length l)) lengths + mapM_ putWord256 offsets + mapM_ putByteString encs + else + foldMap abiPut l + +instance AbiGet a => AbiGet [a] where + abiGet = do len <- fromIntegral <$> getWord256 + if isDynamic (Proxy :: Proxy a) then do + offsets <- replicateM len getWord256 + let currentOffset = 0x20 * len + forM offsets $ \dataOffset -> lookAhead $ do + skip (fromIntegral dataOffset - currentOffset) + abiGet + else + replicateM len abiGet + +instance (AbiType a, KnownNat n) => AbiType (ListN n a) where + isDynamic _ = natVal (Proxy :: Proxy n) > 0 && isDynamic (Proxy :: Proxy a) + +instance (AbiPut a, KnownNat n, 1 <= n+1) => AbiPut (ListN n a) where + abiPut l = if isDynamic (Proxy :: Proxy a) then do + let encs = SL.map (runPut . abiPut) l + lengths = SL.map ((fromIntegral :: Int -> Word256) . B.length) encs + len = natVal (Proxy :: Proxy n) + offsets = SL.init $ SL.scanl' (+) (fromIntegral (0x20 * len)) lengths + SL.mapM_ putWord256 offsets + SL.mapM_ putByteString encs + else + SL.mapM_ abiPut l + +instance (NatWithinBound Int n, KnownNat n, AbiGet a) => AbiGet (ListN n a) where + abiGet = do let len = fromInteger (natVal (Proxy :: Proxy n)) + if isDynamic (Proxy :: Proxy a) then do + offsets <- SL.replicateM getWord256 + let currentOffset = 0x20 * len + flip SL.mapM offsets $ \dataOffset -> lookAhead $ do + skip (fromIntegral dataOffset - currentOffset) + abiGet + else + SL.replicateM abiGet + +instance (NatWithinBound Int n, KnownNat n) => IsList (ListN n a) where + type Item (ListN n a) = a + fromList = toListN_ + toList = unListN diff --git a/packages/solidity/src/Data/Solidity/Prim/String.hs b/packages/solidity/src/Data/Solidity/Prim/String.hs new file mode 100644 index 00000000..244eabbc --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/String.hs @@ -0,0 +1,29 @@ +-- | +-- Module : Data.Solidity.Prim.String +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethereum Abi UTF8-encoded string type. +-- + +module Data.Solidity.Prim.String where + +import Data.Text (Text) +import Data.Text.Encoding (decodeUtf8, encodeUtf8) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), + AbiType (..)) +import Data.Solidity.Prim.Bytes () + +instance AbiType Text where + isDynamic _ = True + +instance AbiPut Text where + abiPut = abiPut . encodeUtf8 + +instance AbiGet Text where + abiGet = decodeUtf8 <$> abiGet diff --git a/packages/solidity/src/Data/Solidity/Prim/Tagged.hs b/packages/solidity/src/Data/Solidity/Prim/Tagged.hs new file mode 100644 index 00000000..7119c298 --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Tagged.hs @@ -0,0 +1,37 @@ +{-# LANGUAGE PolyKinds #-} +{-# LANGUAGE ScopedTypeVariables #-} + +-- | +-- Module : Data.Solidity.Prim.Tagged +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Ethereum Abi tagged types. +-- + +module Data.Solidity.Prim.Tagged + ( + -- * The @Tagged@ type + Tagged + ) where + +import Data.Proxy (Proxy (..)) +import Data.Tagged (Tagged (..)) +import Generics.SOP (Generic) + +import Data.Solidity.Abi (AbiGet (..), AbiPut (..), AbiType (..)) + +instance AbiType a => AbiType (Tagged t a) where + isDynamic _ = isDynamic (Proxy :: Proxy a) + +instance AbiPut a => AbiPut (Tagged t a) where + abiPut (Tagged a) = abiPut a + +instance AbiGet a => AbiGet (Tagged t a) where + abiGet = Tagged <$> abiGet + +instance Generic a => Generic (Tagged t a) diff --git a/packages/solidity/src/Data/Solidity/Prim/Tuple.hs b/packages/solidity/src/Data/Solidity/Prim/Tuple.hs new file mode 100644 index 00000000..9ca0ac1d --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Tuple.hs @@ -0,0 +1,58 @@ +{-# LANGUAGE CPP #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE StandaloneDeriving #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE TypeSynonymInstances #-} + +-- | +-- Module : Data.Solidity.Prim.Tuple +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- Tuple type abi encoding instances. +-- + +module Data.Solidity.Prim.Tuple where + +import Data.Proxy (Proxy (..)) +#if MIN_VERSION_OneTuple(0,3,0) +import Data.Tuple.Solo (Solo (..)) +#else +import Data.Tuple.OneTuple (OneTuple (..)) +#endif +import Generics.SOP (Generic) +#if MIN_VERSION_base(4,15,0) +#else +import qualified GHC.Generics as GHC (Generic) +#endif + +import Data.Solidity.Abi (AbiGet, AbiPut, AbiType (..)) +import Data.Solidity.Abi.Generic () +import Data.Solidity.Prim.Tuple.TH (tupleDecs) + +#if MIN_VERSION_OneTuple(0,3,0) +instance Generic (Solo a) +instance AbiType a => AbiType (Solo a) where + isDynamic _ = isDynamic (Proxy :: Proxy a) + +instance AbiGet a => AbiGet (Solo a) +instance AbiPut a => AbiPut (Solo a) +#else +#if MIN_VERSION_base(4,15,0) +#else +deriving instance GHC.Generic (OneTuple a) +#endif +instance Generic (OneTuple a) + +instance AbiType a => AbiType (OneTuple a) where + isDynamic _ = isDynamic (Proxy :: Proxy a) + +instance AbiGet a => AbiGet (OneTuple a) +instance AbiPut a => AbiPut (OneTuple a) +#endif +$(concat <$> mapM tupleDecs [2..20]) diff --git a/packages/solidity/src/Data/Solidity/Prim/Tuple/TH.hs b/packages/solidity/src/Data/Solidity/Prim/Tuple/TH.hs new file mode 100644 index 00000000..f9f5242b --- /dev/null +++ b/packages/solidity/src/Data/Solidity/Prim/Tuple/TH.hs @@ -0,0 +1,37 @@ +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Data.Solidity.Prim.Tuple.TH +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- This module is for internal usage only. +-- It contains tuple abi encoding template haskell generator. +-- + +module Data.Solidity.Prim.Tuple.TH (tupleDecs) where + + +import Control.Monad (replicateM) +import Data.Proxy +import Language.Haskell.TH (DecsQ, Type (VarT), appT, clause, conT, + cxt, funD, instanceD, listE, newName, + normalB, tupleT) + +import Data.Solidity.Abi (AbiGet, AbiPut, AbiType (..)) + +tupleDecs :: Int -> DecsQ +tupleDecs n = do + vars <- replicateM n $ newName "a" + let types = fmap (pure . VarT) vars + areDynamic = listE $ flip fmap types $ \t -> [| isDynamic (Proxy :: Proxy $(t)) |] + + sequence $ + [ instanceD (cxt $ map (appT $ conT ''AbiType) types) (appT (conT ''AbiType) (foldl appT (tupleT n) types)) + [funD 'isDynamic [clause [] (normalB [|const (or $(areDynamic))|]) []]] + , instanceD (cxt $ map (appT $ conT ''AbiGet) types) (appT (conT ''AbiGet) (foldl appT (tupleT n) types)) [] + , instanceD (cxt $ map (appT $ conT ''AbiPut) types) (appT (conT ''AbiPut) (foldl appT (tupleT n) types)) [] ] diff --git a/packages/solidity/src/Language/Solidity/Abi.hs b/packages/solidity/src/Language/Solidity/Abi.hs new file mode 100644 index 00000000..70013c2a --- /dev/null +++ b/packages/solidity/src/Language/Solidity/Abi.hs @@ -0,0 +1,353 @@ +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TemplateHaskell #-} + +-- | +-- Module : Data.Solidity.Abi.Json +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : noportable +-- +-- JSON encoded contract ABI parsers. +-- + +module Language.Solidity.Abi + ( + -- * Contract ABI declarations + ContractAbi(..) + , Declaration(..) + , FunctionArg(..) + , EventArg(..) + , StateMutability(..) + + -- * Method/Event id encoder + , signature + , methodId + , eventId + + -- * Solidity type parser + , SolidityType(..) + , parseSolidityFunctionArgType + , parseSolidityEventArgType + ) where + +import Control.Monad (void) +import Crypto.Ethereum.Utils (keccak256) +import Data.Aeson (FromJSON (parseJSON), + Options (constructorTagModifier, fieldLabelModifier, sumEncoding), + SumEncoding (TaggedObject), + ToJSON (toJSON), defaultOptions, + withObject, (.:), (.:?)) +import Data.Aeson.TH (deriveJSON, deriveToJSON) +import qualified Data.ByteArray as A (take) +import Data.ByteArray.HexString (toText) +import Data.Char (toLower) +import Data.Text (Text) +import qualified Data.Text as T (dropEnd, unlines, unpack) +import Data.Text.Encoding (encodeUtf8) +import Lens.Micro (_head, over) +import Text.Parsec (ParseError, char, choice, digit, eof, + lookAhead, many1, manyTill, + optionMaybe, parse, string, try, + (<|>)) +import Text.Parsec.Text (Parser) + +-- | Method argument +data FunctionArg = FunctionArg + { funArgName :: Text + -- ^ Argument name + , funArgType :: Text + -- ^ Argument type + , funArgComponents :: Maybe [FunctionArg] + -- ^ Argument components for tuples + } + deriving (Show, Eq, Ord) + +$(deriveJSON + (defaultOptions {fieldLabelModifier = over _head toLower . drop 6}) + ''FunctionArg) + +-- | Event argument +data EventArg = EventArg + { eveArgName :: Text + -- ^ Argument name + , eveArgType :: Text + -- ^ Argument type + , eveArgIndexed :: Bool + -- ^ Argument is indexed (e.g. placed on topics of event) + } + deriving (Show, Eq, Ord) + +$(deriveJSON + (defaultOptions {fieldLabelModifier = over _head toLower . drop 6}) + ''EventArg) + +data StateMutability + = SMPure + | SMView + | SMPayable + | SMNonPayable + deriving (Eq, Ord, Show) + +$(deriveJSON (defaultOptions { + sumEncoding = TaggedObject "stateMutability" "contents" + , constructorTagModifier = fmap toLower . drop 2 }) + ''StateMutability) + +-- | Elementary contract interface item +data Declaration = DConstructor + { conInputs :: [FunctionArg] + -- ^ Contract constructor + } + | DFunction + { funName :: Text + , funConstant :: Bool + , funInputs :: [FunctionArg] + , funOutputs :: Maybe [FunctionArg] + -- ^ Method + } + | DEvent + { eveName :: Text + , eveInputs :: [EventArg] + , eveAnonymous :: Bool + -- ^ Event + } + | DError + { errName :: Text + , errInputs :: [FunctionArg] + -- ^ Error + } + | DFallback + { falPayable :: Bool + -- ^ Fallback function + } + deriving Show + +instance Eq Declaration where + (DConstructor a) == (DConstructor b) = length a == length b + (DFunction a _ _ _) == (DFunction b _ _ _) = a == b + (DEvent a _ _) == (DEvent b _ _) = a == b + (DError a _) == (DError b _) = a == b + (DFallback _) == (DFallback _) = True + (==) _ _ = False + +instance Ord Declaration where + compare (DConstructor a) (DConstructor b) = compare (length a) (length b) + compare (DFunction a _ _ _) (DFunction b _ _ _) = compare a b + compare (DEvent a _ _) (DEvent b _ _) = compare a b + compare (DError a _) (DError b _) = compare a b + compare (DFallback _) (DFallback _) = EQ + + compare DConstructor {} DFunction {} = LT + compare DConstructor {} DEvent {} = LT + compare DConstructor {} DError {} = LT + compare DConstructor {} DFallback {} = LT + + compare DFunction {} DConstructor {} = GT + compare DFunction {} DEvent {} = LT + compare DFunction {} DError {} = LT + compare DFunction {} DFallback {} = LT + + compare DEvent {} DConstructor {} = GT + compare DEvent {} DFunction {} = GT + compare DEvent {} DError {} = LT + compare DEvent {} DFallback {} = LT + + compare DError {} DConstructor {} = GT + compare DError {} DFunction {} = GT + compare DError {} DEvent {} = GT + compare DError {} DFallback {} = LT + + compare DFallback {} DConstructor {} = GT + compare DFallback {} DFunction {} = GT + compare DFallback {} DEvent {} = GT + compare DFallback {} DError {} = GT + +instance FromJSON Declaration where + parseJSON = withObject "Declaration" $ \o -> do + t :: Text <- o .: "type" + case t of + "fallback" -> DFallback <$> o .: "payable" + "constructor" -> DConstructor <$> o .: "inputs" + "event" -> DEvent <$> o .: "name" <*> o .: "inputs" <*> o .: "anonymous" + "error" -> DError <$> o .: "name" <*> o .: "inputs" + "function" -> DFunction <$> o .: "name" <*> parseSm o <*> o .: "inputs" <*> o .:? "outputs" + _ -> fail "value of 'type' not recognized" + where + parseSm o = do + o .:? "stateMutability" >>= \case + Nothing -> o .: "constant" + Just sm -> pure $ sm `elem` [SMPure, SMView] + +$(deriveToJSON + (defaultOptions { + sumEncoding = TaggedObject "type" "contents" + , constructorTagModifier = over _head toLower . drop 1 + , fieldLabelModifier = over _head toLower . drop 3 }) + ''Declaration) + +-- | Contract Abi is a list of method / event declarations +newtype ContractAbi = ContractAbi { unAbi :: [Declaration] } + deriving (Eq, Ord) + +instance FromJSON ContractAbi where + parseJSON = fmap ContractAbi . parseJSON + +instance ToJSON ContractAbi where + toJSON = toJSON . unAbi + +instance Show ContractAbi where + show (ContractAbi c) = T.unpack $ T.unlines $ + [ "Contract:" ] + ++ foldMap showConstructor c ++ + [ "\tEvents:" ] + ++ foldMap showEvent c ++ + [ "\tMethods:" ] + ++ foldMap showMethod c + +showConstructor :: Declaration -> [Text] +showConstructor x = case x of + DConstructor{} -> ["\tConstructor " <> signature x] + _ -> [] + +showEvent :: Declaration -> [Text] +showEvent x = case x of + DEvent{} -> ["\t\t" <> signature x] + _ -> [] + +showMethod :: Declaration -> [Text] +showMethod x = case x of + DFunction{} -> + ["\t\t" <> methodId x <> " " <> signature x] + _ -> [] + +funArgs :: [FunctionArg] -> Text +funArgs [] = "" +funArgs [x] = funArgType x +funArgs (x:xs) = case funArgComponents x of + Nothing -> funArgType x <> "," <> funArgs xs + Just cmps -> case funArgType x of + "tuple" -> "(" <> funArgs cmps <> ")," <> funArgs xs + "tuple[]" -> "(" <> funArgs cmps <> ")[]," <> funArgs xs + typ -> error $ "Unexpected type " ++ T.unpack typ ++ " - expected tuple or tuple[]" + +-- | Take a signature by given decl, e.g. foo(uint,string) +signature :: Declaration -> Text + +signature (DConstructor inputs) = "(" <> funArgs inputs <> ")" +signature (DFallback _) = "()" +signature (DFunction name _ inputs _) = name <> "(" <> funArgs inputs <> ")" +signature (DError name inputs) = name <> "(" <> funArgs inputs <> ")" +signature (DEvent name inputs _) = name <> "(" <> args inputs <> ")" + where + args :: [EventArg] -> Text + args = T.dropEnd 1 . foldMap (<> ",") . fmap eveArgType + +-- | Generate method selector by given method 'Delcaration' +methodId :: Declaration -> Text +{-# INLINE methodId #-} +methodId = toText . A.take 4 . keccak256 . encodeUtf8 . signature + +-- | Generate event `topic0` hash by givent event 'Delcaration' +eventId :: Declaration -> Text +{-# INLINE eventId #-} +eventId = toText . keccak256 . encodeUtf8 . signature + +-- | Solidity types and parsers +data SolidityType = SolidityBool + | SolidityAddress + | SolidityUint Int + | SolidityInt Int + | SolidityString + | SolidityBytesN Int + | SolidityBytes + | SolidityTuple [SolidityType] + | SolidityVector [Int] SolidityType + | SolidityArray SolidityType + deriving (Eq, Show) + +numberParser :: Parser Int +numberParser = read <$> many1 digit + +parseUint :: Parser SolidityType +parseUint = do + _ <- string "uint" + SolidityUint <$> numberParser + +parseInt :: Parser SolidityType +parseInt = do + _ <- string "int" + SolidityInt <$> numberParser + +parseBool :: Parser SolidityType +parseBool = string "bool" >> pure SolidityBool + +parseString :: Parser SolidityType +parseString = string "string" >> pure SolidityString + +parseBytes :: Parser SolidityType +parseBytes = do + _ <- string "bytes" + mn <- optionMaybe numberParser + pure $ maybe SolidityBytes SolidityBytesN mn + +parseAddress :: Parser SolidityType +parseAddress = string "address" >> pure SolidityAddress + +solidityBasicTypeParser :: Parser SolidityType +solidityBasicTypeParser = + choice [ try parseUint + , try parseInt + , try parseAddress + , try parseBool + , try parseString + , parseBytes + ] + +parseVector :: Parser SolidityType +parseVector = do + s <- solidityBasicTypeParser + ns <- many1Till lengthParser (lookAhead (void $ string "[]") <|> eof) + pure $ SolidityVector ns s + where + many1Till :: Parser Int -> Parser () -> Parser [Int] + many1Till p end = do + a <- p + as <- manyTill p end + return (a : as) + + lengthParser = do + _ <- char '[' + n <- numberParser + _ <- char ']' + pure n + +parseArray :: Parser SolidityType +parseArray = do + s <- try (parseVector <* string "[]") <|> (solidityBasicTypeParser <* string "[]") + pure $ SolidityArray s + + +solidityTypeParser :: Parser SolidityType +solidityTypeParser = + choice [ try parseArray + , try parseVector + , solidityBasicTypeParser + ] + +parseSolidityFunctionArgType :: FunctionArg -> Either ParseError SolidityType +parseSolidityFunctionArgType (FunctionArg _ typ mcmps) = case mcmps of + Nothing -> parse solidityTypeParser "Solidity" typ + Just cmps -> do + tpl <- SolidityTuple <$> mapM parseSolidityFunctionArgType cmps + case typ of + "tuple" -> return tpl + "tuple[]" -> return $ SolidityArray tpl + _ -> error $ "Unexpected type " ++ T.unpack typ ++ " - expected tuple or tuple[]" + +parseSolidityEventArgType :: EventArg -> Either ParseError SolidityType +parseSolidityEventArgType (EventArg _ typ _) = parse solidityTypeParser "Solidity" typ diff --git a/packages/solidity/tests/Data/Solidity/Test/AddressSpec.hs b/packages/solidity/tests/Data/Solidity/Test/AddressSpec.hs new file mode 100644 index 00000000..dffafc08 --- /dev/null +++ b/packages/solidity/tests/Data/Solidity/Test/AddressSpec.hs @@ -0,0 +1,73 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Data.Solidity.Test.AddressSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.Solidity.Test.AddressSpec where + +import Data.ByteString (ByteString) +import Data.ByteString.Char8 (unpack) +import Data.Foldable (for_) +import Test.Hspec + +import Crypto.Ecdsa.Utils (derivePubKey, importKey) +import Data.ByteArray.HexString (HexString) +import Data.Solidity.Prim.Address + +spec :: Spec +spec = parallel $ do + describe "EIP55 Test Vectors" $ for_ checksummedAddrs $ \addr -> + it (unpack addr <> " should be checksummed") $ verifyChecksum addr `shouldBe` True + + describe "EIP55 Test Vectors Tampered" $ for_ unchecksummedAddrs $ \addr -> + it (unpack addr <> " should not be checksummed") $ verifyChecksum addr `shouldBe` False + + describe "Conversion from/to hex string" $ do + it "should convert from/to on valid hex" $ do + fromHexString "0x6370eF2f4Db3611D657b90667De398a2Cc2a370C" + `shouldBe` Right "0x6370eF2f4Db3611D657b90667De398a2Cc2a370C" + + toHexString "0x6370eF2f4Db3611D657b90667De398a2Cc2a370C" + `shouldBe` "0x6370eF2f4Db3611D657b90667De398a2Cc2a370C" + + it "should fail on broken hex" $ do + fromHexString "0x42" + `shouldBe` Left "Incorrect address length: 1" + + + describe "Conversion from ECC keys" $ do + it "can derive address from public key" $ do + let key = "0x0102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f20" :: HexString + fromPubKey (derivePubKey $ importKey key) + `shouldBe` "0x6370eF2f4Db3611D657b90667De398a2Cc2a370C" + +checksummedAddrs :: [ByteString] +checksummedAddrs = + [ "0x52908400098527886E0F7030069857D2E4169EE7" + , "0x8617E340B3D01FA5F11F306F4090FD50E238070D" + , "0xde709f2102306220921060314715629080e2fb77" + , "0x27b1fdb04752bbc536007a920d24acb045561c26" + , "0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAed" + , "0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5d359" + , "0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6FB" + , "0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDb" + ] + +unchecksummedAddrs :: [ByteString] +unchecksummedAddrs = + [ "0x52908400098527886E0F7030069857D2E4169Ee7" + , "0x8617E340B3D01FA5F11F306F4090FD50E238070d" + , "0xde709f2102306220921060314715629080e2fB77" + , "0x27b1fdb04752bbc536007a920d24acb045561C26" + , "0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAeD" + , "0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5D359" + , "0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6Fb" + , "0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDB" + ] diff --git a/unit/Network/Ethereum/Web3/Test/EncodingSpec.hs b/packages/solidity/tests/Data/Solidity/Test/EncodingSpec.hs similarity index 86% rename from unit/Network/Ethereum/Web3/Test/EncodingSpec.hs rename to packages/solidity/tests/Data/Solidity/Test/EncodingSpec.hs index 7a9559f9..456fadc2 100644 --- a/unit/Network/Ethereum/Web3/Test/EncodingSpec.hs +++ b/packages/solidity/tests/Data/Solidity/Test/EncodingSpec.hs @@ -3,31 +3,35 @@ {-# LANGUAGE OverloadedLists #-} {-# LANGUAGE OverloadedStrings #-} {-# LANGUAGE TypeFamilies #-} - -module Network.Ethereum.Web3.Test.EncodingSpec where - -import Control.Exception (evaluate) -import Data.Monoid ((<>)) -import Data.Text (Text) -import Generics.SOP (Generic, Rep) +{-# LANGUAGE TypeOperators #-} + +-- | +-- Module : Data.Solidity.Test.EncodingSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.Solidity.Test.EncodingSpec where + +import Control.Exception (evaluate) +import Data.Text (Text) +import Data.Tuple.OneTuple +import Generics.SOP (Generic, Rep) import Test.Hspec -import Network.Ethereum.ABI.Class (ABIGet, ABIPut, - GenericABIGet, - GenericABIPut) -import Network.Ethereum.ABI.Codec (decode, decode', encode, - encode') -import Network.Ethereum.ABI.Prim.Address (Address, fromHexString, - toHexString) -import Network.Ethereum.ABI.Prim.Bool () -import Network.Ethereum.ABI.Prim.Bytes (Bytes, BytesN) -import Network.Ethereum.ABI.Prim.Int (IntN, UIntN) -import Network.Ethereum.ABI.Prim.List (ListN) -import Network.Ethereum.ABI.Prim.String () -import Network.Ethereum.ABI.Prim.Tuple (Singleton (..)) +import Data.Solidity.Abi (AbiGet, AbiPut, GenericAbiGet, + GenericAbiPut) +import Data.Solidity.Abi.Codec (decode, decode', encode, encode') +import Data.Solidity.Prim (Address, Bytes, BytesN, IntN, + ListN, UIntN) +import Data.Solidity.Prim.Address (fromHexString, toHexString) spec :: Spec -spec = do +spec = parallel $ do intNTest bytesTest bytesNTest @@ -155,7 +159,7 @@ tuplesTest = in roundTripGeneric decoded encoded it "can encode 1-tuples with dynamic arg" $ do - let decoded = Singleton ([True, False] :: [Bool]) + let decoded = OneTuple ([True, False] :: [Bool]) encoded = "0x0000000000000000000000000000000000000000000000000000000000000020" <> "0x0000000000000000000000000000000000000000000000000000000000000002" <> "0x0000000000000000000000000000000000000000000000000000000000000001" @@ -182,12 +186,12 @@ tuplesTest = bool = True int224 = 221 :: IntN 224 bools = [True, False] :: ListN 2 Bool - ints = [1, (-1), 3] :: [IntN 32] + ints = [1, -1, 3] :: [IntN 32] string = "hello" :: Text bytes16 = "0x12345678123456781234567812345678" :: BytesN 16 - elem = "0x1234" :: BytesN 2 - bytes2s = [ [elem, elem, elem, elem] - , [elem, elem, elem, elem] + elem1 = "0x1234" :: BytesN 2 + bytes2s = [ [elem1, elem1, elem1, elem1] + , [elem1, elem1, elem1, elem1] ] :: [ListN 4 (BytesN 2)] decoded = (uint, int, bool, int224, bools, ints, string, bytes16, bytes2s) @@ -232,21 +236,21 @@ addressTest = fromHexString "0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a" `shouldBe` Right ("0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a" :: Address) - fromHexString "0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a" - `shouldBe` fromHexString "4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a" - toHexString "0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a" `shouldBe` "0x4af013afbadb22d8a88c92d68fc96b033b9ebb8a" it "fails for invalid address length" $ do - fromHexString "0x0" `shouldBe` Left "base16: input: invalid length" - fromHexString "0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a00" `shouldBe` Left "Invalid address length" + evaluate (fromHexString "0x0") + `shouldThrow` errorCall "base16: input: invalid length" + + fromHexString "0x4af013AfBAdb22D8A88c92D68Fc96B033b9Ebb8a00" + `shouldBe` Left "Incorrect address length: 21" -- | Run encoded/decoded comaration roundTrip :: ( Show a , Eq a - , ABIPut a - , ABIGet a + , AbiPut a + , AbiGet a ) => a -> Bytes @@ -260,8 +264,8 @@ roundTripGeneric :: ( Show a , Eq a , Generic a , Rep a ~ rep - , GenericABIPut rep - , GenericABIGet rep + , GenericAbiPut rep + , GenericAbiGet rep ) => a -> Bytes diff --git a/packages/solidity/tests/Data/Solidity/Test/IntSpec.hs b/packages/solidity/tests/Data/Solidity/Test/IntSpec.hs new file mode 100644 index 00000000..560a0a45 --- /dev/null +++ b/packages/solidity/tests/Data/Solidity/Test/IntSpec.hs @@ -0,0 +1,44 @@ +{-# LANGUAGE DataKinds #-} + +-- | +-- Module : Data.Solidity.Test.IntSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Data.Solidity.Test.IntSpec where + +import Test.Hspec + +import Data.Solidity.Prim.Int + +spec :: Spec +spec = parallel $ do + describe "Unsigned integer overflow" $ do + it "UIntN 256" $ do + (negate 1 :: UIntN 256) `shouldBe` 115792089237316195423570985008687907853269984665640564039457584007913129639935 + (maxBound + 1 :: UIntN 256) `shouldBe` 0 + + it "UIntN 128" $ do + (negate 1 :: UIntN 128) `shouldBe` 340282366920938463463374607431768211455 + (maxBound + 1 :: UIntN 128) `shouldBe` 0 + + it "UIntN 64" $ do + (negate 1 :: UIntN 64) `shouldBe` 18446744073709551615 + (maxBound + 1 :: UIntN 64) `shouldBe` 0 + + it "UIntN 32" $ do + (negate 1 :: UIntN 32) `shouldBe` 4294967295 + (maxBound + 1 :: UIntN 32) `shouldBe` 0 + + it "UIntN 16" $ do + (negate 1 :: UIntN 16) `shouldBe` 65535 + (maxBound + 1 :: UIntN 16) `shouldBe` 0 + + it "UIntN 8" $ do + (negate 1 :: UIntN 8) `shouldBe` 255 + (maxBound + 1 :: UIntN 8) `shouldBe` 0 diff --git a/packages/solidity/tests/Language/Solidity/Test/AbiSpec.hs b/packages/solidity/tests/Language/Solidity/Test/AbiSpec.hs new file mode 100644 index 00000000..3be0f543 --- /dev/null +++ b/packages/solidity/tests/Language/Solidity/Test/AbiSpec.hs @@ -0,0 +1,97 @@ +{-# LANGUAGE OverloadedStrings #-} + +-- | +-- Module : Language.Solidity.Test.AbiSpec +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- + +module Language.Solidity.Test.AbiSpec where + + +import Data.Either (isLeft) +import Data.Text (Text) +import Language.Solidity.Abi +import Test.Hspec + + +spec :: Spec +spec = parallel $ do + describe "parseSolidityType" $ + describe "tuple type" $ do + it "can parses a FunctionArg with tuple type" $ do + let maa = FunctionArg "makerAssetAmount" "uint256" Nothing + ma = FunctionArg "makeAddress" "address" Nothing + tupleFA = FunctionArg "order" "tuple" (Just [maa, ma]) + eRes = parseSolidityFunctionArgType tupleFA + eRes `shouldBe` Right (SolidityTuple [SolidityUint 256, SolidityAddress]) + it "fails to parse a FunctionArg with invalid tuple" $ do + let tupleFA = FunctionArg "order" "tuple" Nothing + eRes = parseSolidityFunctionArgType tupleFA + isLeft eRes `shouldBe` True + describe "signature" $ do + it "can generate signature for fillOrder" $ do + let expected = "fillOrder((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes),uint256,bytes)" + sig = signature fillOrderDec + sig `shouldBe` expected + it "can generate signature for fillManyOrders" $ do + let expected = "fillManyOrders((address,address,address,address,uint256,uint256,uint256,uint256,uint256,uint256,bytes,bytes)[],uint256,bytes)" + sig = signature fillManyOrdersDec + sig `shouldBe` expected + describe "methodId" $ do + it "can generate methodId for fillOrder" $ do + let expected = "0xb4be83d5" + mId = methodId fillOrderDec + mId `shouldBe` expected + it "can generate methodId for fillManyOrders" $ do + let expected = "0xd52e8a68" + mId = methodId fillManyOrdersDec + mId `shouldBe` expected + +orderTupleComponents :: [(Text, Text)] +orderTupleComponents = + [ ("makerAddress", "address") + , ("takerAddress", "address") + , ("feeRecipientAddress", "address") + , ("senderAddress", "address") + , ("makerAssetAmount", "uint256") + , ("takerAssetAmount", "uint256") + , ("makerFee", "uint256") + , ("takerFee", "uint256") + , ("expirationTimeSeconds", "uint256") + , ("salt", "uint256") + , ("makerAssetData", "bytes") + , ("takerAssetData", "bytes") + ] + +fillOrderDec :: Declaration +fillOrderDec = DFunction "fillOrder" False funInputs' funOutputs' + where + funInputs' = + [ makeTupleFuncArg ("order", "tuple") orderTupleComponents + , makeBasicFuncArg ("takerAssetFillAmount", "uint256") + , makeBasicFuncArg ("signature", "bytes") + ] + funOutputs' = Nothing + makeBasicFuncArg (n,t) = + FunctionArg n t Nothing + makeTupleFuncArg (n,t) cmps = + FunctionArg n t (Just $ map makeBasicFuncArg cmps) + +fillManyOrdersDec :: Declaration +fillManyOrdersDec = DFunction "fillManyOrders" False funInputs' funOutputs' + where + funInputs' = + [ makeTupleFuncArg ("orders", "tuple[]") orderTupleComponents + , makeBasicFuncArg ("takerAssetFillAmount", "uint256") + , makeBasicFuncArg ("signature", "bytes") + ] + funOutputs' = Nothing + makeBasicFuncArg (n,t) = + FunctionArg n t Nothing + makeTupleFuncArg (n,t) cmps = + FunctionArg n t (Just $ map makeBasicFuncArg cmps) diff --git a/packages/solidity/tests/Spec.hs b/packages/solidity/tests/Spec.hs new file mode 100644 index 00000000..a824f8c3 --- /dev/null +++ b/packages/solidity/tests/Spec.hs @@ -0,0 +1 @@ +{-# OPTIONS_GHC -F -pgmF hspec-discover #-} diff --git a/packages/solidity/web3-solidity.cabal b/packages/solidity/web3-solidity.cabal new file mode 100644 index 00000000..3e453121 --- /dev/null +++ b/packages/solidity/web3-solidity.cabal @@ -0,0 +1,117 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3-solidity +version: 1.1.0.0 +synopsis: Solidity language for Haskell Web3 library. +description: This package contains Solidity parsec-based parser and primitive types. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Data.Solidity.Abi + Data.Solidity.Abi.Codec + Data.Solidity.Abi.Generic + Data.Solidity.Event + Data.Solidity.Event.Internal + Data.Solidity.Prim + Data.Solidity.Prim.Address + Data.Solidity.Prim.Bool + Data.Solidity.Prim.Bytes + Data.Solidity.Prim.Int + Data.Solidity.Prim.List + Data.Solidity.Prim.String + Data.Solidity.Prim.Tagged + Data.Solidity.Prim.Tuple + Data.Solidity.Prim.Tuple.TH + Language.Solidity.Abi + other-modules: + Paths_web3_solidity + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + OneTuple >=0.2 && <0.5 + , aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , basement ==0.0.* + , bytestring >=0.10 && <0.13 + , cereal ==0.5.* + , data-default >=0.7 && <0.9 + , generics-sop >=0.3 && <0.6 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , parsec ==3.1.* + , tagged ==0.8.* + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , web3-crypto >=1.0 && <1.2 + default-language: Haskell2010 + +test-suite tests + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Data.Solidity.Test.AddressSpec + Data.Solidity.Test.EncodingSpec + Data.Solidity.Test.IntSpec + Language.Solidity.Test.AbiSpec + Data.Solidity.Abi + Data.Solidity.Abi.Codec + Data.Solidity.Abi.Generic + Data.Solidity.Event + Data.Solidity.Event.Internal + Data.Solidity.Prim + Data.Solidity.Prim.Address + Data.Solidity.Prim.Bool + Data.Solidity.Prim.Bytes + Data.Solidity.Prim.Int + Data.Solidity.Prim.List + Data.Solidity.Prim.String + Data.Solidity.Prim.Tagged + Data.Solidity.Prim.Tuple + Data.Solidity.Prim.Tuple.TH + Language.Solidity.Abi + Paths_web3_solidity + hs-source-dirs: + tests + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + OneTuple >=0.2 && <0.5 + , aeson >=1.2 && <2.3 + , base >=4.11 && <4.21 + , basement ==0.0.* + , bytestring >=0.10 && <0.13 + , cereal ==0.5.* + , data-default >=0.7 && <0.9 + , generics-sop >=0.3 && <0.6 + , hspec >=2.4.4 && <2.12 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.12 + , hspec-expectations >=0.8.2 && <0.9 + , memory >=0.14 && <0.19 + , memory-hexstring >=1.0 && <1.2 + , microlens ==0.4.* + , parsec ==3.1.* + , tagged ==0.8.* + , template-haskell >=2.11 && <2.23 + , text >=1.2 && <2.2 + , web3-crypto >=1.0 && <1.2 + default-language: Haskell2010 diff --git a/packages/web3/LICENSE b/packages/web3/LICENSE new file mode 100644 index 00000000..500bc3e6 --- /dev/null +++ b/packages/web3/LICENSE @@ -0,0 +1,211 @@ + 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 + +APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + +Copyright 2016-2026 Aleksandr Krupenkin + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. + + NOTE + +Individual files contain the following tag instead of the full license +text. + + SPDX-License-Identifier: Apache-2.0 + +This enables machine processing of license information based on the SPDX +License Identifiers that are here available: http://spdx.org/licenses/ diff --git a/packages/web3/Setup.hs b/packages/web3/Setup.hs new file mode 100644 index 00000000..9a994af6 --- /dev/null +++ b/packages/web3/Setup.hs @@ -0,0 +1,2 @@ +import Distribution.Simple +main = defaultMain diff --git a/packages/web3/package.yaml b/packages/web3/package.yaml new file mode 100644 index 00000000..98f898bd --- /dev/null +++ b/packages/web3/package.yaml @@ -0,0 +1,44 @@ +name: web3 +version: 1.1.0.0 +synopsis: Haskell Web3 library. +description: Client library for Third Generation of Web. +github: "airalab/hs-web3" +license: Apache-2.0 +license-file: LICENSE +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: "(c) Aleksandr Krupenkin 2016-2026" +category: Network + +dependencies: +- base >=4.11 && <4.21 +- web3-provider >=1.0 && <1.2 +- web3-ethereum >=1.0 && <1.2 +- web3-polkadot >=1.0 && <1.2 + +ghc-options: +- -funbox-strict-fields +- -Wduplicate-exports +- -Widentities +- -Woverlapping-patterns +- -Wpartial-type-signatures +- -Wunrecognised-pragmas +- -Wtyped-holes +- -Wincomplete-patterns +- -Wincomplete-uni-patterns +- -Wmissing-fields +- -Wmissing-methods +- -Wmissing-exported-signatures +- -Wmissing-signatures +- -Wname-shadowing +- -Wunused-binds +- -Wunused-top-binds +- -Wunused-local-binds +- -Wunused-pattern-binds +- -Wunused-imports +- -Wunused-matches +- -Wunused-foralls +- -Wtabs + +library: + source-dirs: src diff --git a/packages/web3/src/Network/Web3.hs b/packages/web3/src/Network/Web3.hs new file mode 100644 index 00000000..d3b1d6ad --- /dev/null +++ b/packages/web3/src/Network/Web3.hs @@ -0,0 +1,25 @@ +-- | +-- Module : Network.Web3 +-- Copyright : Aleksandr Krupenkin 2016-2024 +-- License : Apache-2.0 +-- +-- Maintainer : mail@akru.me +-- Stability : experimental +-- Portability : unportable +-- +-- Client library for Third Generation of Web. +-- + +module Network.Web3 + ( + -- * Web3 library uses JSON-RPC over WebSocket/HTTP(S) to access node functionality. + Web3 + , runWeb3 + -- * Re-export popular Web3 platforms. + , module Network.Ethereum + , module Network.Polkadot + ) where + +import Network.Ethereum +import Network.Polkadot +import Network.Web3.Provider (Web3, runWeb3) diff --git a/packages/web3/web3.cabal b/packages/web3/web3.cabal new file mode 100644 index 00000000..0de6b050 --- /dev/null +++ b/packages/web3/web3.cabal @@ -0,0 +1,38 @@ +cabal-version: 1.12 + +-- This file has been generated from package.yaml by hpack version 0.39.1. +-- +-- see: https://github.com/sol/hpack + +name: web3 +version: 1.1.0.0 +synopsis: Haskell Web3 library. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Aleksandr Krupenkin +maintainer: mail@akru.me +copyright: (c) Aleksandr Krupenkin 2016-2026 +license: Apache-2.0 +license-file: LICENSE +build-type: Simple + +source-repository head + type: git + location: https://github.com/airalab/hs-web3 + +library + exposed-modules: + Network.Web3 + other-modules: + Paths_web3 + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + base >=4.11 && <4.21 + , web3-ethereum >=1.0 && <1.2 + , web3-polkadot >=1.0 && <1.2 + , web3-provider >=1.0 && <1.2 + default-language: Haskell2010 diff --git a/src/Data/String/Extra.hs b/src/Data/String/Extra.hs deleted file mode 100644 index c697d12c..00000000 --- a/src/Data/String/Extra.hs +++ /dev/null @@ -1,25 +0,0 @@ --- | --- Module : Data.String.Extra --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : portable --- --- Extra string manipulation functions. --- - -module Data.String.Extra where - -import Data.Char (toLower, toUpper) - --- | Lower first char of string -toLowerFirst :: String -> String -toLowerFirst [] = [] -toLowerFirst (x : xs) = toLower x : xs - --- | Upper first char of string -toUpperFirst :: String -> String -toUpperFirst [] = [] -toUpperFirst (x : xs) = toUpper x : xs diff --git a/src/Network/Ethereum/ABI/Codec.hs b/src/Network/Ethereum/ABI/Codec.hs deleted file mode 100644 index 285327a1..00000000 --- a/src/Network/Ethereum/ABI/Codec.hs +++ /dev/null @@ -1,63 +0,0 @@ -{-# LANGUAGE TypeFamilies #-} - --- | --- Module : Network.Ethereum.ABI.Codec --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI encoding codec functions. --- - -module Network.Ethereum.ABI.Codec ( - encode - , decode - , encode' - , decode' - ) where - -import Data.ByteArray (ByteArray, ByteArrayAccess, - convert) -import Data.Serialize (runGet, runPut) -import Generics.SOP (Generic, Rep, from, to) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - GenericABIGet (..), - GenericABIPut (..)) -import Network.Ethereum.ABI.Generic () - --- | Encode datatype to Ethereum ABI-encoding -encode :: (ABIPut a, ByteArray ba) - => a - -> ba -{-# INLINE encode #-} -encode = convert . runPut . abiPut - --- | Generic driven version of 'encode' -encode' :: (Generic a, - Rep a ~ rep, - GenericABIPut rep, - ByteArray ba) - => a - -> ba -{-# INLINE encode' #-} -encode' = convert . runPut . gAbiPut . from - --- | Decode datatype from Ethereum ABI-encoding -decode :: (ByteArrayAccess ba, ABIGet a) - => ba - -> Either String a -{-# INLINE decode #-} -decode = runGet abiGet . convert - --- | Generic driven version of 'decode' -decode' :: (Generic a, - Rep a ~ rep, - GenericABIGet rep, - ByteArrayAccess ba) - => ba - -> Either String a -decode' = runGet (to <$> gAbiGet) . convert diff --git a/src/Network/Ethereum/ABI/Generic.hs b/src/Network/Ethereum/ABI/Generic.hs deleted file mode 100644 index 4d9528f5..00000000 --- a/src/Network/Ethereum/ABI/Generic.hs +++ /dev/null @@ -1,126 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE TypeInType #-} -{-# LANGUAGE TypeOperators #-} - --- | --- Module : Network.Ethereum.ABI.Generic --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- This module is internal, the purpose is to define helper classes and functions --- to assist in encoding and decoding Solidity types for function calls and events. --- The user of this library should have no need to use this directly in application code. --- - -module Network.Ethereum.ABI.Generic () where - -import qualified Data.ByteString.Lazy as LBS -import Data.Int (Int64) -import qualified Data.List as L -import Data.Monoid ((<>)) -import Data.Proxy (Proxy (..)) -import Data.Serialize (Get, Put) -import Data.Serialize.Get (bytesRead, lookAheadE, skip) -import Data.Serialize.Put (runPutLazy) -import Generics.SOP (I (..), NP (..), NS (..), - SOP (..)) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..), - GenericABIGet (..), - GenericABIPut (..)) -import Network.Ethereum.ABI.Prim.Int (getWord256, putWord256) - -data EncodedValue = - EncodedValue { order :: Int64 - , offset :: Maybe Int64 - , encoding :: Put - } - -instance Eq EncodedValue where - ev1 == ev2 = order ev1 == order ev2 - -instance Ord EncodedValue where - compare ev1 ev2 = order ev1 `compare` order ev2 - -combineEncodedValues :: [EncodedValue] -> Put -combineEncodedValues encodings = - let sortedEs = adjust headsOffset $ L.sort encodings - encodings' = addTailOffsets headsOffset [] sortedEs - in let heads = foldl (\acc EncodedValue{..} -> case offset of - Nothing -> acc <> encoding - Just o -> acc <> putWord256 (fromIntegral o) - ) mempty encodings' - tails = foldl (\acc EncodedValue{..} -> case offset of - Nothing -> acc - Just _ -> acc <> encoding - ) mempty encodings' - in heads <> tails - where - adjust :: Int64 -> [EncodedValue] -> [EncodedValue] - adjust n = map (\ev -> ev {offset = (+) n <$> offset ev}) - addTailOffsets :: Int64 -> [EncodedValue] -> [EncodedValue] -> [EncodedValue] - addTailOffsets init' acc es = case es of - [] -> reverse acc - (e : tail') -> case offset e of - Nothing -> addTailOffsets init' (e : acc) tail' - Just _ -> addTailOffsets init' (e : acc) (adjust (LBS.length . runPutLazy . encoding $ e) tail') - headsOffset :: Int64 - headsOffset = foldl (\acc e -> case offset e of - Nothing -> acc + (LBS.length . runPutLazy . encoding $ e) - Just _ -> acc + 32 - ) 0 encodings - -class ABIData a where - _serialize :: [EncodedValue] -> a -> [EncodedValue] - -instance ABIData (NP f '[]) where - _serialize encoded _ = encoded - -instance (ABIType b, ABIPut b, ABIData (NP I as)) => ABIData (NP I (b :as)) where - _serialize encoded (I b :* a) = - if isDynamic (Proxy :: Proxy b) - then _serialize (dynEncoding : encoded) a - else _serialize (staticEncoding : encoded) a - where - staticEncoding = EncodedValue { encoding = abiPut b - , offset = Nothing - , order = 1 + (fromInteger . toInteger . L.length $ encoded) - } - dynEncoding = EncodedValue { encoding = abiPut b - , offset = Just 0 - , order = 1 + (fromInteger . toInteger . L.length $ encoded) - } - -instance ABIData (NP f as) => GenericABIPut (SOP f '[as]) where - gAbiPut (SOP (Z a)) = combineEncodedValues $ _serialize [] a - gAbiPut _ = error "Impossible branch" - -instance GenericABIGet (NP f '[]) where - gAbiGet = return Nil - -instance (ABIGet a, GenericABIGet (NP I as)) => GenericABIGet (NP I (a : as)) where - gAbiGet = (:*) <$> (I <$> factorParser) <*> gAbiGet - -instance GenericABIGet (NP f as) => GenericABIGet (SOP f '[as]) where - gAbiGet = SOP . Z <$> gAbiGet - -factorParser :: forall a . ABIGet a => Get a -factorParser - | not $ isDynamic (Proxy :: Proxy a) = abiGet - | otherwise = do - dataOffset <- fromIntegral <$> getWord256 - currentOffset <- bytesRead - Left x <- lookAheadE $ do - skip (dataOffset - currentOffset) - Left <$> abiGet - return x diff --git a/src/Network/Ethereum/ABI/Json.hs b/src/Network/Ethereum/ABI/Json.hs deleted file mode 100644 index 820cf077..00000000 --- a/src/Network/Ethereum/ABI/Json.hs +++ /dev/null @@ -1,280 +0,0 @@ -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.ABI.Json --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- JSON encoded contract ABI parsers. --- - -module Network.Ethereum.ABI.Json ( - ContractABI(..) - , Declaration(..) - , FunctionArg(..) - , EventArg(..) - , signature - , methodId - , eventId - , SolidityType(..) - , parseSolidityType - ) where - -import Control.Monad (void) -import Crypto.Hash (Digest, Keccak_256, hash) -import Data.Aeson (FromJSON (parseJSON), Options (constructorTagModifier, fieldLabelModifier, sumEncoding), - SumEncoding (TaggedObject), - ToJSON (toJSON), defaultOptions) -import Data.Aeson.TH (deriveJSON) -import Data.Monoid ((<>)) -import Data.Text (Text) -import qualified Data.Text as T (dropEnd, pack, take, unlines, unpack) -import Data.Text.Encoding (encodeUtf8) -import Text.Parsec (ParseError, char, choice, digit, eof, - lookAhead, many1, manyTill, optionMaybe, - parse, string, try, (<|>)) -import Text.Parsec.Text (Parser) - -import Data.String.Extra (toLowerFirst) - --- | Method argument -data FunctionArg = FunctionArg - { funArgName :: Text - -- ^ Argument name - , funArgType :: Text - -- ^ Argument type - } deriving (Show, Eq, Ord) - -$(deriveJSON - (defaultOptions {fieldLabelModifier = toLowerFirst . drop 6}) - ''FunctionArg) - --- | Event argument -data EventArg = EventArg - { eveArgName :: Text - -- ^ Argument name - , eveArgType :: Text - -- ^ Argument type - , eveArgIndexed :: Bool - -- ^ Argument is indexed (e.g. placed on topics of event) - } deriving (Show, Eq, Ord) - -$(deriveJSON - (defaultOptions {fieldLabelModifier = toLowerFirst . drop 6}) - ''EventArg) - --- | Elementrary contract interface item -data Declaration - = DConstructor { conInputs :: [FunctionArg] } - -- ^ Contract constructor - | DFunction { funName :: Text - , funConstant :: Bool - , funInputs :: [FunctionArg] - , funOutputs :: Maybe [FunctionArg] } - -- ^ Method - | DEvent { eveName :: Text - , eveInputs :: [EventArg] - , eveAnonymous :: Bool } - -- ^ Event - | DFallback { falPayable :: Bool } - -- ^ Fallback function - deriving Show - -instance Eq Declaration where - (DConstructor a) == (DConstructor b) = length a == length b - (DFunction a _ _ _) == (DFunction b _ _ _) = a == b - (DEvent a _ _) == (DEvent b _ _) = a == b - (DFallback _) == (DFallback _) = True - (==) _ _ = False - -instance Ord Declaration where - compare (DConstructor a) (DConstructor b) = compare (length a) (length b) - compare (DFunction a _ _ _) (DFunction b _ _ _) = compare a b - compare (DEvent a _ _) (DEvent b _ _) = compare a b - compare (DFallback _) (DFallback _) = EQ - - compare DConstructor {} DFunction {} = LT - compare DConstructor {} DEvent {} = LT - compare DConstructor {} DFallback {} = LT - - compare DFunction {} DConstructor {} = GT - compare DFunction {} DEvent {} = LT - compare DFunction {} DFallback {} = LT - - compare DEvent {} DConstructor {} = GT - compare DEvent {} DFunction {} = GT - compare DEvent {} DFallback {} = LT - - compare DFallback {} DConstructor {} = GT - compare DFallback {} DFunction {} = GT - compare DFallback {} DEvent {} = GT - -$(deriveJSON (defaultOptions { - sumEncoding = TaggedObject "type" "contents" - , constructorTagModifier = toLowerFirst . drop 1 - , fieldLabelModifier = toLowerFirst . drop 3 }) - ''Declaration) - --- | Contract ABI is a list of method / event declarations -newtype ContractABI = ContractABI { unABI :: [Declaration] } - deriving (Eq, Ord) - -instance FromJSON ContractABI where - parseJSON = fmap ContractABI . parseJSON - -instance ToJSON ContractABI where - toJSON = toJSON . unABI - -instance Show ContractABI where - show (ContractABI c) = T.unpack $ T.unlines $ - [ "Contract:" ] - ++ foldMap showConstructor c ++ - [ "\tEvents:" ] - ++ foldMap showEvent c ++ - [ "\tMethods:" ] - ++ foldMap showMethod c - -showConstructor :: Declaration -> [Text] -showConstructor x = case x of - DConstructor{} -> ["\tConstructor " <> signature x] - _ -> [] - -showEvent :: Declaration -> [Text] -showEvent x = case x of - DEvent{} -> ["\t\t" <> signature x] - _ -> [] - -showMethod :: Declaration -> [Text] -showMethod x = case x of - DFunction{} -> - ["\t\t" <> methodId x <> " " <> signature x] - _ -> [] - --- | Take a signature by given decl, e.g. foo(uint,string) -signature :: Declaration -> Text - -signature (DConstructor inputs) = "(" <> args inputs <> ")" - where - args :: [FunctionArg] -> Text - args = T.dropEnd 1 . foldMap (<> ",") . fmap funArgType - -signature (DFallback _) = "()" - -signature (DFunction name _ inputs _) = name <> "(" <> args inputs <> ")" - where - args :: [FunctionArg] -> Text - args = T.dropEnd 1 . foldMap (<> ",") . fmap funArgType - -signature (DEvent name inputs _) = name <> "(" <> args inputs <> ")" - where - args :: [EventArg] -> Text - args = T.dropEnd 1 . foldMap (<> ",") . fmap eveArgType - --- | Localy compute Keccak-256 hash of given text -sha3 :: Text -> Text -{-# INLINE sha3 #-} -sha3 x = T.pack (show digest) - where digest :: Digest Keccak_256 - digest = hash (encodeUtf8 x) - --- | Generate method selector by given method 'Delcaration' -methodId :: Declaration -> Text -{-# INLINE methodId #-} -methodId = ("0x" <>) . T.take 8 . sha3 . signature - --- | Generate event `topic0` hash by givent event 'Delcaration' -eventId :: Declaration -> Text -{-# INLINE eventId #-} -eventId = ("0x" <>) . sha3 . signature - --- | Solidity types and parsers -data SolidityType = - SolidityBool - | SolidityAddress - | SolidityUint Int - | SolidityInt Int - | SolidityString - | SolidityBytesN Int - | SolidityBytes - | SolidityVector [Int] SolidityType - | SolidityArray SolidityType - deriving (Eq, Show) - -numberParser :: Parser Int -numberParser = read <$> many1 digit - -parseUint :: Parser SolidityType -parseUint = do - _ <- string "uint" - n <- numberParser - pure $ SolidityUint n - -parseInt :: Parser SolidityType -parseInt = do - _ <- string "int" - n <- numberParser - pure $ SolidityInt n - -parseBool :: Parser SolidityType -parseBool = string "bool" >> pure SolidityBool - -parseString :: Parser SolidityType -parseString = string "string" >> pure SolidityString - -parseBytes :: Parser SolidityType -parseBytes = do - _ <- string "bytes" - mn <- optionMaybe numberParser - pure $ maybe SolidityBytes SolidityBytesN mn - -parseAddress :: Parser SolidityType -parseAddress = string "address" >> pure SolidityAddress - -solidityBasicTypeParser :: Parser SolidityType -solidityBasicTypeParser = - choice [ try parseUint - , try parseInt - , try parseAddress - , try parseBool - , try parseString - , parseBytes - ] - -parseVector :: Parser SolidityType -parseVector = do - s <- solidityBasicTypeParser - ns <- many1Till lengthParser ((lookAhead $ void (string "[]")) <|> eof) - pure $ SolidityVector ns s - where - many1Till :: Parser Int -> Parser () -> Parser [Int] - many1Till p end = do - a <- p - as <- manyTill p end - return (a : as) - - lengthParser = do - _ <- char '[' - n <- numberParser - _ <- char ']' - pure n - -parseArray :: Parser SolidityType -parseArray = do - s <- (try $ parseVector <* string "[]") <|> (solidityBasicTypeParser <* string "[]") - pure $ SolidityArray s - - -solidityTypeParser :: Parser SolidityType -solidityTypeParser = - choice [ try parseArray - , try parseVector - , solidityBasicTypeParser - ] - -parseSolidityType :: Text -> Either ParseError SolidityType -parseSolidityType = parse solidityTypeParser "Solidity" diff --git a/src/Network/Ethereum/ABI/Prim.hs b/src/Network/Ethereum/ABI/Prim.hs deleted file mode 100644 index a9fa47ad..00000000 --- a/src/Network/Ethereum/ABI/Prim.hs +++ /dev/null @@ -1,30 +0,0 @@ --- | --- Module : Network.Ethereum.ABI.Prim --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI encoding primitive types. --- - -module Network.Ethereum.ABI.Prim ( - Address - , Bytes - , BytesN - , IntN - , UIntN - , ListN - , Singleton(..) - ) where - -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.ABI.Prim.Bool () -import Network.Ethereum.ABI.Prim.Bytes (Bytes, BytesN) -import Network.Ethereum.ABI.Prim.Int (IntN, UIntN) -import Network.Ethereum.ABI.Prim.List (ListN) -import Network.Ethereum.ABI.Prim.String () -import Network.Ethereum.ABI.Prim.Tagged () -import Network.Ethereum.ABI.Prim.Tuple (Singleton (..)) diff --git a/src/Network/Ethereum/ABI/Prim/Address.hs b/src/Network/Ethereum/ABI/Prim/Address.hs deleted file mode 100644 index 63a19eb9..00000000 --- a/src/Network/Ethereum/ABI/Prim/Address.hs +++ /dev/null @@ -1,103 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE OverloadedStrings #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Address --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI address type. --- - -module Network.Ethereum.ABI.Prim.Address ( - Address - , fromHexString - , toHexString - , toChecksum - , verifyChecksum - ) where - -import Control.Monad ((<=<)) -import Crypto.Hash (Keccak_256 (..), hashWith) -import Data.Aeson (FromJSON (..), ToJSON (..), - Value (String)) -import Data.Bits ((.&.)) -import Data.Bool (bool) -import Data.ByteArray (Bytes, convert, length, zero) -import Data.ByteArray.Encoding (Base (Base16), convertFromBase, - convertToBase) -import Data.ByteString (ByteString) -import qualified Data.ByteString as BS (take, unpack) -import qualified Data.ByteString.Char8 as C8 (drop, pack, take, unpack) -import qualified Data.Char as C (toLower, toUpper) -import Data.Monoid ((<>)) -import Data.String (IsString (..)) -import Data.Text.Encoding (decodeUtf8, encodeUtf8) -import Generics.SOP (Generic) -import qualified GHC.Generics as GHC (Generic) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) -import Network.Ethereum.ABI.Codec (decode, encode) -import Network.Ethereum.ABI.Prim.Int (UIntN) -import Prelude hiding (length) - --- | Ethereum account address -newtype Address = Address { unAddress :: UIntN 160 } - deriving (Eq, Ord, GHC.Generic) - -instance Generic Address - --- TODO: Address . drop 12 . sha3 -{- -fromPublic :: ByteArrayAccess bin => bin -> Maybe Address -fromPublic = undefined --} - -fromHexString :: ByteString -> Either String Address -fromHexString = decode . align <=< lenck <=< convertFromBase Base16 . trim0x - where trim0x s | C8.take 2 s == "0x" = C8.drop 2 s - | otherwise = s - lenck a | length a == 20 = pure a - | otherwise = Left "Invalid address length" - align = (zero 12 <>) :: Bytes -> Bytes - -toHexString :: Address -> ByteString -toHexString = ("0x" <>) . convertToBase Base16 . C8.drop 12 . encode - -toChecksum :: ByteString -> ByteString -toChecksum addr = ("0x"<>) . C8.pack $ zipWith ($) upcaseVector lower - where - upcaseVector = (>>= fourthBits) . BS.unpack . BS.take 20 . convert $ hashWith Keccak_256 (C8.pack lower) - fourthBits n = bool id C.toUpper <$> [n .&. 0x80 /= 0, n .&. 0x08 /= 0] - lower = drop 2 . fmap C.toLower . C8.unpack $ addr - -verifyChecksum :: ByteString -> Bool -verifyChecksum = toChecksum >>= (==) - -instance Show Address where - show = C8.unpack . toHexString - -instance IsString Address where - fromString = either error id . fromHexString . C8.pack - -instance ABIType Address where - isDynamic _ = False - -instance ABIGet Address where - abiGet = Address <$> abiGet - -instance ABIPut Address where - abiPut = abiPut . unAddress - -instance FromJSON Address where - parseJSON (String a) = either fail return $ fromHexString (encodeUtf8 a) - parseJSON _ = fail "Address should be a string" - -instance ToJSON Address where - toJSON = String . decodeUtf8 . toHexString diff --git a/src/Network/Ethereum/ABI/Prim/Bool.hs b/src/Network/Ethereum/ABI/Prim/Bool.hs deleted file mode 100644 index 0ccb17cc..00000000 --- a/src/Network/Ethereum/ABI/Prim/Bool.hs +++ /dev/null @@ -1,29 +0,0 @@ -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Bool --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI boolean type. --- - -module Network.Ethereum.ABI.Prim.Bool () where - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) -import Network.Ethereum.ABI.Prim.Int (getWord256, putWord256) - -instance ABIType Bool where - isDynamic _ = False - -instance ABIGet Bool where - abiGet = toEnum . fromIntegral <$> getWord256 - -instance ABIPut Bool where - abiPut = putWord256 . fromIntegral . fromEnum diff --git a/src/Network/Ethereum/ABI/Prim/Bytes.hs b/src/Network/Ethereum/ABI/Prim/Bytes.hs deleted file mode 100644 index 5fb1c44d..00000000 --- a/src/Network/Ethereum/ABI/Prim/Bytes.hs +++ /dev/null @@ -1,125 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE TypeOperators #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Bytes --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI bytes and bytesN types. --- - -module Network.Ethereum.ABI.Prim.Bytes ( - Bytes - , BytesN - ) where - -import Control.Monad (unless) -import Data.Aeson (FromJSON (..), ToJSON (..), - Value (String)) -import Data.ByteArray (Bytes, convert, length, zero) -import Data.ByteArray.Encoding (Base (Base16), convertFromBase, - convertToBase) -import Data.ByteArray.Sized (SizedByteArray, - unSizedByteArray, - unsafeFromByteArrayAccess) -import qualified Data.ByteArray.Sized as S (take) -import Data.ByteString (ByteString) -import qualified Data.ByteString.Char8 as C8 -import Data.Monoid ((<>)) -import Data.Proxy (Proxy (..)) -import Data.Serialize (Get, Putter, getBytes, - putByteString) -import Data.String (IsString (..)) -import qualified Data.Text as T (append, drop, take) -import Data.Text.Encoding (decodeUtf8, encodeUtf8) -import GHC.TypeLits -import Prelude hiding (length) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) -import Network.Ethereum.ABI.Prim.Int (getWord256, putWord256) - -instance ABIType ByteString where - isDynamic _ = True - -instance ABIGet ByteString where - abiGet = abiGetByteString - -instance ABIPut ByteString where - abiPut = abiPutByteString - -instance ABIType Bytes where - isDynamic _ = True - -instance ABIGet Bytes where - abiGet = convert <$> abiGetByteString - -instance ABIPut Bytes where - abiPut = abiPutByteString . convert - -instance IsString Bytes where - fromString ('0' : 'x' : hex) = either error id $ convertFromBase Base16 (C8.pack hex) - fromString str = convert (C8.pack str) - -instance FromJSON Bytes where - parseJSON (String hex) - | T.take 2 hex == "0x" = - either fail pure $ convertFromBase Base16 $ encodeUtf8 $ T.drop 2 hex - | otherwise = fail "Hex string should have '0x' prefix" - parseJSON _ = fail "Bytes should be encoded as hex string" - -instance ToJSON Bytes where - toJSON = toJSON . T.append "0x" . decodeUtf8 . convertToBase Base16 - -type BytesN n = SizedByteArray n Bytes - -instance (n <= 32) => ABIType (BytesN n) where - isDynamic _ = False - -instance (KnownNat n, n <= 32) => ABIGet (BytesN n) where - abiGet = do - ba <- unsafeFromByteArrayAccess <$> getBytes 32 - return $ S.take (ba :: BytesN 32) - -instance (KnownNat n, n <= 32) => ABIPut (BytesN n) where - abiPut ba = putByteString $ convert ba <> zero (32 - len) - where len = fromIntegral $ natVal (Proxy :: Proxy n) - -instance (KnownNat n, n <= 32) => IsString (BytesN n) where - fromString s = unsafeFromByteArrayAccess padded - where bytes = fromString s :: Bytes - len = fromIntegral $ natVal (Proxy :: Proxy n) - padded = bytes <> zero (len - length bytes) - -instance (KnownNat n, n <= 32) => FromJSON (BytesN n) where - parseJSON v = do ba <- parseJSON v - return $ unsafeFromByteArrayAccess (ba :: Bytes) - -instance (KnownNat n, n <= 32) => ToJSON (BytesN n) where - toJSON ba = toJSON (unSizedByteArray ba :: Bytes) - -abiGetByteString :: Get ByteString -abiGetByteString = do - len <- fromIntegral <$> getWord256 - if len == 0 then - return "" - else do - ba <- getBytes len - return ba - -abiPutByteString :: Putter ByteString -abiPutByteString bs = do - putWord256 $ fromIntegral len - unless (len == 0) $ - putByteString $ bs <> zero (32 - len `mod` 32) - where len = length bs diff --git a/src/Network/Ethereum/ABI/Prim/Int.hs b/src/Network/Ethereum/ABI/Prim/Int.hs deleted file mode 100644 index 7098205b..00000000 --- a/src/Network/Ethereum/ABI/Prim/Int.hs +++ /dev/null @@ -1,119 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE KindSignatures #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE TypeOperators #-} - --- | --- Module : Network.Ethereum.Encoding.Prim.Int --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI intN and uintN types. --- - -module Network.Ethereum.ABI.Prim.Int ( - IntN - , UIntN - , getWord256 - , putWord256 - ) where - -import qualified Basement.Numerical.Number as Basement (toInteger) -import Basement.Types.Word256 (Word256 (Word256)) -import qualified Basement.Types.Word256 as Basement (quot, rem) -import Data.Bits (Bits (testBit)) -import Data.Proxy (Proxy (..)) -import Data.Serialize (Get, Putter, Serialize (get, put)) -import GHC.Generics (Generic) -import GHC.TypeLits - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) - -instance Real Word256 where - toRational = toRational . toInteger - -instance Integral Word256 where - toInteger = Basement.toInteger - quotRem a b = (Basement.quot a b, Basement.rem a b) - -newtype UIntN (n :: Nat) = UIntN { unUIntN :: Word256 } - deriving (Eq, Ord, Enum, Num, Bits, Generic) - -instance (KnownNat n, n <= 256) => Show (UIntN n) where - show = show . unUIntN - -instance (KnownNat n, n <= 256) => Bounded (UIntN n) where - minBound = 0 - maxBound = 2 ^ (natVal (Proxy :: Proxy n)) - 1 - -instance (KnownNat n, n <= 256) => Real (UIntN n) where - toRational = toRational . toInteger - -instance (KnownNat n, n <= 256) => Integral (UIntN n) where - toInteger = toInteger . unUIntN - quotRem (UIntN a) (UIntN b) = (UIntN $ quot a b, UIntN $ rem a b) - -instance (n <= 256) => ABIType (UIntN n) where - isDynamic _ = False - -instance (n <= 256) => ABIGet (UIntN n) where - abiGet = UIntN <$> getWord256 - -instance (n <= 256) => ABIPut (UIntN n) where - abiPut = putWord256 . unUIntN - --- TODO: Signed data type -newtype IntN (n :: Nat) = IntN { unIntN :: Word256 } - deriving (Eq, Ord, Enum, Bits, Generic) - -instance (KnownNat n, n <= 256) => Show (IntN n) where - show = show . toInteger - -instance (KnownNat n, n <= 256) => Bounded (IntN n) where - minBound = negate $ 2 ^ (natVal (Proxy :: Proxy (n :: Nat)) - 1) - maxBound = 2 ^ (natVal (Proxy :: Proxy (n :: Nat)) - 1) - 1 - -instance (KnownNat n, n <= 256) => Num (IntN n) where - a + b = fromInteger (toInteger a + toInteger b) - a - b = fromInteger (toInteger a - toInteger b) - a * b = fromInteger (toInteger a * toInteger b) - abs = fromInteger . abs . toInteger - negate = fromInteger . negate . toInteger - signum = fromInteger . signum . toInteger - fromInteger x - | x >= 0 = IntN (fromInteger x) - | otherwise = IntN (fromInteger $ 2 ^ 256 + x) - -instance (KnownNat n, n <= 256) => Real (IntN n) where - toRational = toRational . toInteger - -instance (KnownNat n, n <= 256) => Integral (IntN n) where - quotRem (IntN a) (IntN b) = (IntN $ quot a b, IntN $ rem a b) - toInteger x - | testBit x 255 = toInteger (unIntN x) - 2 ^ 256 - | otherwise = toInteger $ unIntN x - -instance (n <= 256) => ABIType (IntN n) where - isDynamic _ = False - -instance (n <= 256) => ABIGet (IntN n) where - abiGet = IntN <$> getWord256 - -instance (n <= 256) => ABIPut (IntN n) where - abiPut = putWord256 . unIntN - -putWord256 :: Putter Word256 -putWord256 (Word256 a3 a2 a1 a0) = - put a3 >> put a2 >> put a1 >> put a0 - -getWord256 :: Get Word256 -getWord256 = Word256 <$> get <*> get <*> get <*> get diff --git a/src/Network/Ethereum/ABI/Prim/List.hs b/src/Network/Ethereum/ABI/Prim/List.hs deleted file mode 100644 index d7006b25..00000000 --- a/src/Network/Ethereum/ABI/Prim/List.hs +++ /dev/null @@ -1,55 +0,0 @@ -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE UndecidableInstances #-} - --- | --- Module : Network.Ethereum.ABI.Prim.List --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI dynamic and static size vectors based on linked lists. --- - -module Network.Ethereum.ABI.Prim.List ( - ListN - ) where - -import Basement.Nat (NatWithinBound) -import Basement.Sized.List (ListN, toListN_, unListN) -import qualified Basement.Sized.List as SL (mapM_, replicateM) -import Control.Monad (replicateM) -import GHC.Exts (IsList (..)) -import GHC.TypeLits (KnownNat) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) -import Network.Ethereum.ABI.Prim.Int (getWord256, putWord256) - -instance ABIType [a] where - isDynamic _ = True - -instance ABIPut a => ABIPut [a] where - abiPut l = do putWord256 $ fromIntegral (length l) - foldMap abiPut l - -instance ABIGet a => ABIGet [a] where - abiGet = do len <- fromIntegral <$> getWord256 - replicateM len abiGet - -instance ABIType (ListN n a) where - isDynamic _ = False - -instance ABIPut a => ABIPut (ListN n a) where - abiPut = SL.mapM_ abiPut - -instance (NatWithinBound Int n, KnownNat n, ABIGet a) => ABIGet (ListN n a) where - abiGet = SL.replicateM abiGet - -instance (NatWithinBound Int n, KnownNat n) => IsList (ListN n a) where - type Item (ListN n a) = a - fromList = toListN_ - toList = unListN diff --git a/src/Network/Ethereum/ABI/Prim/String.hs b/src/Network/Ethereum/ABI/Prim/String.hs deleted file mode 100644 index e884c9e0..00000000 --- a/src/Network/Ethereum/ABI/Prim/String.hs +++ /dev/null @@ -1,29 +0,0 @@ --- | --- Module : Network.Ethereum.ABI.Prim.String --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI UTF8-encoded string type. --- - -module Network.Ethereum.ABI.Prim.String () where - -import Data.Text (Text) -import Data.Text.Encoding (decodeUtf8, encodeUtf8) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) -import Network.Ethereum.ABI.Prim.Bytes () - -instance ABIType Text where - isDynamic _ = True - -instance ABIPut Text where - abiPut = abiPut . encodeUtf8 - -instance ABIGet Text where - abiGet = decodeUtf8 <$> abiGet diff --git a/src/Network/Ethereum/ABI/Prim/Tagged.hs b/src/Network/Ethereum/ABI/Prim/Tagged.hs deleted file mode 100644 index 47a46ff2..00000000 --- a/src/Network/Ethereum/ABI/Prim/Tagged.hs +++ /dev/null @@ -1,43 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE PolyKinds #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeFamilies #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Tagged --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Ethereum ABI UTF8-encoded tagged types. --- - -module Network.Ethereum.ABI.Prim.Tagged ( - Tagged - ) where - -import Data.Proxy (Proxy (..)) -import Data.Tagged (Tagged (..)) -import Generics.SOP (Code, Generic (..), I (..), - NP (..), NS (..), SOP (..)) - -import Network.Ethereum.ABI.Class (ABIGet (..), ABIPut (..), - ABIType (..)) - -instance ABIType a => ABIType (Tagged t a) where - isDynamic _ = isDynamic (Proxy :: Proxy a) - -instance ABIPut a => ABIPut (Tagged t a) where - abiPut (Tagged a) = abiPut a - -instance ABIGet a => ABIGet (Tagged t a) where - abiGet = Tagged <$> abiGet - -instance Generic (Tagged t a) where - type Code (Tagged t a) = '[ '[a]] - from (Tagged a) = SOP (Z (I a :* Nil)) - to (SOP (Z (I a :* Nil))) = Tagged a - to _ = error "Invalid Tagged SOP decomposition" diff --git a/src/Network/Ethereum/ABI/Prim/Tuple.hs b/src/Network/Ethereum/ABI/Prim/Tuple.hs deleted file mode 100644 index 35330c70..00000000 --- a/src/Network/Ethereum/ABI/Prim/Tuple.hs +++ /dev/null @@ -1,45 +0,0 @@ -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE StandaloneDeriving #-} -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Tuple --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- Tuple type abi encoding instances. --- - -module Network.Ethereum.ABI.Prim.Tuple ( - Singleton(..) - ) where - -import Data.Proxy (Proxy (..)) -import Generics.SOP (Generic) -import qualified GHC.Generics as GHC (Generic) - -import Network.Ethereum.ABI.Class (ABIGet, ABIPut, - ABIType (..)) -import Network.Ethereum.ABI.Generic () -import Network.Ethereum.ABI.Prim.Tuple.TH (tupleDecs) - --- | The type for one-tuples -newtype Singleton a = Singleton { unSingleton :: a } - deriving GHC.Generic - -deriving instance Eq a => Eq (Singleton a) -deriving instance Show a => Show (Singleton a) -instance Generic (Singleton a) - -instance ABIType a => ABIType (Singleton a) where - isDynamic _ = isDynamic (Proxy :: Proxy a) - -instance ABIGet a => ABIGet (Singleton a) -instance ABIPut a => ABIPut (Singleton a) - -$(fmap concat $ sequence $ map tupleDecs [2..20]) diff --git a/src/Network/Ethereum/ABI/Prim/Tuple/TH.hs b/src/Network/Ethereum/ABI/Prim/Tuple/TH.hs deleted file mode 100644 index 5c3303d6..00000000 --- a/src/Network/Ethereum/ABI/Prim/Tuple/TH.hs +++ /dev/null @@ -1,34 +0,0 @@ -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.ABI.Prim.Tuple.TH --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : noportable --- --- This module is for internal usage only. --- It contains tuple abi encoding template haskell generator. --- - -module Network.Ethereum.ABI.Prim.Tuple.TH (tupleDecs) where - - -import Control.Monad (replicateM) -import Language.Haskell.TH (DecsQ, Type (VarT), appT, clause, - conT, cxt, funD, instanceD, - newName, normalB, tupleT) - -import Network.Ethereum.ABI.Class (ABIGet, ABIPut, ABIType (..)) - -tupleDecs :: Int -> DecsQ -tupleDecs n = do - vars <- replicateM n $ newName "a" - let types = fmap (pure . VarT) vars - sequence $ - [ instanceD (cxt $ map (appT $ conT ''ABIType) types) (appT (conT ''ABIType) (foldl appT (tupleT n) types)) - [funD 'isDynamic [clause [] (normalB [|const False|]) []]] - , instanceD (cxt $ map (appT $ conT ''ABIGet) types) (appT (conT ''ABIGet) (foldl appT (tupleT n) types)) [] - , instanceD (cxt $ map (appT $ conT ''ABIPut) types) (appT (conT ''ABIPut) (foldl appT (tupleT n) types)) [] ] diff --git a/src/Network/Ethereum/Contract/Event.hs b/src/Network/Ethereum/Contract/Event.hs deleted file mode 100644 index fab7c9f6..00000000 --- a/src/Network/Ethereum/Contract/Event.hs +++ /dev/null @@ -1,40 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE FunctionalDependencies #-} -{-# LANGUAGE GADTs #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE RankNTypes #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TypeApplications #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE TypeFamilyDependencies #-} -{-# LANGUAGE TypeOperators #-} -{-# LANGUAGE UndecidableInstances #-} - - --- | --- Module : Network.Ethereum.Contract.Event --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- Ethereum contract event support. --- - -module Network.Ethereum.Contract.Event - ( module Network.Ethereum.Contract.Event.Common - , module Network.Ethereum.Contract.Event.SingleFilter - , module Network.Ethereum.Contract.Event.MultiFilter - ) where - -import Network.Ethereum.Contract.Event.Common -import Network.Ethereum.Contract.Event.MultiFilter -import Network.Ethereum.Contract.Event.SingleFilter - --------------------------------------------------------------------------------- - diff --git a/src/Network/Ethereum/Contract/Event/Common.hs b/src/Network/Ethereum/Contract/Event/Common.hs deleted file mode 100644 index e7932183..00000000 --- a/src/Network/Ethereum/Contract/Event/Common.hs +++ /dev/null @@ -1,74 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE FunctionalDependencies #-} -{-# LANGUAGE GADTs #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE UndecidableInstances #-} - -module Network.Ethereum.Contract.Event.Common where - -import Control.Concurrent (threadDelay) -import Control.Exception (Exception, throwIO) -import Control.Monad.IO.Class (liftIO) -import Data.Either (lefts, rights) -import Network.Ethereum.ABI.Event (DecodeEvent (..)) -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Change (..), DefaultBlock (..), - Filter (..), Quantity) - --- | Event callback control response -data EventAction = ContinueEvent - -- ^ Continue to listen events - | TerminateEvent - -- ^ Terminate event listener - deriving (Show, Eq) - - -data FilterChange a = - FilterChange { filterChangeRawChange :: Change - , filterChangeEvent :: a - } - -data EventParseFailure = EventParseFailure String deriving (Show) - -instance Exception EventParseFailure - -mkFilterChanges :: DecodeEvent i ni e - => [Change] - -> IO [FilterChange e] -mkFilterChanges changes = - let eChanges = map (\c@Change{..} -> FilterChange c <$> decodeEvent c) changes - ls = lefts eChanges - rs = rights eChanges - in if ls /= [] then throwIO (EventParseFailure $ (show ls)) else pure rs - - -data FilterStreamState e = - FilterStreamState { fssCurrentBlock :: Quantity - , fssInitialFilter :: Filter e - , fssWindowSize :: Integer - } - - --- | Coerce a 'DefaultBlock' into a numerical block number. -mkBlockNumber :: DefaultBlock -> Web3 Quantity -mkBlockNumber bm = case bm of - BlockWithNumber bn -> return bn - Earliest -> return 0 - _ -> Eth.blockNumber - - -pollTillBlockProgress - :: Quantity - -> Web3 Quantity -pollTillBlockProgress currentBlock = do - bn <- Eth.blockNumber - if currentBlock >= bn - then do - liftIO $ threadDelay 3000000 - pollTillBlockProgress currentBlock - else pure bn diff --git a/src/Network/Ethereum/Contract/Method.hs b/src/Network/Ethereum/Contract/Method.hs deleted file mode 100644 index c6a0d3ed..00000000 --- a/src/Network/Ethereum/Contract/Method.hs +++ /dev/null @@ -1,101 +0,0 @@ -{-# LANGUAGE ScopedTypeVariables #-} - --- | --- Module : Network.Ethereum.Contract.Method --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- Ethereum contract method support. --- - -module Network.Ethereum.Contract.Method ( - Method(..) - , call - , sendTx - , sendTx' - ) where - -import Control.Monad.Catch (throwM) -import Control.Monad.Reader -import Data.Monoid ((<>)) -import Data.Proxy (Proxy (..)) -import Data.Text (Text) - -import Network.Ethereum.ABI.Class (ABIGet, ABIPut, - ABIType (..)) -import Network.Ethereum.ABI.Codec (decode, encode) -import Network.Ethereum.ABI.Prim.Bytes (Bytes) -import qualified Network.Ethereum.Web3.Eth as Eth -import qualified Network.Ethereum.Web3.Personal as Personal -import Network.Ethereum.Web3.Provider (Provider (..), - SigningConfiguration (..), - Web3, - Web3Error (ParserFail, UserFail)) -import Network.Ethereum.Web3.Transaction (createRawTransaction) -import Network.Ethereum.Web3.Types (Call (callData), - DefaultBlock, Hash) - -class ABIPut a => Method a where - selector :: Proxy a -> Bytes - -instance ABIType () where - isDynamic _ = False - -instance ABIPut () - --- | Send transaction without method selection -instance Method () where - selector = mempty - --- | 'sendTx' is used to submit a state changing transaction. -sendTx :: Method a - => Call - -- ^ Call configuration - -> a - -- ^ method data - -> Web3 Hash -sendTx call' (dat :: a) = do - let sel = selector (Proxy :: Proxy a) - callArgs = call' { callData = Just $ sel <> encode dat } - signingConfigM <- asks (signingConfiguration . fst) - case signingConfigM of - Just (SigningConfiguration privKey chainId) -> do - txBytes <- either (throwM . UserFail) pure $ - createRawTransaction callArgs chainId privKey - Eth.sendRawTransaction txBytes - Nothing -> Eth.sendTransaction callArgs - -sendTx' :: Method a - => Text - -- ^ Password for account unlocking - -> Call - -- ^ Call configuration - -> a - -- ^ method data - -> Web3 Hash -sendTx' pass call' (dat :: a) = do - let sel = selector (Proxy :: Proxy a) - callArgs = call' { callData = Just $ sel <> encode dat } - Personal.sendTransaction callArgs pass - --- | 'call' is used to call contract methods that have no state changing effects. -call :: (Method a, ABIGet b) - => Call - -- ^ Call configuration - -> DefaultBlock - -- ^ State mode for constant call (latest or pending) - -> a - -- ^ Method data - -> Web3 b - -- ^ 'Web3' wrapped result -call call' mode (dat :: a) = do - let sel = selector (Proxy :: Proxy a) - c = (call' { callData = Just $ sel <> encode dat }) - res <- Eth.call c mode - case decode res of - Left e -> throwM $ ParserFail $ "Unable to parse response: " ++ e - Right x -> return x diff --git a/src/Network/Ethereum/Contract/TH.hs b/src/Network/Ethereum/Contract/TH.hs deleted file mode 100644 index 137ab816..00000000 --- a/src/Network/Ethereum/Contract/TH.hs +++ /dev/null @@ -1,303 +0,0 @@ -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.Contract.TH --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- Contract abstraction is a high level interface of web3 library. --- --- The Application Binary Interface is the standard way to interact --- with contracts in the Ethereum ecosystem. It can be described by --- specially JSON file, like @ERC20.json@. This module use TemplateHaskell --- for generation described in ABI contract methods and events. Helper --- functions and instances inserted in haskell module and can be used in --- another modules or in place. --- --- @ --- import Network.Ethereum.Contract.TH --- --- [abiFrom|examples/ERC20.json|] --- --- main = do --- runWeb3 $ event' def $ --- \(Transfer _ to val) -> liftIO $ do print to --- print val --- @ --- --- Full code example available in examples folder. --- - -module Network.Ethereum.Contract.TH (abi, abiFrom) where - -import Control.Applicative ((<|>)) -import Control.Lens ((^?)) -import Control.Monad (replicateM, (<=<)) -import Data.Aeson (eitherDecode) -import Data.Aeson.Lens (key, _JSON) -import qualified Data.Char as Char -import Data.Default (Default (..)) -import Data.List (group, sort, uncons) -import Data.Monoid ((<>)) -import Data.Tagged (Tagged) -import Data.Text (Text) -import qualified Data.Text as T -import qualified Data.Text.Lazy as LT -import qualified Data.Text.Lazy.Encoding as LT -import Generics.SOP (Generic) -import qualified GHC.Generics as GHC (Generic) -import Language.Haskell.TH -import Language.Haskell.TH.Quote - -import Data.String.Extra (toLowerFirst, toUpperFirst) -import Network.Ethereum.ABI.Class (ABIGet, ABIPut, ABIType (..)) -import Network.Ethereum.ABI.Event (IndexedEvent (..)) -import Network.Ethereum.ABI.Json (ContractABI (..), - Declaration (..), - EventArg (..), - FunctionArg (..), - SolidityType (..), eventId, - methodId, parseSolidityType) -import Network.Ethereum.ABI.Prim (Address, Bytes, BytesN, IntN, - ListN, Singleton (..), UIntN) -import Network.Ethereum.Contract.Method (Method (..), call, sendTx) -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Call, DefaultBlock (..), - Filter (..), Hash) - --- | Read contract ABI from file -abiFrom :: QuasiQuoter -abiFrom = quoteFile abi - --- | QQ reader for contract ABI -abi :: QuasiQuoter -abi = QuasiQuoter - { quoteDec = quoteAbiDec - , quoteExp = quoteAbiExp - , quotePat = undefined - , quoteType = undefined - } - --- | Instance declaration with empty context -instanceD' :: Name -> TypeQ -> [DecQ] -> DecQ -instanceD' name insType = - instanceD (cxt []) (appT insType (conT name)) - --- | Simple data type declaration with one constructor -dataD' :: Name -> ConQ -> [Name] -> DecQ -dataD' name rec' derive = - dataD (cxt []) name [] Nothing [rec'] [derivClause Nothing (conT <$> derive)] - --- | Simple function declaration -funD' :: Name -> [PatQ] -> ExpQ -> DecQ -funD' name p f = funD name [clause p (normalB f) []] - --- | ABI and Haskell types association -toHSType :: SolidityType -> TypeQ -toHSType s = case s of - SolidityBool -> conT ''Bool - SolidityAddress -> conT ''Address - SolidityUint n -> appT (conT ''UIntN) (numLit n) - SolidityInt n -> appT (conT ''IntN) (numLit n) - SolidityString -> conT ''Text - SolidityBytesN n -> appT (conT ''BytesN) (numLit n) - SolidityBytes -> conT ''Bytes - SolidityVector ns a -> expandVector ns a - SolidityArray a -> appT listT $ toHSType a - where - numLit n = litT (numTyLit $ toInteger n) - expandVector :: [Int] -> SolidityType -> TypeQ - expandVector ns a = case uncons ns of - Just (n, rest) -> - if length rest == 0 - then (conT ''ListN) `appT` numLit n `appT` toHSType a - else (conT ''ListN) `appT` numLit n `appT` expandVector rest a - _ -> error $ "Impossible Nothing branch in `expandVector`: " ++ show ns ++ " " ++ show a - -typeQ :: Text -> TypeQ -typeQ t = case parseSolidityType t of - Left e -> error $ "Unable to parse solidity type: " ++ show e - Right ty -> toHSType ty - --- | Function argument to TH type -funBangType :: FunctionArg -> BangTypeQ -funBangType (FunctionArg _ typ) = - bangType (bang sourceNoUnpack sourceStrict) (typeQ typ) - -funWrapper :: Bool - -- ^ Is constant? - -> Name - -- ^ Function name - -> Name - -- ^ Function data name - -> [FunctionArg] - -- ^ Parameters - -> Maybe [FunctionArg] - -- ^ Results - -> DecsQ -funWrapper c name dname args result = - if c - then do - a : b : vars <- replicateM (length args + 2) (newName "t") - let params = appsE $ conE dname : fmap varE vars - sequence [ sigD name $ [t|$(arrowing $ [t|Call|] : [t|DefaultBlock|] : inputT ++ [outputT])|] - , funD' name (varP <$> a : b : vars) $ - case result of - Just [_] -> [|unSingleton <$> call $(varE a) $(varE b) $(params)|] - _ -> [|call $(varE a) $(varE b) $(params)|] - ] - - else do - a : _ : vars <- replicateM (length args + 2) (newName "t") - let params = appsE $ conE dname : fmap varE vars - sequence [ sigD name $ [t|$(arrowing $ [t|Call|] : inputT ++ [[t|Web3 Hash|]])|] - , funD' name (varP <$> a : vars) $ - [|sendTx $(varE a) $(params)|] ] - where - arrowing [] = error "Impossible branch call" - arrowing [x] = x - arrowing (x : xs) = [t|$x -> $(arrowing xs)|] - inputT = fmap (typeQ . funArgType) args - outputT = case result of - Nothing -> [t|Web3 ()|] - Just [x] -> [t|Web3 $(typeQ $ funArgType x)|] - Just xs -> let outs = fmap (typeQ . funArgType) xs - in [t|Web3 $(foldl appT (tupleT (length xs)) outs)|] - -mkDecl :: Declaration -> DecsQ - -mkDecl ev@(DEvent uncheckedName inputs anonymous) = sequence - [ dataD' indexedName (normalC indexedName (map (toBang <=< tag) indexedArgs)) derivingD - , instanceD' indexedName (conT ''Generic) [] - , instanceD' indexedName (conT ''ABIType) [funD' 'isDynamic [] [|const False|]] - , instanceD' indexedName (conT ''ABIGet) [] - , dataD' nonIndexedName (normalC nonIndexedName (map (toBang <=< tag) nonIndexedArgs)) derivingD - , instanceD' nonIndexedName (conT ''Generic) [] - , instanceD' nonIndexedName (conT ''ABIType) [funD' 'isDynamic [] [|const False|]] - , instanceD' nonIndexedName (conT ''ABIGet) [] - , dataD' allName (recC allName (map (\(n, a) -> ((\(b,t) -> return (n,b,t)) <=< toBang <=< typeQ $ a)) allArgs)) derivingD - , instanceD' allName (conT ''Generic) [] - , instanceD (cxt []) - (pure $ ConT ''IndexedEvent `AppT` ConT indexedName `AppT` ConT nonIndexedName `AppT` ConT allName) - [funD' 'isAnonymous [] [|const anonymous|]] - , instanceD (cxt []) - (pure $ ConT ''Default `AppT` (ConT ''Filter `AppT` ConT allName)) - [funD' 'def [] [|Filter Nothing Latest Latest $ Just topics|] ] - ] - where - name = if Char.toLower (T.head uncheckedName) == Char.toUpper (T.head uncheckedName) then "EvT" <> uncheckedName else uncheckedName - topics = [Just (T.unpack $ eventId ev)] <> replicate (length indexedArgs) Nothing - toBang ty = bangType (bang sourceNoUnpack sourceStrict) (return ty) - tag (n, ty) = AppT (AppT (ConT ''Tagged) (LitT $ NumTyLit n)) <$> typeQ ty - labeledArgs = zip [1..] inputs - indexedArgs = map (\(n, ea) -> (n, eveArgType ea)) . filter (eveArgIndexed . snd) $ labeledArgs - indexedName = mkName $ toUpperFirst (T.unpack name) <> "Indexed" - nonIndexedArgs = map (\(n, ea) -> (n, eveArgType ea)) . filter (not . eveArgIndexed . snd) $ labeledArgs - nonIndexedName = mkName $ toUpperFirst (T.unpack name) <> "NonIndexed" - allArgs = makeArgs name $ map (\i -> (eveArgName i, eveArgType i)) inputs - allName = mkName $ toUpperFirst (T.unpack name) - derivingD = [''Show, ''Eq, ''Ord, ''GHC.Generic] - --- TODO change this type name also --- | Method delcarations maker -mkDecl fun@(DFunction name constant inputs outputs) = (++) - <$> funWrapper constant fnName dataName inputs outputs - <*> sequence - [ dataD' dataName (normalC dataName bangInput) derivingD - , instanceD' dataName (conT ''Generic) [] - , instanceD' dataName (conT ''ABIType) - [funD' 'isDynamic [] [|const False|]] - , instanceD' dataName (conT ''ABIPut) [] - , instanceD' dataName (conT ''ABIGet) [] - , instanceD' dataName (conT ''Method) - [funD' 'selector [] [|const mIdent|]] - ] - where mIdent = T.unpack (methodId $ fun {funName = T.replace "'" "" name}) - dataName = mkName (toUpperFirst (T.unpack $ name <> "Data")) - fnName = mkName (toLowerFirst (T.unpack name)) - bangInput = fmap funBangType inputs - derivingD = [''Show, ''Eq, ''Ord, ''GHC.Generic] - -mkDecl _ = return [] - --- | this function gives appropriate names for the accessors in the following way --- | argName -> evArgName --- | arg_name -> evArg_name --- | _argName -> evArgName --- | "" -> evi , for example Transfer(address, address uint256) ~> Transfer {transfer1 :: address, transfer2 :: address, transfer3 :: Integer} -makeArgs :: Text -> [(Text, Text)] -> [(Name, Text)] -makeArgs prefix ns = go 1 ns - where - prefixStr = toLowerFirst . T.unpack $ prefix - go :: Int -> [(Text, Text)] -> [(Name, Text)] - go _ [] = [] - go i ((h, ty) : tail') = if T.null h - then (mkName $ prefixStr ++ show i, ty) : go (i + 1) tail' - else (mkName . (++ "_") . (++) prefixStr . toUpperFirst . T.unpack $ h, ty) : go (i + 1) tail' - -escape :: [Declaration] -> [Declaration] -escape = escapeEqualNames . fmap escapeReservedNames - -escapeEqualNames :: [Declaration] -> [Declaration] -escapeEqualNames = concat . fmap go . group . sort - where go [] = [] - go (x : xs) = x : zipWith appendToName xs hats - hats = [T.replicate n "'" | n <- [1..]] - appendToName d@(DFunction n _ _ _) a = d { funName = n <> a } - appendToName d@(DEvent n _ _) a = d { eveName = n <> a } - appendToName d _ = d - -escapeReservedNames :: Declaration -> Declaration -escapeReservedNames d@(DFunction n _ _ _) - | isKeyword n = d { funName = n <> "'" } - | otherwise = d -escapeReservedNames d = d - -isKeyword :: Text -> Bool -isKeyword = flip elem [ "as", "case", "of", "class" - , "data", "family", "instance" - , "default", "deriving", "do" - , "forall", "foreign", "hiding" - , "if", "then", "else", "import" - , "infix", "infixl", "infixr" - , "let", "in", "mdo", "module" - , "newtype", "proc", "qualified" - , "rec", "type", "where"] - -quoteAbiDec :: String -> Q [Dec] -quoteAbiDec abi_string = - let abi_lbs = LT.encodeUtf8 (LT.pack abi_string) - eabi = abiDec abi_lbs <|> abiDecNested abi_lbs - in case eabi of - Left e -> fail ("Error in quoteAbiDec: " ++ e) - Right a -> concat <$> mapM mkDecl (escape a) - where - abiDec _abi_lbs = case eitherDecode _abi_lbs of - Left e -> Left e - Right (ContractABI a) -> Right a - abiDecNested _abi_lbs = case _abi_lbs ^? key "abi" . _JSON of - Nothing -> Left $ "Failed to find ABI at 'abi' key in JSON object." - Just (ContractABI a) -> Right a - --- | ABI information string -quoteAbiExp :: String -> ExpQ -quoteAbiExp abi_string = stringE $ - let abi_lbs = LT.encodeUtf8 (LT.pack abi_string) - eabi = abiDec abi_lbs <|> abiDecNested abi_lbs - in case eabi of - Left e -> "Error in 'quoteAbiExp' : " ++ e - Right a -> a - where - abiDec _abi_lbs = case eitherDecode _abi_lbs of - Left e -> Left e - Right a -> Right $ show (a :: ContractABI) - abiDecNested _abi_lbs = case _abi_lbs ^? key "abi" . _JSON of - Nothing -> Left $ "Failed to find ABI at 'abi' key in JSON object." - Just a -> Right $ show (a :: ContractABI) diff --git a/src/Network/Ethereum/Web3.hs b/src/Network/Ethereum/Web3.hs deleted file mode 100644 index 138f1e55..00000000 --- a/src/Network/Ethereum/Web3.hs +++ /dev/null @@ -1,50 +0,0 @@ --- | --- Module : Network.Ethereum.Web3 --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- An Ethereum node offers a RPC interface. This interface gives Ðapp’s --- access to the Ethereum blockchain and functionality that the node provides, --- such as compiling smart contract code. It uses a subset of the JSON-RPC 2.0 --- specification (no support for notifications or named parameters) as serialisation --- protocol and is available over HTTP and IPC (unix domain sockets on linux/OSX --- and named pipe’s on Windows). --- --- Web3 Haskell library currently use JSON-RPC over HTTP to access node functionality. --- - -module Network.Ethereum.Web3 ( - - -- ** Monad as base of any Ethereum node communication - Web3 - , runWeb3 - - -- ** Basic transaction sending - , sendTx - , sendTx' - , Call(..) - - -- ** Basic event listening - , EventAction(..) - , event - , event' - - -- ** Primitive data types - , module Network.Ethereum.ABI.Prim - - -- ** Metric unit system - , module Network.Ethereum.Unit - - ) where - -import Network.Ethereum.ABI.Prim -import Network.Ethereum.Contract.Event (EventAction (..), event, - event') -import Network.Ethereum.Contract.Method (sendTx, sendTx') -import Network.Ethereum.Unit -import Network.Ethereum.Web3.Provider (Web3, runWeb3) -import Network.Ethereum.Web3.Types (Call (..)) diff --git a/src/Network/Ethereum/Web3/Provider.hs b/src/Network/Ethereum/Web3/Provider.hs deleted file mode 100644 index e2399593..00000000 --- a/src/Network/Ethereum/Web3/Provider.hs +++ /dev/null @@ -1,100 +0,0 @@ -{-# LANGUAGE CPP #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE MultiParamTypeClasses #-} - --- | --- Module : Network.Ethereum.Web3.Provider --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : portable --- --- Web3 service provider. --- - -module Network.Ethereum.Web3.Provider where - -import Control.Concurrent.Async (Async, async) -import Control.Exception (Exception, try) -import Control.Monad.Catch (MonadThrow) -import Control.Monad.IO.Class (MonadIO (..)) -import Control.Monad.Reader (MonadReader (..)) -import Control.Monad.Trans.Reader (ReaderT, mapReaderT, runReaderT) -import Data.ByteString (ByteString) -import Data.Default (Default (..)) -import GHC.Generics (Generic) -import Network.HTTP.Client (Manager, newManager) - -#ifdef TLS_MANAGER -import Network.HTTP.Client.TLS (tlsManagerSettings) -#else -import Network.HTTP.Client (defaultManagerSettings) -#endif - --- | Any communication with Ethereum node wrapped with 'Web3' monad -newtype Web3 a = Web3 { unWeb3 :: ReaderT (Provider, Manager) IO a } - deriving (Functor, Applicative, Monad, MonadIO, MonadThrow) - -instance MonadReader (Provider, Manager) Web3 where - ask = Web3 ask - local f = Web3 . local f . unWeb3 - --- | Some peace of error response -data Web3Error - = JsonRpcFail !String - -- ^ JSON-RPC communication error - | ParserFail !String - -- ^ Error in parser state - | UserFail !String - -- ^ Common head for user errors - deriving (Show, Eq, Generic) - -instance Exception Web3Error - --- | JSON-RPC server URI -type ServerUri = String - ---TODO: Change to `HttpProvider ServerUri | IpcProvider FilePath` to support IPC -data JsonRpcProvider = HttpProvider ServerUri - deriving (Show, Eq, Generic) - --- | Web3 Provider -data Provider = Provider { jsonRpc :: JsonRpcProvider - , signingConfiguration :: Maybe SigningConfiguration - } deriving (Show, Eq) - -data SigningConfiguration = SigningConfiguration { privateKey :: ByteString - , chainIdentifier :: Integer } deriving (Show, Eq) - -instance Default Provider where - def = Provider (HttpProvider "http://localhost:8545") Nothing - --- | 'Web3' monad runner, using the supplied Manager -runWeb3With :: MonadIO m => Manager -> Provider -> Web3 a -> m (Either Web3Error a) -runWeb3With manager provider = - liftIO . try . flip runReaderT (provider, manager) . unWeb3 - --- | 'Web3' monad runner -runWeb3' :: MonadIO m => Provider -> Web3 a -> m (Either Web3Error a) -runWeb3' provider f = do - manager <- liftIO $ -#ifdef TLS_MANAGER - newManager tlsManagerSettings -#else - newManager defaultManagerSettings -#endif - runWeb3With manager provider f - --- | 'Web3' runner for default provider -runWeb3 :: MonadIO m => Web3 a -> m (Either Web3Error a) -{-# INLINE runWeb3 #-} -runWeb3 = runWeb3' def - --- | Fork 'Web3' with the same 'Provider' -forkWeb3 :: Web3 a -> Web3 (Async a) -{-# INLINE forkWeb3 #-} -forkWeb3 = Web3 . mapReaderT async . unWeb3 diff --git a/src/Network/Ethereum/Web3/Transaction.hs b/src/Network/Ethereum/Web3/Transaction.hs deleted file mode 100644 index b95ebecc..00000000 --- a/src/Network/Ethereum/Web3/Transaction.hs +++ /dev/null @@ -1,62 +0,0 @@ -module Network.Ethereum.Web3.Transaction where - -import Crypto.Hash (Digest, Keccak_256, hash) -import Crypto.Secp256k1 -import Data.ByteArray (Bytes, convert) -import Data.ByteArray.Encoding -import Data.ByteString -import qualified Data.ByteString as BS -import Data.ByteString.Short (fromShort) -import Data.Maybe (fromMaybe) -import Data.RLP -import Network.Ethereum.ABI.Prim.Address (toHexString) -import Network.Ethereum.Web3.Types - -unpackCallParameters :: Call -> Either String (Integer, Integer, Integer, ByteString, Integer, ByteString) -unpackCallParameters call = do - nonce <- toError "nonce" $ unQuantity <$> callNonce call - gasPrice <- toError "gasPrice" $ unQuantity <$> callGasPrice call - gasLimit <- toError "gas" $ unQuantity <$> callGas call - to <- convertFromBase Base16 =<< toError "to" (BS.drop 2 . toHexString <$> callTo call) - value <- toError "value" (unQuantity <$> callValue call) - let txData = fromMaybe empty $ convert <$> callData call - return (nonce, gasPrice, gasLimit, to, value, txData) - where toError field = - maybe (Left $ field ++ " must be set when creating raw transaction") pure - -createRawTransaction :: Call -> Integer -> ByteString -> Either String Bytes -createRawTransaction call chainId privateKey = do - (nonce, gasPrice, gasLimit, to, value, txData) <- unpackCallParameters call - let rlpEndcoding = packRLP $ rlpEncode ( nonce - , gasPrice - , gasLimit - , to - , value - , txData - , chainId - , 0 :: Integer - , 0 :: Integer - ) - rlpHash = convert (hash rlpEndcoding :: Digest Keccak_256) - recSig <- maybe (Left "Cannot create transaction signature") pure $ ecsign rlpHash privateKey - let r = fromShort $ getCompactRecSigR recSig - s = fromShort $ getCompactRecSigS recSig - v = getCompactRecSigV recSig - return . convert . packRLP $ - rlpEncode ( nonce - , gasPrice - , gasLimit - , to - , value - , txData - , fromIntegral v + 27 + chainId * 2 + 8 - , s -- swapping s & r, still don't know why - , r - ) - - -ecsign :: ByteString -> ByteString -> Maybe CompactRecSig -ecsign msgHash privateKey = do - msgHash' <- msg msgHash - privateKey' <- secKey privateKey - return . exportCompactRecSig $ signRecMsg privateKey' msgHash' diff --git a/src/Network/Ethereum/Web3/Types.hs b/src/Network/Ethereum/Web3/Types.hs deleted file mode 100644 index 0e7edb8b..00000000 --- a/src/Network/Ethereum/Web3/Types.hs +++ /dev/null @@ -1,317 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.Web3.Types --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : portable --- --- Ethereum generic JSON-RPC types. --- - -module Network.Ethereum.Web3.Types where - -import Data.Aeson (FromJSON (..), Options (fieldLabelModifier, omitNothingFields), - ToJSON (..), - Value (Bool, String), - defaultOptions, object, - (.=)) -import Data.Aeson.TH (deriveJSON) -import Data.Default (Default (..)) -import Data.Monoid ((<>)) -import Data.String (IsString (..)) -import qualified Data.Text as T (pack) -import qualified Data.Text.Lazy.Builder as B (toLazyText) -import qualified Data.Text.Lazy.Builder.Int as B (hexadecimal) -import qualified Data.Text.Read as R (decimal, hexadecimal) -import GHC.Generics (Generic) - -import Data.String.Extra (toLowerFirst) -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.ABI.Prim.Bytes (Bytes, BytesN) -import Network.Ethereum.Unit - --- | 32 byte type synonym for transaction and block hashes. -type Hash = BytesN 32 - --- | Should be viewed as type to representing QUANTITY in Web3 JSON RPC docs --- --- When encoding QUANTITIES (integers, numbers): encode as hex, prefix with "0x", --- the most compact representation (slight exception: zero should be represented as "0x0"). --- Examples: --- --- 0x41 (65 in decimal) --- 0x400 (1024 in decimal) --- WRONG: 0x (should always have at least one digit - zero is "0x0") --- WRONG: 0x0400 (no leading zeroes allowed) --- WRONG: ff (must be prefixed 0x) -newtype Quantity = Quantity { unQuantity :: Integer } - deriving (Read, Num, Real, Enum, Eq, Ord, Generic) - -instance Show Quantity where - show = show . unQuantity - -instance IsString Quantity where - fromString ('0' : 'x' : hex) = - case R.hexadecimal (T.pack hex) of - Right (x, "") -> Quantity x - _ -> error "Unable to parse Quantity!" - fromString str = - case R.decimal (T.pack str) of - Right (x, "") -> Quantity x - _ -> error "Unable to parse Quantity!" - -instance ToJSON Quantity where - toJSON (Quantity x) = - let hexValue = B.toLazyText (B.hexadecimal x) - in toJSON ("0x" <> hexValue) - -instance FromJSON Quantity where - parseJSON (String v) = - case R.hexadecimal v of - Right (x, "") -> return (Quantity x) - _ -> fail "Unable to parse Quantity" - parseJSON _ = fail "Quantity may only be parsed from a JSON String" - -instance Fractional Quantity where - (/) a b = Quantity $ div (unQuantity a) (unQuantity b) - fromRational = Quantity . floor - -instance Unit Quantity where - fromWei = Quantity - toWei = unQuantity - -instance UnitSpec Quantity where - divider = const 1 - name = const "quantity" - --- | An object with sync status data. -data SyncActive = SyncActive - { syncStartingBlock :: !Quantity - -- ^ QUANTITY - The block at which the import started (will only be reset, after the sync reached his head). - , syncCurrentBlock :: !Quantity - -- ^ QUANTITY - The current block, same as eth_blockNumber. - , syncHighestBlock :: !Quantity - -- ^ QUANTITY - The estimated highest block. - } deriving (Eq, Generic, Show) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 4 }) ''SyncActive) - --- | Sync state pulled by low-level call 'eth_syncing'. -data SyncingState = Syncing SyncActive | NotSyncing - deriving (Eq, Generic, Show) - -instance FromJSON SyncingState where - parseJSON (Bool _) = pure NotSyncing - parseJSON v = Syncing <$> parseJSON v - --- | Changes pulled by low-level call 'eth_getFilterChanges', 'eth_getLogs', --- and 'eth_getFilterLogs' -data Change = Change - { changeLogIndex :: !(Maybe Quantity) - -- ^ QUANTITY - integer of the log index position in the block. null when its pending log. - , changeTransactionIndex :: !(Maybe Quantity) - -- ^ QUANTITY - integer of the transactions index position log was created from. null when its pending log. - , changeTransactionHash :: !(Maybe Hash) - -- ^ DATA, 32 Bytes - hash of the transactions this log was created from. null when its pending log. - , changeBlockHash :: !(Maybe Hash) - -- ^ DATA, 32 Bytes - hash of the block where this log was in. null when its pending. null when its pending log. - , changeBlockNumber :: !(Maybe Quantity) - -- ^ QUANTITY - the block number where this log was in. null when its pending. null when its pending log. - , changeAddress :: !Address - -- ^ DATA, 20 Bytes - address from which this log originated. - , changeData :: !Bytes - -- ^ DATA - contains one or more 32 Bytes non-indexed arguments of the log. - , changeTopics :: ![BytesN 32] - -- ^ Array of DATA - Array of 0 to 4 32 Bytes DATA of indexed log arguments. - -- (In solidity: The first topic is the hash of the signature of the event - -- (e.g. Deposit(address, bytes32, uint256)), except you declared the event with - -- the anonymous specifier.) - } deriving (Eq, Show, Generic) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 6 }) ''Change) - --- | The contract call params. -data Call = Call - { callFrom :: !(Maybe Address) - -- ^ DATA, 20 Bytes - The address the transaction is send from. - , callTo :: !(Maybe Address) - -- ^ DATA, 20 Bytes - (optional when creating new contract) The address the transaction is directed to. - , callGas :: !(Maybe Quantity) - -- ^ QUANTITY - (optional, default: 3000000) Integer of the gas provided for the transaction execution. It will return unused gas. - , callGasPrice :: !(Maybe Quantity) - -- ^ QUANTITY - (optional, default: To-Be-Determined) Integer of the gasPrice used for each paid gas. - , callValue :: !(Maybe Quantity) - -- ^ QUANTITY - (optional) Integer of the value sent with this transaction. - , callData :: !(Maybe Bytes) - -- ^ DATA - The compiled code of a contract OR the hash of the invoked method signature and encoded parameters. - , callNonce :: !(Maybe Quantity) - -- ^ QUANTITY - (optional) Integer of a nonce. This allows to overwrite your own pending transactions that use the same nonce. - } deriving (Eq, Show, Generic) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 4 - , omitNothingFields = True }) ''Call) - -instance Default Call where - def = Call Nothing Nothing (Just 3000000) Nothing (Just 0) Nothing Nothing - --- | The state of blockchain for contract call. -data DefaultBlock = BlockWithNumber Quantity - | Earliest - | Latest - | Pending - deriving (Eq, Show, Generic) - -instance ToJSON DefaultBlock where - toJSON (BlockWithNumber bn) = toJSON bn - toJSON parameter = toJSON . toLowerFirst . show $ parameter - --- | Low-level event filter data structure. -data Filter e = Filter - { filterAddress :: !(Maybe [Address]) - -- ^ DATA|Array, 20 Bytes - (optional) Contract address or a list of addresses from which logs should originate. - , filterFromBlock :: !DefaultBlock - -- ^ QUANTITY|TAG - (optional, default: "latest") Integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions. - , filterToBlock :: !DefaultBlock - -- ^ QUANTITY|TAG - (optional, default: "latest") Integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions. - , filterTopics :: !(Maybe [Maybe (BytesN 32)]) - -- ^ Array of DATA, - (optional) Array of 32 Bytes DATA topics. Topics are order-dependent. Each topic can also be an array of DATA with "or" options. - -- 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)" - } deriving (Eq, Show, Generic) - -instance ToJSON (Filter e) where - toJSON f = object [ "address" .= filterAddress f - , "fromBlock" .= filterFromBlock f - , "toBlock" .= filterToBlock f - , "topics" .= filterTopics f ] - -instance Ord DefaultBlock where - compare Pending Pending = EQ - compare Latest Latest = EQ - compare Earliest Earliest = EQ - compare (BlockWithNumber a) (BlockWithNumber b) = compare a b - compare _ Pending = LT - compare Pending Latest = GT - compare _ Latest = LT - compare Earliest _ = LT - compare a b = case compare b a of - LT -> GT - GT -> LT - EQ -> EQ - --- | The Receipt of a Transaction -data TxReceipt = TxReceipt - { receiptTransactionHash :: !Hash - -- ^ DATA, 32 Bytes - hash of the transaction. - , receiptTransactionIndex :: !Quantity - -- ^ QUANTITY - index of the transaction. - , receiptBlockHash :: !(Maybe Hash) - -- ^ DATA, 32 Bytes - hash of the block where this transaction was in. null when its pending. - , receiptBlockNumber :: !(Maybe Quantity) - -- ^ QUANTITY - block number where this transaction was in. null when its pending. - , receiptCumulativeGasUsed :: !Quantity - -- ^ QUANTITY - The total amount of gas used when this transaction was executed in the block. - , receiptGasUsed :: !Quantity - -- ^ QUANTITY - The amount of gas used by this specific transaction alone. - , receiptContractAddress :: !(Maybe Address) - -- ^ DATA, 20 Bytes - The contract address created, if the transaction was a contract creation, otherwise null. - , receiptLogs :: ![Change] - -- ^ Array - Array of log objects, which this transaction generated. - , receiptLogsBloom :: !Bytes - -- ^ DATA, 256 Bytes - Bloom filter for light clients to quickly retrieve related logs. - , receiptStatus :: !(Maybe Quantity) - -- ^ QUANTITY either 1 (success) or 0 (failure) - } deriving (Show, Generic) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 7 }) ''TxReceipt) - --- | Transaction information. -data Transaction = Transaction - { txHash :: !Hash - -- ^ DATA, 32 Bytes - hash of the transaction. - , txNonce :: !Quantity - -- ^ QUANTITY - the number of transactions made by the sender prior to this one. - , txBlockHash :: !(Maybe Hash) - -- ^ DATA, 32 Bytes - hash of the block where this transaction was in. null when its pending. - , txBlockNumber :: !(Maybe Quantity) - -- ^ QUANTITY - block number where this transaction was in. null when its pending. - , txTransactionIndex :: !(Maybe Quantity) - -- ^ QUANTITY - integer of the transactions index position in the block. null when its pending. - , txFrom :: !Address - -- ^ DATA, 20 Bytes - address of the sender. - , txTo :: !(Maybe Address) - -- ^ DATA, 20 Bytes - address of the receiver. null when its a contract creation transaction. - , txValue :: !Quantity - -- ^ QUANTITY - value transferred in Wei. - , txGasPrice :: !Quantity - -- ^ QUANTITY - gas price provided by the sender in Wei. - , txGas :: !Quantity - -- ^ QUANTITY - gas provided by the sender. - , txInput :: !Bytes - -- ^ DATA - the data send along with the transaction. - } deriving (Eq, Show, Generic) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 2 }) ''Transaction) - --- | Block information. -data Block = Block - { blockNumber :: !(Maybe Quantity) - -- ^ QUANTITY - the block number. null when its pending block. - , blockHash :: !(Maybe Hash) - -- ^ DATA, 32 Bytes - hash of the block. null when its pending block. - , blockParentHash :: !Hash - -- ^ DATA, 32 Bytes - hash of the parent block. - , blockNonce :: !(Maybe Bytes) - -- ^ DATA, 8 Bytes - hash of the generated proof-of-work. null when its pending block. - , blockSha3Uncles :: !(BytesN 32) - -- ^ DATA, 32 Bytes - SHA3 of the uncles data in the block. - , blockLogsBloom :: !(Maybe Bytes) - -- ^ DATA, 256 Bytes - the bloom filter for the logs of the block. null when its pending block. - , blockTransactionsRoot :: !(BytesN 32) - -- ^ DATA, 32 Bytes - the root of the transaction trie of the block. - , blockStateRoot :: !(BytesN 32) - -- ^ DATA, 32 Bytes - the root of the final state trie of the block. - , blockReceiptRoot :: !(Maybe (BytesN 32)) - -- ^ DATA, 32 Bytes - the root of the receipts trie of the block. - , blockMiner :: !Address - -- ^ DATA, 20 Bytes - the address of the beneficiary to whom the mining rewards were given. - , blockDifficulty :: !Quantity - -- ^ QUANTITY - integer of the difficulty for this block. - , blockTotalDifficulty :: !Quantity - -- ^ QUANTITY - integer of the total difficulty of the chain until this block. - , blockExtraData :: !Bytes - -- ^ DATA - the "extra data" field of this block. - , blockSize :: !Quantity - -- ^ QUANTITY - integer the size of this block in bytes. - , blockGasLimit :: !Quantity - -- ^ QUANTITY - the maximum gas allowed in this block. - , blockGasUsed :: !Quantity - -- ^ QUANTITY - the total used gas by all transactions in this block. - , blockTimestamp :: !Quantity - -- ^ QUANTITY - the unix timestamp for when the block was collated. - , blockTransactions :: ![Transaction] - -- ^ Array of transaction objects. - , blockUncles :: ![Hash] - -- ^ Array - Array of uncle hashes. - } deriving (Show, Generic) - -$(deriveJSON (defaultOptions - { fieldLabelModifier = toLowerFirst . drop 5 }) ''Block) diff --git a/src/Network/Ethereum/Web3/Web3.hs b/src/Network/Ethereum/Web3/Web3.hs deleted file mode 100644 index 5c80cb02..00000000 --- a/src/Network/Ethereum/Web3/Web3.hs +++ /dev/null @@ -1,31 +0,0 @@ -{-# LANGUAGE OverloadedStrings #-} - --- | --- Module : Network.Ethereum.Web3.Web3 --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unknown --- --- Ethereum node JSON-RPC API methods with `web3_` prefix. --- - -module Network.Ethereum.Web3.Web3 where - -import Data.Text (Text) -import Network.Ethereum.ABI.Prim.Bytes (Bytes) -import Network.Ethereum.Web3.Provider (Web3) -import Network.Ethereum.Web3.Types (Hash) -import Network.JsonRpc.TinyClient (remote) - --- | Returns current node version string. -clientVersion :: Web3 Text -{-# INLINE clientVersion #-} -clientVersion = remote "web3_clientVersion" - --- | Returns Keccak-256 (not the standardized SHA3-256) of the given data. -sha3 :: Bytes -> Web3 Hash -{-# INLINE sha3 #-} -sha3 = remote "web3_sha3" diff --git a/src/Network/JsonRpc/TinyClient.hs b/src/Network/JsonRpc/TinyClient.hs deleted file mode 100644 index 6e4e85f6..00000000 --- a/src/Network/JsonRpc/TinyClient.hs +++ /dev/null @@ -1,173 +0,0 @@ -{-# LANGUAGE DefaultSignatures #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE FunctionalDependencies #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE TypeFamilies #-} -{-# LANGUAGE UndecidableInstances #-} - --- | --- Module : Network.JsonRpc.TinyClient --- Copyright : Alexander Krupenkin 2016-2018 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : portable --- --- Tiny JSON-RPC 2.0 client. --- Functions for implementing the client side of JSON-RPC 2.0. --- See . --- - -module Network.JsonRpc.TinyClient ( - JsonRpcException(..) - , RpcError(..) - , MethodName - , ServerUri - , Remote - , remote - ) where - -import Control.Applicative ((<|>)) -import Control.Exception (Exception) -import Control.Monad ((<=<)) -import Control.Monad.Catch (MonadThrow, throwM) -import Control.Monad.IO.Class (MonadIO, liftIO) -import Control.Monad.Reader (MonadReader, ask) -import Data.Aeson -import Data.ByteString.Lazy (ByteString) -import Data.Text (Text, unpack) -import Network.Ethereum.Web3.Provider -import Network.HTTP.Client (Manager, - RequestBody (RequestBodyLBS), - httpLbs, method, parseRequest, - requestBody, requestHeaders, - responseBody) -import System.Random (randomIO) - -instance FromJSON a => Remote Web3 (Web3 a) - --- | Name of called method. -type MethodName = Text - --- | JSON-RPC minimal client config -type Config = (Provider, Manager) - --- | JSON-RPC request. -data Request = Request { rqMethod :: !Text - , rqId :: !Int - , rqParams :: !Value } - -instance ToJSON Request where - toJSON rq = object [ "jsonrpc" .= String "2.0" - , "method" .= rqMethod rq - , "params" .= rqParams rq - , "id" .= rqId rq ] - --- | JSON-RPC response. -data Response = Response - { rsResult :: !(Either RpcError Value) - } deriving (Eq, Show) - -instance FromJSON Response where - parseJSON = - withObject "JSON-RPC response object" $ - \v -> Response <$> - (Right <$> v .: "result" <|> Left <$> v .: "error") - --- | JSON-RPC error message -data RpcError = RpcError - { errCode :: !Int - , errMessage :: !Text - , errData :: !(Maybe Value) - } deriving Eq - -instance Show RpcError where - show (RpcError code msg dat) = - "JSON-RPC error " ++ show code ++ ": " ++ unpack msg - ++ ". Data: " ++ show dat - -instance FromJSON RpcError where - parseJSON = withObject "JSON-RPC error object" $ - \v -> RpcError <$> v .: "code" - <*> v .: "message" - <*> v .:? "data" - --- | Typeclass for JSON-RPC monad base. --- --- If you have monad with 'MonadIO', 'MonadThrow' and 'MonadReader' instances, --- it can be used as base for JSON-RPC calls. --- --- Example: --- --- @ --- newtype MyMonad a = ... --- --- instance Remote MyMonad (Mymonad a) --- --- foo :: Int -> Bool -> Mymonad Text --- foo = remote "foo" --- @ --- -class (MonadIO m, MonadThrow m, MonadReader Config m) => Remote m a | a -> m where - remote_ :: ([Value] -> m ByteString) -> a - - default remote_ :: (FromJSON b, m b ~ a) => ([Value] -> m ByteString) -> a - remote_ f = decodeResponse =<< f [] - -instance (ToJSON a, Remote m b) => Remote m (a -> b) where - remote_ f x = remote_ (\xs -> f (toJSON x : xs)) - --- | Remote call of JSON-RPC method. --- --- Arguments of function are stored into @params@ request array. --- --- Example: --- --- @ --- myMethod :: Int -> Bool -> m String --- myMethod = remote "myMethod" --- @ --- -remote :: Remote m a => MethodName -> a -{-# INLINE remote #-} -remote = remote_ . call - -call :: (MonadIO m, - MonadThrow m, - MonadReader Config m) - => MethodName - -> [Value] - -> m ByteString -call m r = do - rid <- abs <$> liftIO randomIO - connection . encode $ Request m rid (toJSON r) - where - connection body = do - ((Provider (HttpProvider uri) _), manager) <- ask - request <- parseRequest uri - let request' = request - { requestBody = RequestBodyLBS body - , requestHeaders = [("Content-Type", "application/json")] - , method = "POST" - } - responseBody <$> liftIO (httpLbs request' manager) - -data JsonRpcException - = ParsingException String - | CallException RpcError - deriving (Eq, Show) - -instance Exception JsonRpcException - -decodeResponse :: (MonadThrow m, FromJSON a) - => ByteString - -> m a -decodeResponse = (tryParse . eitherDecode . encode) - <=< tryResult . rsResult - <=< tryParse . eitherDecode - where - tryParse = either (throwM . ParsingException) return - tryResult = either (throwM . CallException) return diff --git a/stack.yaml b/stack.yaml index b32631ea..50f799de 100644 --- a/stack.yaml +++ b/stack.yaml @@ -1,24 +1,36 @@ # Resolver to choose a 'specific' stackage snapshot or a compiler version. -resolver: lts-11.7 +resolver: lts-24.32 + # User packages to be built. packages: -- '.' -# Dependency packages to be pulled from upstream that are not in the resolver -# (e.g., acme-missiles-0.3) -extra-deps: - - relapse-1.0.0.0 - - secp256k1-0.5.2 - - type-list-0.5.0.0 - +- 'packages/web3' +- 'packages/scale' +- 'packages/crypto' +- 'packages/bignum' +- 'packages/jsonrpc' +- 'packages/provider' +- 'packages/solidity' +- 'packages/ethereum' +- 'packages/polkadot' +- 'packages/hexstring' +- 'examples/erc20' +- 'examples/scale' +- 'examples/polkadot' -allow-newer: true +# Extra package dependencies +extra-deps: -# Override default flag values for local packages and extra-deps -flags: {} -# Extra package databases containing global packages -extra-package-dbs: [] # Dependencies bounds pvp-bounds: both + # Nix integration nix: - packages: [ zlib ] + packages: + - haskellPackages.stylish-haskell + - haskellPackages.hlint + - zlib + +flags: + # bitvec C FFI causes unkown symbol error in windows build, disabling it + bitvec: + simd: false diff --git a/test-support/.gitignore b/test-support/.gitignore deleted file mode 100644 index 8028e1c8..00000000 --- a/test-support/.gitignore +++ /dev/null @@ -1,11 +0,0 @@ -/bower_components/ -/node_modules/ -/.pulp-cache/ -/output/ -/generated-docs/ -/.psc-package/ -/.psc* -/.purs* -/.psa* -package-lock.json -src/Contracts diff --git a/test-support/Makefile b/test-support/Makefile deleted file mode 100644 index 74aa7146..00000000 --- a/test-support/Makefile +++ /dev/null @@ -1,23 +0,0 @@ -.PHONY: install build compile-contracts deploy test - -help: ## Ask for help! - @grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}' - -all: install - @echo prereqs that are newer than install: $? - -install: ## Install all dependencies - npm install; - bower install - -build: ## Builds the application - ./node_modules/.bin/pulp build - -compile-contracts: ## Compile contracts - ./node_modules/.bin/pulp build --src-path compile -m Compile --to compile.js && node compile.js --log-level info; rm -f compile.js - -deploy: compile-contracts build ## Deploy contracts - ./node_modules/.bin/pulp run - -test: compile-contracts ## Test contracts - ./node_modules/.bin/pulp test diff --git a/test-support/abis/ERC20.json b/test-support/abis/ERC20.json deleted file mode 100644 index d0d773a8..00000000 --- a/test-support/abis/ERC20.json +++ /dev/null @@ -1,110 +0,0 @@ -[ - { - "constant": true, - "inputs": [], - "name": "totalSupply", - "outputs": [ - { - "name": "", - "type": "uint256" - } - ], - "payable": false, - "stateMutability": "view", - "type": "function" - }, - { - "constant": true, - "inputs": [ - { - "name": "", - "type": "address" - } - ], - "name": "balances", - "outputs": [ - { - "name": "", - "type": "uint256" - } - ], - "payable": false, - "stateMutability": "view", - "type": "function" - }, - { - "constant": true, - "inputs": [ - { - "name": "_owner", - "type": "address" - } - ], - "name": "balanceOf", - "outputs": [ - { - "name": "balance", - "type": "uint256" - } - ], - "payable": false, - "stateMutability": "view", - "type": "function" - }, - { - "constant": false, - "inputs": [ - { - "name": "_to", - "type": "address" - }, - { - "name": "_value", - "type": "uint256" - } - ], - "name": "transfer", - "outputs": [ - { - "name": "", - "type": "bool" - } - ], - "payable": false, - "stateMutability": "nonpayable", - "type": "function" - }, - { - "inputs": [ - { - "name": "owner", - "type": "address" - } - ], - "payable": false, - "stateMutability": "nonpayable", - "type": "constructor" - }, - { - "anonymous": false, - "inputs": [ - { - "indexed": true, - "name": "to", - "type": "address" - }, - { - "indexed": true, - "name": "from", - "type": "address" - }, - { - "indexed": false, - "name": "value", - "type": "uint256" - } - ], - "name": "Transfer", - "type": "event" - } -] diff --git a/test-support/bower.json b/test-support/bower.json deleted file mode 100644 index 7360b12f..00000000 --- a/test-support/bower.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "name": "test-support", - "ignore": [ - "**/.*", - "node_modules", - "bower_components", - "output" - ], - "devDependencies": { - "purescript-chanterelle": "f-o-a-m/chanterelle#v0.11.0" - } -} diff --git a/test-support/chanterelle.json b/test-support/chanterelle.json deleted file mode 100644 index 9f2c342d..00000000 --- a/test-support/chanterelle.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "name": "hs-web3-test-support", - "version": "0.0.1", - "source-dir": "contracts", - "artifacts-dir": "build/contracts/abis", - "modules": [ "ComplexStorage" - , "SimpleStorage" - , "Linearization" - , "Registry" - ], - "dependencies": [], - "extra-abis": "abis", - "libraries": { - }, - "purescript-generator": { - "output-path": "src", - "module-prefix": "Contracts" - } -} diff --git a/test-support/compile/Compile.purs b/test-support/compile/Compile.purs deleted file mode 100644 index 7259016b..00000000 --- a/test-support/compile/Compile.purs +++ /dev/null @@ -1,20 +0,0 @@ -module Compile where - -import Prelude -import Chanterelle (compileMain) -import Control.Monad.Aff.Console (CONSOLE) -import Control.Monad.Eff (Eff) -import Control.Monad.Eff.Exception (EXCEPTION) -import Node.FS.Aff (FS) -import Node.Process (PROCESS) - -main :: forall eff. - Eff - ( console :: CONSOLE - , fs :: FS - , process :: PROCESS - , exception :: EXCEPTION - | eff - ) - Unit -main = compileMain diff --git a/test-support/contracts/ComplexStorage.sol b/test-support/contracts/ComplexStorage.sol deleted file mode 100644 index 97d0420f..00000000 --- a/test-support/contracts/ComplexStorage.sol +++ /dev/null @@ -1,34 +0,0 @@ -pragma solidity ^0.4.13; - -contract ComplexStorage { - uint public uintVal; - int public intVal; - bool public boolVal; - int224 public int224Val; - bool[2] public boolVectorVal; - int[] public intListVal; - string public stringVal; - bytes16 public bytes16Val; - bytes2[4][] public bytes2VectorListVal; - - event ValsSet(uint a, int b, bool c, int224 d, bool[2] e, int[] f, string g, bytes16 h, bytes2[4][] i); - - function setValues(uint _uintVal, int _intVal, bool _boolVal, int224 _int224Val, bool[2] _boolVectorVal, int[] _intListVal, string _stringVal, bytes16 _bytes16Val, bytes2[4][] _bytes2VectorListVal) public { - uintVal = _uintVal; - intVal = _intVal; - boolVal = _boolVal; - int224Val = _int224Val; - boolVectorVal = _boolVectorVal; - intListVal = _intListVal; - stringVal = _stringVal; - bytes16Val = _bytes16Val; - bytes2VectorListVal = _bytes2VectorListVal; - - ValsSet(_uintVal, _intVal, _boolVal, _int224Val, _boolVectorVal, _intListVal, _stringVal, _bytes16Val, _bytes2VectorListVal); - } - - function getVals () constant public returns (uint, int, bool, int224, bool[2], int[], string, bytes16, bytes2[4][]) { - return (uintVal, intVal, boolVal, int224Val, boolVectorVal, intListVal, stringVal, bytes16Val, bytes2VectorListVal); - } - -} diff --git a/test-support/contracts/Linearization.sol b/test-support/contracts/Linearization.sol deleted file mode 100644 index a5bd9803..00000000 --- a/test-support/contracts/Linearization.sol +++ /dev/null @@ -1,35 +0,0 @@ -pragma solidity ^0.4.22; - -contract Linearization { - - event E1(address sender, uint amount); - event E2(string tag, bytes4 uuid); - event E3(address txOrigin, uint blockNumber); - event E4(bytes4 sig, bytes32 blockHash); - - function e12() public { - emit E1(msg.sender, 0); - emit E2("hello", 0xdeadbeef); - } - - function e21() public { - emit E2("hello", 0xdeadbeef); - emit E1(msg.sender, 0); - } - - function e1() public { - emit E1(msg.sender, 0); - } - - function e2() public { - emit E2("hello", 0xdeadbeef); - } - - function e3() public { - emit E3(tx.origin, block.number); - } - - function e4() public { - emit E4(msg.sig, blockhash(block.number)); - } -} \ No newline at end of file diff --git a/test-support/contracts/Migrations.sol b/test-support/contracts/Migrations.sol deleted file mode 100644 index 7e7fe8d4..00000000 --- a/test-support/contracts/Migrations.sol +++ /dev/null @@ -1,23 +0,0 @@ -pragma solidity ^0.4.4; - -contract Migrations { - address public owner; - uint public last_completed_migration; - - modifier restricted() { - if (msg.sender == owner) _; - } - - function Migrations() { - owner = msg.sender; - } - - function setCompleted(uint completed) restricted { - last_completed_migration = completed; - } - - function upgrade(address new_address) restricted { - Migrations upgraded = Migrations(new_address); - upgraded.setCompleted(last_completed_migration); - } -} diff --git a/test-support/contracts/Registry.sol b/test-support/contracts/Registry.sol deleted file mode 100644 index d08547eb..00000000 --- a/test-support/contracts/Registry.sol +++ /dev/null @@ -1,10 +0,0 @@ -pragma solidity ^0.4.22; - -contract Registry { - - - event A(bytes32 indexed listingHash); - event B(address indexed sender, bytes32 listingHash); - event C(address dog, bytes32 cat); - -} diff --git a/test-support/contracts/SimpleStorage.sol b/test-support/contracts/SimpleStorage.sol deleted file mode 100644 index d77b1f5c..00000000 --- a/test-support/contracts/SimpleStorage.sol +++ /dev/null @@ -1,12 +0,0 @@ -pragma solidity ^0.4.15; - -contract SimpleStorage { - uint public count; - - event _CountSet(uint _count); - - function setCount(uint _count) { - count = _count; - _CountSet(_count); - } -} diff --git a/test-support/inject-contract-addresses.sh b/test-support/inject-contract-addresses.sh deleted file mode 100755 index ac551c9d..00000000 --- a/test-support/inject-contract-addresses.sh +++ /dev/null @@ -1,26 +0,0 @@ -#!/usr/bin/env bash - -set -ex - -EXPORT_STORE=${EXPORT_STORE:-/tmp/detected-vars} -SEARCH_DIRECTORY=${SEARCH_DIRECTORY:-build/contracts} - -function detect_contract_addresses() { - for file in $(find $SEARCH_DIRECTORY -maxdepth 1 -type f -name '*.json'); do - maybe_address=`jq -r .networks[].address $file | grep -v null | head -n 1` - if [ -z "${maybe_address}" ]; then - echo no addresses detected for $file >&2 - else - contract_name=`echo $file | sed -e 's@'$SEARCH_DIRECTORY'/@@g' -e 's/.json//g'` - echo found address "${maybe_address}" for "${contract_name}" >&2 - contract_var=`echo $contract_name | tr '[:lower:]' '[:upper:]'`_CONTRACT_ADDRESS - echo the var for "${contract_name}" is "${contract_var}" >&2 - echo "export ${contract_var}=`echo ${maybe_address} | sed s/0x//`" - fi - done -} - -detect_contract_addresses 2>/dev/null >$EXPORT_STORE - -source $EXPORT_STORE -$@ diff --git a/test-support/package.json b/test-support/package.json deleted file mode 100644 index 52c5e566..00000000 --- a/test-support/package.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "name": "hs-web3-test-support", - "private": true, - "devDependencies": { - "bower": "^1.8.2", - "pulp": "^12.0.1", - "purescript": "^0.11.7", - "solc": "^0.4.22", - "crypto-js": "^3.1.8", - "ethjs-provider-http": "^0.1.6", - "keccak": "^1.4.0", - "mkdirp": "^0.5.1", - "rlp": "^2.0.0", - "secp256k1": "^3.5.0", - "zeppelin-solidity": "^1.7.0" - }, - "dependencies": {} -} diff --git a/test-support/src/ContractConfig.purs b/test-support/src/ContractConfig.purs deleted file mode 100644 index d142ae2b..00000000 --- a/test-support/src/ContractConfig.purs +++ /dev/null @@ -1,46 +0,0 @@ -module ContractConfig - ( simpleStorageConfig - , complexStorageConfig - , linearizationConfig - ) where - -import Chanterelle.Internal.Types (ContractConfig, NoArgs, noArgs, constructorNoArgs) - --------------------------------------------------------------------------------- --- | SimpleStorage --------------------------------------------------------------------------------- - -simpleStorageConfig - :: ContractConfig NoArgs -simpleStorageConfig = - { filepath : "build/contracts/abis/SimpleStorage.json" - , name : "SimpleStorage" - , constructor : constructorNoArgs - , unvalidatedArgs : noArgs - } - --------------------------------------------------------------------------------- --- | Linearization --------------------------------------------------------------------------------- - -linearizationConfig - :: ContractConfig NoArgs -linearizationConfig = - { filepath : "build/contracts/abis/Linearization.json" - , name : "Linearization" - , constructor : constructorNoArgs - , unvalidatedArgs : noArgs - } - --------------------------------------------------------------------------------- --- | ComplexStorage --------------------------------------------------------------------------------- - -complexStorageConfig - :: ContractConfig NoArgs -complexStorageConfig = - { filepath : "build/contracts/abis/ComplexStorage.json" - , name : "ComplexStorage" - , constructor : constructorNoArgs - , unvalidatedArgs : noArgs - } diff --git a/test-support/src/Main.purs b/test-support/src/Main.purs deleted file mode 100644 index 12c541f0..00000000 --- a/test-support/src/Main.purs +++ /dev/null @@ -1,44 +0,0 @@ -module Main where - -import Prelude - -import Chanterelle (deployMain) -import Chanterelle.Deploy (deployContract) -import Chanterelle.Internal.Types (DeployM, DeployConfig(..)) -import ContractConfig (simpleStorageConfig, complexStorageConfig, linearizationConfig) -import Control.Monad.Eff (Eff) -import Control.Monad.Eff.Console (CONSOLE) -import Control.Monad.Eff.Exception (EXCEPTION) -import Control.Monad.Reader.Class (ask) -import Data.Lens ((?~)) -import Data.Maybe (fromJust) -import Network.Ethereum.Web3 (Address, ETH, _from, _gas, defaultTransactionOptions) -import Network.Ethereum.Core.BigNumber (parseBigNumber, decimal) -import Node.FS.Aff (FS) -import Node.Process (PROCESS) -import Partial.Unsafe (unsafePartial) - -main :: forall e. Eff (console :: CONSOLE, eth :: ETH, fs :: FS, process :: PROCESS, exception :: EXCEPTION | e) Unit -main = deployMain deployScript - - - -type DeployResults = - ( simpleStorage :: Address - , complexStorage :: Address - , linearization :: Address - ) - -deployScript :: forall eff. DeployM eff (Record DeployResults) -deployScript = do - deployCfg@(DeployConfig {primaryAccount}) <- ask - let bigGasLimit = unsafePartial fromJust $ parseBigNumber decimal "4712388" - txOpts = defaultTransactionOptions # _from ?~ primaryAccount - # _gas ?~ bigGasLimit - simpleStorage <- deployContract txOpts simpleStorageConfig - complexStorage <- deployContract txOpts complexStorageConfig - linearization <- deployContract txOpts linearizationConfig - pure { simpleStorage: simpleStorage.deployAddress - , complexStorage: complexStorage.deployAddress - , linearization: linearization.deployAddress - } diff --git a/test/Network/Ethereum/Web3/Test/ComplexStorageSpec.hs b/test/Network/Ethereum/Web3/Test/ComplexStorageSpec.hs deleted file mode 100644 index 5b98918e..00000000 --- a/test/Network/Ethereum/Web3/Test/ComplexStorageSpec.hs +++ /dev/null @@ -1,128 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE NamedFieldPuns #-} -{-# LANGUAGE OverloadedLists #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE TemplateHaskell #-} - --- | --- Module : Network.Ethereum.Web3.Test.ComplexStorage --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- ComplexStorage is a Solidity contract which has global variables of --- several different types. The point of this test is to test the encoding --- of a complicated Solidity tuple, consisting of dynamically and statically --- sized components. --- - -module Network.Ethereum.Web3.Test.ComplexStorageSpec where - -import Control.Concurrent.Async (wait) -import Control.Concurrent.MVar -import Control.Monad.IO.Class (liftIO) -import Data.ByteArray (convert) -import Data.ByteString (ByteString) -import Data.Default -import Data.Either (isRight) -import Data.Maybe -import Data.String (fromString) -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 hiding (convert) -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Test.Utils -import Network.Ethereum.Web3.Types -import System.IO.Unsafe (unsafePerformIO) - - -import Test.Hspec - -[abiFrom|test-support/build/contracts/abis/ComplexStorage.json|] - -spec :: Spec -spec = makeEnv `before` complexStorageSpec - -complexStorageSpec :: SpecWith (ContractsEnv, Address) -complexStorageSpec = do - describe "can interact with a ComplexStorage contract" $ do - -- todo: these should ideally be arbitrary! - let sUint = 1 - sInt = -1 - sBool = True - sInt224 = 221 - sBools = [True, False] - sInts = [1, 1, -3] - sString = "hello" - sBytes16 = "\x12\x34\x56\x78\x12\x34\x56\x78\x12\x34\x56\x78\x12\x34\x56\x78" - sByte2sElem = "\x12\x34" - sByte2sVec = [sByte2sElem, sByte2sElem, sByte2sElem, sByte2sElem] - sByte2s = [sByte2sVec, sByte2sVec] - - it "can set the values of a ComplexStorage and validate them with an event" $ - \(ContractsEnv{complexStorage}, primaryAccount) -> do - let theCall = callFromTo primaryAccount complexStorage - fltr = (def :: Filter ValsSet) { filterAddress = Just [complexStorage] } - -- kick off listening for the ValsSet event - vals <- newEmptyMVar - fiber <- runWeb3Configured' $ - event fltr $ \vs -> do - liftIO $ putMVar vals vs - pure TerminateEvent - -- kick off tx - ret <- runWeb3Configured $ setValues theCall - sUint - sInt - sBool - sInt224 - sBools - sInts - sString - sBytes16 - sByte2s - -- wait for its ValsSet event - wait fiber - (ValsSet vsA vsB vsC vsD vsE vsF vsG vsH vsI) <- takeMVar vals - vsA `shouldBe` sUint - vsB `shouldBe` sInt - vsC `shouldBe` sBool - vsD `shouldBe` sInt224 - vsE `shouldBe` sBools - vsF `shouldBe` sInts - vsG `shouldBe` sString - vsH `shouldBe` sBytes16 - vsI `shouldBe` sByte2s - - it "can verify that it set the values correctly" $ \(ContractsEnv{complexStorage}, primaryAccount) -> do - let theCall = callFromTo primaryAccount complexStorage - runGetterCall f = runWeb3Configured (f theCall) - -- there really has to be a better way to do this - uintVal' <- runWeb3Configured $ uintVal theCall Latest - intVal' <- runWeb3Configured $ intVal theCall Latest - boolVal' <- runWeb3Configured $ boolVal theCall Latest - int224Val' <- runWeb3Configured $ int224Val theCall Latest - boolsVal <- runWeb3Configured $ boolVectorVal theCall Latest 0 - intsVal <- runWeb3Configured $ intListVal theCall Latest 0 - stringVal' <- runWeb3Configured $ stringVal theCall Latest - bytes16Val' <- runWeb3Configured $ bytes16Val theCall Latest - bytes2s <- runWeb3Configured $ bytes2VectorListVal theCall Latest 0 0 - uintVal' `shouldBe` sUint - intVal' `shouldBe` sInt - boolVal' `shouldBe` sBool - int224Val' `shouldBe` sInt224 - boolsVal `shouldBe` True - intsVal `shouldBe` sInts Prelude.!! 0 - stringVal' `shouldBe` sString - bytes16Val' `shouldBe` sBytes16 - bytes2s `shouldBe` sByte2sElem - - it "can decode a complicated value correctly" $ \(ContractsEnv{complexStorage}, primaryAccount) -> do - let theCall = callFromTo primaryAccount complexStorage - allVals <- runWeb3Configured $ getVals theCall Latest - allVals `shouldBe` (sUint, sInt, sBool, sInt224, sBools, sInts, sString, sBytes16, sByte2s) diff --git a/test/Network/Ethereum/Web3/Test/ERC20Spec.hs b/test/Network/Ethereum/Web3/Test/ERC20Spec.hs deleted file mode 100644 index 0f1cbb87..00000000 --- a/test/Network/Ethereum/Web3/Test/ERC20Spec.hs +++ /dev/null @@ -1,27 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE OverloadedLists #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE TemplateHaskell #-} - -module Network.Ethereum.Web3.Test.ERC20Spec where - -import Data.Default -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 -import Network.Ethereum.Web3.Types - - -import Test.Hspec - -[abiFrom|test-support/abis/ERC20.json|] - -spec :: Spec -spec = return () - - -getBalance :: Web3 (UIntN 256) -getBalance = balanceOf def Latest ("0x1234567890123456789011234567890234567890" :: Address) diff --git a/test/Network/Ethereum/Web3/Test/LinearizationSpec.hs b/test/Network/Ethereum/Web3/Test/LinearizationSpec.hs deleted file mode 100644 index 6003df7a..00000000 --- a/test/Network/Ethereum/Web3/Test/LinearizationSpec.hs +++ /dev/null @@ -1,195 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE KindSignatures #-} -{-# LANGUAGE LambdaCase #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE NamedFieldPuns #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TemplateHaskell #-} -{-# LANGUAGE TypeApplications #-} - --- Module : Network.Ethereum.Web3.Test.SimpleStorage --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- SimpleStorage is a Solidity contract which stores a uint256. --- The point of this test is to test function calls to update and --- read the value, as well as an event monitor. - -module Network.Ethereum.Web3.Test.LinearizationSpec where - -import Control.Concurrent (forkIO) -import Control.Concurrent.Async (Async, async, wait) -import Control.Concurrent.MVar -import Control.Concurrent.STM (atomically) -import Control.Concurrent.STM.TQueue (TQueue, flushTQueue, - newTQueueIO, writeTQueue) -import Control.Concurrent.STM.TSem (TSem, newTSem, signalTSem, - waitTSem) -import Control.Monad (forM, void) -import Control.Monad.IO.Class (MonadIO, liftIO) -import Control.Monad.Trans.Reader (ReaderT, ask) -import Data.Default -import Data.Either -import Data.List (sort) -import Data.Maybe (fromJust) -import Network.Ethereum.Contract.Event -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 hiding (convert) -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Test.Utils -import Network.Ethereum.Web3.Types -import System.Environment (getEnv) -import System.Random (randomRIO) -import Test.Hspec - -[abiFrom|test-support/build/contracts/abis/Linearization.json|] - -spec :: Spec -spec = do - makeEnv `before` linearizationSpec - makeEnv `before` floodSpec - -floodCount :: Int -floodCount = 200 - --- waitTSem will block until the counter is positive (i.e., > 0) --- so if there's -(floodCount - 1), that means when the floodCount `signalTSem`s are done --- there will be 1 unit left in the TSem for the waitTSem at the end of a test -floodSemCount :: Int -floodSemCount = -(floodCount - 1) - -linearizationSpec :: SpecWith (ContractsEnv, Address) -linearizationSpec = describe "can bundle and linearize events" $ do - it "can call e12" $ \(ContractsEnv{linearization}, primaryAccount) -> do - let theCall = callFromTo primaryAccount linearization - var <- monitorE1OrE2 linearization - _ <- runWeb3Configured' (e12 theCall) - res <- takeMVar var - res `shouldSatisfy` isLeft - it "can call e21" $ \(ContractsEnv{linearization}, primaryAccount) -> do - -- wait on the next block - runWeb3Configured Eth.blockNumber >>= \bn -> awaitBlock (bn + 1) - let theCall = callFromTo primaryAccount linearization - var <- monitorE1OrE2 linearization - _ <- runWeb3Configured' (e21 theCall) - res <- takeMVar var - res `shouldSatisfy` isRight - -singleFlood :: forall m. (MonadIO m) => Address -> Address -> m Hash -singleFlood from to = liftIO $ do - rando :: Int <- randomRIO (1, 4) - let theCall = callFromTo from to - fnToCall = case rando of - 1 -> e1 - 2 -> e2 - 3 -> e3 - 4 -> e4 - _ -> error "got a number outside of (1,4) after randomR (1,4)" - runWeb3Configured' (fnToCall theCall) - -floodSpec :: SpecWith (ContractsEnv, Address) -floodSpec = describe "can correctly demonstrate the difference between `multiEvent` and multiple `event'`s" $ do - it "properly linearizes with `multiEvent` when flooded and doesn't with multiple `event`s" $ - \(ContractsEnv{linearization}, primaryAccount) -> do - multiQ <- monitorAllFourMulti linearization - parQ <- monitorAllFourPar linearization - sleepBlocks 10 -- to let the filter settle so we dont block indefinitely on missing events? - - -- flood em and wait for all to finish - void . forM [1..floodCount] . const $ singleFlood primaryAccount linearization - sleepBlocks 10 -- to let the event listeners catch up - - -- wait for all multiEvents to be received and flush em out - multiReceivedEvents <- liftIO . atomically $ flushTQueue multiQ - parReceivedEvents <- liftIO . atomically $ flushTQueue parQ - - -- did we get at least 1/4 of the events? (this is a gotcha when flooding, sometimes nonces get repeated) - length multiReceivedEvents `shouldSatisfy` (>= (floodCount `div` 4)) - length parReceivedEvents `shouldSatisfy` (>= (floodCount `div` 4)) - - -- did both listeners see the same amount of events? - length multiReceivedEvents `shouldBe` length parReceivedEvents - - -- the events pushed into the multi TQueue should already be sorted if they happened in the right order - sort multiReceivedEvents `shouldBe` multiReceivedEvents - -- the events pushed into the TQueue should not be sorted if they didnt come in in the right order - sort parReceivedEvents `shouldNotBe` parReceivedEvents - - -monitorE1OrE2 - :: Address - -> IO (MVar (Either E1 E2)) -monitorE1OrE2 addr = do - var <- newEmptyMVar - let fltr1 = (def :: Filter E1) { filterAddress = Just [addr] } - fltr2 = (def :: Filter E2) { filterAddress = Just [addr] } - filters = fltr1 :? fltr2 :? NilFilters - handler1 e1 = do - liftIO $ putMVar var (Left e1) - pure TerminateEvent - handler2 e2 = do - liftIO $ putMVar var (Right e2) - pure TerminateEvent - handlers = H handler1 :& H handler2 :& RNil - _ <- runWeb3Configured' $ multiEvent filters handlers - pure var - -data EventTag = ETE1 | ETE2 | ETE3 | ETE4 - deriving (Eq, Read, Show) - -instance {-# OVERLAPPING #-} Ord (EventTag, Integer, Integer) where - (_, b1, t1) `compare` (_, b2, t2) = - let bCmp = b1 `compare` b2 - in if bCmp == EQ - then t1 `compare` t2 - else bCmp - -monitorAllFourMulti - :: Address - -> IO (TQueue (EventTag, Integer, Integer)) -- (EventTag, BlockNumber, LogIndex) -monitorAllFourMulti addr = do - q <- newTQueueIO - let f :: forall a. Default (Filter a) => Filter a - f = defFilter addr - h = enqueueingHandler q - filters = f @E1 :? f @E2 :? f @E3 :? f @E4 :? NilFilters - handlers = h ETE1 :& h ETE2 :& h ETE3 :& h ETE4 :& RNil - void . runWeb3Configured' $ multiEvent filters handlers - return q - -monitorAllFourPar - :: Address - -> IO (TQueue (EventTag, Integer, Integer)) -- (EventTag, BlockNumber, LogIndex) -monitorAllFourPar addr = do - q <- newTQueueIO - let f :: forall a. Default (Filter a) => Filter a - f = defFilter addr - h = enqueueingHandler q - unH (H h) = h - - void . forkIO . runWeb3Configured' $ event' (f @E1) (unH $ h ETE1) - void . forkIO . runWeb3Configured' $ event' (f @E2) (unH $ h ETE2) - void . forkIO . runWeb3Configured' $ event' (f @E3) (unH $ h ETE3) - void . forkIO . runWeb3Configured' $ event' (f @E4) (unH $ h ETE4) - return q - -defFilter :: forall a. Default (Filter a) => Address -> Filter a -defFilter addr = (def :: Filter a) { filterAddress = Just [addr] } - -enqueueingHandler :: forall a. TQueue (EventTag, Integer, Integer) -> EventTag -> Handler (ReaderT Change Web3 EventAction) a -enqueueingHandler q tag = H . const $ do - Change{..} <- ask - let bn = unQuantity $ fromJust changeBlockNumber - li = unQuantity $ fromJust changeLogIndex - liftIO . atomically $ writeTQueue q (tag, bn, li) - pure ContinueEvent diff --git a/test/Network/Ethereum/Web3/Test/RegistrySpec.hs b/test/Network/Ethereum/Web3/Test/RegistrySpec.hs deleted file mode 100644 index a7265db0..00000000 --- a/test/Network/Ethereum/Web3/Test/RegistrySpec.hs +++ /dev/null @@ -1,33 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE OverloadedLists #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE TemplateHaskell #-} - -module Network.Ethereum.Web3.Test.RegistrySpec where - -import Data.Default -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 -import Network.Ethereum.Web3.Types - - -import Test.Hspec - -[abiFrom|test-support/build/contracts/abis/Registry.json|] - --- this spec is just to test compilation -spec :: Spec -spec = return () - - -monitor :: Web3 () -monitor = do - let fltr1 = def :: Filter A - fltr2 = def :: Filter B - event fltr1 $ \_ -> pure TerminateEvent - event fltr2 $ \_ -> pure TerminateEvent - pure () diff --git a/test/Network/Ethereum/Web3/Test/SimpleStorageSpec.hs b/test/Network/Ethereum/Web3/Test/SimpleStorageSpec.hs deleted file mode 100644 index a3fa53d0..00000000 --- a/test/Network/Ethereum/Web3/Test/SimpleStorageSpec.hs +++ /dev/null @@ -1,205 +0,0 @@ -{-# LANGUAGE DataKinds #-} -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE FlexibleInstances #-} -{-# LANGUAGE KindSignatures #-} -{-# LANGUAGE LambdaCase #-} -{-# LANGUAGE MultiParamTypeClasses #-} -{-# LANGUAGE NamedFieldPuns #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE QuasiQuotes #-} -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE TemplateHaskell #-} - --- Module : Network.Ethereum.Web3.Test.SimpleStorage --- Copyright : Alexander Krupenkin 2016 --- License : BSD3 --- --- Maintainer : mail@akru.me --- Stability : experimental --- Portability : unportable --- --- SimpleStorage is a Solidity contract which stores a uint256. --- The point of this test is to test function calls to update and --- read the value, as well as an event monitor. - -module Network.Ethereum.Web3.Test.SimpleStorageSpec where - -import Control.Concurrent (threadDelay) -import Control.Concurrent.Async (wait) -import Control.Concurrent.MVar -import Control.Monad (void) -import Control.Monad.IO.Class (liftIO) -import Control.Monad.Trans.Class (lift) -import Control.Monad.Trans.Reader (ask) -import Data.ByteString (ByteString) -import Data.Default -import Data.Either (isRight) -import Data.Foldable (forM_) -import Data.List (sort) -import Data.Maybe -import Data.Monoid -import Data.String (fromString) -import qualified Data.Text as T -import Data.Traversable (for) -import GHC.TypeLits - -import Network.Ethereum.Contract.TH -import Network.Ethereum.Web3 hiding (convert) -import qualified Network.Ethereum.Web3.Eth as Eth -import Network.Ethereum.Web3.Provider (forkWeb3) -import Network.Ethereum.Web3.Types - -import Numeric (showHex) -import System.Environment (getEnv) -import System.IO.Unsafe (unsafePerformIO) -import Test.Hspec - -import Network.Ethereum.Web3.Test.Utils - -[abiFrom|test-support/build/contracts/abis/SimpleStorage.json|] - -unEvT_CountSet :: EvT_CountSet -> UIntN 256 -unEvT_CountSet (EvT_CountSet n) = n - -spec :: Spec -spec = makeEnv `before` do - interactions - events - -interactions :: SpecWith (ContractsEnv, Address) -interactions = describe "can interact with a SimpleStorage contract" $ do - -- todo: this should ideally be arbitrary! - let theValue = 12345 - it "can set the value of a SimpleStorage contract" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - let theCall = callFromTo primaryAccount simpleStorage - ret <- runWeb3Configured $ setCount theCall theValue - True `shouldBe` True -- we need to get this far - - it "can read the value back" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - let theCall = callFromTo primaryAccount simpleStorage - now <- runWeb3Configured Eth.blockNumber - let later = now + 3 - awaitBlock later - v <- runWeb3Configured (count theCall Latest) - v `shouldBe` theValue - -events :: SpecWith (ContractsEnv, Address) -events = describe "can interact with a SimpleStorage contract across block intervals" $ do - it "can stream events starting and ending in the future, unbounded" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - var <- newMVar [] - let theCall = callFromTo primaryAccount simpleStorage - theSets = [1, 2, 3] - print "Setting up the filter..." - fiber <- runWeb3Configured' $ do - let fltr = (def :: Filter EvT_CountSet) { filterAddress = Just [simpleStorage] } - forkWeb3 $ processUntil' var fltr ((3 ==) . length) - print "Setting the values..." - setValues theCall theSets - wait fiber - print "Filter caught 3 values..." - vals <- takeMVar var - sort (unEvT_CountSet <$> vals) `shouldBe` sort theSets - - it "can stream events starting and ending in the future, bounded" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - runWeb3Configured Eth.blockNumber >>= \bn -> awaitBlock (bn + 1) - var <- newMVar [] - let theCall = callFromTo primaryAccount simpleStorage - theSets = [13, 14, 15] - start <- runWeb3Configured Eth.blockNumber - let later = BlockWithNumber (start + 3) - latest = BlockWithNumber (start + 8) - fltr = (def :: Filter EvT_CountSet) { filterAddress = Just [simpleStorage] - , filterFromBlock = later - , filterToBlock = latest - } - print "Setting up the filter..." - fiber <- runWeb3Configured' $ - forkWeb3 $ processUntil' var fltr ((3 ==) . length) - awaitBlock (start + 3) - print "Setting the values..." - setValues theCall theSets - wait fiber - print "Filter caught 3 values..." - vals <- takeMVar var - sort (unEvT_CountSet <$> vals) `shouldBe` sort theSets - - it "can stream events starting in the past and ending in the future" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - runWeb3Configured Eth.blockNumber >>= \bn -> awaitBlock (bn + 1) - var <- newMVar [] - blockNumberVar <- newEmptyMVar - let theCall = callFromTo primaryAccount simpleStorage - theSets1 = [7, 8, 9] - theSets2 = [10, 11, 12] - start <- runWeb3Configured Eth.blockNumber - let fltr = (def :: Filter EvT_CountSet) { filterAddress = Just [simpleStorage] } - fiber <- runWeb3Configured' $ do - forkWeb3 $ processUntil var fltr ((3 ==) . length) (liftIO . putMVar blockNumberVar . changeBlockNumber) - print "Running first transactions as past transactions..." - setValues theCall theSets1 - wait fiber - print "All past transactions succeeded... " - Just end <- takeMVar blockNumberVar - awaitBlock $ end + 1 -- make past transactions definitively in past - var' <- newMVar [] - fiber <- runWeb3Configured' $ do - let fltr = (def :: Filter EvT_CountSet) { filterAddress = Just [simpleStorage - ] - , filterFromBlock = BlockWithNumber start} - forkWeb3 $ processUntil' var' fltr ((6 ==) . length) - print "Setting more values" - setValues theCall theSets2 - wait fiber - print "All new values have ben set" - vals <- takeMVar var' - sort (unEvT_CountSet <$> vals) `shouldBe` sort (theSets1 <> theSets2) - - it "can stream events starting and ending in the past, bounded" $ \(ContractsEnv{simpleStorage}, primaryAccount) -> do - runWeb3Configured Eth.blockNumber >>= \bn -> awaitBlock (bn + 1) - var <- newMVar [] - let theCall = callFromTo primaryAccount simpleStorage - theSets = [4, 5, 6] - start <- runWeb3Configured Eth.blockNumber - blockNumberVar <- newEmptyMVar - let fltr = (def :: Filter EvT_CountSet) { filterAddress = Just [simpleStorage] } - print "Setting up filter for past transactions..." - fiber <- runWeb3Configured' $ do - forkWeb3 $ processUntil var fltr ((3 ==) . length) (liftIO . putMVar blockNumberVar . changeBlockNumber) - print "Setting values" - setValues theCall theSets - wait fiber - print "All values have been set" - Just end <- takeMVar blockNumberVar - var' <- newMVar [] - let fltr' = fltr { filterFromBlock = BlockWithNumber start - , filterToBlock = BlockWithNumber end - } - awaitBlock $ end + 1 -- make it definitively in the past - runWeb3Configured $ processUntil' var' fltr' ((3 ==) . length) - vals <- takeMVar var' - sort (unEvT_CountSet <$> vals) `shouldBe` sort theSets - -processUntil :: MVar [EvT_CountSet] - -> Filter EvT_CountSet - -> ([EvT_CountSet] -> Bool) -- TODO: make it work for any event - -> (Change -> Web3 ()) - -> Web3 () -processUntil var filter predicate action = do - event' filter $ \(ev :: EvT_CountSet) -> do - newV <- liftIO $ modifyMVar var $ \v -> return (ev:v, ev:v) - if predicate newV - then do - change <- ask - lift $ action change - return TerminateEvent - else return ContinueEvent - -processUntil' :: MVar [EvT_CountSet] - -> Filter EvT_CountSet - -> ([EvT_CountSet] -> Bool) - -> Web3 () -processUntil' var filter predicate = processUntil var filter predicate (const $ return ()) - -setValues :: Call -> [UIntN 256] -> IO () -setValues theCall theSets = forM_ theSets $ \v -> do - runWeb3Configured (setCount theCall v) - threadDelay 1000000 diff --git a/test/Network/Ethereum/Web3/Test/Utils.hs b/test/Network/Ethereum/Web3/Test/Utils.hs deleted file mode 100644 index d335ed66..00000000 --- a/test/Network/Ethereum/Web3/Test/Utils.hs +++ /dev/null @@ -1,162 +0,0 @@ -{-# LANGUAGE DeriveGeneric #-} -{-# LANGUAGE LambdaCase #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE ScopedTypeVariables #-} - -module Network.Ethereum.Web3.Test.Utils - ( makeEnv - , ContractsEnv(..) - , runWeb3Configured - , runWeb3Configured' - , retryWeb3Configured - , withAccounts - , withPrimaryEthereumAccount - , callFromTo - , sleepSeconds - , microtime - , awaitBlock - , awaitTxMined - , sleepBlocks - ) where - -import Control.Concurrent (MVar, threadDelay, - tryTakeMVar) -import Control.Exception (SomeException, catch, - handle, throwIO) -import Control.Lens ((^?)) -import Control.Monad.IO.Class (liftIO) -import Data.Aeson (FromJSON, eitherDecode) -import Data.Aeson.Lens (key, _JSON, _Object) -import Data.Aeson.Types (Value (..)) -import qualified Data.ByteString.Lazy as BSL -import Data.Default -import Data.Either (isRight) -import Data.List.Split (splitOn) -import Data.Maybe (fromMaybe, isJust) -import Data.Ratio (numerator) -import Data.String (IsString, fromString) -import qualified Data.Text as T -import Data.Time.Clock.POSIX (getPOSIXTime) -import Data.Traversable (for) -import GHC.Generics (Generic) -import Network.Ethereum.ABI.Prim.Address (Address) -import Network.Ethereum.Web3.Eth (accounts, blockNumber, - getTransactionReceipt) -import Network.Ethereum.Web3.Net as Net -import Network.Ethereum.Web3.Provider (JsonRpcProvider (..), - Provider (..), Web3, - Web3Error, runWeb3With) -import Network.Ethereum.Web3.Types (Call (..), Hash, Quantity, - TxReceipt (..)) -import Network.HTTP.Client (Manager, ManagerSettings, - defaultManagerSettings, - managerConnCount, - managerRawConnection, - managerRetryableException, - newManager) -import System.Environment (lookupEnv, setEnv) -import System.IO.Unsafe (unsafePerformIO) -import Test.Hspec.Expectations (shouldSatisfy) - --- shared manager used throughout the helpers here to prevent hammering geth from ruining everything --- this also retrys on ALL exceptions, including ConnectionResetByPeer and stuff like that -sharedManager :: Manager -sharedManager = unsafePerformIO $ newManager defaultManagerSettings - { managerConnCount = 5 - , managerRetryableException = const False - , managerRawConnection = fixRawConnection retryOpenConnection - } - - where retryOpenConnection = threadDelay 500000 >> managerRawConnection defaultManagerSettings - fixRawConnection f = f `catch` (\(_ :: SomeException) -> fixRawConnection f) -{-# NOINLINE sharedManager #-} - -makeEnv :: IO (ContractsEnv, Address) -makeEnv = do - cenv <- makeContractsEnv - a <- withPrimaryEthereumAccount - pure (cenv, a) - -rpcUri :: IO String -rpcUri = liftIO (fromMaybe "http://localhost:8545" <$> lookupEnv "WEB3_PROVIDER") - -data ContractsEnv = - ContractsEnv { simpleStorage :: Address - , complexStorage :: Address - , linearization :: Address - } - -makeContractsEnv :: IO ContractsEnv -makeContractsEnv = do - net <- runWeb3Configured' Net.version - ss <- grabAddress net <$> BSL.readFile "test-support/build/contracts/abis/SimpleStorage.json" - cs <- grabAddress net <$> BSL.readFile "test-support/build/contracts/abis/ComplexStorage.json" - lin <- grabAddress net <$> BSL.readFile "test-support/build/contracts/abis/Linearization.json" - pure $ ContractsEnv ss cs lin - where - grabAddress :: T.Text -> BSL.ByteString -> Address - grabAddress nid bs = case eitherDecode bs :: Either String Value of - Right val -> fromMaybe (error "address key missing") (val ^? key "networks" . key nid . key "address" . _JSON) - Left e -> error e - -runWeb3Configured :: Show a => Web3 a -> IO a -runWeb3Configured f = do - provider <- (flip Provider Nothing . HttpProvider) <$> rpcUri - v <- runWeb3With sharedManager provider f - v `shouldSatisfy` isRight - let Right a = v in return a - -runWeb3Configured' :: Web3 a -> IO a -runWeb3Configured' f = do - provider <- (flip Provider Nothing . HttpProvider) <$> rpcUri - Right v <- runWeb3With sharedManager provider f - return v - -retryWeb3Configured :: Web3 a -> IO a -retryWeb3Configured f = do - provider <- (flip Provider Nothing . HttpProvider) <$> rpcUri - v <- runWeb3With sharedManager provider f - case v of - Left _ -> threadDelay 1000000 >> retryWeb3Configured f - Right v -> return v - -withAccounts :: ([Address] -> IO a) -> IO a -withAccounts f = runWeb3Configured accounts >>= f - -withPrimaryEthereumAccount :: IO Address -withPrimaryEthereumAccount = withAccounts (pure . head) - -callFromTo :: Address -> Address -> Call -callFromTo from to = - def { callFrom = Just from - , callTo = Just to - , callGasPrice = Just 4000000000 - } - -sleepSeconds :: Int -> IO () -sleepSeconds = threadDelay . (* 1000000) - -microtime :: IO Integer -microtime = numerator . toRational . (* 1000000) <$> getPOSIXTime - -awaitBlock :: Quantity -> IO () -awaitBlock bn = do - bn' <- retryWeb3Configured blockNumber - -- putStrLn $ "awaiting block " ++ show bn ++ ", currently " ++ show bn' - if bn' >= bn - then return () - else threadDelay 1000000 >> awaitBlock bn - -sleepBlocks :: Int -> IO () -sleepBlocks n = do - now <- retryWeb3Configured blockNumber - awaitBlock $ now + (fromIntegral n) - -awaitTxMined :: Hash -> IO TxReceipt -awaitTxMined hash = do - mReceipt <- retryWeb3Configured $ getTransactionReceipt hash - case mReceipt of - Nothing -> threadDelay 1000000 >> awaitTxMined hash - Just receipt -> if isJust (receiptBlockHash receipt) - then return receipt - else threadDelay 1000000 >> awaitTxMined hash diff --git a/unit/Network/Ethereum/ABI/Prim/Test/AddressSpec.hs b/unit/Network/Ethereum/ABI/Prim/Test/AddressSpec.hs deleted file mode 100644 index 03aa4d2b..00000000 --- a/unit/Network/Ethereum/ABI/Prim/Test/AddressSpec.hs +++ /dev/null @@ -1,40 +0,0 @@ -{-# LANGUAGE OverloadedStrings #-} -module Network.Ethereum.ABI.Prim.Test.AddressSpec where - -import Test.Hspec -import Data.ByteString (ByteString) -import Data.ByteString.Char8 (unpack) -import Data.Foldable (for_) -import Data.Monoid ((<>)) -import Network.Ethereum.ABI.Prim.Address - -spec :: Spec -spec = do - describe "EIP55 Test Vectors" $ for_ checksummedAddrs (\addr -> - it (unpack addr <> " should be checksummed") $ verifyChecksum addr `shouldBe` True) - describe "EIP55 Test Vectors Tampered" $ for_ unchecksummedAddrs (\addr -> - it (unpack addr <> " should not be checksummed") $ verifyChecksum addr `shouldBe` False) - -checksummedAddrs :: [ByteString] -checksummedAddrs = - [ "0x52908400098527886E0F7030069857D2E4169EE7" - , "0x8617E340B3D01FA5F11F306F4090FD50E238070D" - , "0xde709f2102306220921060314715629080e2fb77" - , "0x27b1fdb04752bbc536007a920d24acb045561c26" - , "0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAed" - , "0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5d359" - , "0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6FB" - , "0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDb" - ] - -unchecksummedAddrs :: [ByteString] -unchecksummedAddrs = - [ "0x52908400098527886E0F7030069857D2E4169Ee7" - , "0x8617E340B3D01FA5F11F306F4090FD50E238070d" - , "0xde709f2102306220921060314715629080e2fB77" - , "0x27b1fdb04752bbc536007a920d24acb045561C26" - , "0x5aAeb6053F3E94C9b9A09f33669435E7Ef1BeAeD" - , "0xfB6916095ca1df60bB79Ce92cE3Ea74c37c5D359" - , "0xdbF03B407c01E7cD3CBea99509d93f8DDDC8C6Fb" - , "0xD1220A0cf47c7B9Be7A2E6BA89F429762e7b9aDB" - ] \ No newline at end of file diff --git a/unit/Network/Ethereum/Web3/Test/MethodDumpSpec.hs b/unit/Network/Ethereum/Web3/Test/MethodDumpSpec.hs deleted file mode 100644 index 5f7e454f..00000000 --- a/unit/Network/Ethereum/Web3/Test/MethodDumpSpec.hs +++ /dev/null @@ -1,14 +0,0 @@ -{-# LANGUAGE QuasiQuotes #-} - -module Network.Ethereum.Web3.Test.MethodDumpSpec where - -import Network.Ethereum.Contract.TH -import Test.Hspec -import Text.Printf - - -spec :: Spec -spec = describe "methodDump" $ - it "can dump an ABI" $ do - let theApiDump = [abiFrom|examples/ERC20.json|] - in theApiDump `shouldNotBe` "" diff --git a/unit/Network/Ethereum/Web3/Test/SignatureSpec.hs b/unit/Network/Ethereum/Web3/Test/SignatureSpec.hs deleted file mode 100644 index 45ce32f7..00000000 --- a/unit/Network/Ethereum/Web3/Test/SignatureSpec.hs +++ /dev/null @@ -1,31 +0,0 @@ -{-# LANGUAGE OverloadedStrings #-} - -module Network.Ethereum.Web3.Test.SignatureSpec where - -import Data.ByteArray (Bytes, convert) -import Data.ByteArray.Encoding -import Data.ByteString (ByteString) -import Data.Either (fromRight) -import qualified Data.Text as T -import qualified Data.Text.Encoding as T -import Network.Ethereum.Web3.Types -import Network.Ethereum.Web3.Transaction -import Test.Hspec - - --- using same example as in this blog post: --- https://medium.com/@codetractio/walkthrough-of-an-ethereum-improvement-proposal-eip-6fda3966d171 -spec :: Spec -spec = describe "transaction signing" $ - it "can create valid raw transaction" $ do - let rawTx = T.decodeUtf8 . convertToBase Base16 . (convert :: Bytes -> ByteString) <$> createRawTransaction testCall 1 privKey - rawTx `shouldBe` Right correctSignedTx - where testCall = Call Nothing - (Just "0x3535353535353535353535353535353535353535") - (Just . Quantity $ 21000) - (Just . Quantity $ 20000000000) - (Just . Quantity $ 1000000000000000000) - Nothing - (Just 9) - privKey = fromRight (error "failed to encode private key") . convertFromBase Base16 . T.encodeUtf8 $ "4646464646464646464646464646464646464646464646464646464646464646" - correctSignedTx = "f86c098504a817c800825208943535353535353535353535353535353535353535880de0b6b3a76400008025a028ef61340bd939bc2195fe537567866003e1a15d3c71ff63e1590620aa636276a067cbe9d8997f761aecb703304b3800ccf555c9f3dc64214b297fb1966a3b6d83" diff --git a/web3.cabal b/web3.cabal index 765c4412..5ed7f650 100644 --- a/web3.cabal +++ b/web3.cabal @@ -1,171 +1,600 @@ -name: web3 -version: 0.7.3.0 -synopsis: Ethereum API for Haskell -description: Web3 is a Haskell client library for Ethereum -homepage: https://github.com/airalab/hs-web3#readme -license: BSD3 -license-file: LICENSE -author: Alexander Krupenkin -maintainer: mail@akru.me -copyright: Alexander Krupenkin -category: Network -build-type: Simple -cabal-version: >=1.10 +cabal-version: 2.2 +-- This file has been generated from package.yaml by hpack version 0.37.0. +-- +-- see: https://github.com/sol/hpack +-- +-- hash: 8629eacf81afc4f67aa79d16d9f4fc8c77d49100c617c8237e7154357c699d6e + +name: web3 +version: 0.9.1.0 +synopsis: Web3 API for Haskell. +description: Client library for Third Generation of Web. +category: Network +homepage: https://github.com/airalab/hs-web3#readme +bug-reports: https://github.com/airalab/hs-web3/issues +author: Alexander Krupenkin +maintainer: mail@akru.me +copyright: (c) Alexander Krupenkin 2016 +license: BSD-3-Clause +license-file: LICENSE +build-type: Simple extra-source-files: - README.md - CHANGELOG.md - test-support/contracts/SimpleStorage.sol - test-support/contracts/ComplexStorage.sol - test-support/chanterelle.json - test-support/compile/Compile.purs - test-support/src/ContractConfig.purs - test-support/src/Main.purs - examples/ERC20.hs - examples/ERC20.json - examples/TokenInfo.hs + README.md + CHANGELOG.md + stack.yaml + examples/token/ERC20.hs + examples/token/ERC20.json + examples/token/Main.hs + examples/token/stack.yaml + examples/token/package.yaml + examples/polkadot/Main.hs + examples/polkadot/stack.yaml + examples/polkadot/package.yaml + examples/scale/Main.hs + examples/scale/stack.yaml + examples/scale/package.yaml + test/contracts/Registry.json + test/contracts/SimpleStorage.json + test/contracts/ComplexStorage.json + test/contracts/Linearization.json source-repository head - type: git + type: git location: https://github.com/airalab/hs-web3 -flag tls - description: Enable TLS support +flag compiler + description: Enable Solidity compiler + manual: True default: False -library - hs-source-dirs: src - exposed-modules: Network.Ethereum.Web3 - , Network.Ethereum.Web3.Eth - , Network.Ethereum.Web3.Net - , Network.Ethereum.Web3.Personal - , Network.Ethereum.Web3.Web3 - , Network.Ethereum.Web3.Types - , Network.Ethereum.Web3.Provider - , Network.Ethereum.Web3.Transaction - , Network.Ethereum.Unit - , Network.Ethereum.ABI.Json - , Network.Ethereum.ABI.Class - , Network.Ethereum.ABI.Codec - , Network.Ethereum.ABI.Event - , Network.Ethereum.ABI.Event.Internal - , Network.Ethereum.ABI.Generic - , Network.Ethereum.ABI.Prim - , Network.Ethereum.ABI.Prim.Int - , Network.Ethereum.ABI.Prim.Bool - , Network.Ethereum.ABI.Prim.List - , Network.Ethereum.ABI.Prim.Bytes - , Network.Ethereum.ABI.Prim.Tuple - , Network.Ethereum.ABI.Prim.Tuple.TH - , Network.Ethereum.ABI.Prim.String - , Network.Ethereum.ABI.Prim.Tagged - , Network.Ethereum.ABI.Prim.Address - , Network.Ethereum.Contract.TH - , Network.Ethereum.Contract.Event - , Network.Ethereum.Contract.Event.MultiFilter - , Network.Ethereum.Contract.Event.SingleFilter - , Network.Ethereum.Contract.Event.Common - , Network.Ethereum.Contract.Method - , Network.JsonRpc.TinyClient - , Data.String.Extra - build-depends: base >4.9 && <4.12 - , template-haskell >=2.12.0.0 && <2.14 - , data-default >=0.7.1.1 && <0.8 - , generics-sop >=0.3.2.0 && <0.4 - , transformers >=0.5.2.0 && <0.6 - , http-client >=0.5.12.1 && <0.6 - , exceptions >=0.8.3 && <0.11 - , bytestring >=0.10.8.2 && <0.11 - , cryptonite ==0.25.* - , basement >=0.0.7 && <0.1 - , lens - , lens-aeson - , machines >=0.6.3 && <0.7 - , tagged >=0.8.5 && <0.9 - , parsec >=3.1.13.0 && <3.2 - , memory >=0.14.16 && <0.15 - , cereal >=0.5.5.0 && <0.6 - , aeson >=1.2.4.0 && <1.4 - , async >=2.1.1.1 && <2.3 - , relapse ==1.0.0.0 - , secp256k1 >=0.5.2 && <0.6 - , text >=1.2.3.0 && <1.3 - , mtl >=2.2.2 && <2.3 - , vinyl - , random >=1.1 && <1.2 +flag debug + description: Enable debug compiler options + manual: True + default: False - if flag(tls) - build-depends: http-client-tls >=0.3.5.3 && <0.4 - cpp-options: -DTLS_MANAGER +library + exposed-modules: + Codec.Scale + Codec.Scale.Class + Codec.Scale.Compact + Codec.Scale.Core + Codec.Scale.Generic + Codec.Scale.SingletonEnum + Codec.Scale.Skip + Codec.Scale.TH + Crypto.Ecdsa.Signature + Crypto.Ecdsa.Utils + Crypto.Ethereum + Crypto.Ethereum.Keyfile + Crypto.Ethereum.Signature + Crypto.Ethereum.Utils + Crypto.Random.HmacDrbg + Data.ByteArray.HexString + Data.Solidity.Abi + Data.Solidity.Abi.Codec + Data.Solidity.Abi.Generic + Data.Solidity.Event + Data.Solidity.Event.Internal + Data.Solidity.Prim + Data.Solidity.Prim.Address + Data.Solidity.Prim.Bool + Data.Solidity.Prim.Bytes + Data.Solidity.Prim.Int + Data.Solidity.Prim.List + Data.Solidity.Prim.String + Data.Solidity.Prim.Tagged + Data.Solidity.Prim.Tuple + Data.Solidity.Prim.Tuple.TH + Data.String.Extra + Language.Solidity.Abi + Network.Ethereum + Network.Ethereum.Account + Network.Ethereum.Account.Class + Network.Ethereum.Account.Default + Network.Ethereum.Account.Internal + Network.Ethereum.Account.LocalKey + Network.Ethereum.Account.Personal + Network.Ethereum.Account.Safe + Network.Ethereum.Api.Eth + Network.Ethereum.Api.Net + Network.Ethereum.Api.Personal + Network.Ethereum.Api.Types + Network.Ethereum.Api.Web3 + Network.Ethereum.Chain + Network.Ethereum.Contract + Network.Ethereum.Contract.Event + Network.Ethereum.Contract.Event.Common + Network.Ethereum.Contract.Event.MultiFilter + Network.Ethereum.Contract.Event.SingleFilter + Network.Ethereum.Contract.Method + Network.Ethereum.Contract.TH + Network.Ethereum.Ens + Network.Ethereum.Ens.PublicResolver + Network.Ethereum.Ens.Registry + Network.Ethereum.Transaction + Network.Ethereum.Unit + Network.Ipfs.Api.Bitswap + Network.Ipfs.Api.Block + Network.Ipfs.Api.Bootstrap + Network.Ipfs.Api.Cid + Network.Ipfs.Api.Config + Network.Ipfs.Api.Core + Network.Ipfs.Api.Dag + Network.Ipfs.Api.Dht + Network.Ipfs.Api.Files + Network.Ipfs.Api.Internal + Network.Ipfs.Api.Internal.Call + Network.Ipfs.Api.Internal.Stream + Network.Ipfs.Api.Key + Network.Ipfs.Api.Log + Network.Ipfs.Api.Object + Network.Ipfs.Api.Pin + Network.Ipfs.Api.Pubsub + Network.Ipfs.Api.Repo + Network.Ipfs.Api.Stats + Network.Ipfs.Api.Swarm + Network.Ipfs.Api.Types + Network.Ipfs.Api.Types.Stream + Network.Ipfs.Client + Network.JsonRpc.TinyClient + Network.Polkadot.Api.Account + Network.Polkadot.Api.Author + Network.Polkadot.Api.Babe + Network.Polkadot.Api.Chain + Network.Polkadot.Api.Childstate + Network.Polkadot.Api.Contracts + Network.Polkadot.Api.Engine + Network.Polkadot.Api.Grandpa + Network.Polkadot.Api.Offchain + Network.Polkadot.Api.Payment + Network.Polkadot.Api.Rpc + Network.Polkadot.Api.State + Network.Polkadot.Api.System + Network.Polkadot.Api.Types + Network.Web3 + Network.Web3.Provider + other-modules: + Paths_web3 + autogen-modules: + Paths_web3 + hs-source-dirs: + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Whi-shadowing -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-monadfail-instances -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs + build-depends: + OneTuple >=0.2.1 && <0.5 + , aeson >=1.2.2.0 && <2.2 + , async >=2.1.1.1 && <2.3 + , attoparsec >=0.13.2.1 && <0.15 + , base >4.11 && <4.18 + , base58string >=0.10.0 && <0.11 + , basement >=0.0.4 && <0.1 + , bitvec >=1.0.0 && <2.0 + , bytestring >=0.10.8.1 && <0.12 + , cereal >=0.5.4.0 && <0.6 + , cryptonite >=0.23 && <0.31 + , data-default >=0.7.1.1 && <0.8 + , errors >=2.2 && <2.4 + , exceptions >=0.8.3 && <0.11 + , generics-sop >=0.3.1.0 && <0.6 + , hspec >=2.4 && <2.11 + , http-client >=0.5.7.1 && <0.8 + , http-client-tls >=0.3.5.1 && <0.4 + , http-media >=0.7 && <0.8.2 + , http-types >=0.12 && <0.14 + , machines >=0.6.3 && <0.8 + , memory >=0.14.11 && <0.19 + , microlens >=0.4.8.1 && <0.5 + , microlens-aeson >=2.2.0.2 && <2.6 + , microlens-mtl >=0.1.11.0 && <0.3 + , microlens-th >=0.4.1.1 && <0.5 + , mtl >=2.2.1 && <2.3 + , network >=2.6 && <3.2 + , parsec >=3.1.11 && <3.2 + , relapse >=1.0.0.0 && <2.0 + , servant >=0.13 && <0.20 + , servant-client >=0.13 && <0.20 + , tagged >=0.8.5 && <0.9 + , tar ==0.5.* + , template-haskell >=2.12 && <2.20 + , text >=1.2.2.2 && <2.1 + , transformers >=0.5.2.0 && <0.6 + , unordered-containers ==0.2.* + , uuid-types >=1.0.3 && <1.1 + , vector >=0.12 && <0.14 + , vinyl >=0.5.3 && <0.15 + , websockets >=0.11 && <0.13 + default-language: Haskell2010 + if flag(debug) + ghc-options: -ddump-splices + if flag(compiler) + other-modules: + Language.Solidity.Compiler + Language.Solidity.Compiler.Foreign + hs-source-dirs: + compiler + cpp-options: -DSOLIDITY_COMPILER + include-dirs: + ./compiler/cbits + c-sources: + ./compiler/cbits/solidity_lite.cpp + extra-libraries: + solidity + build-depends: + containers - default-language: Haskell2010 - ghc-options: -Wduplicate-exports -Whi-shadowing -Widentities -Wnoncanonical-monoid-instances - -Woverlapping-patterns -Wtabs -Wpartial-type-signatures -Wderiving-typeable - -Wunrecognised-pragmas -Wunticked-promoted-constructors -Wtyped-holes - -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods - -Wmissing-exported-signatures -Wmissing-monadfail-instances -Wmissing-signatures - -Wname-shadowing -Wnoncanonical-monad-instances -Wnoncanonical-monadfail-instances - -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds - -Wunused-imports -Wunused-matches -Wunused-foralls -Wunused-do-bind -Wwrong-do-bind - -Wtrustworthy-safe -Wwarnings-deprecations -Wdeferred-type-errors +test-suite live + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Network.Ethereum.Test.ComplexStorageSpec + Network.Ethereum.Test.ERC20Spec + Network.Ethereum.Test.LinearizationSpec + Network.Ethereum.Test.LocalAccountSpec + Network.Ethereum.Test.RegistrySpec + Network.Ethereum.Test.SimpleStorageSpec + Network.Ethereum.Test.Utils + Network.Ipfs.Api.Test.Key + Codec.Scale + Codec.Scale.Class + Codec.Scale.Compact + Codec.Scale.Core + Codec.Scale.Generic + Codec.Scale.SingletonEnum + Codec.Scale.Skip + Codec.Scale.TH + Crypto.Ecdsa.Signature + Crypto.Ecdsa.Utils + Crypto.Ethereum + Crypto.Ethereum.Keyfile + Crypto.Ethereum.Signature + Crypto.Ethereum.Utils + Crypto.Random.HmacDrbg + Data.ByteArray.HexString + Data.Solidity.Abi + Data.Solidity.Abi.Codec + Data.Solidity.Abi.Generic + Data.Solidity.Event + Data.Solidity.Event.Internal + Data.Solidity.Prim + Data.Solidity.Prim.Address + Data.Solidity.Prim.Bool + Data.Solidity.Prim.Bytes + Data.Solidity.Prim.Int + Data.Solidity.Prim.List + Data.Solidity.Prim.String + Data.Solidity.Prim.Tagged + Data.Solidity.Prim.Tuple + Data.Solidity.Prim.Tuple.TH + Data.String.Extra + Language.Solidity.Abi + Network.Ethereum + Network.Ethereum.Account + Network.Ethereum.Account.Class + Network.Ethereum.Account.Default + Network.Ethereum.Account.Internal + Network.Ethereum.Account.LocalKey + Network.Ethereum.Account.Personal + Network.Ethereum.Account.Safe + Network.Ethereum.Api.Eth + Network.Ethereum.Api.Net + Network.Ethereum.Api.Personal + Network.Ethereum.Api.Types + Network.Ethereum.Api.Web3 + Network.Ethereum.Chain + Network.Ethereum.Contract + Network.Ethereum.Contract.Event + Network.Ethereum.Contract.Event.Common + Network.Ethereum.Contract.Event.MultiFilter + Network.Ethereum.Contract.Event.SingleFilter + Network.Ethereum.Contract.Method + Network.Ethereum.Contract.TH + Network.Ethereum.Ens + Network.Ethereum.Ens.PublicResolver + Network.Ethereum.Ens.Registry + Network.Ethereum.Transaction + Network.Ethereum.Unit + Network.Ipfs.Api.Bitswap + Network.Ipfs.Api.Block + Network.Ipfs.Api.Bootstrap + Network.Ipfs.Api.Cid + Network.Ipfs.Api.Config + Network.Ipfs.Api.Core + Network.Ipfs.Api.Dag + Network.Ipfs.Api.Dht + Network.Ipfs.Api.Files + Network.Ipfs.Api.Internal + Network.Ipfs.Api.Internal.Call + Network.Ipfs.Api.Internal.Stream + Network.Ipfs.Api.Key + Network.Ipfs.Api.Log + Network.Ipfs.Api.Object + Network.Ipfs.Api.Pin + Network.Ipfs.Api.Pubsub + Network.Ipfs.Api.Repo + Network.Ipfs.Api.Stats + Network.Ipfs.Api.Swarm + Network.Ipfs.Api.Types + Network.Ipfs.Api.Types.Stream + Network.Ipfs.Client + Network.JsonRpc.TinyClient + Network.Polkadot.Api.Account + Network.Polkadot.Api.Author + Network.Polkadot.Api.Babe + Network.Polkadot.Api.Chain + Network.Polkadot.Api.Childstate + Network.Polkadot.Api.Contracts + Network.Polkadot.Api.Engine + Network.Polkadot.Api.Grandpa + Network.Polkadot.Api.Offchain + Network.Polkadot.Api.Payment + Network.Polkadot.Api.Rpc + Network.Polkadot.Api.State + Network.Polkadot.Api.System + Network.Polkadot.Api.Types + Network.Web3 + Network.Web3.Provider + Paths_web3 + autogen-modules: + Paths_web3 + hs-source-dirs: + test + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Whi-shadowing -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-monadfail-instances -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + OneTuple >=0.2.1 && <0.5 + , aeson >=1.2.2.0 && <2.2 + , async >=2.1.1.1 && <2.3 + , attoparsec >=0.13.2.1 && <0.15 + , base >4.11 && <4.18 + , base58string >=0.10.0 && <0.11 + , basement >=0.0.4 && <0.1 + , bitvec >=1.0.0 && <2.0 + , bytestring >=0.10.8.1 && <0.12 + , cereal >=0.5.4.0 && <0.6 + , cryptonite >=0.23 && <0.31 + , data-default >=0.7.1.1 && <0.8 + , errors >=2.2 && <2.4 + , exceptions >=0.8.3 && <0.11 + , generics-sop >=0.3.1.0 && <0.6 + , hspec >=2.4.4 && <2.8 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.8 + , hspec-expectations >=0.8.2 && <0.9 + , http-client >=0.5.7.1 && <0.8 + , http-client-tls >=0.3.5.1 && <0.4 + , http-media >=0.7 && <0.8.2 + , http-types >=0.12 && <0.14 + , machines >=0.6.3 && <0.8 + , memory >=0.14.11 && <0.19 + , microlens >=0.4.8.1 && <0.5 + , microlens-aeson >=2.2.0.2 && <2.6 + , microlens-mtl >=0.1.11.0 && <0.3 + , microlens-th >=0.4.1.1 && <0.5 + , mtl >=2.2.1 && <2.3 + , network >=2.6 && <3.2 + , parsec >=3.1.11 && <3.2 + , random ==1.1.* + , relapse >=1.0.0.0 && <2.0 + , servant >=0.13 && <0.20 + , servant-client >=0.13 && <0.20 + , split >=0.2.3 && <0.3 + , stm >=2.4.4 && <2.6 + , tagged >=0.8.5 && <0.9 + , tar ==0.5.* + , template-haskell >=2.12 && <2.20 + , text >=1.2.2.2 && <2.1 + , time >=1.6.0 && <1.11 + , transformers >=0.5.2.0 && <0.6 + , unordered-containers ==0.2.* + , uuid-types >=1.0.3 && <1.1 + , vector >=0.12 && <0.14 + , vinyl >=0.5.3 && <0.15 + , websockets >=0.11 && <0.13 + default-language: Haskell2010 + if flag(debug) + ghc-options: -ddump-splices + if flag(compiler) + other-modules: + Language.Solidity.Compiler + Language.Solidity.Compiler.Foreign + hs-source-dirs: + compiler + cpp-options: -DSOLIDITY_COMPILER + include-dirs: + ./compiler/cbits + c-sources: + ./compiler/cbits/solidity_lite.cpp + extra-libraries: + solidity + build-depends: + containers test-suite unit - type: exitcode-stdio-1.0 - hs-source-dirs: unit - main-is: Spec.hs - other-modules: Network.Ethereum.ABI.Prim.Test.AddressSpec - , Network.Ethereum.Web3.Test.MethodDumpSpec - , Network.Ethereum.Web3.Test.EncodingSpec - , Network.Ethereum.Web3.Test.EventSpec - , Network.Ethereum.Web3.Test.SignatureSpec - build-depends: base >4.9 && <4.12 - , hspec-expectations >=0.8.2 && <0.9 - , hspec-discover >=2.4.8 && <2.6 - , hspec-contrib >=0.4.0 && <0.6 - , hspec >=2.4.8 && <2.6 - , data-default >=0.7.1.1 && <0.8 - , generics-sop >=0.3.2.0 && <0.4 - , transformers >=0.5.2.0 && <0.6 - , bytestring >=0.10.8.2 && <0.11 - , memory >=0.14.16 && <0.15 - , tagged >=0.8.5 && <0.9 - , split >=0.2.3.3 && <0.3 - , time >=1.8.0.2 && <1.9 - , text >=1.2.3.0 && <1.3 - , web3 - ghc-options: -threaded -rtsopts -with-rtsopts=-N - default-language: Haskell2010 - -test-suite live - type: exitcode-stdio-1.0 - hs-source-dirs: test - main-is: Spec.hs - other-modules: Network.Ethereum.Web3.Test.ComplexStorageSpec - , Network.Ethereum.Web3.Test.SimpleStorageSpec - , Network.Ethereum.Web3.Test.LinearizationSpec - , Network.Ethereum.Web3.Test.ERC20Spec - , Network.Ethereum.Web3.Test.RegistrySpec - , Network.Ethereum.Web3.Test.Utils - build-depends: base >4.9 && <4.12 - , aeson - , lens-aeson - , hspec-expectations >=0.8.2 && <0.9 - , hspec-discover >=2.4.8 && <2.6 - , hspec-contrib >=0.4.0 && <0.6 - , hspec >=2.4.8 && <2.6 - , lens - , transformers >=0.5.2.0 && <0.6 - , data-default >=0.7.1.1 && <0.8 - , bytestring >=0.10.8.2 && <0.11 - , memory >=0.14.16 && <0.15 - , tagged >=0.8.5 && <0.9 - , split >=0.2.3.3 && <0.3 - , async >=2.1.1.1 && <2.3 - , random >=1.1 && <1.2 - , time >=1.8.0.2 && <1.9 - , text >=1.2.3.0 && <1.3 - , stm >=2.4.5.0 && <2.5 - , http-client >=0.5.12.1 && <0.6 - , web3 - ghc-options: -threaded -rtsopts -with-rtsopts=-N - default-language: Haskell2010 + type: exitcode-stdio-1.0 + main-is: Spec.hs + other-modules: + Codec.Scale.Test.CoreSpec + Codec.Scale.Test.SingleFieldStructSpec + Codec.Scale.Test.SkipSpec + Crypto.Ethereum.Test.KeyfileSpec + Crypto.Ethereum.Test.SignatureSpec + Crypto.Random.Test.HmacDrbgSpec + Data.Solidity.Test.AddressSpec + Data.Solidity.Test.EncodingSpec + Data.Solidity.Test.IntSpec + Language.Solidity.Test.AbiSpec + Language.Solidity.Test.CompilerSpec + Network.Ethereum.Contract.Test.THSpec + Network.Ethereum.Web3.Test.EventSpec + Network.Ethereum.Web3.Test.MethodDumpSpec + Codec.Scale + Codec.Scale.Class + Codec.Scale.Compact + Codec.Scale.Core + Codec.Scale.Generic + Codec.Scale.SingletonEnum + Codec.Scale.Skip + Codec.Scale.TH + Crypto.Ecdsa.Signature + Crypto.Ecdsa.Utils + Crypto.Ethereum + Crypto.Ethereum.Keyfile + Crypto.Ethereum.Signature + Crypto.Ethereum.Utils + Crypto.Random.HmacDrbg + Data.ByteArray.HexString + Data.Solidity.Abi + Data.Solidity.Abi.Codec + Data.Solidity.Abi.Generic + Data.Solidity.Event + Data.Solidity.Event.Internal + Data.Solidity.Prim + Data.Solidity.Prim.Address + Data.Solidity.Prim.Bool + Data.Solidity.Prim.Bytes + Data.Solidity.Prim.Int + Data.Solidity.Prim.List + Data.Solidity.Prim.String + Data.Solidity.Prim.Tagged + Data.Solidity.Prim.Tuple + Data.Solidity.Prim.Tuple.TH + Data.String.Extra + Language.Solidity.Abi + Network.Ethereum + Network.Ethereum.Account + Network.Ethereum.Account.Class + Network.Ethereum.Account.Default + Network.Ethereum.Account.Internal + Network.Ethereum.Account.LocalKey + Network.Ethereum.Account.Personal + Network.Ethereum.Account.Safe + Network.Ethereum.Api.Eth + Network.Ethereum.Api.Net + Network.Ethereum.Api.Personal + Network.Ethereum.Api.Types + Network.Ethereum.Api.Web3 + Network.Ethereum.Chain + Network.Ethereum.Contract + Network.Ethereum.Contract.Event + Network.Ethereum.Contract.Event.Common + Network.Ethereum.Contract.Event.MultiFilter + Network.Ethereum.Contract.Event.SingleFilter + Network.Ethereum.Contract.Method + Network.Ethereum.Contract.TH + Network.Ethereum.Ens + Network.Ethereum.Ens.PublicResolver + Network.Ethereum.Ens.Registry + Network.Ethereum.Transaction + Network.Ethereum.Unit + Network.Ipfs.Api.Bitswap + Network.Ipfs.Api.Block + Network.Ipfs.Api.Bootstrap + Network.Ipfs.Api.Cid + Network.Ipfs.Api.Config + Network.Ipfs.Api.Core + Network.Ipfs.Api.Dag + Network.Ipfs.Api.Dht + Network.Ipfs.Api.Files + Network.Ipfs.Api.Internal + Network.Ipfs.Api.Internal.Call + Network.Ipfs.Api.Internal.Stream + Network.Ipfs.Api.Key + Network.Ipfs.Api.Log + Network.Ipfs.Api.Object + Network.Ipfs.Api.Pin + Network.Ipfs.Api.Pubsub + Network.Ipfs.Api.Repo + Network.Ipfs.Api.Stats + Network.Ipfs.Api.Swarm + Network.Ipfs.Api.Types + Network.Ipfs.Api.Types.Stream + Network.Ipfs.Client + Network.JsonRpc.TinyClient + Network.Polkadot.Api.Account + Network.Polkadot.Api.Author + Network.Polkadot.Api.Babe + Network.Polkadot.Api.Chain + Network.Polkadot.Api.Childstate + Network.Polkadot.Api.Contracts + Network.Polkadot.Api.Engine + Network.Polkadot.Api.Grandpa + Network.Polkadot.Api.Offchain + Network.Polkadot.Api.Payment + Network.Polkadot.Api.Rpc + Network.Polkadot.Api.State + Network.Polkadot.Api.System + Network.Polkadot.Api.Types + Network.Web3 + Network.Web3.Provider + Paths_web3 + autogen-modules: + Paths_web3 + hs-source-dirs: + unit + src + ghc-options: -funbox-strict-fields -Wduplicate-exports -Whi-shadowing -Widentities -Woverlapping-patterns -Wpartial-type-signatures -Wunrecognised-pragmas -Wtyped-holes -Wincomplete-patterns -Wincomplete-uni-patterns -Wmissing-fields -Wmissing-methods -Wmissing-exported-signatures -Wmissing-monadfail-instances -Wmissing-signatures -Wname-shadowing -Wunused-binds -Wunused-top-binds -Wunused-local-binds -Wunused-pattern-binds -Wunused-imports -Wunused-matches -Wunused-foralls -Wtabs -threaded -rtsopts -with-rtsopts=-N + build-depends: + OneTuple >=0.2.1 && <0.5 + , aeson >=1.2.2.0 && <2.2 + , async >=2.1.1.1 && <2.3 + , attoparsec >=0.13.2.1 && <0.15 + , base >4.11 && <4.18 + , base58string >=0.10.0 && <0.11 + , basement >=0.0.4 && <0.1 + , bitvec >=1.0.0 && <2.0 + , bytestring >=0.10.8.1 && <0.12 + , cereal >=0.5.4.0 && <0.6 + , cryptonite >=0.23 && <0.31 + , data-default >=0.7.1.1 && <0.8 + , errors >=2.2 && <2.4 + , exceptions >=0.8.3 && <0.11 + , generics-sop >=0.3.1.0 && <0.6 + , hspec >=2.4.4 && <2.8 + , hspec-contrib >=0.4.0 && <0.6 + , hspec-discover >=2.4.4 && <2.8 + , hspec-expectations >=0.8.2 && <0.9 + , http-client >=0.5.7.1 && <0.8 + , http-client-tls >=0.3.5.1 && <0.4 + , http-media >=0.7 && <0.8.2 + , http-types >=0.12 && <0.14 + , machines >=0.6.3 && <0.8 + , memory >=0.14.11 && <0.19 + , microlens >=0.4.8.1 && <0.5 + , microlens-aeson >=2.2.0.2 && <2.6 + , microlens-mtl >=0.1.11.0 && <0.3 + , microlens-th >=0.4.1.1 && <0.5 + , mtl >=2.2.1 && <2.3 + , network >=2.6 && <3.2 + , parsec >=3.1.11 && <3.2 + , relapse >=1.0.0.0 && <2.0 + , servant >=0.13 && <0.20 + , servant-client >=0.13 && <0.20 + , tagged >=0.8.5 && <0.9 + , tar ==0.5.* + , template-haskell >=2.12 && <2.20 + , text >=1.2.2.2 && <2.1 + , transformers >=0.5.2.0 && <0.6 + , unordered-containers ==0.2.* + , uuid-types >=1.0.3 && <1.1 + , vector >=0.12 && <0.14 + , vinyl >=0.5.3 && <0.15 + , websockets >=0.11 && <0.13 + default-language: Haskell2010 + if flag(debug) + ghc-options: -ddump-splices + if flag(compiler) + other-modules: + Language.Solidity.Compiler + Language.Solidity.Compiler.Foreign + hs-source-dirs: + compiler + cpp-options: -DSOLIDITY_COMPILER + include-dirs: + ./compiler/cbits + c-sources: + ./compiler/cbits/solidity_lite.cpp + extra-libraries: + solidity + build-depends: + containers