From a0dbcc17c17087eeba51ba001df57779df72ef9f Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 15:21:48 -0500 Subject: [PATCH 01/42] feat(world): initial package scaffold --- .vscode/settings.json | 3 +- package.json | 1 + packages/store/package.json | 2 +- packages/world/.gitignore | 10 + packages/world/.npmignore | 7 + packages/world/.nvmrc | 1 + packages/world/.prettierrc | 7 + packages/world/.solhint.json | 8 + packages/world/CHANGELOG.md | 4 + packages/world/CHANGELOG.yml | 1 + packages/world/README.md | 1 + packages/world/foundry.toml | 9 + packages/world/git-install.sh | 5 + packages/world/hardhat.config.ts | 23 + packages/world/index.ts | 1 + packages/world/index.yml | 2 + packages/world/package.json | 51 + packages/world/remappings.txt | 3 + packages/world/src/System.sol | 12 + packages/world/src/World.sol | 4 + packages/world/src/schemas/Address.sol | 65 + packages/world/src/schemas/AddressArray.sol | 86 + packages/world/tasks/compile.ts | 38 + packages/world/test/World.t.sol | 22 + packages/world/tsconfig.json | 102 + packages/world/yarn.lock | 3309 +++++++++++++++++++ 26 files changed, 3775 insertions(+), 2 deletions(-) create mode 100644 packages/world/.gitignore create mode 100644 packages/world/.npmignore create mode 100644 packages/world/.nvmrc create mode 100644 packages/world/.prettierrc create mode 100644 packages/world/.solhint.json create mode 100644 packages/world/CHANGELOG.md create mode 100644 packages/world/CHANGELOG.yml create mode 100644 packages/world/README.md create mode 100644 packages/world/foundry.toml create mode 100755 packages/world/git-install.sh create mode 100644 packages/world/hardhat.config.ts create mode 100644 packages/world/index.ts create mode 100644 packages/world/index.yml create mode 100644 packages/world/package.json create mode 100644 packages/world/remappings.txt create mode 100644 packages/world/src/System.sol create mode 100644 packages/world/src/World.sol create mode 100644 packages/world/src/schemas/Address.sol create mode 100644 packages/world/src/schemas/AddressArray.sol create mode 100644 packages/world/tasks/compile.ts create mode 100644 packages/world/test/World.t.sol create mode 100644 packages/world/tsconfig.json create mode 100644 packages/world/yarn.lock diff --git a/.vscode/settings.json b/.vscode/settings.json index b58c7696ed..db9181bbc5 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -9,6 +9,7 @@ "ds-test/=node_modules/ds-test/src/", "solecs/=node_modules/@latticexyz/solecs/src/", "royalty-registry/=node_modules/@manifoldxzy/royalty-registry/contracts/", - "std-contracts/=node_modules/@latticexyz/std-contracts/src/" + "std-contracts/=node_modules/@latticexyz/std-contracts/src/", + "store/=node_modules/@latticexyz/store/src/" ] } diff --git a/package.json b/package.json index 6ddd52e2b6..0315b2d0cf 100644 --- a/package.json +++ b/package.json @@ -13,6 +13,7 @@ "packages/schema-type", "packages/solecs", "packages/store", + "packages/world", "packages/cli", "packages/recs", "packages/react", diff --git a/packages/store/package.json b/packages/store/package.json index 28a3e6d8ef..a2c2c109d2 100644 --- a/packages/store/package.json +++ b/packages/store/package.json @@ -1,7 +1,7 @@ { "name": "@latticexyz/store", "license": "MIT", - "version": "1.33.1", + "version": "1.34.0", "description": "Store", "types": "./types/ethers-contracts/", "repository": { diff --git a/packages/world/.gitignore b/packages/world/.gitignore new file mode 100644 index 0000000000..2f6f3adfc2 --- /dev/null +++ b/packages/world/.gitignore @@ -0,0 +1,10 @@ +cache +abi +out +types/ethers-contracts +docs +_docs +DOCS.md +artifacts +yarn-error.log +API \ No newline at end of file diff --git a/packages/world/.npmignore b/packages/world/.npmignore new file mode 100644 index 0000000000..4240dbeb28 --- /dev/null +++ b/packages/world/.npmignore @@ -0,0 +1,7 @@ +* + +!abi/** +!src/** +!types/** +!package.json +!README.md \ No newline at end of file diff --git a/packages/world/.nvmrc b/packages/world/.nvmrc new file mode 100644 index 0000000000..8e2afd3427 --- /dev/null +++ b/packages/world/.nvmrc @@ -0,0 +1 @@ +17 \ No newline at end of file diff --git a/packages/world/.prettierrc b/packages/world/.prettierrc new file mode 100644 index 0000000000..9a5a009900 --- /dev/null +++ b/packages/world/.prettierrc @@ -0,0 +1,7 @@ +{ + "printWidth": 120, + "semi": true, + "tabWidth": 2, + "useTabs": false, + "bracketSpacing": true +} diff --git a/packages/world/.solhint.json b/packages/world/.solhint.json new file mode 100644 index 0000000000..4e2baa8be7 --- /dev/null +++ b/packages/world/.solhint.json @@ -0,0 +1,8 @@ +{ + "extends": "solhint:recommended", + "rules": { + "compiler-version": ["error", ">=0.8.0"], + "avoid-low-level-calls": "off", + "func-visibility": ["warn", { "ignoreConstructors": true }] + } +} diff --git a/packages/world/CHANGELOG.md b/packages/world/CHANGELOG.md new file mode 100644 index 0000000000..e4d87c4d45 --- /dev/null +++ b/packages/world/CHANGELOG.md @@ -0,0 +1,4 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. diff --git a/packages/world/CHANGELOG.yml b/packages/world/CHANGELOG.yml new file mode 100644 index 0000000000..e3f6e391b4 --- /dev/null +++ b/packages/world/CHANGELOG.yml @@ -0,0 +1 @@ +label: Changelog diff --git a/packages/world/README.md b/packages/world/README.md new file mode 100644 index 0000000000..8b429c9f1b --- /dev/null +++ b/packages/world/README.md @@ -0,0 +1 @@ +# World framework diff --git a/packages/world/foundry.toml b/packages/world/foundry.toml new file mode 100644 index 0000000000..5847f2b9a7 --- /dev/null +++ b/packages/world/foundry.toml @@ -0,0 +1,9 @@ +[profile.default] +ffi = false +fuzz_runs = 256 +optimizer = true +optimizer_runs = 1000000 +verbosity = 1 +libs = ["../../node_modules", "../store"] +src = "src" +out = "out" \ No newline at end of file diff --git a/packages/world/git-install.sh b/packages/world/git-install.sh new file mode 100755 index 0000000000..b86de4f8c9 --- /dev/null +++ b/packages/world/git-install.sh @@ -0,0 +1,5 @@ +#! usr/bin/bash +giturl=https://github.com/$1.git +head=$(git ls-remote $giturl HEAD | head -n1 | awk '{print $1;}') +yarn add $giturl#$head +echo "Installed $giturl#$head" \ No newline at end of file diff --git a/packages/world/hardhat.config.ts b/packages/world/hardhat.config.ts new file mode 100644 index 0000000000..da00b249c6 --- /dev/null +++ b/packages/world/hardhat.config.ts @@ -0,0 +1,23 @@ +import { HardhatUserConfig } from "hardhat/config"; +import "./tasks/compile"; +import "solidity-docgen"; + +const config: HardhatUserConfig = { + paths: { + sources: "./src", + }, + solidity: { + version: "0.8.13", + settings: { + optimizer: { + enabled: true, + runs: 200, + }, + }, + }, + docgen: { + outputDir: "API", + }, +}; + +export default config; diff --git a/packages/world/index.ts b/packages/world/index.ts new file mode 100644 index 0000000000..cb0ff5c3b5 --- /dev/null +++ b/packages/world/index.ts @@ -0,0 +1 @@ +export {}; diff --git a/packages/world/index.yml b/packages/world/index.yml new file mode 100644 index 0000000000..67be39bdfd --- /dev/null +++ b/packages/world/index.yml @@ -0,0 +1,2 @@ +label: store +order: 50 diff --git a/packages/world/package.json b/packages/world/package.json new file mode 100644 index 0000000000..3c59128a82 --- /dev/null +++ b/packages/world/package.json @@ -0,0 +1,51 @@ +{ + "name": "@latticexyz/world", + "license": "MIT", + "version": "1.34.0", + "description": "World framework", + "types": "./types/ethers-contracts/", + "repository": { + "type": "git", + "url": "https://github.com/latticexyz/mud.git", + "directory": "packages/world" + }, + "scripts": { + "prepare": "yarn build && chmod u+x git-install.sh", + "git:install": "bash git-install.sh", + "test": "forge test", + "build": "rimraf out && forge build --out out && yarn dist && yarn types", + "dist": "rimraf abi && mkdir abi && cp -rf out/*.sol/*.json abi/ && yarn rimraf abi/*.metadata.json", + "types": "rimraf types && typechain --target=ethers-v5 abi/*.json", + "prettier": "prettier --write 'src/**/*.sol'", + "solhint": "solhint --config ./.solhint.json 'src/**/*.sol'", + "lint": "yarn prettier && yarn solhint", + "link": "yarn link", + "docs": "rimraf API && hardhat docgen && echo 'label: API\norder: 50' > API/index.yml", + "release": "npm publish || echo 'version already published'", + "gasreport": " ../cli/dist/index.js gas-report --path test/** --save gas-report.txt" + }, + "devDependencies": { + "@typechain/ethers-v5": "^9.0.0", + "@types/mocha": "^9.1.1", + "ds-test": "https://github.com/dapphub/ds-test.git#c9ce3f25bde29fc5eb9901842bf02850dfd2d084", + "forge-std": "https://github.com/foundry-rs/forge-std.git#f36dab24d63d1c1945a05ed375ce341d3c1a49ed", + "hardhat": "^2.10.1", + "prettier": "^2.6.2", + "prettier-plugin-solidity": "^1.0.0-beta.19", + "rimraf": "^3.0.2", + "solhint": "^3.3.7", + "solidity-docgen": "^0.6.0-beta.22", + "ts-node": "10.7", + "typechain": "^8.1.1", + "typedoc": "^0.23.10", + "@latticexyz/cli": "^1.34.0", + "@latticexyz/store": "^1.34.0" + + }, + "peerDependencies": { + "ds-test": "https://github.com/dapphub/ds-test.git#c9ce3f25bde29fc5eb9901842bf02850dfd2d084", + "forge-std": "https://github.com/foundry-rs/forge-std.git#f36dab24d63d1c1945a05ed375ce341d3c1a49ed", + "@latticexyz/store": "^1.34.0" + }, + "gitHead": "218f56893d268b0c5157a3e4c603b859e287a343" +} diff --git a/packages/world/remappings.txt b/packages/world/remappings.txt new file mode 100644 index 0000000000..764dfe470c --- /dev/null +++ b/packages/world/remappings.txt @@ -0,0 +1,3 @@ +ds-test/=../../node_modules/ds-test/src/ +forge-std/=../../node_modules/forge-std/src/ +store/=../../node_modules/@latticexyz/store/src/ diff --git a/packages/world/src/System.sol b/packages/world/src/System.sol new file mode 100644 index 0000000000..1fce49db82 --- /dev/null +++ b/packages/world/src/System.sol @@ -0,0 +1,12 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +contract System { + // Extract the trusted msg.sender value appended to the calldata + function _msgSender() internal pure returns (address sender) { + assembly { + // 96 = 256 - 20 * 8 + sender := shr(96, calldataload(sub(calldatasize(), 20))) + } + } +} diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol new file mode 100644 index 0000000000..a77b08a01f --- /dev/null +++ b/packages/world/src/World.sol @@ -0,0 +1,4 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +contract World {} diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/Address.sol new file mode 100644 index 0000000000..46584b4a8e --- /dev/null +++ b/packages/world/src/schemas/Address.sol @@ -0,0 +1,65 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; + +// -- User defined schema and tableId -- +struct AddressSchema { + address addr; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library AddressSchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.Address); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 key, + address addr + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(addr)); + } + + /** Get the table's data */ + function get(bytes32 tableId, bytes32 key) internal view returns (address) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return address(bytes20(blob)); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 key + ) internal view returns (address) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = store.getRecord(tableId, keyTuple); + return address(bytes20(blob)); + } +} diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol new file mode 100644 index 0000000000..63b20fad7a --- /dev/null +++ b/packages/world/src/schemas/AddressArray.sol @@ -0,0 +1,86 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; + +// -- User defined schema and tableId -- +struct AddressArraySchema { + address[] addresses; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library AddressArraySchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.AddressArray); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 key, + address[] memory addresses + ) internal { + bytes memory data = Bytes.from(addresses); + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + StoreSwitch.setField(tableId, keyTuple, 0, data); + } + + /** + * Push an element to the addresses array + * TODO: this is super inefficient right now, need to add support for pushing to arrays to the store core library to avoid reading/writing the entire array + */ + function push( + bytes32 tableId, + bytes32 key, + address addr + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory addresses = abi.encodePacked(StoreSwitch.getField(tableId, keyTuple, 0), addr); + StoreSwitch.setField(tableId, keyTuple, 0, addresses); + } + + /** Get the table's data */ + function get(bytes32 tableId, bytes32 key) internal view returns (address[] memory addresses) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return decode(blob); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 key + ) internal view returns (address[] memory addresses) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = store.getRecord(tableId, keyTuple); + return decode(blob); + } + + function decode(bytes memory blob) internal pure returns (address[] memory addresses) { + if (blob.length == 0) return new address[](0); + return Bytes.toAddressArray(Bytes.slice(blob, 32, blob.length - 32)); + } +} diff --git a/packages/world/tasks/compile.ts b/packages/world/tasks/compile.ts new file mode 100644 index 0000000000..65335021b4 --- /dev/null +++ b/packages/world/tasks/compile.ts @@ -0,0 +1,38 @@ +import { TASK_COMPILE_SOLIDITY } from "hardhat/builtin-tasks/task-names"; +import * as fs from "fs"; +import * as path from "path"; +import { subtask } from "hardhat/config"; + +subtask(TASK_COMPILE_SOLIDITY).setAction(async (_: { force: boolean; quiet: boolean }, { config }, runSuper) => { + console.log("Symlinking forge-style libraries"); + const symlinks: string[] = []; + const remappings = fs + .readFileSync("remappings.txt") + .toString() + .split("\n") + .filter((r) => r.length > 0) + .map((r) => r.split("=")); + + console.log("remappings", remappings); + for (const [library, libraryPath] of remappings) { + const symlinkPath = path.join(process.cwd(), library.replace("/", "")); + console.log("Adding symlink at path: " + symlinkPath); + if (fs.existsSync(symlinkPath)) { + console.warn("symlink already exists!"); + } else { + const libPath = path.join(config.paths.sources, "..", libraryPath); + fs.symlinkSync(libPath, symlinkPath, "dir"); + } + symlinks.push(symlinkPath); + } + try { + await runSuper(); + } catch (e) { + console.error(e); + } finally { + for (const symlink of symlinks) { + console.log("Removing symlink at path: " + symlink); + fs.unlinkSync(symlink); + } + } +}); diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol new file mode 100644 index 0000000000..fcc0f96aa8 --- /dev/null +++ b/packages/world/test/World.t.sol @@ -0,0 +1,22 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import "forge-std/Test.sol"; +import { World } from "../src/World.sol"; +import { System } from "../src/System.sol"; + +contract WorldTestSystem is System { + function msgSender() public pure returns (address) { + return _msgSender(); + } +} + +contract WorldTest is Test { + World internal world; + WorldTestSystem internal system; + + function setUp() public { + world = new World(); + system = new WorldTestSystem(); + } +} diff --git a/packages/world/tsconfig.json b/packages/world/tsconfig.json new file mode 100644 index 0000000000..5587243470 --- /dev/null +++ b/packages/world/tsconfig.json @@ -0,0 +1,102 @@ +{ + "compilerOptions": { + /* Visit https://aka.ms/tsconfig.json to read more about this file */ + + /* Projects */ + // "incremental": true, /* Enable incremental compilation */ + // "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */ + // "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */ + // "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */ + // "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */ + // "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */ + + /* Language and Environment */ + "target": "es2019" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */, + // "lib": [], /* Specify a set of bundled library declaration files that describe the target runtime environment. */ + // "jsx": "preserve", /* Specify what JSX code is generated. */ + // "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */ + // "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */ + // "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */ + // "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */ + // "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */ + // "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */ + // "noLib": true, /* Disable including any library files, including the default lib.d.ts. */ + // "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */ + + /* Modules */ + // "module": "esnext" /* Specify what module code is generated. */, + // "rootDir": "." /* Specify the root folder within your source files. */, + "moduleResolution": "node" /* Specify how TypeScript looks up a file from a given module specifier. */, + // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ + // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ + // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ + // "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */ + "types": ["mocha"] /* Specify type package names to be included without being referenced in a source file. */, + // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + // "resolveJsonModule": true, /* Enable importing .json files */ + // "noResolve": true, /* Disallow `import`s, `require`s or ``s from expanding the number of files TypeScript should add to a project. */ + + /* JavaScript Support */ + // "allowJs": true, /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */ + // "checkJs": true, /* Enable error reporting in type-checked JavaScript files. */ + // "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */ + + /* Emit */ + // "declaration": true /* Generate .d.ts files from TypeScript and JavaScript files in your project. */, + // "declarationMap": true, /* Create sourcemaps for d.ts files. */ + // "emitDeclarationOnly": true /* Only output d.ts files and not JavaScript files. */, + // "sourceMap": true /* Create source map files for emitted JavaScript files. */, + // "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */ + // "outDir": "dist" /* Specify an output folder for all emitted files. */, + // "removeComments": true, /* Disable emitting comments. */ + // "noEmit": true, /* Disable emitting files from a compilation. */ + // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ + // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */ + // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ + // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ + // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ + // "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */ + // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ + // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ + // "newLine": "crlf", /* Set the newline character for emitting files. */ + // "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */ + // "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */ + // "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */ + // "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */ + // "declarationDir": "./", /* Specify the output directory for generated declaration files. */ + // "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */ + + /* Interop Constraints */ + // "isolatedModules": true /* Ensure that each file can be safely transpiled without relying on other imports. */, + // "allowSyntheticDefaultImports": true, /* Allow 'import x from y' when a module doesn't have a default export. */ + "esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */ + // "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */ + // "forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */ + + /* Type Checking */ + // "strict": true /* Enable all strict type-checking options. */ + // "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */ + // "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */ + // "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */ + // "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */ + // "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */ + // "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */ + // "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */ + // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ + // "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */ + // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */ + // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ + // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ + // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ + // "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */ + // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */ + // "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */ + // "allowUnusedLabels": true, /* Disable error reporting for unused labels. */ + // "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */ + + /* Completeness */ + // "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */ + // "skipLibCheck": true /* Skip type checking all .d.ts files. */ + } + // "exclude": ["dist", "**/*.spec.ts", "packages"] +} diff --git a/packages/world/yarn.lock b/packages/world/yarn.lock new file mode 100644 index 0000000000..59f8b2244e --- /dev/null +++ b/packages/world/yarn.lock @@ -0,0 +1,3309 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@babel/code-frame@^7.0.0": + version "7.18.6" + resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.18.6.tgz#3b25d38c89600baa2dcc219edfa88a74eb2c427a" + integrity sha512-TDCmlK5eOvH+eH7cdAFlNXeVJqWIQ7gW9tY1GJIpUtFb6CmjVyq2VM3u71bOyR8CRihcCgMUYoDNyLXao3+70Q== + dependencies: + "@babel/highlight" "^7.18.6" + +"@babel/helper-validator-identifier@^7.18.6": + version "7.19.1" + resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.19.1.tgz#7eea834cf32901ffdc1a7ee555e2f9c27e249ca2" + integrity sha512-awrNfaMtnHUr653GgGEs++LlAvW6w+DcPrOliSMXWCKo597CwL5Acf/wWdNkf/tfEQE3mjkeD1YOVZOUV/od1w== + +"@babel/highlight@^7.18.6": + version "7.18.6" + resolved "https://registry.yarnpkg.com/@babel/highlight/-/highlight-7.18.6.tgz#81158601e93e2563795adcbfbdf5d64be3f2ecdf" + integrity sha512-u7stbOuYjaPezCuLj29hNW1v64M2Md2qupEKP1fHc7WdOA3DgLh37suiSrZYY7haUB7iBeQZ9P1uiRF359do3g== + dependencies: + "@babel/helper-validator-identifier" "^7.18.6" + chalk "^2.0.0" + js-tokens "^4.0.0" + +"@cspotcode/source-map-consumer@0.8.0": + version "0.8.0" + resolved "https://registry.yarnpkg.com/@cspotcode/source-map-consumer/-/source-map-consumer-0.8.0.tgz#33bf4b7b39c178821606f669bbc447a6a629786b" + integrity sha512-41qniHzTU8yAGbCp04ohlmSrZf8bkf/iJsl3V0dRGsQN/5GFfx+LbCSsCpp2gqrqjTVg/K6O8ycoV35JIwAzAg== + +"@cspotcode/source-map-support@0.7.0": + version "0.7.0" + resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.7.0.tgz#4789840aa859e46d2f3173727ab707c66bf344f5" + integrity sha512-X4xqRHqN8ACt2aHVe51OxeA2HjbcL4MqFqXkrmQszJ1NOUuUu5u6Vqx/0lZSVNku7velL5FC/s5uEAj1lsBMhA== + dependencies: + "@cspotcode/source-map-consumer" "0.8.0" + +"@ethersproject/abi@^5.1.2": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abi/-/abi-5.7.0.tgz#b3f3e045bbbeed1af3947335c247ad625a44e449" + integrity sha512-351ktp42TiRcYB3H1OP8yajPeAQstMW/yCFokj/AthP9bLHzQFPlOrxOcwYEDkUAICmOHljvN4K39OMTMUa9RA== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/abstract-provider@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-provider/-/abstract-provider-5.7.0.tgz#b0a8550f88b6bf9d51f90e4795d48294630cb9ef" + integrity sha512-R41c9UkchKCpAqStMYUpdunjo3pkEvZC3FAwZn5S5MGbXoMQOHIdHItezTETxAO5bevtMApSyEhn9+CHcDsWBw== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + +"@ethersproject/abstract-signer@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-signer/-/abstract-signer-5.7.0.tgz#13f4f32117868452191a4649723cb086d2b596b2" + integrity sha512-a16V8bq1/Cz+TGCkE2OPMTOUDLS3grCpdjoJCYNnVBbdYEMSgKrU0+B90s8b6H+ByYTBZN7a3g76jdIJi7UfKQ== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/address@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/address/-/address-5.7.0.tgz#19b56c4d74a3b0a46bfdbb6cfcc0a153fc697f37" + integrity sha512-9wYhYt7aghVGo758POM5nqcOMaE168Q6aRLJZwUmiqSrAungkG74gSSeKEIR7ukixesdRZGPgVqme6vmxs1fkA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + +"@ethersproject/base64@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/base64/-/base64-5.7.0.tgz#ac4ee92aa36c1628173e221d0d01f53692059e1c" + integrity sha512-Dr8tcHt2mEbsZr/mwTPIQAf3Ai0Bks/7gTw9dSqk1mQvhW3XvRlmDJr/4n+wg1JmCl16NZue17CDh8xb/vZ0sQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + +"@ethersproject/bignumber@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bignumber/-/bignumber-5.7.0.tgz#e2f03837f268ba655ffba03a57853e18a18dc9c2" + integrity sha512-n1CAdIHRWjSucQO3MC1zPSVgV/6dy/fjL9pMrPP9peL+QxEg9wOsVqwD4+818B6LUEtaXzVHQiuivzRoxPxUGw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + bn.js "^5.2.1" + +"@ethersproject/bytes@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bytes/-/bytes-5.7.0.tgz#a00f6ea8d7e7534d6d87f47188af1148d71f155d" + integrity sha512-nsbxwgFXWh9NyYWo+U8atvmMsSdKJprTcICAkvbBffT75qDocbuggBU0SJiVK2MuTrp0q+xvLkTnGMPK1+uA9A== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/constants@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/constants/-/constants-5.7.0.tgz#df80a9705a7e08984161f09014ea012d1c75295e" + integrity sha512-DHI+y5dBNvkpYUMiRQyxRBYBefZkJfo70VUkUAsRjcPs47muV9evftfZ0PJVCXYbAiCgght0DtcF9srFQmIgWA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + +"@ethersproject/hash@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hash/-/hash-5.7.0.tgz#eb7aca84a588508369562e16e514b539ba5240a7" + integrity sha512-qX5WrQfnah1EFnO5zJv1v46a8HW0+E5xuBBDTwMFZLuVTx0tbU2kkx15NqdjxecrLGatQN9FGQKpb1FKdHCt+g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/keccak256@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/keccak256/-/keccak256-5.7.0.tgz#3186350c6e1cd6aba7940384ec7d6d9db01f335a" + integrity sha512-2UcPboeL/iW+pSg6vZ6ydF8tCnv3Iu/8tUmLLzWWGzxWKFFqOBQFLo6uLUv6BDrLgCDfN28RJ/wtByx+jZ4KBg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + js-sha3 "0.8.0" + +"@ethersproject/logger@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/logger/-/logger-5.7.0.tgz#6ce9ae168e74fecf287be17062b590852c311892" + integrity sha512-0odtFdXu/XHtjQXJYA3u9G0G8btm0ND5Cu8M7i5vhEcE8/HmF4Lbdqanwyv4uQTr2tx6b7fQRmgLrsnpQlmnig== + +"@ethersproject/networks@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/networks/-/networks-5.7.1.tgz#118e1a981d757d45ccea6bb58d9fd3d9db14ead6" + integrity sha512-n/MufjFYv3yFcUyfhnXotyDlNdFb7onmkSy8aQERi2PjNcnWQ66xXxa3XlS8nCcA8aJKJjIIMNJTC7tu80GwpQ== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/properties@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/properties/-/properties-5.7.0.tgz#a6e12cb0439b878aaf470f1902a176033067ed30" + integrity sha512-J87jy8suntrAkIZtecpxEPxY//szqr1mlBaYlQ0r4RCaiD2hjheqF9s1LVE8vVuJCXisjIP+JgtK/Do54ej4Sw== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/rlp@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/rlp/-/rlp-5.7.0.tgz#de39e4d5918b9d74d46de93af80b7685a9c21304" + integrity sha512-rBxzX2vK8mVF7b0Tol44t5Tb8gomOHkj5guL+HhzQ1yBh/ydjGnpw6at+X6Iw0Kp3OzzzkcKp8N9r0W4kYSs9w== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/signing-key@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/signing-key/-/signing-key-5.7.0.tgz#06b2df39411b00bc57c7c09b01d1e41cf1b16ab3" + integrity sha512-MZdy2nL3wO0u7gkB4nA/pEf8lu1TlFswPNmy8AiYkfKTdO6eXBJyUdmHO/ehm/htHw9K/qF8ujnTyUAD+Ry54Q== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + bn.js "^5.2.1" + elliptic "6.5.4" + hash.js "1.1.7" + +"@ethersproject/strings@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/strings/-/strings-5.7.0.tgz#54c9d2a7c57ae8f1205c88a9d3a56471e14d5ed2" + integrity sha512-/9nu+lj0YswRNSH0NXYqrh8775XNyEdUQAuf3f+SmOrnVewcJ5SBNAjF7lpgehKi4abvNNXyf+HX86czCdJ8Mg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/transactions@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/transactions/-/transactions-5.7.0.tgz#91318fc24063e057885a6af13fdb703e1f993d3b" + integrity sha512-kmcNicCp1lp8qanMTC3RIikGgoJ80ztTyvtsFvCYpSCfkjhD0jZ2LOrnbcuxuToLIUYYf+4XwD1rP+B/erDIhQ== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + +"@ethersproject/web@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/web/-/web-5.7.1.tgz#de1f285b373149bee5928f4eb7bcb87ee5fbb4ae" + integrity sha512-Gueu8lSvyjBWL4cYsWsjh6MtMwM0+H4HvqFPZfB6dV8ctbP9zFAO73VG1cMWae0FLPCtz0peKPpZY8/ugJJX2w== + dependencies: + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@metamask/eth-sig-util@^4.0.0": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-4.0.1.tgz#3ad61f6ea9ad73ba5b19db780d40d9aae5157088" + integrity sha512-tghyZKLHZjcdlDqCA3gNZmLeR0XvOE9U1qoQO9ohyAZT6Pya+H9vkBPcsyXytmYLNgVoin7CKCmweo/R43V+tQ== + dependencies: + ethereumjs-abi "^0.6.8" + ethereumjs-util "^6.2.1" + ethjs-util "^0.1.6" + tweetnacl "^1.0.3" + tweetnacl-util "^0.15.1" + +"@morgan-stanley/ts-mocking-bird@^0.6.2": + version "0.6.4" + resolved "https://registry.yarnpkg.com/@morgan-stanley/ts-mocking-bird/-/ts-mocking-bird-0.6.4.tgz#2e4b60d42957bab3b50b67dbf14c3da2f62a39f7" + integrity sha512-57VJIflP8eR2xXa9cD1LUawh+Gh+BVQfVu0n6GALyg/AqV/Nz25kDRvws3i9kIe1PTrbsZZOYpsYp6bXPd6nVA== + dependencies: + lodash "^4.17.16" + uuid "^7.0.3" + +"@noble/hashes@1.1.2": + version "1.1.2" + resolved "https://registry.yarnpkg.com/@noble/hashes/-/hashes-1.1.2.tgz#e9e035b9b166ca0af657a7848eb2718f0f22f183" + integrity sha512-KYRCASVTv6aeUi1tsF8/vpyR7zpfs3FUzy2Jqm+MU+LmUKhQ0y2FpfwqkCcxSg2ua4GALJd8k2R76WxwZGbQpA== + +"@noble/hashes@~1.1.1": + version "1.1.5" + resolved "https://registry.yarnpkg.com/@noble/hashes/-/hashes-1.1.5.tgz#1a0377f3b9020efe2fae03290bd2a12140c95c11" + integrity sha512-LTMZiiLc+V4v1Yi16TD6aX2gmtKszNye0pQgbaLqkvhIqP7nVsSaJsWloGQjJfJ8offaoP5GtX3yY5swbcJxxQ== + +"@noble/secp256k1@1.6.3", "@noble/secp256k1@~1.6.0": + version "1.6.3" + resolved "https://registry.yarnpkg.com/@noble/secp256k1/-/secp256k1-1.6.3.tgz#7eed12d9f4404b416999d0c87686836c4c5c9b94" + integrity sha512-T04e4iTurVy7I8Sw4+c5OSN9/RkPlo1uKxAomtxQNLq8j1uPAqnsqG1bqvY3Jv7c13gyr6dui0zmh/I3+f/JaQ== + +"@nomicfoundation/ethereumjs-block@^4.0.0": + version "4.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-block/-/ethereumjs-block-4.0.0.tgz#fdd5c045e7baa5169abeed0e1202bf94e4481c49" + integrity sha512-bk8uP8VuexLgyIZAHExH1QEovqx0Lzhc9Ntm63nCRKLHXIZkobaFaeCVwTESV7YkPKUk7NiK11s8ryed4CS9yA== + dependencies: + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-trie" "^5.0.0" + "@nomicfoundation/ethereumjs-tx" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-blockchain@^6.0.0": + version "6.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-blockchain/-/ethereumjs-blockchain-6.0.0.tgz#1a8c243a46d4d3691631f139bfb3a4a157187b0c" + integrity sha512-pLFEoea6MWd81QQYSReLlLfH7N9v7lH66JC/NMPN848ySPPQA5renWnE7wPByfQFzNrPBuDDRFFULMDmj1C0xw== + dependencies: + "@nomicfoundation/ethereumjs-block" "^4.0.0" + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-ethash" "^2.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-trie" "^5.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + abstract-level "^1.0.3" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + level "^8.0.0" + lru-cache "^5.1.1" + memory-level "^1.0.0" + +"@nomicfoundation/ethereumjs-common@^3.0.0": + version "3.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-common/-/ethereumjs-common-3.0.0.tgz#f6bcc7753994555e49ab3aa517fc8bcf89c280b9" + integrity sha512-WS7qSshQfxoZOpHG/XqlHEGRG1zmyjYrvmATvc4c62+gZXgre1ymYP8ZNgx/3FyZY0TWe9OjFlKOfLqmgOeYwA== + dependencies: + "@nomicfoundation/ethereumjs-util" "^8.0.0" + crc-32 "^1.2.0" + +"@nomicfoundation/ethereumjs-ethash@^2.0.0": + version "2.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-ethash/-/ethereumjs-ethash-2.0.0.tgz#11539c32fe0990e1122ff987d1b84cfa34774e81" + integrity sha512-WpDvnRncfDUuXdsAXlI4lXbqUDOA+adYRQaEezIkxqDkc+LDyYDbd/xairmY98GnQzo1zIqsIL6GB5MoMSJDew== + dependencies: + "@nomicfoundation/ethereumjs-block" "^4.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + abstract-level "^1.0.3" + bigint-crypto-utils "^3.0.23" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-evm@^1.0.0": + version "1.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-evm/-/ethereumjs-evm-1.0.0.tgz#99cd173c03b59107c156a69c5e215409098a370b" + integrity sha512-hVS6qRo3V1PLKCO210UfcEQHvlG7GqR8iFzp0yyjTg2TmJQizcChKgWo8KFsdMw6AyoLgLhHGHw4HdlP8a4i+Q== + dependencies: + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + "@types/async-eventemitter" "^0.2.1" + async-eventemitter "^0.2.4" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/ethereumjs-rlp@^4.0.0", "@nomicfoundation/ethereumjs-rlp@^4.0.0-beta.2": + version "4.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-rlp/-/ethereumjs-rlp-4.0.0.tgz#d9a9c5f0f10310c8849b6525101de455a53e771d" + integrity sha512-GaSOGk5QbUk4eBP5qFbpXoZoZUj/NrW7MRa0tKY4Ew4c2HAS0GXArEMAamtFrkazp0BO4K5p2ZCG3b2FmbShmw== + +"@nomicfoundation/ethereumjs-statemanager@^1.0.0": + version "1.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-statemanager/-/ethereumjs-statemanager-1.0.0.tgz#14a9d4e1c828230368f7ab520c144c34d8721e4b" + integrity sha512-jCtqFjcd2QejtuAMjQzbil/4NHf5aAWxUc+CvS0JclQpl+7M0bxMofR2AJdtz+P3u0ke2euhYREDiE7iSO31vQ== + dependencies: + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-trie" "^5.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + functional-red-black-tree "^1.0.1" + +"@nomicfoundation/ethereumjs-trie@^5.0.0": + version "5.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-trie/-/ethereumjs-trie-5.0.0.tgz#dcfbe3be53a94bc061c9767a396c16702bc2f5b7" + integrity sha512-LIj5XdE+s+t6WSuq/ttegJzZ1vliwg6wlb+Y9f4RlBpuK35B9K02bO7xU+E6Rgg9RGptkWd6TVLdedTI4eNc2A== + dependencies: + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + ethereum-cryptography "0.1.3" + readable-stream "^3.6.0" + +"@nomicfoundation/ethereumjs-tx@^4.0.0": + version "4.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-tx/-/ethereumjs-tx-4.0.0.tgz#59dc7452b0862b30342966f7052ab9a1f7802f52" + integrity sha512-Gg3Lir2lNUck43Kp/3x6TfBNwcWC9Z1wYue9Nz3v4xjdcv6oDW9QSMJxqsKw9QEGoBBZ+gqwpW7+F05/rs/g1w== + dependencies: + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-util@^8.0.0": + version "8.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-util/-/ethereumjs-util-8.0.0.tgz#deb2b15d2c308a731e82977aefc4e61ca0ece6c5" + integrity sha512-2emi0NJ/HmTG+CGY58fa+DQuAoroFeSH9gKu9O6JnwTtlzJtgfTixuoOqLEgyyzZVvwfIpRueuePb8TonL1y+A== + dependencies: + "@nomicfoundation/ethereumjs-rlp" "^4.0.0-beta.2" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-vm@^6.0.0": + version "6.0.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-vm/-/ethereumjs-vm-6.0.0.tgz#2bb50d332bf41790b01a3767ffec3987585d1de6" + integrity sha512-JMPxvPQ3fzD063Sg3Tp+UdwUkVxMoo1uML6KSzFhMH3hoQi/LMuXBoEHAoW83/vyNS9BxEe6jm6LmT5xdeEJ6w== + dependencies: + "@nomicfoundation/ethereumjs-block" "^4.0.0" + "@nomicfoundation/ethereumjs-blockchain" "^6.0.0" + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-evm" "^1.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-statemanager" "^1.0.0" + "@nomicfoundation/ethereumjs-trie" "^5.0.0" + "@nomicfoundation/ethereumjs-tx" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + "@types/async-eventemitter" "^0.2.1" + async-eventemitter "^0.2.4" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + functional-red-black-tree "^1.0.1" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/solidity-analyzer-darwin-arm64@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-arm64/-/solidity-analyzer-darwin-arm64-0.1.0.tgz#83a7367342bd053a76d04bbcf4f373fef07cf760" + integrity sha512-vEF3yKuuzfMHsZecHQcnkUrqm8mnTWfJeEVFHpg+cO+le96xQA4lAJYdUan8pXZohQxv1fSReQsn4QGNuBNuCw== + +"@nomicfoundation/solidity-analyzer-darwin-x64@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-x64/-/solidity-analyzer-darwin-x64-0.1.0.tgz#1225f7da647ae1ad25a87125664704ecc0af6ccc" + integrity sha512-dlHeIg0pTL4dB1l9JDwbi/JG6dHQaU1xpDK+ugYO8eJ1kxx9Dh2isEUtA4d02cQAl22cjOHTvifAk96A+ItEHA== + +"@nomicfoundation/solidity-analyzer-freebsd-x64@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-freebsd-x64/-/solidity-analyzer-freebsd-x64-0.1.0.tgz#dbc052dcdfd50ae50fd5ae1788b69b4e0fa40040" + integrity sha512-WFCZYMv86WowDA4GiJKnebMQRt3kCcFqHeIomW6NMyqiKqhK1kIZCxSLDYsxqlx396kKLPN1713Q1S8tu68GKg== + +"@nomicfoundation/solidity-analyzer-linux-arm64-gnu@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-gnu/-/solidity-analyzer-linux-arm64-gnu-0.1.0.tgz#e6b2eea633995b557e74e881d2a43eab4760903d" + integrity sha512-DTw6MNQWWlCgc71Pq7CEhEqkb7fZnS7oly13pujs4cMH1sR0JzNk90Mp1zpSCsCs4oKan2ClhMlLKtNat/XRKQ== + +"@nomicfoundation/solidity-analyzer-linux-arm64-musl@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-musl/-/solidity-analyzer-linux-arm64-musl-0.1.0.tgz#af81107f5afa794f19988a368647727806e18dc4" + integrity sha512-wUpUnR/3GV5Da88MhrxXh/lhb9kxh9V3Jya2NpBEhKDIRCDmtXMSqPMXHZmOR9DfCwCvG6vLFPr/+YrPCnUN0w== + +"@nomicfoundation/solidity-analyzer-linux-x64-gnu@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-gnu/-/solidity-analyzer-linux-x64-gnu-0.1.0.tgz#6877e1da1a06a9f08446070ab6e0a5347109f868" + integrity sha512-lR0AxK1x/MeKQ/3Pt923kPvwigmGX3OxeU5qNtQ9pj9iucgk4PzhbS3ruUeSpYhUxG50jN4RkIGwUMoev5lguw== + +"@nomicfoundation/solidity-analyzer-linux-x64-musl@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-musl/-/solidity-analyzer-linux-x64-musl-0.1.0.tgz#bb6cd83a0c259eccef4183796b6329a66cf7ebd9" + integrity sha512-A1he/8gy/JeBD3FKvmI6WUJrGrI5uWJNr5Xb9WdV+DK0F8msuOqpEByLlnTdLkXMwW7nSl3awvLezOs9xBHJEg== + +"@nomicfoundation/solidity-analyzer-win32-arm64-msvc@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-arm64-msvc/-/solidity-analyzer-win32-arm64-msvc-0.1.0.tgz#9d4bca1cc9a1333fde985675083b0b7d165f6076" + integrity sha512-7x5SXZ9R9H4SluJZZP8XPN+ju7Mx+XeUMWZw7ZAqkdhP5mK19I4vz3x0zIWygmfE8RT7uQ5xMap0/9NPsO+ykw== + +"@nomicfoundation/solidity-analyzer-win32-ia32-msvc@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-ia32-msvc/-/solidity-analyzer-win32-ia32-msvc-0.1.0.tgz#0db5bfc6aa952bea4098d8d2c8947b4e5c4337ee" + integrity sha512-m7w3xf+hnE774YRXu+2mGV7RiF3QJtUoiYU61FascCkQhX3QMQavh7saH/vzb2jN5D24nT/jwvaHYX/MAM9zUw== + +"@nomicfoundation/solidity-analyzer-win32-x64-msvc@0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-x64-msvc/-/solidity-analyzer-win32-x64-msvc-0.1.0.tgz#2e0f39a2924dcd77db6b419828595e984fabcb33" + integrity sha512-xCuybjY0sLJQnJhupiFAXaek2EqF0AP0eBjgzaalPXSNvCEN6ZYHvUzdA50ENDVeSYFXcUsYf3+FsD3XKaeptA== + +"@nomicfoundation/solidity-analyzer@^0.1.0": + version "0.1.0" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer/-/solidity-analyzer-0.1.0.tgz#e5ddc43ad5c0aab96e5054520d8e16212e125f50" + integrity sha512-xGWAiVCGOycvGiP/qrlf9f9eOn7fpNbyJygcB0P21a1MDuVPlKt0Srp7rvtBEutYQ48ouYnRXm33zlRnlTOPHg== + optionalDependencies: + "@nomicfoundation/solidity-analyzer-darwin-arm64" "0.1.0" + "@nomicfoundation/solidity-analyzer-darwin-x64" "0.1.0" + "@nomicfoundation/solidity-analyzer-freebsd-x64" "0.1.0" + "@nomicfoundation/solidity-analyzer-linux-arm64-gnu" "0.1.0" + "@nomicfoundation/solidity-analyzer-linux-arm64-musl" "0.1.0" + "@nomicfoundation/solidity-analyzer-linux-x64-gnu" "0.1.0" + "@nomicfoundation/solidity-analyzer-linux-x64-musl" "0.1.0" + "@nomicfoundation/solidity-analyzer-win32-arm64-msvc" "0.1.0" + "@nomicfoundation/solidity-analyzer-win32-ia32-msvc" "0.1.0" + "@nomicfoundation/solidity-analyzer-win32-x64-msvc" "0.1.0" + +"@scure/base@~1.1.0": + version "1.1.1" + resolved "https://registry.yarnpkg.com/@scure/base/-/base-1.1.1.tgz#ebb651ee52ff84f420097055f4bf46cfba403938" + integrity sha512-ZxOhsSyxYwLJj3pLZCefNitxsj093tb2vq90mp2txoYeBqbcjDjqFhyM8eUjq/uFm6zJ+mUuqxlS2FkuSY1MTA== + +"@scure/bip32@1.1.0": + version "1.1.0" + resolved "https://registry.yarnpkg.com/@scure/bip32/-/bip32-1.1.0.tgz#dea45875e7fbc720c2b4560325f1cf5d2246d95b" + integrity sha512-ftTW3kKX54YXLCxH6BB7oEEoJfoE2pIgw7MINKAs5PsS6nqKPuKk1haTF/EuHmYqG330t5GSrdmtRuHaY1a62Q== + dependencies: + "@noble/hashes" "~1.1.1" + "@noble/secp256k1" "~1.6.0" + "@scure/base" "~1.1.0" + +"@scure/bip39@1.1.0": + version "1.1.0" + resolved "https://registry.yarnpkg.com/@scure/bip39/-/bip39-1.1.0.tgz#92f11d095bae025f166bef3defcc5bf4945d419a" + integrity sha512-pwrPOS16VeTKg98dYXQyIjJEcWfz7/1YJIwxUEPFfQPtc86Ym/1sVgQ2RLoD43AazMk2l/unK4ITySSpW2+82w== + dependencies: + "@noble/hashes" "~1.1.1" + "@scure/base" "~1.1.0" + +"@sentry/core@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/core/-/core-5.30.0.tgz#6b203664f69e75106ee8b5a2fe1d717379b331f3" + integrity sha512-TmfrII8w1PQZSZgPpUESqjB+jC6MvZJZdLtE/0hZ+SrnKhW3x5WlYLvTXZpcWePYBku7rl2wn1RZu6uT0qCTeg== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/hub@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/hub/-/hub-5.30.0.tgz#2453be9b9cb903404366e198bd30c7ca74cdc100" + integrity sha512-2tYrGnzb1gKz2EkMDQcfLrDTvmGcQPuWxLnJKXJvYTQDGLlEvi2tWz1VIHjunmOvJrB5aIQLhm+dcMRwFZDCqQ== + dependencies: + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/minimal@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/minimal/-/minimal-5.30.0.tgz#ce3d3a6a273428e0084adcb800bc12e72d34637b" + integrity sha512-BwWb/owZKtkDX+Sc4zCSTNcvZUq7YcH3uAVlmh/gtR9rmUvbzAA3ewLuB3myi4wWRAMEtny6+J/FN/x+2wn9Xw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@sentry/node@^5.18.1": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/node/-/node-5.30.0.tgz#4ca479e799b1021285d7fe12ac0858951c11cd48" + integrity sha512-Br5oyVBF0fZo6ZS9bxbJZG4ApAjRqAnqFFurMVJJdunNb80brh7a5Qva2kjhm+U6r9NJAB5OmDyPkA1Qnt+QVg== + dependencies: + "@sentry/core" "5.30.0" + "@sentry/hub" "5.30.0" + "@sentry/tracing" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + cookie "^0.4.1" + https-proxy-agent "^5.0.0" + lru_map "^0.3.3" + tslib "^1.9.3" + +"@sentry/tracing@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/tracing/-/tracing-5.30.0.tgz#501d21f00c3f3be7f7635d8710da70d9419d4e1f" + integrity sha512-dUFowCr0AIMwiLD7Fs314Mdzcug+gBVo/+NCMyDw8tFxJkwWAKl7Qa2OZxLQ0ZHjakcj1hNKfCQJ9rhyfOl4Aw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/types@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/types/-/types-5.30.0.tgz#19709bbe12a1a0115bc790b8942917da5636f402" + integrity sha512-R8xOqlSTZ+htqrfteCWU5Nk0CDN5ApUTvrlvBuiH1DyP6czDZ4ktbZB0hAgBlVcK0U+qpD3ag3Tqqpa5Q67rPw== + +"@sentry/utils@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/utils/-/utils-5.30.0.tgz#9a5bd7ccff85ccfe7856d493bffa64cabc41e980" + integrity sha512-zaYmoH0NWWtvnJjC9/CBseXMtKHm/tm40sz3YfJRxeQjyzRqNQPgivpd9R/oDJCYj999mzdW382p/qi2ypjLww== + dependencies: + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@solidity-parser/parser@^0.14.5": + version "0.14.5" + resolved "https://registry.yarnpkg.com/@solidity-parser/parser/-/parser-0.14.5.tgz#87bc3cc7b068e08195c219c91cd8ddff5ef1a804" + integrity sha512-6dKnHZn7fg/iQATVEzqyUOyEidbn05q7YA2mQ9hC0MMXhhV3/JrsxmFSYZAcr7j1yUP700LLhTruvJ3MiQmjJg== + dependencies: + antlr4ts "^0.5.0-alpha.4" + +"@tsconfig/node10@^1.0.7": + version "1.0.9" + resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.9.tgz#df4907fc07a886922637b15e02d4cebc4c0021b2" + integrity sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA== + +"@tsconfig/node12@^1.0.7": + version "1.0.11" + resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d" + integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag== + +"@tsconfig/node14@^1.0.0": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1" + integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow== + +"@tsconfig/node16@^1.0.2": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.3.tgz#472eaab5f15c1ffdd7f8628bd4c4f753995ec79e" + integrity sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ== + +"@typechain/ethers-v5@^9.0.0": + version "9.0.0" + resolved "https://registry.yarnpkg.com/@typechain/ethers-v5/-/ethers-v5-9.0.0.tgz#6aa93bea7425c0463bd8a61eea3643540ef851bd" + integrity sha512-bAanuPl1L2itaUdMvor/QvwnIH+TM/CmG00q17Ilv3ZZMeJ2j8HcarhgJUZ9pBY1teBb85P8cC03dz3mSSx+tQ== + dependencies: + lodash "^4.17.15" + ts-essentials "^7.0.1" + +"@types/async-eventemitter@^0.2.1": + version "0.2.1" + resolved "https://registry.yarnpkg.com/@types/async-eventemitter/-/async-eventemitter-0.2.1.tgz#f8e6280e87e8c60b2b938624b0a3530fb3e24712" + integrity sha512-M2P4Ng26QbAeITiH7w1d7OxtldgfAe0wobpyJzVK/XOb0cUGKU2R4pfAhqcJBXAe2ife5ZOhSv4wk7p+ffURtg== + +"@types/bn.js@^4.11.3": + version "4.11.6" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-4.11.6.tgz#c306c70d9358aaea33cd4eda092a742b9505967c" + integrity sha512-pqr857jrp2kPuO9uRjZ3PwnJTjoQy+fcdxvBTvHm6dkmEL9q+hDD/2j/0ELOBPtPnS8LjCX0gI9nbl8lVkadpg== + dependencies: + "@types/node" "*" + +"@types/bn.js@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-5.1.1.tgz#b51e1b55920a4ca26e9285ff79936bbdec910682" + integrity sha512-qNrYbZqMx0uJAfKnKclPh+dTwK33KfLHYqtyODwd5HnXOjnkhc4qgn3BrK6RWyGZm5+sIFE7Q7Vz6QQtJB7w7g== + dependencies: + "@types/node" "*" + +"@types/lru-cache@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/lru-cache/-/lru-cache-5.1.1.tgz#c48c2e27b65d2a153b19bfc1a317e30872e01eef" + integrity sha512-ssE3Vlrys7sdIzs5LOxCzTVMsU7i9oa/IaW92wF32JFb3CVczqOkru2xspuKczHEbG3nvmPY7IFqVmGGHdNbYw== + +"@types/mocha@^9.1.1": + version "9.1.1" + resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-9.1.1.tgz#e7c4f1001eefa4b8afbd1eee27a237fee3bf29c4" + integrity sha512-Z61JK7DKDtdKTWwLeElSEBcWGRLY8g95ic5FoQqI9CMx0ns/Ghep3B4DfcEimiKMvtamNVULVNKEsiwV3aQmXw== + +"@types/node@*": + version "18.11.18" + resolved "https://registry.yarnpkg.com/@types/node/-/node-18.11.18.tgz#8dfb97f0da23c2293e554c5a50d61ef134d7697f" + integrity sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA== + +"@types/pbkdf2@^3.0.0": + version "3.1.0" + resolved "https://registry.yarnpkg.com/@types/pbkdf2/-/pbkdf2-3.1.0.tgz#039a0e9b67da0cdc4ee5dab865caa6b267bb66b1" + integrity sha512-Cf63Rv7jCQ0LaL8tNXmEyqTHuIJxRdlS5vMh1mj5voN4+QFhVZnlZruezqpWYDiJ8UTzhP0VmeLXCmBk66YrMQ== + dependencies: + "@types/node" "*" + +"@types/prettier@^2.1.1": + version "2.7.2" + resolved "https://registry.yarnpkg.com/@types/prettier/-/prettier-2.7.2.tgz#6c2324641cc4ba050a8c710b2b251b377581fbf0" + integrity sha512-KufADq8uQqo1pYKVIYzfKbJfBAc0sOeXqGbFaSpv8MRmC/zXgowNZmFcbngndGk922QDmOASEXUZCaY48gs4cg== + +"@types/secp256k1@^4.0.1": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/secp256k1/-/secp256k1-4.0.3.tgz#1b8e55d8e00f08ee7220b4d59a6abe89c37a901c" + integrity sha512-Da66lEIFeIz9ltsdMZcpQvmrmmoqrfju8pm1BH8WbYjZSwUgCwXLb9C+9XYogwBITnbsSaMdVPb2ekf7TV+03w== + dependencies: + "@types/node" "*" + +abort-controller@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/abort-controller/-/abort-controller-3.0.0.tgz#eaf54d53b62bae4138e809ca225c8439a6efb392" + integrity sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg== + dependencies: + event-target-shim "^5.0.0" + +abstract-level@^1.0.0, abstract-level@^1.0.2, abstract-level@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/abstract-level/-/abstract-level-1.0.3.tgz#78a67d3d84da55ee15201486ab44c09560070741" + integrity sha512-t6jv+xHy+VYwc4xqZMn2Pa9DjcdzvzZmQGRjTFc8spIbRGHgBrEKbPq+rYXc7CCo0lxgYvSgKVg9qZAhpVQSjA== + dependencies: + buffer "^6.0.3" + catering "^2.1.0" + is-buffer "^2.0.5" + level-supports "^4.0.0" + level-transcoder "^1.0.1" + module-error "^1.0.1" + queue-microtask "^1.2.3" + +acorn-jsx@^5.0.0: + version "5.3.2" + resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-5.3.2.tgz#7ed5bb55908b3b2f1bc55c6af1653bada7f07937" + integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== + +acorn-walk@^8.1.1: + version "8.2.0" + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1" + integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA== + +acorn@^6.0.7: + version "6.4.2" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-6.4.2.tgz#35866fd710528e92de10cf06016498e47e39e1e6" + integrity sha512-XtGIhXwF8YM8bJhGxG5kXgjkEuNGLTkoYqVE+KMR+aspr4KGYmKYg7yUe3KghyQ9yheNwLnjmzh/7+gfDBmHCQ== + +acorn@^8.4.1: + version "8.8.2" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.8.2.tgz#1b2f25db02af965399b9776b0c2c391276d37c4a" + integrity sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw== + +adm-zip@^0.4.16: + version "0.4.16" + resolved "https://registry.yarnpkg.com/adm-zip/-/adm-zip-0.4.16.tgz#cf4c508fdffab02c269cbc7f471a875f05570365" + integrity sha512-TFi4HBKSGfIKsK5YCkKaaFG2m4PEDyViZmEwof3MTIgzimHLto6muaHVpbrljdIvIrFZzEq/p4nafOeLcYegrg== + +agent-base@6: + version "6.0.2" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" + integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== + dependencies: + debug "4" + +aggregate-error@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a" + integrity sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA== + dependencies: + clean-stack "^2.0.0" + indent-string "^4.0.0" + +ajv@^6.10.2, ajv@^6.6.1, ajv@^6.9.1: + version "6.12.6" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" + integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== + dependencies: + fast-deep-equal "^3.1.1" + fast-json-stable-stringify "^2.0.0" + json-schema-traverse "^0.4.1" + uri-js "^4.2.2" + +ansi-colors@4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" + integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== + +ansi-colors@^4.1.1: + version "4.1.3" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.3.tgz#37611340eb2243e70cc604cad35d63270d48781b" + integrity sha512-/6w/C21Pm1A7aZitlI5Ni/2J6FFQN8i1Cvz3kHABAAbw93v/NlvKdVOqz7CCWz/3iv/JplRSEEZ83XION15ovw== + +ansi-escapes@^3.2.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-3.2.0.tgz#8780b98ff9dbf5638152d1f1fe5c1d7b4442976b" + integrity sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ== + +ansi-escapes@^4.3.0: + version "4.3.2" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-4.3.2.tgz#6b2291d1db7d98b6521d5f1efa42d0f3a9feb65e" + integrity sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ== + dependencies: + type-fest "^0.21.3" + +ansi-regex@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-3.0.1.tgz#123d6479e92ad45ad897d4054e3c7ca7db4944e1" + integrity sha512-+O9Jct8wf++lXxxFc4hc8LsjaSq0HFzzL7cVsw8pRDIPdjKD2mT4ytDZlLuSBZ4cLKZFXIrMGO7DbQCtMJJMKw== + +ansi-regex@^4.1.0: + version "4.1.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-4.1.1.tgz#164daac87ab2d6f6db3a29875e2d1766582dabed" + integrity sha512-ILlv4k/3f6vfQ4OoP2AGvirOktlQ98ZEL1k9FaQjxa3L1abBgbuTDAdPOpvbGncC0BTVQrl+OM8xZGK6tWXt7g== + +ansi-regex@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" + integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== + +ansi-styles@^3.2.0, ansi-styles@^3.2.1: + version "3.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" + integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== + dependencies: + color-convert "^1.9.0" + +ansi-styles@^4.0.0, ansi-styles@^4.1.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +antlr4@4.7.1: + version "4.7.1" + resolved "https://registry.yarnpkg.com/antlr4/-/antlr4-4.7.1.tgz#69984014f096e9e775f53dd9744bf994d8959773" + integrity sha512-haHyTW7Y9joE5MVs37P2lNYfU2RWBLfcRDD8OWldcdZm5TiCE91B5Xl1oWSwiDUSd4rlExpt2pu1fksYQjRBYQ== + +antlr4ts@^0.5.0-alpha.4: + version "0.5.0-alpha.4" + resolved "https://registry.yarnpkg.com/antlr4ts/-/antlr4ts-0.5.0-alpha.4.tgz#71702865a87478ed0b40c0709f422cf14d51652a" + integrity sha512-WPQDt1B74OfPv/IMS2ekXAKkTZIHl88uMetg6q3OTqgFxZ/dxDXI0EWLyZid/1Pe6hTftyg5N7gel5wNAGxXyQ== + +anymatch@~3.1.2: + version "3.1.3" + resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.3.tgz#790c58b19ba1720a84205b57c618d5ad8524973e" + integrity sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw== + dependencies: + normalize-path "^3.0.0" + picomatch "^2.0.4" + +arg@^4.1.0: + version "4.1.3" + resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" + integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== + +argparse@^1.0.7: + version "1.0.10" + resolved "https://registry.yarnpkg.com/argparse/-/argparse-1.0.10.tgz#bcd6791ea5ae09725e17e5ad988134cd40b3d911" + integrity sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg== + dependencies: + sprintf-js "~1.0.2" + +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + +array-back@^3.0.1, array-back@^3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-3.1.0.tgz#b8859d7a508871c9a7b2cf42f99428f65e96bfb0" + integrity sha512-TkuxA4UCOvxuDK6NZYXCalszEzj+TLszyASooky+i742l9TqsOdYCMJJupxRic61hwquNtppB3hgcuq9SVSH1Q== + +array-back@^4.0.1, array-back@^4.0.2: + version "4.0.2" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-4.0.2.tgz#8004e999a6274586beeb27342168652fdb89fa1e" + integrity sha512-NbdMezxqf94cnNfWLL7V/im0Ub+Anbb0IoZhvzie8+4HJ4nMQuzHuy49FkGYCJK2yAloZ3meiB6AVMClbrI1vg== + +ast-parents@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/ast-parents/-/ast-parents-0.0.1.tgz#508fd0f05d0c48775d9eccda2e174423261e8dd3" + integrity sha512-XHusKxKz3zoYk1ic8Un640joHbFMhbqneyoZfoKnEGtf2ey9Uh/IdpcQplODdO/kENaMIWsD0nJm4+wX3UNLHA== + +astral-regex@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/astral-regex/-/astral-regex-1.0.0.tgz#6c8c3fb827dd43ee3918f27b82782ab7658a6fd9" + integrity sha512-+Ryf6g3BKoRc7jfp7ad8tM4TtMiaWvbF/1/sQcZPkkS7ag3D5nMBCe2UfOTONtAkaG0tO0ij3C5Lwmf1EiyjHg== + +async-eventemitter@^0.2.4: + version "0.2.4" + resolved "https://registry.yarnpkg.com/async-eventemitter/-/async-eventemitter-0.2.4.tgz#f5e7c8ca7d3e46aab9ec40a292baf686a0bafaca" + integrity sha512-pd20BwL7Yt1zwDFy+8MX8F1+WCT8aQeKj0kQnTrH9WaeRETlRamVhD0JtRPmrV4GfOJ2F9CvdQkZeZhnh2TuHw== + dependencies: + async "^2.4.0" + +async@^2.4.0: + version "2.6.4" + resolved "https://registry.yarnpkg.com/async/-/async-2.6.4.tgz#706b7ff6084664cd7eae713f6f965433b5504221" + integrity sha512-mzo5dfJYwAn29PeiJ0zvwTo04zj8HDJj0Mn8TD7sno7q12prdbnasKJHhkm2c1LgrhlJ0teaea8860oxi51mGA== + dependencies: + lodash "^4.17.14" + +balanced-match@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" + integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== + +base-x@^3.0.2: + version "3.0.9" + resolved "https://registry.yarnpkg.com/base-x/-/base-x-3.0.9.tgz#6349aaabb58526332de9f60995e548a53fe21320" + integrity sha512-H7JU6iBHTal1gp56aKoaa//YUxEaAOUiydvrV/pILqIHXTtqxSkATOnDA2u+jZ/61sD+L/412+7kzXRtWukhpQ== + dependencies: + safe-buffer "^5.0.1" + +base64-js@^1.3.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a" + integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== + +bigint-crypto-utils@^3.0.23: + version "3.1.8" + resolved "https://registry.yarnpkg.com/bigint-crypto-utils/-/bigint-crypto-utils-3.1.8.tgz#e2e0f40cf45488f9d7f0e32ff84152aa73819d5d" + integrity sha512-+VMV9Laq8pXLBKKKK49nOoq9bfR3j7NNQAtbA617a4nw9bVLo8rsqkKMBgM2AJWlNX9fEIyYaYX+d0laqYV4tw== + dependencies: + bigint-mod-arith "^3.1.0" + +bigint-mod-arith@^3.1.0: + version "3.1.2" + resolved "https://registry.yarnpkg.com/bigint-mod-arith/-/bigint-mod-arith-3.1.2.tgz#658e416bc593a463d97b59766226d0a3021a76b1" + integrity sha512-nx8J8bBeiRR+NlsROFH9jHswW5HO8mgfOSqW0AmjicMMvaONDa8AO+5ViKDUUNytBPWiwfvZP4/Bj4Y3lUfvgQ== + +binary-extensions@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.2.0.tgz#75f502eeaf9ffde42fc98829645be4ea76bd9e2d" + integrity sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA== + +blakejs@^1.1.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/blakejs/-/blakejs-1.2.1.tgz#5057e4206eadb4a97f7c0b6e197a505042fc3814" + integrity sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ== + +bn.js@^4.11.0, bn.js@^4.11.8, bn.js@^4.11.9: + version "4.12.0" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.12.0.tgz#775b3f278efbb9718eec7361f483fb36fbbfea88" + integrity sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA== + +bn.js@^5.2.0, bn.js@^5.2.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-5.2.1.tgz#0bc527a6a0d18d0aa8d5b0538ce4a77dccfa7b70" + integrity sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ== + +brace-expansion@^1.1.7: + version "1.1.11" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" + integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + dependencies: + balanced-match "^1.0.0" + concat-map "0.0.1" + +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + +braces@~3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" + integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== + dependencies: + fill-range "^7.0.1" + +brorand@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f" + integrity sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w== + +browser-level@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/browser-level/-/browser-level-1.0.1.tgz#36e8c3183d0fe1c405239792faaab5f315871011" + integrity sha512-XECYKJ+Dbzw0lbydyQuJzwNXtOpbMSq737qxJN11sIRTErOMShvDpbzTlgju7orJKvx4epULolZAuJGLzCmWRQ== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.1" + module-error "^1.0.2" + run-parallel-limit "^1.1.0" + +browser-stdout@1.3.1: + version "1.3.1" + resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" + integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== + +browserify-aes@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/browserify-aes/-/browserify-aes-1.2.0.tgz#326734642f403dabc3003209853bb70ad428ef48" + integrity sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA== + dependencies: + buffer-xor "^1.0.3" + cipher-base "^1.0.0" + create-hash "^1.1.0" + evp_bytestokey "^1.0.3" + inherits "^2.0.1" + safe-buffer "^5.0.1" + +bs58@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/bs58/-/bs58-4.0.1.tgz#be161e76c354f6f788ae4071f63f34e8c4f0a42a" + integrity sha512-Ok3Wdf5vOIlBrgCvTq96gBkJw+JUEzdBgyaza5HLtPm7yTHkjRy8+JzNyHF7BHa0bNWOQIp3m5YF0nnFcOIKLw== + dependencies: + base-x "^3.0.2" + +bs58check@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/bs58check/-/bs58check-2.1.2.tgz#53b018291228d82a5aa08e7d796fdafda54aebfc" + integrity sha512-0TS1jicxdU09dwJMNZtVAfzPi6Q6QeN0pM1Fkzrjn+XYHvzMKPU3pHVpva+769iNVSfIYWf7LJ6WR+BuuMf8cA== + dependencies: + bs58 "^4.0.0" + create-hash "^1.1.0" + safe-buffer "^5.1.2" + +buffer-from@^1.0.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5" + integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== + +buffer-xor@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9" + integrity sha512-571s0T7nZWK6vB67HI5dyUF7wXiNcfaPPPTl6zYCNApANjIvYJTg7hlud/+cJpdAhS7dVzqMLmfhfHR3rAcOjQ== + +buffer@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-6.0.3.tgz#2ace578459cc8fbe2a70aaa8f52ee63b6a74c6c6" + integrity sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.2.1" + +busboy@^1.6.0: + version "1.6.0" + resolved "https://registry.yarnpkg.com/busboy/-/busboy-1.6.0.tgz#966ea36a9502e43cdb9146962523b92f531f6893" + integrity sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA== + dependencies: + streamsearch "^1.1.0" + +bytes@3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/bytes/-/bytes-3.1.2.tgz#8b0beeb98605adf1b128fa4386403c009e0221a5" + integrity sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg== + +call-bind@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/call-bind/-/call-bind-1.0.2.tgz#b1d4e89e688119c3c9a903ad30abb2f6a919be3c" + integrity sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA== + dependencies: + function-bind "^1.1.1" + get-intrinsic "^1.0.2" + +caller-callsite@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/caller-callsite/-/caller-callsite-2.0.0.tgz#847e0fce0a223750a9a027c54b33731ad3154134" + integrity sha512-JuG3qI4QOftFsZyOn1qq87fq5grLIyk1JYd5lJmdA+fG7aQ9pA/i3JIJGcO3q0MrRcHlOt1U+ZeHW8Dq9axALQ== + dependencies: + callsites "^2.0.0" + +caller-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/caller-path/-/caller-path-2.0.0.tgz#468f83044e369ab2010fac5f06ceee15bb2cb1f4" + integrity sha512-MCL3sf6nCSXOwCTzvPKhN18TU7AHTvdtam8DAogxcrJ8Rjfbbg7Lgng64H9Iy+vUV6VGFClN/TyxBkAebLRR4A== + dependencies: + caller-callsite "^2.0.0" + +callsites@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/callsites/-/callsites-2.0.0.tgz#06eb84f00eea413da86affefacbffb36093b3c50" + integrity sha512-ksWePWBloaWPxJYQ8TL0JHvtci6G5QTKwQ95RcWAa/lzoAKuAOflGdAK92hpHXjkwb8zLxoLNUoNYZgVsaJzvQ== + +callsites@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" + integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== + +camelcase@^6.0.0: + version "6.3.0" + resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" + integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== + +catering@^2.1.0, catering@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/catering/-/catering-2.1.1.tgz#66acba06ed5ee28d5286133982a927de9a04b510" + integrity sha512-K7Qy8O9p76sL3/3m7/zLKbRkyOlSZAgzEaLhyj2mXS8PsCud2Eo4hAb8aLtZqHh0QGqLcb9dlJSu6lHRVENm1w== + +chalk@^2.0.0, chalk@^2.1.0, chalk@^2.4.2: + version "2.4.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" + integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== + dependencies: + ansi-styles "^3.2.1" + escape-string-regexp "^1.0.5" + supports-color "^5.3.0" + +chalk@^4.1.0: + version "4.1.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" + integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== + dependencies: + ansi-styles "^4.1.0" + supports-color "^7.1.0" + +chardet@^0.7.0: + version "0.7.0" + resolved "https://registry.yarnpkg.com/chardet/-/chardet-0.7.0.tgz#90094849f0937f2eedc2425d0d28a9e5f0cbad9e" + integrity sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA== + +chokidar@3.5.3, chokidar@^3.4.0: + version "3.5.3" + resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.3.tgz#1cf37c8707b932bd1af1ae22c0432e2acd1903bd" + integrity sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw== + dependencies: + anymatch "~3.1.2" + braces "~3.0.2" + glob-parent "~5.1.2" + is-binary-path "~2.1.0" + is-glob "~4.0.1" + normalize-path "~3.0.0" + readdirp "~3.6.0" + optionalDependencies: + fsevents "~2.3.2" + +ci-info@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-2.0.0.tgz#67a9e964be31a51e15e5010d58e6f12834002f46" + integrity sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ== + +cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de" + integrity sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +classic-level@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/classic-level/-/classic-level-1.2.0.tgz#2d52bdec8e7a27f534e67fdeb890abef3e643c27" + integrity sha512-qw5B31ANxSluWz9xBzklRWTUAJ1SXIdaVKTVS7HcTGKOAmExx65Wo5BUICW+YGORe2FOUaDghoI9ZDxj82QcFg== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.0" + module-error "^1.0.1" + napi-macros "~2.0.0" + node-gyp-build "^4.3.0" + +clean-stack@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" + integrity sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A== + +cli-cursor@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/cli-cursor/-/cli-cursor-2.1.0.tgz#b35dac376479facc3e94747d41d0d0f5238ffcb5" + integrity sha512-8lgKz8LmCRYZZQDpRyT2m5rKJ08TnU4tR9FFFW2rxpxR1FzWi4PQ/NfyODchAatHaUgnSPVcx/R5w6NuTBzFiw== + dependencies: + restore-cursor "^2.0.0" + +cli-width@^2.0.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/cli-width/-/cli-width-2.2.1.tgz#b0433d0b4e9c847ef18868a4ef16fd5fc8271c48" + integrity sha512-GRMWDxpOB6Dgk2E5Uo+3eEBvtOOlimMmpbFiKuLFnQzYDavtLFY3K5ona41jgN/WdRZtG7utuVSVTL4HbZHGkw== + +cliui@^7.0.2: + version "7.0.4" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" + integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.0" + wrap-ansi "^7.0.0" + +color-convert@^1.9.0: + version "1.9.3" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" + integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== + dependencies: + color-name "1.1.3" + +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + +color-name@1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" + integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== + +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + +command-exists@^1.2.8: + version "1.2.9" + resolved "https://registry.yarnpkg.com/command-exists/-/command-exists-1.2.9.tgz#c50725af3808c8ab0260fd60b01fbfa25b954f69" + integrity sha512-LTQ/SGc+s0Xc0Fu5WaKnR0YiygZkm9eKFvyS+fRsU7/ZWFF8ykFM6Pc9aCVf1+xasOOZpO3BAVgVrKvsqKHV7w== + +command-line-args@^5.1.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/command-line-args/-/command-line-args-5.2.1.tgz#c44c32e437a57d7c51157696893c5909e9cec42e" + integrity sha512-H4UfQhZyakIjC74I9d34fGYDwk3XpSr17QhEd0Q3I9Xq1CETHo4Hcuo87WyWHpAF1aSLjLRf5lD9ZGX2qStUvg== + dependencies: + array-back "^3.1.0" + find-replace "^3.0.0" + lodash.camelcase "^4.3.0" + typical "^4.0.0" + +command-line-usage@^6.1.0: + version "6.1.3" + resolved "https://registry.yarnpkg.com/command-line-usage/-/command-line-usage-6.1.3.tgz#428fa5acde6a838779dfa30e44686f4b6761d957" + integrity sha512-sH5ZSPr+7UStsloltmDh7Ce5fb8XPlHyoPzTpyyMuYCtervL65+ubVZ6Q61cFtFl62UyJlc8/JwERRbAFPUqgw== + dependencies: + array-back "^4.0.2" + chalk "^2.4.2" + table-layout "^1.0.2" + typical "^5.2.0" + +commander@2.18.0: + version "2.18.0" + resolved "https://registry.yarnpkg.com/commander/-/commander-2.18.0.tgz#2bf063ddee7c7891176981a2cc798e5754bc6970" + integrity sha512-6CYPa+JP2ftfRU2qkDK+UTVeQYosOg/2GbcjIcKPHfinyOLPVGXu/ovN86RP49Re5ndJK1N0kuiidFFuepc4ZQ== + +commander@3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/commander/-/commander-3.0.2.tgz#6837c3fb677ad9933d1cfba42dd14d5117d6b39e" + integrity sha512-Gar0ASD4BDyKC4hl4DwHqDrmvjoxWKZigVnAbn5H1owvm4CxCPdb0HQDehwNYMJpla5+M2tPmPARzhtYuwpHow== + +concat-map@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" + integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== + +cookie@^0.4.1: + version "0.4.2" + resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.2.tgz#0e41f24de5ecf317947c82fc789e06a884824432" + integrity sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA== + +cosmiconfig@^5.0.7: + version "5.2.1" + resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-5.2.1.tgz#040f726809c591e77a17c0a3626ca45b4f168b1a" + integrity sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA== + dependencies: + import-fresh "^2.0.0" + is-directory "^0.3.1" + js-yaml "^3.13.1" + parse-json "^4.0.0" + +crc-32@^1.2.0: + version "1.2.2" + resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" + integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ== + +create-hash@^1.1.0, create-hash@^1.1.2, create-hash@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/create-hash/-/create-hash-1.2.0.tgz#889078af11a63756bcfb59bd221996be3a9ef196" + integrity sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg== + dependencies: + cipher-base "^1.0.1" + inherits "^2.0.1" + md5.js "^1.3.4" + ripemd160 "^2.0.1" + sha.js "^2.4.0" + +create-hmac@^1.1.4, create-hmac@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/create-hmac/-/create-hmac-1.1.7.tgz#69170c78b3ab957147b2b8b04572e47ead2243ff" + integrity sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg== + dependencies: + cipher-base "^1.0.3" + create-hash "^1.1.0" + inherits "^2.0.1" + ripemd160 "^2.0.0" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +create-require@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333" + integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ== + +cross-spawn@^6.0.5: + version "6.0.5" + resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-6.0.5.tgz#4a5ec7c64dfae22c3a14124dbacdee846d80cbc4" + integrity sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ== + dependencies: + nice-try "^1.0.4" + path-key "^2.0.1" + semver "^5.5.0" + shebang-command "^1.2.0" + which "^1.2.9" + +debug@4, debug@4.3.4, debug@^4.0.1, debug@^4.1.1, debug@^4.3.1, debug@^4.3.3: + version "4.3.4" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" + integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== + dependencies: + ms "2.1.2" + +decamelize@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" + integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== + +deep-extend@~0.6.0: + version "0.6.0" + resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac" + integrity sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA== + +deep-is@~0.1.3: + version "0.1.4" + resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.4.tgz#a6f2dce612fadd2ef1f519b73551f17e85199831" + integrity sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ== + +depd@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/depd/-/depd-2.0.0.tgz#b696163cc757560d09cf22cc8fad1571b79e76df" + integrity sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw== + +diff@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" + integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== + +diff@^4.0.1: + version "4.0.2" + resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d" + integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A== + +doctrine@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-3.0.0.tgz#addebead72a6574db783639dc87a121773973961" + integrity sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w== + dependencies: + esutils "^2.0.2" + +"ds-test@https://github.com/dapphub/ds-test.git#c7a36fb236f298e04edf28e2fee385b80f53945f": + version "0.0.0" + resolved "https://github.com/dapphub/ds-test.git#c7a36fb236f298e04edf28e2fee385b80f53945f" + +elliptic@6.5.4, elliptic@^6.5.2, elliptic@^6.5.4: + version "6.5.4" + resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.5.4.tgz#da37cebd31e79a1367e941b592ed1fbebd58abbb" + integrity sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ== + dependencies: + bn.js "^4.11.9" + brorand "^1.1.0" + hash.js "^1.0.0" + hmac-drbg "^1.0.1" + inherits "^2.0.4" + minimalistic-assert "^1.0.1" + minimalistic-crypto-utils "^1.0.1" + +emoji-regex@^7.0.1: + version "7.0.3" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-7.0.3.tgz#933a04052860c85e83c122479c4748a8e4c72156" + integrity sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA== + +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + +enquirer@^2.3.0: + version "2.3.6" + resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.3.6.tgz#2a7fe5dd634a1e4125a975ec994ff5456dc3734d" + integrity sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg== + dependencies: + ansi-colors "^4.1.1" + +env-paths@^2.2.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/env-paths/-/env-paths-2.2.1.tgz#420399d416ce1fbe9bc0a07c62fa68d67fd0f8f2" + integrity sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A== + +error-ex@^1.3.1: + version "1.3.2" + resolved "https://registry.yarnpkg.com/error-ex/-/error-ex-1.3.2.tgz#b4ac40648107fdcdcfae242f428bea8a14d4f1bf" + integrity sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g== + dependencies: + is-arrayish "^0.2.1" + +escalade@^3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" + integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== + +escape-string-regexp@4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" + integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== + +escape-string-regexp@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" + integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== + +eslint-scope@^4.0.3: + version "4.0.3" + resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-4.0.3.tgz#ca03833310f6889a3264781aa82e63eb9cfe7848" + integrity sha512-p7VutNr1O/QrxysMo3E45FjYDTeXBy0iTltPFNSqKAIfjDSXC+4dj+qfyuD8bfAXrW/y6lW3O76VaYNPKfpKrg== + dependencies: + esrecurse "^4.1.0" + estraverse "^4.1.1" + +eslint-utils@^1.3.1: + version "1.4.3" + resolved "https://registry.yarnpkg.com/eslint-utils/-/eslint-utils-1.4.3.tgz#74fec7c54d0776b6f67e0251040b5806564e981f" + integrity sha512-fbBN5W2xdY45KulGXmLHZ3c3FHfVYmKg0IrAKGOkT/464PQsx2UeIzfz1RmEci+KLm1bBaAzZAh8+/E+XAeZ8Q== + dependencies: + eslint-visitor-keys "^1.1.0" + +eslint-visitor-keys@^1.0.0, eslint-visitor-keys@^1.1.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz#30ebd1ef7c2fdff01c3a4f151044af25fab0523e" + integrity sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ== + +eslint@^5.6.0: + version "5.16.0" + resolved "https://registry.yarnpkg.com/eslint/-/eslint-5.16.0.tgz#a1e3ac1aae4a3fbd8296fcf8f7ab7314cbb6abea" + integrity sha512-S3Rz11i7c8AA5JPv7xAH+dOyq/Cu/VXHiHXBPOU1k/JAM5dXqQPt3qcrhpHSorXmrpu2g0gkIBVXAqCpzfoZIg== + dependencies: + "@babel/code-frame" "^7.0.0" + ajv "^6.9.1" + chalk "^2.1.0" + cross-spawn "^6.0.5" + debug "^4.0.1" + doctrine "^3.0.0" + eslint-scope "^4.0.3" + eslint-utils "^1.3.1" + eslint-visitor-keys "^1.0.0" + espree "^5.0.1" + esquery "^1.0.1" + esutils "^2.0.2" + file-entry-cache "^5.0.1" + functional-red-black-tree "^1.0.1" + glob "^7.1.2" + globals "^11.7.0" + ignore "^4.0.6" + import-fresh "^3.0.0" + imurmurhash "^0.1.4" + inquirer "^6.2.2" + js-yaml "^3.13.0" + json-stable-stringify-without-jsonify "^1.0.1" + levn "^0.3.0" + lodash "^4.17.11" + minimatch "^3.0.4" + mkdirp "^0.5.1" + natural-compare "^1.4.0" + optionator "^0.8.2" + path-is-inside "^1.0.2" + progress "^2.0.0" + regexpp "^2.0.1" + semver "^5.5.1" + strip-ansi "^4.0.0" + strip-json-comments "^2.0.1" + table "^5.2.3" + text-table "^0.2.0" + +espree@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/espree/-/espree-5.0.1.tgz#5d6526fa4fc7f0788a5cf75b15f30323e2f81f7a" + integrity sha512-qWAZcWh4XE/RwzLJejfcofscgMc9CamR6Tn1+XRXNzrvUSSbiAjGOI/fggztjIi7y9VLPqnICMIPiGyr8JaZ0A== + dependencies: + acorn "^6.0.7" + acorn-jsx "^5.0.0" + eslint-visitor-keys "^1.0.0" + +esprima@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71" + integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A== + +esquery@^1.0.1: + version "1.4.0" + resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.4.0.tgz#2148ffc38b82e8c7057dfed48425b3e61f0f24a5" + integrity sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w== + dependencies: + estraverse "^5.1.0" + +esrecurse@^4.1.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" + integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== + dependencies: + estraverse "^5.2.0" + +estraverse@^4.1.1: + version "4.3.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.3.0.tgz#398ad3f3c5a24948be7725e83d11a7de28cdbd1d" + integrity sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw== + +estraverse@^5.1.0, estraverse@^5.2.0: + version "5.3.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-5.3.0.tgz#2eea5290702f26ab8fe5370370ff86c965d21123" + integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== + +esutils@^2.0.2: + version "2.0.3" + resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.3.tgz#74d2eb4de0b8da1293711910d50775b9b710ef64" + integrity sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g== + +ethereum-cryptography@0.1.3, ethereum-cryptography@^0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-0.1.3.tgz#8d6143cfc3d74bf79bbd8edecdf29e4ae20dd191" + integrity sha512-w8/4x1SGGzc+tO97TASLja6SLd3fRIK2tLVcV2Gx4IB21hE19atll5Cq9o3d0ZmAYC/8aw0ipieTSiekAea4SQ== + dependencies: + "@types/pbkdf2" "^3.0.0" + "@types/secp256k1" "^4.0.1" + blakejs "^1.1.0" + browserify-aes "^1.2.0" + bs58check "^2.1.2" + create-hash "^1.2.0" + create-hmac "^1.1.7" + hash.js "^1.1.7" + keccak "^3.0.0" + pbkdf2 "^3.0.17" + randombytes "^2.1.0" + safe-buffer "^5.1.2" + scrypt-js "^3.0.0" + secp256k1 "^4.0.1" + setimmediate "^1.0.5" + +ethereum-cryptography@^1.0.3: + version "1.1.2" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-1.1.2.tgz#74f2ac0f0f5fe79f012c889b3b8446a9a6264e6d" + integrity sha512-XDSJlg4BD+hq9N2FjvotwUET9Tfxpxc3kWGE2AqUG5vcbeunnbImVk3cj6e/xT3phdW21mE8R5IugU4fspQDcQ== + dependencies: + "@noble/hashes" "1.1.2" + "@noble/secp256k1" "1.6.3" + "@scure/bip32" "1.1.0" + "@scure/bip39" "1.1.0" + +ethereumjs-abi@^0.6.8: + version "0.6.8" + resolved "https://registry.yarnpkg.com/ethereumjs-abi/-/ethereumjs-abi-0.6.8.tgz#71bc152db099f70e62f108b7cdfca1b362c6fcae" + integrity sha512-Tx0r/iXI6r+lRsdvkFDlut0N08jWMnKRZ6Gkq+Nmw75lZe4e6o3EkSnkaBP5NF6+m5PTGAr9JP43N3LyeoglsA== + dependencies: + bn.js "^4.11.8" + ethereumjs-util "^6.0.0" + +ethereumjs-util@^6.0.0, ethereumjs-util@^6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/ethereumjs-util/-/ethereumjs-util-6.2.1.tgz#fcb4e4dd5ceacb9d2305426ab1a5cd93e3163b69" + integrity sha512-W2Ktez4L01Vexijrm5EB6w7dg4n/TgpoYU4avuT5T3Vmnw/eCRtiBrJfQYS/DCSvDIOLn2k57GcHdeBcgVxAqw== + dependencies: + "@types/bn.js" "^4.11.3" + bn.js "^4.11.0" + create-hash "^1.1.2" + elliptic "^6.5.2" + ethereum-cryptography "^0.1.3" + ethjs-util "0.1.6" + rlp "^2.2.3" + +ethjs-util@0.1.6, ethjs-util@^0.1.6: + version "0.1.6" + resolved "https://registry.yarnpkg.com/ethjs-util/-/ethjs-util-0.1.6.tgz#f308b62f185f9fe6237132fb2a9818866a5cd536" + integrity sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w== + dependencies: + is-hex-prefixed "1.0.0" + strip-hex-prefix "1.0.0" + +event-target-shim@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/event-target-shim/-/event-target-shim-5.0.1.tgz#5d4d3ebdf9583d63a5333ce2deb7480ab2b05789" + integrity sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ== + +evp_bytestokey@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz#7fcbdb198dc71959432efe13842684e0525acb02" + integrity sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA== + dependencies: + md5.js "^1.3.4" + safe-buffer "^5.1.1" + +external-editor@^3.0.3: + version "3.1.0" + resolved "https://registry.yarnpkg.com/external-editor/-/external-editor-3.1.0.tgz#cb03f740befae03ea4d283caed2741a83f335495" + integrity sha512-hMQ4CX1p1izmuLYyZqLMO/qGNw10wSv9QDCPfzXfyFrOaCSSoRfqE1Kf1s5an66J5JZC62NewG+mK49jOCtQew== + dependencies: + chardet "^0.7.0" + iconv-lite "^0.4.24" + tmp "^0.0.33" + +fast-deep-equal@^3.1.1: + version "3.1.3" + resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" + integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== + +fast-diff@^1.1.2: + version "1.2.0" + resolved "https://registry.yarnpkg.com/fast-diff/-/fast-diff-1.2.0.tgz#73ee11982d86caaf7959828d519cfe927fac5f03" + integrity sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w== + +fast-json-stable-stringify@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" + integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== + +fast-levenshtein@~2.0.6: + version "2.0.6" + resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917" + integrity sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw== + +figures@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/figures/-/figures-2.0.0.tgz#3ab1a2d2a62c8bfb431a0c94cb797a2fce27c962" + integrity sha512-Oa2M9atig69ZkfwiApY8F2Yy+tzMbazyvqv21R0NsSC8floSOC09BbT1ITWAdoMGQvJ/aZnR1KMwdx9tvHnTNA== + dependencies: + escape-string-regexp "^1.0.5" + +file-entry-cache@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/file-entry-cache/-/file-entry-cache-5.0.1.tgz#ca0f6efa6dd3d561333fb14515065c2fafdf439c" + integrity sha512-bCg29ictuBaKUwwArK4ouCaqDgLZcysCFLmM/Yn/FDoqndh/9vNuQfXRDvTuXKLxfD/JtZQGKFT8MGcJBK644g== + dependencies: + flat-cache "^2.0.1" + +fill-range@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" + integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== + dependencies: + to-regex-range "^5.0.1" + +find-replace@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/find-replace/-/find-replace-3.0.0.tgz#3e7e23d3b05167a76f770c9fbd5258b0def68c38" + integrity sha512-6Tb2myMioCAgv5kfvP5/PkZZ/ntTpVK39fHY7WkWBgvbeE+VHd/tZuZ4mrC+bxh4cfOZeYKVPaJIZtZXV7GNCQ== + dependencies: + array-back "^3.0.1" + +find-up@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" + integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== + dependencies: + locate-path "^6.0.0" + path-exists "^4.0.0" + +find-up@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-2.1.0.tgz#45d1b7e506c717ddd482775a2b77920a3c0c57a7" + integrity sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ== + dependencies: + locate-path "^2.0.0" + +flat-cache@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-2.0.1.tgz#5d296d6f04bda44a4630a301413bdbc2ec085ec0" + integrity sha512-LoQe6yDuUMDzQAEH8sgmh4Md6oZnc/7PjtwjNFSzveXqSHt6ka9fPBuso7IGf9Rz4uqnSnWiFH2B/zj24a5ReA== + dependencies: + flatted "^2.0.0" + rimraf "2.6.3" + write "1.0.3" + +flat@^5.0.2: + version "5.0.2" + resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" + integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== + +flatted@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/flatted/-/flatted-2.0.2.tgz#4575b21e2bcee7434aa9be662f4b7b5f9c2b5138" + integrity sha512-r5wGx7YeOwNWNlCA0wQ86zKyDLMQr+/RB8xy74M4hTphfmjlijTSSXGuH8rnvKZnfT9i+75zmd8jcKdMR4O6jA== + +follow-redirects@^1.12.1: + version "1.15.2" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.2.tgz#b460864144ba63f2681096f274c4e57026da2c13" + integrity sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA== + +"forge-std@https://github.com/foundry-rs/forge-std.git#37a3fe48c3a4d8239cda93445f0b5e76b1507436": + version "0.0.0" + resolved "https://github.com/foundry-rs/forge-std.git#37a3fe48c3a4d8239cda93445f0b5e76b1507436" + +fp-ts@1.19.3: + version "1.19.3" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.3.tgz#261a60d1088fbff01f91256f91d21d0caaaaa96f" + integrity sha512-H5KQDspykdHuztLTg+ajGN0Z2qUjcEf3Ybxc6hLt0k7/zPkn29XnKnxlBPyW2XIddWrGaJBzBl4VLYOtk39yZg== + +fp-ts@^1.0.0: + version "1.19.5" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.5.tgz#3da865e585dfa1fdfd51785417357ac50afc520a" + integrity sha512-wDNqTimnzs8QqpldiId9OavWK2NptormjXnRJTQecNjzwfyp6P/8s/zG8e4h3ja3oqkKaY72UlTjQYt/1yXf9A== + +fs-extra@^0.30.0: + version "0.30.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.30.0.tgz#f233ffcc08d4da7d432daa449776989db1df93f0" + integrity sha512-UvSPKyhMn6LEd/WpUaV9C9t3zATuqoqfWc3QdPhPLb58prN9tqYPlPWi8Krxi44loBoUzlobqZ3+8tGpxxSzwA== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^2.1.0" + klaw "^1.0.0" + path-is-absolute "^1.0.0" + rimraf "^2.2.8" + +fs-extra@^7.0.0, fs-extra@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" + integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^4.0.0" + universalify "^0.1.0" + +fs.realpath@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" + integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== + +fsevents@~2.3.2: + version "2.3.2" + resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.2.tgz#8a526f78b8fdf4623b709e0b975c52c24c02fd1a" + integrity sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA== + +function-bind@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" + integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A== + +functional-red-black-tree@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" + integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g== + +get-caller-file@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" + integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== + +get-intrinsic@^1.0.2: + version "1.2.0" + resolved "https://registry.yarnpkg.com/get-intrinsic/-/get-intrinsic-1.2.0.tgz#7ad1dc0535f3a2904bba075772763e5051f6d05f" + integrity sha512-L049y6nFOuom5wGyRc3/gdTLO94dySVKRACj1RmJZBQXlbTMhtNIgkWkUHq+jYmZvKf14EW1EoJnnjbmoHij0Q== + dependencies: + function-bind "^1.1.1" + has "^1.0.3" + has-symbols "^1.0.3" + +glob-parent@~5.1.2: + version "5.1.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" + integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== + dependencies: + is-glob "^4.0.1" + +glob@7.1.7: + version "7.1.7" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.7.tgz#3b193e9233f01d42d0b3f78294bbeeb418f94a90" + integrity sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@7.2.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023" + integrity sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^7.1.2, glob@^7.1.3: + version "7.2.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b" + integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.1.1" + once "^1.3.0" + path-is-absolute "^1.0.0" + +globals@^11.7.0: + version "11.12.0" + resolved "https://registry.yarnpkg.com/globals/-/globals-11.12.0.tgz#ab8795338868a0babd8525758018c2a7eb95c42e" + integrity sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA== + +graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.1.9: + version "4.2.10" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c" + integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA== + +handlebars@^4.7.7: + version "4.7.7" + resolved "https://registry.yarnpkg.com/handlebars/-/handlebars-4.7.7.tgz#9ce33416aad02dbd6c8fafa8240d5d98004945a1" + integrity sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA== + dependencies: + minimist "^1.2.5" + neo-async "^2.6.0" + source-map "^0.6.1" + wordwrap "^1.0.0" + optionalDependencies: + uglify-js "^3.1.4" + +hardhat@^2.10.1: + version "2.12.6" + resolved "https://registry.yarnpkg.com/hardhat/-/hardhat-2.12.6.tgz#ea3c058bbd81850867389d10f76037cfa52a0019" + integrity sha512-0Ent1O5DsPgvaVb5sxEgsQ3bJRt/Ex92tsoO+xjoNH2Qc4bFmhI5/CHVlFikulalxOPjNmw5XQ2vJFuVQFESAA== + dependencies: + "@ethersproject/abi" "^5.1.2" + "@metamask/eth-sig-util" "^4.0.0" + "@nomicfoundation/ethereumjs-block" "^4.0.0" + "@nomicfoundation/ethereumjs-blockchain" "^6.0.0" + "@nomicfoundation/ethereumjs-common" "^3.0.0" + "@nomicfoundation/ethereumjs-evm" "^1.0.0" + "@nomicfoundation/ethereumjs-rlp" "^4.0.0" + "@nomicfoundation/ethereumjs-statemanager" "^1.0.0" + "@nomicfoundation/ethereumjs-trie" "^5.0.0" + "@nomicfoundation/ethereumjs-tx" "^4.0.0" + "@nomicfoundation/ethereumjs-util" "^8.0.0" + "@nomicfoundation/ethereumjs-vm" "^6.0.0" + "@nomicfoundation/solidity-analyzer" "^0.1.0" + "@sentry/node" "^5.18.1" + "@types/bn.js" "^5.1.0" + "@types/lru-cache" "^5.1.0" + abort-controller "^3.0.0" + adm-zip "^0.4.16" + aggregate-error "^3.0.0" + ansi-escapes "^4.3.0" + chalk "^2.4.2" + chokidar "^3.4.0" + ci-info "^2.0.0" + debug "^4.1.1" + enquirer "^2.3.0" + env-paths "^2.2.0" + ethereum-cryptography "^1.0.3" + ethereumjs-abi "^0.6.8" + find-up "^2.1.0" + fp-ts "1.19.3" + fs-extra "^7.0.1" + glob "7.2.0" + immutable "^4.0.0-rc.12" + io-ts "1.10.4" + keccak "^3.0.2" + lodash "^4.17.11" + mnemonist "^0.38.0" + mocha "^10.0.0" + p-map "^4.0.0" + qs "^6.7.0" + raw-body "^2.4.1" + resolve "1.17.0" + semver "^6.3.0" + solc "0.7.3" + source-map-support "^0.5.13" + stacktrace-parser "^0.1.10" + tsort "0.0.1" + undici "^5.14.0" + uuid "^8.3.2" + ws "^7.4.6" + +has-flag@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" + integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== + +has-flag@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" + integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== + +has-symbols@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.0.3.tgz#bb7b2c4349251dce87b125f7bdf874aa7c8b39f8" + integrity sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A== + +has@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" + integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== + dependencies: + function-bind "^1.1.1" + +hash-base@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/hash-base/-/hash-base-3.1.0.tgz#55c381d9e06e1d2997a883b4a3fddfe7f0d3af33" + integrity sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA== + dependencies: + inherits "^2.0.4" + readable-stream "^3.6.0" + safe-buffer "^5.2.0" + +hash.js@1.1.7, hash.js@^1.0.0, hash.js@^1.0.3, hash.js@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/hash.js/-/hash.js-1.1.7.tgz#0babca538e8d4ee4a0f8988d68866537a003cf42" + integrity sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA== + dependencies: + inherits "^2.0.3" + minimalistic-assert "^1.0.1" + +he@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" + integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== + +hmac-drbg@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1" + integrity sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg== + dependencies: + hash.js "^1.0.3" + minimalistic-assert "^1.0.0" + minimalistic-crypto-utils "^1.0.1" + +http-errors@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-2.0.0.tgz#b7774a1486ef73cf7667ac9ae0858c012c57b9d3" + integrity sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ== + dependencies: + depd "2.0.0" + inherits "2.0.4" + setprototypeof "1.2.0" + statuses "2.0.1" + toidentifier "1.0.1" + +https-proxy-agent@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" + integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== + dependencies: + agent-base "6" + debug "4" + +iconv-lite@0.4.24, iconv-lite@^0.4.24: + version "0.4.24" + resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" + integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== + dependencies: + safer-buffer ">= 2.1.2 < 3" + +ieee754@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" + integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== + +ignore@^4.0.6: + version "4.0.6" + resolved "https://registry.yarnpkg.com/ignore/-/ignore-4.0.6.tgz#750e3db5862087b4737ebac8207ffd1ef27b25fc" + integrity sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg== + +immutable@^4.0.0-rc.12: + version "4.2.2" + resolved "https://registry.yarnpkg.com/immutable/-/immutable-4.2.2.tgz#2da9ff4384a4330c36d4d1bc88e90f9e0b0ccd16" + integrity sha512-fTMKDwtbvO5tldky9QZ2fMX7slR0mYpY5nbnFWYp0fOzDhHqhgIw9KoYgxLWsoNTS9ZHGauHj18DTyEw6BK3Og== + +import-fresh@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-2.0.0.tgz#d81355c15612d386c61f9ddd3922d4304822a546" + integrity sha512-eZ5H8rcgYazHbKC3PG4ClHNykCSxtAhxSSEM+2mb+7evD2CKF5V7c0dNum7AdpDh0ZdICwZY9sRSn8f+KH96sg== + dependencies: + caller-path "^2.0.0" + resolve-from "^3.0.0" + +import-fresh@^3.0.0: + version "3.3.0" + resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b" + integrity sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw== + dependencies: + parent-module "^1.0.0" + resolve-from "^4.0.0" + +imurmurhash@^0.1.4: + version "0.1.4" + resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" + integrity sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA== + +indent-string@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-4.0.0.tgz#624f8f4497d619b2d9768531d58f4122854d7251" + integrity sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg== + +inflight@^1.0.4: + version "1.0.6" + resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" + integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== + dependencies: + once "^1.3.0" + wrappy "1" + +inherits@2, inherits@2.0.4, inherits@^2.0.1, inherits@^2.0.3, inherits@^2.0.4: + version "2.0.4" + resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" + integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== + +inquirer@^6.2.2: + version "6.5.2" + resolved "https://registry.yarnpkg.com/inquirer/-/inquirer-6.5.2.tgz#ad50942375d036d327ff528c08bd5fab089928ca" + integrity sha512-cntlB5ghuB0iuO65Ovoi8ogLHiWGs/5yNrtUcKjFhSSiVeAIVpD7koaSU9RM8mpXw5YDi9RdYXGQMaOURB7ycQ== + dependencies: + ansi-escapes "^3.2.0" + chalk "^2.4.2" + cli-cursor "^2.1.0" + cli-width "^2.0.0" + external-editor "^3.0.3" + figures "^2.0.0" + lodash "^4.17.12" + mute-stream "0.0.7" + run-async "^2.2.0" + rxjs "^6.4.0" + string-width "^2.1.0" + strip-ansi "^5.1.0" + through "^2.3.6" + +io-ts@1.10.4: + version "1.10.4" + resolved "https://registry.yarnpkg.com/io-ts/-/io-ts-1.10.4.tgz#cd5401b138de88e4f920adbcb7026e2d1967e6e2" + integrity sha512-b23PteSnYXSONJ6JQXRAlvJhuw8KOtkqa87W4wDtvMrud/DTJd5X+NpOOI+O/zZwVq6v0VLAaJ+1EDViKEuN9g== + dependencies: + fp-ts "^1.0.0" + +is-arrayish@^0.2.1: + version "0.2.1" + resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d" + integrity sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg== + +is-binary-path@~2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" + integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== + dependencies: + binary-extensions "^2.0.0" + +is-buffer@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-2.0.5.tgz#ebc252e400d22ff8d77fa09888821a24a658c191" + integrity sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ== + +is-directory@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/is-directory/-/is-directory-0.3.1.tgz#61339b6f2475fc772fd9c9d83f5c8575dc154ae1" + integrity sha512-yVChGzahRFvbkscn2MlwGismPO12i9+znNruC5gVEntG3qu0xQMzsGg/JFbrsqDOHtHFPci+V5aP5T9I+yeKqw== + +is-extglob@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" + integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== + +is-fullwidth-code-point@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz#a3b30a5c4f199183167aaab93beefae3ddfb654f" + integrity sha512-VHskAKYM8RfSFXwee5t5cbN5PZeq1Wrh6qd5bkyiXIf6UQcN6w/A0eXM9r6t8d+GYOh+o6ZhiEnb88LN/Y8m2w== + +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + +is-glob@^4.0.1, is-glob@~4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" + integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== + dependencies: + is-extglob "^2.1.1" + +is-hex-prefixed@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz#7d8d37e6ad77e5d127148913c573e082d777f554" + integrity sha512-WvtOiug1VFrE9v1Cydwm+FnXd3+w9GaeVUss5W4v/SLy3UW00vP+6iNF2SdnfiBoLy4bTqVdkftNGTUeOFVsbA== + +is-number@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== + +is-plain-obj@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" + integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== + +is-unicode-supported@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz#3f26c76a809593b52bfa2ecb5710ed2779b522a7" + integrity sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw== + +isexe@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" + integrity sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw== + +js-sha3@0.8.0, js-sha3@^0.8.0: + version "0.8.0" + resolved "https://registry.yarnpkg.com/js-sha3/-/js-sha3-0.8.0.tgz#b9b7a5da73afad7dedd0f8c463954cbde6818840" + integrity sha512-gF1cRrHhIzNfToc802P800N8PpXS+evLLXfsVpowqmAFR9uwbi89WvXg2QspOmXL8QL86J4T1EpFu+yUkwJY3Q== + +js-tokens@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499" + integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ== + +js-yaml@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" + integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== + dependencies: + argparse "^2.0.1" + +js-yaml@^3.12.0, js-yaml@^3.13.0, js-yaml@^3.13.1: + version "3.14.1" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.14.1.tgz#dae812fdb3825fa306609a8717383c50c36a0537" + integrity sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g== + dependencies: + argparse "^1.0.7" + esprima "^4.0.0" + +json-parse-better-errors@^1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz#bb867cfb3450e69107c131d1c514bab3dc8bcaa9" + integrity sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw== + +json-schema-traverse@^0.4.1: + version "0.4.1" + resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz#69f6a87d9513ab8bb8fe63bdb0979c448e684660" + integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== + +json-stable-stringify-without-jsonify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz#9db7b59496ad3f3cfef30a75142d2d930ad72651" + integrity sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw== + +jsonc-parser@^3.2.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/jsonc-parser/-/jsonc-parser-3.2.0.tgz#31ff3f4c2b9793f89c67212627c51c6394f88e76" + integrity sha512-gfFQZrcTc8CnKXp6Y4/CBT3fTc0OVuDofpre4aEeEpSBPV5X5v4+Vmx+8snU7RLPrNHPKSgLxGo9YuQzz20o+w== + +jsonfile@^2.1.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-2.4.0.tgz#3736a2b428b87bbda0cc83b53fa3d633a35c2ae8" + integrity sha512-PKllAqbgLgxHaj8TElYymKCAgrASebJrWpTnEkOaTowt23VKXXN0sUeriJ+eh7y6ufb/CC5ap11pz71/cM0hUw== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb" + integrity sha512-m6F1R3z8jjlf2imQHS2Qez5sjKWQzbuuhuJ/FKYFRZvPE3PuHcSMVZzfsLhGVOkfd20obL5SWEBew5ShlquNxg== + optionalDependencies: + graceful-fs "^4.1.6" + +keccak@^3.0.0, keccak@^3.0.2: + version "3.0.3" + resolved "https://registry.yarnpkg.com/keccak/-/keccak-3.0.3.tgz#4bc35ad917be1ef54ff246f904c2bbbf9ac61276" + integrity sha512-JZrLIAJWuZxKbCilMpNz5Vj7Vtb4scDG3dMXLOsbzBmQGyjwE61BbW7bJkfKKCShXiQZt3T6sBgALRtmd+nZaQ== + dependencies: + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + readable-stream "^3.6.0" + +klaw@^1.0.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/klaw/-/klaw-1.3.1.tgz#4088433b46b3b1ba259d78785d8e96f73ba02439" + integrity sha512-TED5xi9gGQjGpNnvRWknrwAB1eL5GciPfVFOt3Vk1OJCVDQbzuSfrF3hkUQKlsgKrG1F+0t5W0m+Fje1jIt8rw== + optionalDependencies: + graceful-fs "^4.1.9" + +level-supports@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/level-supports/-/level-supports-4.0.1.tgz#431546f9d81f10ff0fea0e74533a0e875c08c66a" + integrity sha512-PbXpve8rKeNcZ9C1mUicC9auIYFyGpkV9/i6g76tLgANwWhtG2v7I4xNBUlkn3lE2/dZF3Pi0ygYGtLc4RXXdA== + +level-transcoder@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/level-transcoder/-/level-transcoder-1.0.1.tgz#f8cef5990c4f1283d4c86d949e73631b0bc8ba9c" + integrity sha512-t7bFwFtsQeD8cl8NIoQ2iwxA0CL/9IFw7/9gAjOonH0PWTTiRfY7Hq+Ejbsxh86tXobDQ6IOiddjNYIfOBs06w== + dependencies: + buffer "^6.0.3" + module-error "^1.0.1" + +level@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/level/-/level-8.0.0.tgz#41b4c515dabe28212a3e881b61c161ffead14394" + integrity sha512-ypf0jjAk2BWI33yzEaaotpq7fkOPALKAgDBxggO6Q9HGX2MRXn0wbP1Jn/tJv1gtL867+YOjOB49WaUF3UoJNQ== + dependencies: + browser-level "^1.0.1" + classic-level "^1.2.0" + +levn@^0.3.0, levn@~0.3.0: + version "0.3.0" + resolved "https://registry.yarnpkg.com/levn/-/levn-0.3.0.tgz#3b09924edf9f083c0490fdd4c0bc4421e04764ee" + integrity sha512-0OO4y2iOHix2W6ujICbKIaEQXvFQHue65vUG3pb5EUomzPI90z9hsA1VsO/dbIIpC53J8gxM9Q4Oho0jrCM/yA== + dependencies: + prelude-ls "~1.1.2" + type-check "~0.3.2" + +locate-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" + integrity sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA== + dependencies: + p-locate "^2.0.0" + path-exists "^3.0.0" + +locate-path@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" + integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== + dependencies: + p-locate "^5.0.0" + +lodash.camelcase@^4.3.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" + integrity sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA== + +lodash@^4.17.11, lodash@^4.17.12, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.16: + version "4.17.21" + resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" + integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== + +log-symbols@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.1.0.tgz#3fbdbb95b4683ac9fc785111e792e558d4abd503" + integrity sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg== + dependencies: + chalk "^4.1.0" + is-unicode-supported "^0.1.0" + +lru-cache@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-5.1.1.tgz#1da27e6710271947695daf6848e847f01d84b920" + integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== + dependencies: + yallist "^3.0.2" + +lru-cache@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" + integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== + dependencies: + yallist "^4.0.0" + +lru_map@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/lru_map/-/lru_map-0.3.3.tgz#b5c8351b9464cbd750335a79650a0ec0e56118dd" + integrity sha512-Pn9cox5CsMYngeDbmChANltQl+5pi6XmTrraMSzhPmMBbmgcxmqWry0U3PGapCU1yB4/LqCcom7qhHZiF/jGfQ== + +lunr@^2.3.9: + version "2.3.9" + resolved "https://registry.yarnpkg.com/lunr/-/lunr-2.3.9.tgz#18b123142832337dd6e964df1a5a7707b25d35e1" + integrity sha512-zTU3DaZaF3Rt9rhN3uBMGQD3dD2/vFQqnvZCDv4dl5iOzq2IZQqTxu90r4E5J+nP70J3ilqVCrbho2eWaeW8Ow== + +make-error@^1.1.1: + version "1.3.6" + resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2" + integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw== + +marked@^4.2.5: + version "4.2.12" + resolved "https://registry.yarnpkg.com/marked/-/marked-4.2.12.tgz#d69a64e21d71b06250da995dcd065c11083bebb5" + integrity sha512-yr8hSKa3Fv4D3jdZmtMMPghgVt6TWbk86WQaWhDloQjRSQhMMYCAro7jP7VDJrjjdV8pxVxMssXS8B8Y5DZ5aw== + +mcl-wasm@^0.7.1: + version "0.7.9" + resolved "https://registry.yarnpkg.com/mcl-wasm/-/mcl-wasm-0.7.9.tgz#c1588ce90042a8700c3b60e40efb339fc07ab87f" + integrity sha512-iJIUcQWA88IJB/5L15GnJVnSQJmf/YaxxV6zRavv83HILHaJQb6y0iFyDMdDO0gN8X37tdxmAOrH/P8B6RB8sQ== + +md5.js@^1.3.4: + version "1.3.5" + resolved "https://registry.yarnpkg.com/md5.js/-/md5.js-1.3.5.tgz#b5d07b8e3216e3e27cd728d72f70d1e6a342005f" + integrity sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + safe-buffer "^5.1.2" + +memory-level@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/memory-level/-/memory-level-1.0.0.tgz#7323c3fd368f9af2f71c3cd76ba403a17ac41692" + integrity sha512-UXzwewuWeHBz5krr7EvehKcmLFNoXxGcvuYhC41tRnkrTbJohtS7kVn9akmgirtRygg+f7Yjsfi8Uu5SGSQ4Og== + dependencies: + abstract-level "^1.0.0" + functional-red-black-tree "^1.0.1" + module-error "^1.0.1" + +memorystream@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/memorystream/-/memorystream-0.3.1.tgz#86d7090b30ce455d63fbae12dda51a47ddcaf9b2" + integrity sha512-S3UwM3yj5mtUSEfP41UZmt/0SCoVYUcU1rkXv+BQ5Ig8ndL4sPoJNBUJERafdPb5jjHJGuMgytgKvKIf58XNBw== + +mimic-fn@^1.0.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/mimic-fn/-/mimic-fn-1.2.0.tgz#820c86a39334640e99516928bd03fca88057d022" + integrity sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ== + +minimalistic-assert@^1.0.0, minimalistic-assert@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz#2e194de044626d4a10e7f7fbc00ce73e83e4d5c7" + integrity sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A== + +minimalistic-crypto-utils@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a" + integrity sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg== + +minimatch@5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.0.1.tgz#fb9022f7528125187c92bd9e9b6366be1cf3415b" + integrity sha512-nLDxIFRyhDblz3qMuq+SoRZED4+miJ/G+tdDrjkkkRnjAsBexeGpgjLEQ0blJy7rHhR2b93rhQY4SvyWu9v03g== + dependencies: + brace-expansion "^2.0.1" + +minimatch@^3.0.4, minimatch@^3.1.1: + version "3.1.2" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^5.1.2: + version "5.1.6" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.6.tgz#1cfcb8cf5522ea69952cd2af95ae09477f122a96" + integrity sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g== + dependencies: + brace-expansion "^2.0.1" + +minimist@^1.2.5, minimist@^1.2.6: + version "1.2.7" + resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.7.tgz#daa1c4d91f507390437c6a8bc01078e7000c4d18" + integrity sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g== + +mkdirp@^0.5.1: + version "0.5.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.6.tgz#7def03d2432dcae4ba1d611445c48396062255f6" + integrity sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw== + dependencies: + minimist "^1.2.6" + +mkdirp@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" + integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== + +mnemonist@^0.38.0: + version "0.38.5" + resolved "https://registry.yarnpkg.com/mnemonist/-/mnemonist-0.38.5.tgz#4adc7f4200491237fe0fa689ac0b86539685cade" + integrity sha512-bZTFT5rrPKtPJxj8KSV0WkPyNxl72vQepqqVUAW2ARUpUSF2qXMB6jZj7hW5/k7C1rtpzqbD/IIbJwLXUjCHeg== + dependencies: + obliterator "^2.0.0" + +mocha@^10.0.0: + version "10.2.0" + resolved "https://registry.yarnpkg.com/mocha/-/mocha-10.2.0.tgz#1fd4a7c32ba5ac372e03a17eef435bd00e5c68b8" + integrity sha512-IDY7fl/BecMwFHzoqF2sg/SHHANeBoMMXFlS9r0OXKDssYE1M5O43wUY/9BVPeIvfH2zmEbBfseqN9gBQZzXkg== + dependencies: + ansi-colors "4.1.1" + browser-stdout "1.3.1" + chokidar "3.5.3" + debug "4.3.4" + diff "5.0.0" + escape-string-regexp "4.0.0" + find-up "5.0.0" + glob "7.2.0" + he "1.2.0" + js-yaml "4.1.0" + log-symbols "4.1.0" + minimatch "5.0.1" + ms "2.1.3" + nanoid "3.3.3" + serialize-javascript "6.0.0" + strip-json-comments "3.1.1" + supports-color "8.1.1" + workerpool "6.2.1" + yargs "16.2.0" + yargs-parser "20.2.4" + yargs-unparser "2.0.0" + +module-error@^1.0.1, module-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/module-error/-/module-error-1.0.2.tgz#8d1a48897ca883f47a45816d4fb3e3c6ba404d86" + integrity sha512-0yuvsqSCv8LbaOKhnsQ/T5JhyFlCYLPXK3U2sgV10zoKQwzs/MyfuQUOZQ1V/6OCOJsK/TRgNVrPuPDqtdMFtA== + +ms@2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" + integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== + +ms@2.1.3: + version "2.1.3" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" + integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== + +mute-stream@0.0.7: + version "0.0.7" + resolved "https://registry.yarnpkg.com/mute-stream/-/mute-stream-0.0.7.tgz#3075ce93bc21b8fab43e1bc4da7e8115ed1e7bab" + integrity sha512-r65nCZhrbXXb6dXOACihYApHw2Q6pV0M3V0PSxd74N0+D8nzAdEAITq2oAjA1jVnKI+tGvEBUpqiMh0+rW6zDQ== + +nanoid@3.3.3: + version "3.3.3" + resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.3.tgz#fd8e8b7aa761fe807dba2d1b98fb7241bb724a25" + integrity sha512-p1sjXuopFs0xg+fPASzQ28agW1oHD7xDsd9Xkf3T15H3c/cifrFHVwrh74PdoklAPi+i7MdRsE47vm2r6JoB+w== + +napi-macros@~2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/napi-macros/-/napi-macros-2.0.0.tgz#2b6bae421e7b96eb687aa6c77a7858640670001b" + integrity sha512-A0xLykHtARfueITVDernsAWdtIMbOJgKgcluwENp3AlsKN/PloyO10HtmoqnFAQAcxPkgZN7wdfPfEd0zNGxbg== + +natural-compare@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" + integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== + +neo-async@^2.6.0: + version "2.6.2" + resolved "https://registry.yarnpkg.com/neo-async/-/neo-async-2.6.2.tgz#b4aafb93e3aeb2d8174ca53cf163ab7d7308305f" + integrity sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw== + +nice-try@^1.0.4: + version "1.0.5" + resolved "https://registry.yarnpkg.com/nice-try/-/nice-try-1.0.5.tgz#a3378a7696ce7d223e88fc9b764bd7ef1089e366" + integrity sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ== + +node-addon-api@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/node-addon-api/-/node-addon-api-2.0.2.tgz#432cfa82962ce494b132e9d72a15b29f71ff5d32" + integrity sha512-Ntyt4AIXyaLIuMHF6IOoTakB3K+RWxwtsHNRxllEoA6vPwP9o4866g6YWDLUdnucilZhmkxiHwHr11gAENw+QA== + +node-gyp-build@^4.2.0, node-gyp-build@^4.3.0: + version "4.6.0" + resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.6.0.tgz#0c52e4cbf54bbd28b709820ef7b6a3c2d6209055" + integrity sha512-NTZVKn9IylLwUzaKjkas1e4u2DLNcV4rdYagA4PWdPwW87Bi7z+BznyKSRwS/761tV/lzCGXplWsiaMjLqP2zQ== + +normalize-path@^3.0.0, normalize-path@~3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" + integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== + +object-inspect@^1.9.0: + version "1.12.3" + resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.12.3.tgz#ba62dffd67ee256c8c086dfae69e016cd1f198b9" + integrity sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g== + +obliterator@^2.0.0: + version "2.0.4" + resolved "https://registry.yarnpkg.com/obliterator/-/obliterator-2.0.4.tgz#fa650e019b2d075d745e44f1effeb13a2adbe816" + integrity sha512-lgHwxlxV1qIg1Eap7LgIeoBWIMFibOjbrYPIPJZcI1mmGAI2m3lNYpK12Y+GBdPQ0U1hRwSord7GIaawz962qQ== + +once@^1.3.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" + integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== + dependencies: + wrappy "1" + +onetime@^2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/onetime/-/onetime-2.0.1.tgz#067428230fd67443b2794b22bba528b6867962d4" + integrity sha512-oyyPpiMaKARvvcgip+JV+7zci5L8D1W9RZIz2l1o08AM3pfspitVWnPt3mzHcBPp12oYMTy0pqrFs/C+m3EwsQ== + dependencies: + mimic-fn "^1.0.0" + +optionator@^0.8.2: + version "0.8.3" + resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.8.3.tgz#84fa1d036fe9d3c7e21d99884b601167ec8fb495" + integrity sha512-+IW9pACdk3XWmmTXG8m3upGUJst5XRGzxMRjXzAuJ1XnIFNvfhjjIuYkDvysnPQ7qzqVzLt78BCruntqRhWQbA== + dependencies: + deep-is "~0.1.3" + fast-levenshtein "~2.0.6" + levn "~0.3.0" + prelude-ls "~1.1.2" + type-check "~0.3.2" + word-wrap "~1.2.3" + +os-tmpdir@~1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274" + integrity sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g== + +p-limit@^1.1.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.3.0.tgz#b86bd5f0c25690911c7590fcbfc2010d54b3ccb8" + integrity sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q== + dependencies: + p-try "^1.0.0" + +p-limit@^3.0.2: + version "3.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" + integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== + dependencies: + yocto-queue "^0.1.0" + +p-locate@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" + integrity sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg== + dependencies: + p-limit "^1.1.0" + +p-locate@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" + integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== + dependencies: + p-limit "^3.0.2" + +p-map@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-map/-/p-map-4.0.0.tgz#bb2f95a5eda2ec168ec9274e06a747c3e2904d2b" + integrity sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ== + dependencies: + aggregate-error "^3.0.0" + +p-try@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3" + integrity sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww== + +parent-module@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/parent-module/-/parent-module-1.0.1.tgz#691d2709e78c79fae3a156622452d00762caaaa2" + integrity sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g== + dependencies: + callsites "^3.0.0" + +parse-json@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/parse-json/-/parse-json-4.0.0.tgz#be35f5425be1f7f6c747184f98a788cb99477ee0" + integrity sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw== + dependencies: + error-ex "^1.3.1" + json-parse-better-errors "^1.0.1" + +path-exists@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515" + integrity sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ== + +path-exists@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" + integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== + +path-is-absolute@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" + integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== + +path-is-inside@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/path-is-inside/-/path-is-inside-1.0.2.tgz#365417dede44430d1c11af61027facf074bdfc53" + integrity sha512-DUWJr3+ULp4zXmol/SZkFf3JGsS9/SIv+Y3Rt93/UjPpDpklB5f1er4O3POIbUuUJ3FXgqte2Q7SrU6zAqwk8w== + +path-key@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/path-key/-/path-key-2.0.1.tgz#411cadb574c5a140d3a4b1910d40d80cc9f40b40" + integrity sha512-fEHGKCSmUSDPv4uoj8AlD+joPlq3peND+HRYyxFz4KPw4z926S/b8rIuFs2FYJg3BwsxJf6A9/3eIdLaYC+9Dw== + +path-parse@^1.0.6: + version "1.0.7" + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" + integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== + +pbkdf2@^3.0.17: + version "3.1.2" + resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.1.2.tgz#dd822aa0887580e52f1a039dc3eda108efae3075" + integrity sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA== + dependencies: + create-hash "^1.1.2" + create-hmac "^1.1.4" + ripemd160 "^2.0.1" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +picomatch@^2.0.4, picomatch@^2.2.1: + version "2.3.1" + resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" + integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== + +prelude-ls@~1.1.2: + version "1.1.2" + resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.1.2.tgz#21932a549f5e52ffd9a827f570e04be62a97da54" + integrity sha512-ESF23V4SKG6lVSGZgYNpbsiaAkdab6ZgOxe52p7+Kid3W3u3bxR4Vfd/o21dmN7jSt0IwgZ4v5MUd26FEtXE9w== + +prettier-plugin-solidity@^1.0.0-beta.19: + version "1.1.1" + resolved "https://registry.yarnpkg.com/prettier-plugin-solidity/-/prettier-plugin-solidity-1.1.1.tgz#4d3375b85f97812ffcbe48d5a8b3fe914d69c91f" + integrity sha512-uD24KO26tAHF+zMN2nt1OUzfknzza5AgxjogQQrMLZc7j8xiQrDoNWNeOlfFC0YLTwo12CLD10b9niLyP6AqXg== + dependencies: + "@solidity-parser/parser" "^0.14.5" + semver "^7.3.8" + solidity-comments-extractor "^0.0.7" + +prettier@^1.14.3: + version "1.19.1" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-1.19.1.tgz#f7d7f5ff8a9cd872a7be4ca142095956a60797cb" + integrity sha512-s7PoyDv/II1ObgQunCbB9PdLmUcBZcnWOcxDh7O0N/UwDEsHyqkW+Qh28jW+mVuCdx7gLB0BotYI1Y6uI9iyew== + +prettier@^2.3.1, prettier@^2.6.2: + version "2.8.3" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.8.3.tgz#ab697b1d3dd46fb4626fbe2f543afe0cc98d8632" + integrity sha512-tJ/oJ4amDihPoufT5sM0Z1SKEuKay8LfVAMlbbhnnkvt6BUserZylqo2PN+p9KeljLr0OHa2rXHU1T8reeoTrw== + +progress@^2.0.0: + version "2.0.3" + resolved "https://registry.yarnpkg.com/progress/-/progress-2.0.3.tgz#7e8cf8d8f5b8f239c1bc68beb4eb78567d572ef8" + integrity sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA== + +punycode@^2.1.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.0.tgz#f67fa67c94da8f4d0cfff981aee4118064199b8f" + integrity sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA== + +qs@^6.7.0: + version "6.11.0" + resolved "https://registry.yarnpkg.com/qs/-/qs-6.11.0.tgz#fd0d963446f7a65e1367e01abd85429453f0c37a" + integrity sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q== + dependencies: + side-channel "^1.0.4" + +queue-microtask@^1.2.2, queue-microtask@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/queue-microtask/-/queue-microtask-1.2.3.tgz#4929228bbc724dfac43e0efb058caf7b6cfb6243" + integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== + +randombytes@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" + integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== + dependencies: + safe-buffer "^5.1.0" + +raw-body@^2.4.1: + version "2.5.1" + resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.5.1.tgz#fe1b1628b181b700215e5fd42389f98b71392857" + integrity sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig== + dependencies: + bytes "3.1.2" + http-errors "2.0.0" + iconv-lite "0.4.24" + unpipe "1.0.0" + +readable-stream@^3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.0.tgz#337bbda3adc0706bd3e024426a286d4b4b2c9198" + integrity sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA== + dependencies: + inherits "^2.0.3" + string_decoder "^1.1.1" + util-deprecate "^1.0.1" + +readdirp@~3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.6.0.tgz#74a370bd857116e245b29cc97340cd431a02a6c7" + integrity sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA== + dependencies: + picomatch "^2.2.1" + +reduce-flatten@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/reduce-flatten/-/reduce-flatten-2.0.0.tgz#734fd84e65f375d7ca4465c69798c25c9d10ae27" + integrity sha512-EJ4UNY/U1t2P/2k6oqotuX2Cc3T6nxJwsM0N0asT7dhrtH1ltUxDn4NalSYmPE2rCkVpcf/X6R0wDwcFpzhd4w== + +regexpp@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/regexpp/-/regexpp-2.0.1.tgz#8d19d31cf632482b589049f8281f93dbcba4d07f" + integrity sha512-lv0M6+TkDVniA3aD1Eg0DVpfU/booSu7Eev3TDO/mZKHBfVjgCGTV4t4buppESEYDtkArYFOxTJWv6S5C+iaNw== + +require-directory@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" + integrity sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q== + +require-from-string@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/require-from-string/-/require-from-string-2.0.2.tgz#89a7fdd938261267318eafe14f9c32e598c36909" + integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== + +resolve-from@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-3.0.0.tgz#b22c7af7d9d6881bc8b6e653335eebcb0a188748" + integrity sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw== + +resolve-from@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-4.0.0.tgz#4abcd852ad32dd7baabfe9b40e00a36db5f392e6" + integrity sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g== + +resolve@1.17.0: + version "1.17.0" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" + integrity sha512-ic+7JYiV8Vi2yzQGFWOkiZD5Z9z7O2Zhm9XMaTxdJExKasieFCr+yXZ/WmXsckHiKl12ar0y6XiXDx3m4RHn1w== + dependencies: + path-parse "^1.0.6" + +restore-cursor@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/restore-cursor/-/restore-cursor-2.0.0.tgz#9f7ee287f82fd326d4fd162923d62129eee0dfaf" + integrity sha512-6IzJLuGi4+R14vwagDHX+JrXmPVtPpn4mffDJ1UdR7/Edm87fl6yi8mMBIVvFtJaNTUvjughmW4hwLhRG7gC1Q== + dependencies: + onetime "^2.0.0" + signal-exit "^3.0.2" + +rimraf@2.6.3: + version "2.6.3" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.3.tgz#b2d104fe0d8fb27cf9e0a1cda8262dd3833c6cab" + integrity sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA== + dependencies: + glob "^7.1.3" + +rimraf@^2.2.8: + version "2.7.1" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.7.1.tgz#35797f13a7fdadc566142c29d4f07ccad483e3ec" + integrity sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w== + dependencies: + glob "^7.1.3" + +rimraf@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" + integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== + dependencies: + glob "^7.1.3" + +ripemd160@^2.0.0, ripemd160@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/ripemd160/-/ripemd160-2.0.2.tgz#a1c1a6f624751577ba5d07914cbc92850585890c" + integrity sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + +rlp@^2.2.3: + version "2.2.7" + resolved "https://registry.yarnpkg.com/rlp/-/rlp-2.2.7.tgz#33f31c4afac81124ac4b283e2bd4d9720b30beaf" + integrity sha512-d5gdPmgQ0Z+AklL2NVXr/IoSjNZFfTVvQWzL/AM2AOcSzYP2xjlb0AC8YyCLc41MSNf6P6QVtjgPdmVtzb+4lQ== + dependencies: + bn.js "^5.2.0" + +run-async@^2.2.0: + version "2.4.1" + resolved "https://registry.yarnpkg.com/run-async/-/run-async-2.4.1.tgz#8440eccf99ea3e70bd409d49aab88e10c189a455" + integrity sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ== + +run-parallel-limit@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/run-parallel-limit/-/run-parallel-limit-1.1.0.tgz#be80e936f5768623a38a963262d6bef8ff11e7ba" + integrity sha512-jJA7irRNM91jaKc3Hcl1npHsFLOXOoTkPCUL1JEa1R82O2miplXXRaGdjW/KM/98YQWDhJLiSs793CnXfblJUw== + dependencies: + queue-microtask "^1.2.2" + +rustbn.js@~0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/rustbn.js/-/rustbn.js-0.2.0.tgz#8082cb886e707155fd1cb6f23bd591ab8d55d0ca" + integrity sha512-4VlvkRUuCJvr2J6Y0ImW7NvTCriMi7ErOAqWk1y69vAdoNIzCF3yPmgeNzx+RQTLEDFq5sHfscn1MwHxP9hNfA== + +rxjs@^6.4.0: + version "6.6.7" + resolved "https://registry.yarnpkg.com/rxjs/-/rxjs-6.6.7.tgz#90ac018acabf491bf65044235d5863c4dab804c9" + integrity sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ== + dependencies: + tslib "^1.9.0" + +safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.0, safe-buffer@~5.2.0: + version "5.2.1" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +"safer-buffer@>= 2.1.2 < 3": + version "2.1.2" + resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" + integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== + +scrypt-js@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/scrypt-js/-/scrypt-js-3.0.1.tgz#d314a57c2aef69d1ad98a138a21fe9eafa9ee312" + integrity sha512-cdwTTnqPu0Hyvf5in5asVdZocVDTNRmR7XEcJuIzMjJeSHybHl7vpB66AzwTaIg6CLSbtjcxc8fqcySfnTkccA== + +secp256k1@^4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/secp256k1/-/secp256k1-4.0.3.tgz#c4559ecd1b8d3c1827ed2d1b94190d69ce267303" + integrity sha512-NLZVf+ROMxwtEj3Xa562qgv2BK5e2WNmXPiOdVIPLgs6lyTzMvBq0aWTYMI5XCP9jZMVKOcqZLw/Wc4vDkuxhA== + dependencies: + elliptic "^6.5.4" + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + +semver@^5.5.0, semver@^5.5.1: + version "5.7.1" + resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.1.tgz#a954f931aeba508d307bbf069eff0c01c96116f7" + integrity sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ== + +semver@^6.3.0: + version "6.3.0" + resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d" + integrity sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw== + +semver@^7.3.8: + version "7.3.8" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.3.8.tgz#07a78feafb3f7b32347d725e33de7e2a2df67798" + integrity sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A== + dependencies: + lru-cache "^6.0.0" + +serialize-javascript@6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz#efae5d88f45d7924141da8b5c3a7a7e663fefeb8" + integrity sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag== + dependencies: + randombytes "^2.1.0" + +setimmediate@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/setimmediate/-/setimmediate-1.0.5.tgz#290cbb232e306942d7d7ea9b83732ab7856f8285" + integrity sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA== + +setprototypeof@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.2.0.tgz#66c9a24a73f9fc28cbe66b09fed3d33dcaf1b424" + integrity sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw== + +sha.js@^2.4.0, sha.js@^2.4.8: + version "2.4.11" + resolved "https://registry.yarnpkg.com/sha.js/-/sha.js-2.4.11.tgz#37a5cf0b81ecbc6943de109ba2960d1b26584ae7" + integrity sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +shebang-command@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-1.2.0.tgz#44aac65b695b03398968c39f363fee5deafdf1ea" + integrity sha512-EV3L1+UQWGor21OmnvojK36mhg+TyIKDh3iFBKBohr5xeXIhNBcx8oWdgkTEEQ+BEFFYdLRuqMfd5L84N1V5Vg== + dependencies: + shebang-regex "^1.0.0" + +shebang-regex@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-1.0.0.tgz#da42f49740c0b42db2ca9728571cb190c98efea3" + integrity sha512-wpoSFAxys6b2a2wHZ1XpDSgD7N9iVjg29Ph9uV/uaP9Ex/KXlkTZTeddxDPSYQpgvzKLGJke2UU0AzoGCjNIvQ== + +shiki@^0.12.1: + version "0.12.1" + resolved "https://registry.yarnpkg.com/shiki/-/shiki-0.12.1.tgz#26fce51da12d055f479a091a5307470786f300cd" + integrity sha512-aieaV1m349rZINEBkjxh2QbBvFFQOlgqYTNtCal82hHj4dDZ76oMlQIX+C7ryerBTDiga3e5NfH6smjdJ02BbQ== + dependencies: + jsonc-parser "^3.2.0" + vscode-oniguruma "^1.7.0" + vscode-textmate "^8.0.0" + +side-channel@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.0.4.tgz#efce5c8fdc104ee751b25c58d4290011fa5ea2cf" + integrity sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw== + dependencies: + call-bind "^1.0.0" + get-intrinsic "^1.0.2" + object-inspect "^1.9.0" + +signal-exit@^3.0.2: + version "3.0.7" + resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.7.tgz#a9a1767f8af84155114eaabd73f99273c8f59ad9" + integrity sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ== + +slice-ansi@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/slice-ansi/-/slice-ansi-2.1.0.tgz#cacd7693461a637a5788d92a7dd4fba068e81636" + integrity sha512-Qu+VC3EwYLldKa1fCxuuvULvSJOKEgk9pi8dZeCVK7TqBfUNTH4sFkk4joj8afVSfAYgJoSOetjx9QWOJ5mYoQ== + dependencies: + ansi-styles "^3.2.0" + astral-regex "^1.0.0" + is-fullwidth-code-point "^2.0.0" + +solc@0.7.3: + version "0.7.3" + resolved "https://registry.yarnpkg.com/solc/-/solc-0.7.3.tgz#04646961bd867a744f63d2b4e3c0701ffdc7d78a" + integrity sha512-GAsWNAjGzIDg7VxzP6mPjdurby3IkGCjQcM8GFYZT6RyaoUZKmMU6Y7YwG+tFGhv7dwZ8rmR4iwFDrrD99JwqA== + dependencies: + command-exists "^1.2.8" + commander "3.0.2" + follow-redirects "^1.12.1" + fs-extra "^0.30.0" + js-sha3 "0.8.0" + memorystream "^0.3.1" + require-from-string "^2.0.0" + semver "^5.5.0" + tmp "0.0.33" + +solhint@^3.3.7: + version "3.3.8" + resolved "https://registry.yarnpkg.com/solhint/-/solhint-3.3.8.tgz#b1773c881cfaf0b5008c78ad658a69603d3fa051" + integrity sha512-TkYyJ6uUJCaiqRKuhHhFuoAoyco9Ia+RDKhl3usjG/rkaNk8/LdLRla2Xln7MVdBTaPKNAU8ezTRSit50Yy4qw== + dependencies: + "@solidity-parser/parser" "^0.14.5" + ajv "^6.6.1" + antlr4 "4.7.1" + ast-parents "0.0.1" + chalk "^2.4.2" + commander "2.18.0" + cosmiconfig "^5.0.7" + eslint "^5.6.0" + fast-diff "^1.1.2" + glob "^7.1.3" + ignore "^4.0.6" + js-yaml "^3.12.0" + lodash "^4.17.11" + semver "^6.3.0" + optionalDependencies: + prettier "^1.14.3" + +solidity-ast@^0.4.38: + version "0.4.44" + resolved "https://registry.yarnpkg.com/solidity-ast/-/solidity-ast-0.4.44.tgz#dd6732bd65bb1d01777fc537de99cbb3d4e0089d" + integrity sha512-Ct3ppqWS0uTWNYxM2cgruUeWYzqYmeikANsCHgGBnMjAMsqONgqnYrlpifQxNFwXOPHD3vZQLmCjaYnQ+i3eQA== + +solidity-comments-extractor@^0.0.7: + version "0.0.7" + resolved "https://registry.yarnpkg.com/solidity-comments-extractor/-/solidity-comments-extractor-0.0.7.tgz#99d8f1361438f84019795d928b931f4e5c39ca19" + integrity sha512-wciNMLg/Irp8OKGrh3S2tfvZiZ0NEyILfcRCXCD4mp7SgK/i9gzLfhY2hY7VMCQJ3kH9UB9BzNdibIVMchzyYw== + +solidity-docgen@^0.6.0-beta.22: + version "0.6.0-beta.34" + resolved "https://registry.yarnpkg.com/solidity-docgen/-/solidity-docgen-0.6.0-beta.34.tgz#f1766b13ea864ea71b8e727796d30a69ea90014a" + integrity sha512-igdGrkg8gT1jn+B2NwzjEtSf+7NTrSi/jz88zO7MZWgETmcWbXaxgAsQP4BQeC4YFeH0Pie1NsLP7+9qDgvFtA== + dependencies: + handlebars "^4.7.7" + solidity-ast "^0.4.38" + +source-map-support@^0.5.13: + version "0.5.21" + resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.21.tgz#04fe7c7f9e1ed2d662233c28cb2b35b9f63f6e4f" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + +source-map@^0.6.0, source-map@^0.6.1: + version "0.6.1" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" + integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== + +sprintf-js@~1.0.2: + version "1.0.3" + resolved "https://registry.yarnpkg.com/sprintf-js/-/sprintf-js-1.0.3.tgz#04e6926f662895354f3dd015203633b857297e2c" + integrity sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g== + +stacktrace-parser@^0.1.10: + version "0.1.10" + resolved "https://registry.yarnpkg.com/stacktrace-parser/-/stacktrace-parser-0.1.10.tgz#29fb0cae4e0d0b85155879402857a1639eb6051a" + integrity sha512-KJP1OCML99+8fhOHxwwzyWrlUuVX5GQ0ZpJTd1DFXhdkrvg1szxfHhawXUZ3g9TkXORQd4/WG68jMlQZ2p8wlg== + dependencies: + type-fest "^0.7.1" + +statuses@2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/statuses/-/statuses-2.0.1.tgz#55cb000ccf1d48728bd23c685a063998cf1a1b63" + integrity sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ== + +streamsearch@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/streamsearch/-/streamsearch-1.1.0.tgz#404dd1e2247ca94af554e841a8ef0eaa238da764" + integrity sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg== + +string-format@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/string-format/-/string-format-2.0.0.tgz#f2df2e7097440d3b65de31b6d40d54c96eaffb9b" + integrity sha512-bbEs3scLeYNXLecRRuk6uJxdXUSj6le/8rNPHChIJTn2V79aXVTR1EH2OH5zLKKoz0V02fOUKZZcw01pLUShZA== + +string-width@^2.1.0: + version "2.1.1" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-2.1.1.tgz#ab93f27a8dc13d28cac815c462143a6d9012ae9e" + integrity sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw== + dependencies: + is-fullwidth-code-point "^2.0.0" + strip-ansi "^4.0.0" + +string-width@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-3.1.0.tgz#22767be21b62af1081574306f69ac51b62203961" + integrity sha512-vafcv6KjVZKSgz06oM/H6GDBrAtz8vdhQakGjFIvNrHA6y3HCF1CInLy+QLq8dTJPQ1b+KDUqDFctkdRW44e1w== + dependencies: + emoji-regex "^7.0.1" + is-fullwidth-code-point "^2.0.0" + strip-ansi "^5.1.0" + +string-width@^4.1.0, string-width@^4.2.0: + version "4.2.3" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010" + integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.1" + +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + +strip-ansi@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-4.0.0.tgz#a8479022eb1ac368a871389b635262c505ee368f" + integrity sha512-4XaJ2zQdCzROZDivEVIDPkcQn8LMFSa8kj8Gxb/Lnwzv9A8VctNZ+lfivC/sV3ivW8ElJTERXZoPBRrZKkNKow== + dependencies: + ansi-regex "^3.0.0" + +strip-ansi@^5.1.0: + version "5.2.0" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-5.2.0.tgz#8c9a536feb6afc962bdfa5b104a5091c1ad9c0ae" + integrity sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA== + dependencies: + ansi-regex "^4.1.0" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-hex-prefix@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz#0c5f155fef1151373377de9dbb588da05500e36f" + integrity sha512-q8d4ue7JGEiVcypji1bALTos+0pWtyGlivAWyPuTkHzuTCJqrK9sWxYQZUq6Nq3cuyv3bm734IhHvHtGGURU6A== + dependencies: + is-hex-prefixed "1.0.0" + +strip-json-comments@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" + integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== + +strip-json-comments@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-2.0.1.tgz#3c531942e908c2697c0ec344858c286c7ca0a60a" + integrity sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ== + +supports-color@8.1.1: + version "8.1.1" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" + integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== + dependencies: + has-flag "^4.0.0" + +supports-color@^5.3.0: + version "5.5.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" + integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== + dependencies: + has-flag "^3.0.0" + +supports-color@^7.1.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" + integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== + dependencies: + has-flag "^4.0.0" + +table-layout@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/table-layout/-/table-layout-1.0.2.tgz#c4038a1853b0136d63365a734b6931cf4fad4a04" + integrity sha512-qd/R7n5rQTRFi+Zf2sk5XVVd9UQl6ZkduPFC3S7WEGJAmetDTjY3qPN50eSKzwuzEyQKy5TN2TiZdkIjos2L6A== + dependencies: + array-back "^4.0.1" + deep-extend "~0.6.0" + typical "^5.2.0" + wordwrapjs "^4.0.0" + +table@^5.2.3: + version "5.4.6" + resolved "https://registry.yarnpkg.com/table/-/table-5.4.6.tgz#1292d19500ce3f86053b05f0e8e7e4a3bb21079e" + integrity sha512-wmEc8m4fjnob4gt5riFRtTu/6+4rSe12TpAELNSqHMfF3IqnA+CH37USM6/YR3qRZv7e56kAEAtd6nKZaxe0Ug== + dependencies: + ajv "^6.10.2" + lodash "^4.17.14" + slice-ansi "^2.1.0" + string-width "^3.0.0" + +text-table@^0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/text-table/-/text-table-0.2.0.tgz#7f5ee823ae805207c00af2df4a84ec3fcfa570b4" + integrity sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw== + +through@^2.3.6: + version "2.3.8" + resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" + integrity sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg== + +tmp@0.0.33, tmp@^0.0.33: + version "0.0.33" + resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.0.33.tgz#6d34335889768d21b2bcda0aa277ced3b1bfadf9" + integrity sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw== + dependencies: + os-tmpdir "~1.0.2" + +to-regex-range@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== + dependencies: + is-number "^7.0.0" + +toidentifier@1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/toidentifier/-/toidentifier-1.0.1.tgz#3be34321a88a820ed1bd80dfaa33e479fbb8dd35" + integrity sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA== + +ts-command-line-args@^2.2.0: + version "2.4.2" + resolved "https://registry.yarnpkg.com/ts-command-line-args/-/ts-command-line-args-2.4.2.tgz#b4815b23c35f8a0159d4e69e01012d95690bc448" + integrity sha512-mJLQQBOdyD4XI/ZWQY44PIdYde47JhV2xl380O7twPkTQ+Y5vFDHsk8LOeXKuz7dVY5aDCfAzRarNfSqtKOkQQ== + dependencies: + "@morgan-stanley/ts-mocking-bird" "^0.6.2" + chalk "^4.1.0" + command-line-args "^5.1.1" + command-line-usage "^6.1.0" + string-format "^2.0.0" + +ts-essentials@^7.0.1: + version "7.0.3" + resolved "https://registry.yarnpkg.com/ts-essentials/-/ts-essentials-7.0.3.tgz#686fd155a02133eedcc5362dc8b5056cde3e5a38" + integrity sha512-8+gr5+lqO3G84KdiTSMRLtuyJ+nTBVRKuCrK4lidMPdVeEp0uqC875uE5NMcaA7YYMN7XsNiFQuMvasF8HT/xQ== + +ts-node@10.7: + version "10.7.0" + resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.7.0.tgz#35d503d0fab3e2baa672a0e94f4b40653c2463f5" + integrity sha512-TbIGS4xgJoX2i3do417KSaep1uRAW/Lu+WAL2doDHC0D6ummjirVOXU5/7aiZotbQ5p1Zp9tP7U6cYhA0O7M8A== + dependencies: + "@cspotcode/source-map-support" "0.7.0" + "@tsconfig/node10" "^1.0.7" + "@tsconfig/node12" "^1.0.7" + "@tsconfig/node14" "^1.0.0" + "@tsconfig/node16" "^1.0.2" + acorn "^8.4.1" + acorn-walk "^8.1.1" + arg "^4.1.0" + create-require "^1.1.0" + diff "^4.0.1" + make-error "^1.1.1" + v8-compile-cache-lib "^3.0.0" + yn "3.1.1" + +tslib@^1.9.0, tslib@^1.9.3: + version "1.14.1" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" + integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== + +tsort@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/tsort/-/tsort-0.0.1.tgz#e2280f5e817f8bf4275657fd0f9aebd44f5a2786" + integrity sha512-Tyrf5mxF8Ofs1tNoxA13lFeZ2Zrbd6cKbuH3V+MQ5sb6DtBj5FjrXVsRWT8YvNAQTqNoz66dz1WsbigI22aEnw== + +tweetnacl-util@^0.15.1: + version "0.15.1" + resolved "https://registry.yarnpkg.com/tweetnacl-util/-/tweetnacl-util-0.15.1.tgz#b80fcdb5c97bcc508be18c44a4be50f022eea00b" + integrity sha512-RKJBIj8lySrShN4w6i/BonWp2Z/uxwC3h4y7xsRrpP59ZboCd0GpEVsOnMDYLMmKBpYhb5TgHzZXy7wTfYFBRw== + +tweetnacl@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-1.0.3.tgz#ac0af71680458d8a6378d0d0d050ab1407d35596" + integrity sha512-6rt+RN7aOi1nGMyC4Xa5DdYiukl2UWCbcJft7YhxReBGQD7OAM8Pbxw6YMo4r2diNEA8FEmu32YOn9rhaiE5yw== + +type-check@~0.3.2: + version "0.3.2" + resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.3.2.tgz#5884cab512cf1d355e3fb784f30804b2b520db72" + integrity sha512-ZCmOJdvOWDBYJlzAoFkC+Q0+bUyEOS1ltgp1MGU03fqHG+dbi9tBFU2Rd9QKiDZFAYrhPh2JUf7rZRIuHRKtOg== + dependencies: + prelude-ls "~1.1.2" + +type-fest@^0.21.3: + version "0.21.3" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.21.3.tgz#d260a24b0198436e133fa26a524a6d65fa3b2e37" + integrity sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w== + +type-fest@^0.7.1: + version "0.7.1" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.7.1.tgz#8dda65feaf03ed78f0a3f9678f1869147f7c5c48" + integrity sha512-Ne2YiiGN8bmrmJJEuTWTLJR32nh/JdL1+PSicowtNb0WFpn59GK8/lfD61bVtzguz7b3PBt74nxpv/Pw5po5Rg== + +typechain@^8.1.1: + version "8.1.1" + resolved "https://registry.yarnpkg.com/typechain/-/typechain-8.1.1.tgz#9c2e8012c2c4c586536fc18402dcd7034c4ff0bd" + integrity sha512-uF/sUvnXTOVF2FHKhQYnxHk4su4JjZR8vr4mA2mBaRwHTbwh0jIlqARz9XJr1tA0l7afJGvEa1dTSi4zt039LQ== + dependencies: + "@types/prettier" "^2.1.1" + debug "^4.3.1" + fs-extra "^7.0.0" + glob "7.1.7" + js-sha3 "^0.8.0" + lodash "^4.17.15" + mkdirp "^1.0.4" + prettier "^2.3.1" + ts-command-line-args "^2.2.0" + ts-essentials "^7.0.1" + +typedoc@^0.23.10: + version "0.23.24" + resolved "https://registry.yarnpkg.com/typedoc/-/typedoc-0.23.24.tgz#01cf32c09f2c19362e72a9ce1552d6e5b48c4fef" + integrity sha512-bfmy8lNQh+WrPYcJbtjQ6JEEsVl/ce1ZIXyXhyW+a1vFrjO39t6J8sL/d6FfAGrJTc7McCXgk9AanYBSNvLdIA== + dependencies: + lunr "^2.3.9" + marked "^4.2.5" + minimatch "^5.1.2" + shiki "^0.12.1" + +typical@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-4.0.0.tgz#cbeaff3b9d7ae1e2bbfaf5a4e6f11eccfde94fc4" + integrity sha512-VAH4IvQ7BDFYglMd7BPRDfLgxZZX4O4TFcRDA6EN5X7erNJJq+McIEp8np9aVtxrCJ6qx4GTYVfOWNjcqwZgRw== + +typical@^5.2.0: + version "5.2.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-5.2.0.tgz#4daaac4f2b5315460804f0acf6cb69c52bb93066" + integrity sha512-dvdQgNDNJo+8B2uBQoqdb11eUCE1JQXhvjC/CZtgvZseVd5TYMXnq0+vuUemXbd/Se29cTaUuPX3YIc2xgbvIg== + +uglify-js@^3.1.4: + version "3.17.4" + resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.17.4.tgz#61678cf5fa3f5b7eb789bb345df29afb8257c22c" + integrity sha512-T9q82TJI9e/C1TAxYvfb16xO120tMVFZrGA3f9/P4424DNu6ypK103y0GPFVa17yotwSyZW5iYXgjYHkGrJW/g== + +undici@^5.14.0: + version "5.16.0" + resolved "https://registry.yarnpkg.com/undici/-/undici-5.16.0.tgz#6b64f9b890de85489ac6332bd45ca67e4f7d9943" + integrity sha512-KWBOXNv6VX+oJQhchXieUznEmnJMqgXMbs0xxH2t8q/FUAWSJvOSr/rMaZKnX5RIVq7JDn0JbP4BOnKG2SGXLQ== + dependencies: + busboy "^1.6.0" + +universalify@^0.1.0: + version "0.1.2" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66" + integrity sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg== + +unpipe@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" + integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ== + +uri-js@^4.2.2: + version "4.4.1" + resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.4.1.tgz#9b1a52595225859e55f669d928f88c6c57f2a77e" + integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== + dependencies: + punycode "^2.1.0" + +util-deprecate@^1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" + integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== + +uuid@^7.0.3: + version "7.0.3" + resolved "https://registry.yarnpkg.com/uuid/-/uuid-7.0.3.tgz#c5c9f2c8cf25dc0a372c4df1441c41f5bd0c680b" + integrity sha512-DPSke0pXhTZgoF/d+WSt2QaKMCFSfx7QegxEWT+JOuHF5aWrKEn0G+ztjuJg/gG8/ItK+rbPCD/yNv8yyih6Cg== + +uuid@^8.3.2: + version "8.3.2" + resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2" + integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg== + +v8-compile-cache-lib@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf" + integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg== + +vscode-oniguruma@^1.7.0: + version "1.7.0" + resolved "https://registry.yarnpkg.com/vscode-oniguruma/-/vscode-oniguruma-1.7.0.tgz#439bfad8fe71abd7798338d1cd3dc53a8beea94b" + integrity sha512-L9WMGRfrjOhgHSdOYgCt/yRMsXzLDJSL7BPrOZt73gU0iWO4mpqzqQzOz5srxqTvMBaR0XZTSrVWo4j55Rc6cA== + +vscode-textmate@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/vscode-textmate/-/vscode-textmate-8.0.0.tgz#2c7a3b1163ef0441097e0b5d6389cd5504b59e5d" + integrity sha512-AFbieoL7a5LMqcnOF04ji+rpXadgOXnZsxQr//r83kLPr7biP7am3g9zbaZIaBGwBRWeSvoMD4mgPdX3e4NWBg== + +which@^1.2.9: + version "1.3.1" + resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a" + integrity sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ== + dependencies: + isexe "^2.0.0" + +word-wrap@~1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/word-wrap/-/word-wrap-1.2.3.tgz#610636f6b1f703891bd34771ccb17fb93b47079c" + integrity sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ== + +wordwrap@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-1.0.0.tgz#27584810891456a4171c8d0226441ade90cbcaeb" + integrity sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q== + +wordwrapjs@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/wordwrapjs/-/wordwrapjs-4.0.1.tgz#d9790bccfb110a0fc7836b5ebce0937b37a8b98f" + integrity sha512-kKlNACbvHrkpIw6oPeYDSmdCTu2hdMHoyXLTcUKala++lx5Y+wjJ/e474Jqv5abnVmwxw08DiTuHmw69lJGksA== + dependencies: + reduce-flatten "^2.0.0" + typical "^5.2.0" + +workerpool@6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.2.1.tgz#46fc150c17d826b86a008e5a4508656777e9c343" + integrity sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw== + +wrap-ansi@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" + integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + +wrappy@1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" + integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== + +write@1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/write/-/write-1.0.3.tgz#0800e14523b923a387e415123c865616aae0f5c3" + integrity sha512-/lg70HAjtkUgWPVZhZcm+T4hkL8Zbtp1nFNOn3lRrxnlv50SRBv7cR7RqR+GMsd3hUXy9hWBo4CHTbFTcOYwig== + dependencies: + mkdirp "^0.5.1" + +ws@^7.4.6: + version "7.5.9" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.9.tgz#54fa7db29f4c7cec68b1ddd3a89de099942bb591" + integrity sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q== + +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + +yallist@^3.0.2: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" + integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== + +yallist@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" + integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== + +yargs-parser@20.2.4: + version "20.2.4" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" + integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== + +yargs-parser@^20.2.2: + version "20.2.9" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" + integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== + +yargs-unparser@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" + integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== + dependencies: + camelcase "^6.0.0" + decamelize "^4.0.0" + flat "^5.0.2" + is-plain-obj "^2.1.0" + +yargs@16.2.0: + version "16.2.0" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" + integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== + dependencies: + cliui "^7.0.2" + escalade "^3.1.1" + get-caller-file "^2.0.5" + require-directory "^2.1.1" + string-width "^4.2.0" + y18n "^5.0.5" + yargs-parser "^20.2.2" + +yn@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50" + integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q== + +yocto-queue@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" + integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== From ee1ce703a2f1b32cf05a17c66e1701ecaee07229 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 17:03:38 -0500 Subject: [PATCH 02/42] feat(world): add core tables --- packages/world/src/World.sol | 26 +++++++ packages/world/src/schemas/AddressArray.sol | 6 +- .../world/src/schemas/AddressToBytes32.sol | 65 ++++++++++++++++ packages/world/src/schemas/Bool.sol | 66 ++++++++++++++++ packages/world/src/schemas/RouteAccess.sol | 75 ++++++++++++++++++ packages/world/src/schemas/String.sol | 66 ++++++++++++++++ packages/world/src/schemas/System.sol | 77 +++++++++++++++++++ packages/world/src/tables/OwnerTable.sol | 39 ++++++++++ .../world/src/tables/RouteAccessTable.sol | 47 +++++++++++ packages/world/src/tables/RouteTable.sol | 39 ++++++++++ .../world/src/tables/SystemRouteTable.sol | 39 ++++++++++ packages/world/src/tables/SystemTable.sol | 43 +++++++++++ packages/world/test/System.t.sol | 25 ++++++ packages/world/test/World.t.sol | 22 ------ 14 files changed, 611 insertions(+), 24 deletions(-) create mode 100644 packages/world/src/schemas/AddressToBytes32.sol create mode 100644 packages/world/src/schemas/Bool.sol create mode 100644 packages/world/src/schemas/RouteAccess.sol create mode 100644 packages/world/src/schemas/String.sol create mode 100644 packages/world/src/schemas/System.sol create mode 100644 packages/world/src/tables/OwnerTable.sol create mode 100644 packages/world/src/tables/RouteAccessTable.sol create mode 100644 packages/world/src/tables/RouteTable.sol create mode 100644 packages/world/src/tables/SystemRouteTable.sol create mode 100644 packages/world/src/tables/SystemTable.sol create mode 100644 packages/world/test/System.t.sol delete mode 100644 packages/world/test/World.t.sol diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index a77b08a01f..f59164c58d 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -2,3 +2,29 @@ pragma solidity >=0.8.0; contract World {} + +// RouteKey: [routeId] +struct RouteSchema { + string preImage; +} + +// RouteAccessKey: [routeId, caller] +struct RouteAccessSchema { + bool access; +} + +// OwnerKey: [owned] +struct OwnerSchema { + address owner; +} + +// SystemKey: [routeId] +struct SystemSchema { + bool openAccess; + address system; +} + +// SystemToRouteKey: [systemAddress] +struct SystemToRouteSchema { + bytes32 routeId; +} diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index 63b20fad7a..e1b4ab8546 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -7,6 +7,8 @@ import { StoreSwitch } from "store/StoreSwitch.sol"; import { StoreCore } from "store/StoreCore.sol"; import { SchemaType } from "store/Types.sol"; import { Bytes } from "store/Bytes.sol"; +import { SliceLib } from "store/Slice.sol"; +import { EncodeArray } from "store/tightcoder/EncodeArray.sol"; import { Schema, SchemaLib } from "store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; @@ -39,7 +41,7 @@ library AddressArraySchemaLib { bytes32 key, address[] memory addresses ) internal { - bytes memory data = Bytes.from(addresses); + bytes memory data = EncodeArray.encode(addresses); bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; StoreSwitch.setField(tableId, keyTuple, 0, data); @@ -81,6 +83,6 @@ library AddressArraySchemaLib { function decode(bytes memory blob) internal pure returns (address[] memory addresses) { if (blob.length == 0) return new address[](0); - return Bytes.toAddressArray(Bytes.slice(blob, 32, blob.length - 32)); + SliceLib.getSubslice(blob, 32).toAddressArray(); } } diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol new file mode 100644 index 0000000000..f43979996b --- /dev/null +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -0,0 +1,65 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; + +// -- User defined schema and tableId -- +struct AddressToBytes32Schema { + bytes32 value; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library AddressToBytes32SchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.Bytes32); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + address key, + bytes32 value + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = bytes20(key); + StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(value)); + } + + /** Get the table's data */ + function get(bytes32 tableId, address key) internal view returns (bytes32) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = bytes20(key); + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return bytes32(blob); + } + + function get( + bytes32 tableId, + IStore store, + address key + ) internal view returns (bytes32) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = bytes20(key); + bytes memory blob = store.getRecord(tableId, keyTuple); + return bytes32(blob); + } +} diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol new file mode 100644 index 0000000000..b9bd7b0dc4 --- /dev/null +++ b/packages/world/src/schemas/Bool.sol @@ -0,0 +1,66 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { SliceLib } from "store/Slice.sol"; + +// -- User defined schema and tableId -- +struct BoolSchema { + bool value; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library BoolSchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.Bool); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 key, + bool value + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(value)); + } + + /** Get the table's data */ + function get(bytes32 tableId, bytes32 key) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return SliceLib.fromBytes(blob).toBool(); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 key + ) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = store.getRecord(tableId, keyTuple); + return SliceLib.fromBytes(blob).toBool(); + } +} diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol new file mode 100644 index 0000000000..3e1795305c --- /dev/null +++ b/packages/world/src/schemas/RouteAccess.sol @@ -0,0 +1,75 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { SliceLib } from "store/Slice.sol"; + +// -- User defined schema and tableId -- +struct RouteAccessSchema { + bool value; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library RouteAccessSchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.Bool); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 routeId, + address caller, + bool access + ) internal { + bytes32[] memory keyTuple = new bytes32[](2); + keyTuple[0] = routeId; + keyTuple[1] = bytes32(bytes20(caller)); + StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(access)); + } + + /** Get the table's data */ + function get( + bytes32 tableId, + bytes32 routeId, + address caller + ) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](2); + keyTuple[0] = routeId; + keyTuple[1] = bytes32(bytes20(caller)); + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return SliceLib.fromBytes(blob).toBool(); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 routeId, + address caller + ) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](2); + keyTuple[0] = routeId; + keyTuple[1] = bytes32(bytes20(caller)); + bytes memory blob = store.getRecord(tableId, keyTuple); + return SliceLib.fromBytes(blob).toBool(); + } +} diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol new file mode 100644 index 0000000000..fd68fb96de --- /dev/null +++ b/packages/world/src/schemas/String.sol @@ -0,0 +1,66 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { SliceLib } from "store/Slice.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; + +// -- User defined schema and tableId -- +struct StringSchema { + string value; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library StringSchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.String); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 key, + string memory value + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + StoreSwitch.setField(tableId, keyTuple, 0, bytes(value)); + } + + /** Get the table's data */ + function get(bytes32 tableId, bytes32 key) internal view returns (string memory) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + return SliceLib.getSubslice(blob, 32).toString(); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 key + ) internal view returns (string memory) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = store.getRecord(tableId, keyTuple); + return SliceLib.getSubslice(blob, 32).toString(); + } +} diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol new file mode 100644 index 0000000000..e5eb9b6e85 --- /dev/null +++ b/packages/world/src/schemas/System.sol @@ -0,0 +1,77 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Bytes } from "store/Bytes.sol"; +import { Schema, SchemaLib } from "store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { SliceLib } from "store/Slice.sol"; + +// -- User defined schema and tableId -- +struct SystemSchema { + address system; + bool publicAccess; +} + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library SystemSchemaLib { + /** Get the table's schema */ + function getSchema() internal pure returns (Schema schema) { + schema = SchemaLib.encode(SchemaType.Bool, SchemaType.Address); + } + + /** Register the table's schema */ + function registerSchema(bytes32 tableId) internal { + StoreSwitch.registerSchema(tableId, getSchema()); + } + + function registerSchema(bytes32 tableId, IStore store) internal { + store.registerSchema(tableId, getSchema()); + } + + /** Set the table's data */ + function set( + bytes32 tableId, + bytes32 key, + SystemSchema memory value + ) internal { + set(tableId, key, value.system, value.publicAccess); + } + + function set( + bytes32 tableId, + bytes32 key, + address system, + bool publicAccess + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(system, publicAccess)); + } + + function get(bytes32 tableId, bytes32 key) internal view returns (address system, bool publicAccess) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + system = SliceLib.fromBytes(blob).toAddress(); + publicAccess = SliceLib.getSubslice(blob, 20).toBool(); + } + + function get( + bytes32 tableId, + IStore store, + bytes32 key + ) internal view returns (address system, bool publicAccess) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = store.getRecord(tableId, keyTuple); + system = SliceLib.fromBytes(blob).toAddress(); + publicAccess = SliceLib.getSubslice(blob, 20).toBool(); + } +} diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/OwnerTable.sol new file mode 100644 index 0000000000..66668a4f23 --- /dev/null +++ b/packages/world/src/tables/OwnerTable.sol @@ -0,0 +1,39 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Schema } from "store/Schema.sol"; +import { AddressSchemaLib as SchemaLib } from "../schemas/Address.sol"; + +// -- User defined schema and tableId -- +bytes32 constant tableId = keccak256("mud.world.table.address"); + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library OwnerTable { + /** Register the table's schema */ + function registerSchema() internal { + SchemaLib.registerSchema(tableId); + } + + function registerSchema(IStore store) internal { + SchemaLib.registerSchema(tableId, store); + } + + /** Set the table's data */ + function set(bytes32 key, address value) internal { + SchemaLib.set(tableId, key, value); + } + + /** Get the table's data */ + function get(bytes32 key) internal view returns (address) { + return SchemaLib.get(tableId, key); + } + + function get(IStore store, bytes32 key) internal view returns (address) { + return SchemaLib.get(tableId, store, key); + } +} diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol new file mode 100644 index 0000000000..10ace843ca --- /dev/null +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -0,0 +1,47 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Schema } from "store/Schema.sol"; +import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccess.sol"; + +// -- User defined schema and tableId -- +bytes32 constant tableId = keccak256("mud.world.table.routeAccess"); + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library RouteAccessTable { + /** Register the table's schema */ + function registerSchema() internal { + SchemaLib.registerSchema(tableId); + } + + function registerSchema(IStore store) internal { + SchemaLib.registerSchema(tableId, store); + } + + /** Set the table's data */ + function set( + bytes32 routeId, + address caller, + bool access + ) internal { + SchemaLib.set(tableId, routeId, caller, access); + } + + /** Get the table's data */ + function get(bytes32 routeId, address caller) internal view returns (bool) { + return SchemaLib.get(tableId, routeId, caller); + } + + function get( + IStore store, + bytes32 routeId, + address caller + ) internal view returns (bool) { + return SchemaLib.get(tableId, store, routeId, caller); + } +} diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol new file mode 100644 index 0000000000..3b5d0dec75 --- /dev/null +++ b/packages/world/src/tables/RouteTable.sol @@ -0,0 +1,39 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Schema } from "store/Schema.sol"; +import { StringSchemaLib as SchemaLib } from "../schemas/String.sol"; + +// -- User defined schema and tableId -- +bytes32 constant tableId = keccak256("mud.world.table.route"); + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library RouteTable { + /** Register the table's schema */ + function registerSchema() internal { + SchemaLib.registerSchema(tableId); + } + + function registerSchema(IStore store) internal { + SchemaLib.registerSchema(tableId, store); + } + + /** Set the table's data */ + function set(bytes32 key, string memory value) internal { + SchemaLib.set(tableId, key, value); + } + + /** Get the table's data */ + function get(bytes32 key) internal view returns (string memory) { + return SchemaLib.get(tableId, key); + } + + function get(IStore store, bytes32 key) internal view returns (string memory) { + return SchemaLib.get(tableId, store, key); + } +} diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol new file mode 100644 index 0000000000..91f08e94f1 --- /dev/null +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -0,0 +1,39 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Schema } from "store/Schema.sol"; +import { AddressToBytes32SchemaLib as SchemaLib } from "../schemas/AddressToBytes32.sol"; + +// -- User defined schema and tableId -- +bytes32 constant tableId = keccak256("mud.world.table.systemRoute"); + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library SystemRouteTable { + /** Register the table's schema */ + function registerSchema() internal { + SchemaLib.registerSchema(tableId); + } + + function registerSchema(IStore store) internal { + SchemaLib.registerSchema(tableId, store); + } + + /** Set the table's data */ + function set(address system, bytes32 route) internal { + SchemaLib.set(tableId, system, route); + } + + /** Get the table's data */ + function get(address system) internal view returns (bytes32) { + return SchemaLib.get(tableId, system); + } + + function get(IStore store, address system) internal view returns (bytes32) { + return SchemaLib.get(tableId, store, system); + } +} diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol new file mode 100644 index 0000000000..6d824d9798 --- /dev/null +++ b/packages/world/src/tables/SystemTable.sol @@ -0,0 +1,43 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { console } from "forge-std/console.sol"; +import { IStore } from "store/IStore.sol"; +import { SchemaType } from "store/Types.sol"; +import { Schema } from "store/Schema.sol"; +import { SystemSchemaLib as SchemaLib } from "../schemas/System.sol"; + +// -- User defined schema and tableId -- +bytes32 constant tableId = keccak256("mud.world.table.system"); + +// -- Autogenerated library to interact with tables with this schema -- +// TODO: autogenerate + +library SystemTable { + /** Register the table's schema */ + function registerSchema() internal { + SchemaLib.registerSchema(tableId); + } + + function registerSchema(IStore store) internal { + SchemaLib.registerSchema(tableId, store); + } + + /** Set the table's data */ + function set( + bytes32 key, + address system, + bool publicAccess + ) internal { + SchemaLib.set(tableId, key, system, publicAccess); + } + + /** Get the table's data */ + function get(bytes32 key) internal view returns (address, bool) { + return SchemaLib.get(tableId, key); + } + + function get(IStore store, bytes32 key) internal view returns (address, bool) { + return SchemaLib.get(tableId, store, key); + } +} diff --git a/packages/world/test/System.t.sol b/packages/world/test/System.t.sol new file mode 100644 index 0000000000..01b8a4abcf --- /dev/null +++ b/packages/world/test/System.t.sol @@ -0,0 +1,25 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import "forge-std/Test.sol"; +import { World } from "../src/World.sol"; +import { System } from "../src/System.sol"; + +contract TestSystem is System { + function msgSender() public pure returns (address) { + return _msgSender(); + } +} + +contract SystemTest is Test { + TestSystem internal system; + + function setUp() public { + system = new TestSystem(); + } + + function testCallSystem() public { + (, bytes memory data) = address(system).call(abi.encodeWithSignature("msgSender()", address(this))); + assertEq(address(uint160(uint256(bytes32(data)))), address(this)); + } +} diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol deleted file mode 100644 index fcc0f96aa8..0000000000 --- a/packages/world/test/World.t.sol +++ /dev/null @@ -1,22 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity >=0.8.0; - -import "forge-std/Test.sol"; -import { World } from "../src/World.sol"; -import { System } from "../src/System.sol"; - -contract WorldTestSystem is System { - function msgSender() public pure returns (address) { - return _msgSender(); - } -} - -contract WorldTest is Test { - World internal world; - WorldTestSystem internal system; - - function setUp() public { - world = new World(); - system = new WorldTestSystem(); - } -} From f39c2ce3a192224fae3917392d9027630b49017c Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 17:04:15 -0500 Subject: [PATCH 03/42] feat(store): add more types and overloads --- packages/store/src/Slice.sol | 7 +++++++ packages/store/src/tightcoder/DecodeSlice.sol | 4 ++++ 2 files changed, 11 insertions(+) diff --git a/packages/store/src/Slice.sol b/packages/store/src/Slice.sol index 7bef83bbca..8516ef72db 100644 --- a/packages/store/src/Slice.sol +++ b/packages/store/src/Slice.sol @@ -36,6 +36,13 @@ library SliceLib { return Slice.wrap((_pointer << 128) | (data.length & MASK_LEN)); } + /** + * @dev Subslice a bytes array using the given start index until the end of the array (without copying data) + */ + function getSubslice(bytes memory data, uint256 start) internal pure returns (Slice) { + return getSubslice(data, start, data.length - 1); + } + /** * @dev Subslice a bytes array using the given indexes (without copying data) */ diff --git a/packages/store/src/tightcoder/DecodeSlice.sol b/packages/store/src/tightcoder/DecodeSlice.sol index 260aa668a4..27e3f1ed5c 100644 --- a/packages/store/src/tightcoder/DecodeSlice.sol +++ b/packages/store/src/tightcoder/DecodeSlice.sol @@ -468,6 +468,10 @@ library DecodeSlice { } } + function toString(Slice self) internal view returns (string memory output) { + return string(self.toBytes()); + } + /************************************************************************ * * bytes1 - bytes32 From dad190befc5eae0378d0a0404dfce6730e26b094 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 17:18:07 -0500 Subject: [PATCH 04/42] feat(world): register core tables --- packages/store/src/Store.sol | 42 +++++++++++++++++++ packages/store/src/StoreView.sol | 38 ++--------------- packages/world/src/World.sol | 39 +++++++---------- packages/world/src/schemas/Address.sol | 4 ++ packages/world/src/schemas/AddressArray.sol | 4 ++ .../world/src/schemas/AddressToBytes32.sol | 4 ++ packages/world/src/schemas/Bool.sol | 4 ++ packages/world/src/schemas/RouteAccess.sol | 4 ++ packages/world/src/schemas/String.sol | 4 ++ packages/world/src/schemas/System.sol | 4 ++ packages/world/src/tables/OwnerTable.sol | 4 ++ .../world/src/tables/RouteAccessTable.sol | 4 ++ packages/world/src/tables/RouteTable.sol | 4 ++ .../world/src/tables/SystemRouteTable.sol | 4 ++ packages/world/src/tables/SystemTable.sol | 4 ++ packages/world/test/World.t.sol | 17 ++++++++ 16 files changed, 124 insertions(+), 60 deletions(-) create mode 100644 packages/store/src/Store.sol create mode 100644 packages/world/test/World.t.sol diff --git a/packages/store/src/Store.sol b/packages/store/src/Store.sol new file mode 100644 index 0000000000..b1f6d4dab7 --- /dev/null +++ b/packages/store/src/Store.sol @@ -0,0 +1,42 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import { SchemaType } from "./Types.sol"; +import { IStore, IStoreHook } from "./IStore.sol"; +import { StoreCore } from "./StoreCore.sol"; +import { Schema } from "./Schema.sol"; + +abstract contract Store is IStore { + constructor() { + StoreCore.initialize(); + } + + function getSchema(uint256 table) public view virtual returns (Schema schema) { + schema = StoreCore.getSchema(table); + } + + // Get full record (including full array, load schema from storage) + function getRecord(uint256 table, bytes32[] memory key) public view virtual returns (bytes memory data) { + data = StoreCore.getRecord(table, key); + } + + // Get full record (including full array) + function getRecord( + uint256 table, + bytes32[] memory key, + Schema schema + ) public view virtual returns (bytes memory data) { + data = StoreCore.getRecord(table, key, schema); + } + + // Get partial data at schema index + function getField( + uint256 table, + bytes32[] memory key, + uint8 schemaIndex + ) public view virtual returns (bytes memory data) { + data = StoreCore.getField(table, key, schemaIndex); + } + + function isStore() public view {} +} diff --git a/packages/store/src/StoreView.sol b/packages/store/src/StoreView.sol index 9ae7095b8f..a35375b86e 100644 --- a/packages/store/src/StoreView.sol +++ b/packages/store/src/StoreView.sol @@ -2,22 +2,15 @@ pragma solidity >=0.8.0; import { SchemaType } from "./Types.sol"; -import { IStore, IStoreHook } from "./IStore.sol"; +import { IStoreHook } from "./IStore.sol"; import { StoreCore } from "./StoreCore.sol"; import { Schema } from "./Schema.sol"; +import { Store } from "./Store.sol"; // Not abstract, so that it can be used as a base contract for testing and wherever write access is not needed -contract StoreView is IStore { +contract StoreView is Store { error StoreView_NotImplemented(); - constructor() { - StoreCore.initialize(); - } - - function getSchema(uint256 table) public view virtual returns (Schema schema) { - schema = StoreCore.getSchema(table); - } - function registerSchema(uint256, Schema) public virtual { revert StoreView_NotImplemented(); } @@ -47,29 +40,4 @@ contract StoreView is IStore { function deleteRecord(uint256, bytes32[] memory) public virtual { revert StoreView_NotImplemented(); } - - // Get full record (including full array, load schema from storage) - function getRecord(uint256 table, bytes32[] memory key) public view virtual returns (bytes memory data) { - data = StoreCore.getRecord(table, key); - } - - // Get full record (including full array) - function getRecord( - uint256 table, - bytes32[] memory key, - Schema schema - ) public view virtual returns (bytes memory data) { - data = StoreCore.getRecord(table, key, schema); - } - - // Get partial data at schema index - function getField( - uint256 table, - bytes32[] memory key, - uint8 schemaIndex - ) public view virtual returns (bytes memory data) { - data = StoreCore.getField(table, key, schemaIndex); - } - - function isStore() public view {} } diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index f59164c58d..8353b7de86 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -1,30 +1,19 @@ // SPDX-License-Identifier: MIT pragma solidity >=0.8.0; -contract World {} +import { StoreView } from "store/StoreView.sol"; +import { OwnerTable } from "./tables/OwnerTable.sol"; +import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; +import { RouteTable } from "./tables/RouteTable.sol"; +import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; +import { SystemTable } from "./tables/SystemTable.sol"; -// RouteKey: [routeId] -struct RouteSchema { - string preImage; -} - -// RouteAccessKey: [routeId, caller] -struct RouteAccessSchema { - bool access; -} - -// OwnerKey: [owned] -struct OwnerSchema { - address owner; -} - -// SystemKey: [routeId] -struct SystemSchema { - bool openAccess; - address system; -} - -// SystemToRouteKey: [systemAddress] -struct SystemToRouteSchema { - bytes32 routeId; +contract World is StoreView { + constructor() { + SystemTable.registerSchemaInternal(); + RouteTable.registerSchemaInternal(); + RouteAccessTable.registerSchemaInternal(); + SystemRouteTable.registerSchemaInternal(); + OwnerTable.registerSchemaInternal(); + } } diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/Address.sol index 46584b4a8e..295c585bc7 100644 --- a/packages/world/src/schemas/Address.sol +++ b/packages/world/src/schemas/Address.sol @@ -33,6 +33,10 @@ library AddressSchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index e1b4ab8546..6167b46c1a 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -35,6 +35,10 @@ library AddressArraySchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol index f43979996b..23965dc0ea 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -33,6 +33,10 @@ library AddressToBytes32SchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index b9bd7b0dc4..36ccad8491 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -34,6 +34,10 @@ library BoolSchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index 3e1795305c..e6a1be3e43 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -34,6 +34,10 @@ library RouteAccessSchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index fd68fb96de..5847533ccb 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -34,6 +34,10 @@ library StringSchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index e5eb9b6e85..c872feb7da 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -35,6 +35,10 @@ library SystemSchemaLib { store.registerSchema(tableId, getSchema()); } + function registerSchemaInternal(bytes32 tableId) internal { + StoreCore.registerSchema(tableId, getSchema()); + } + /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/OwnerTable.sol index 66668a4f23..d2f850004d 100644 --- a/packages/world/src/tables/OwnerTable.sol +++ b/packages/world/src/tables/OwnerTable.sol @@ -23,6 +23,10 @@ library OwnerTable { SchemaLib.registerSchema(tableId, store); } + function registerSchemaInternal() internal { + SchemaLib.registerSchemaInternal(tableId); + } + /** Set the table's data */ function set(bytes32 key, address value) internal { SchemaLib.set(tableId, key, value); diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index 10ace843ca..b8d6cfa4f0 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -23,6 +23,10 @@ library RouteAccessTable { SchemaLib.registerSchema(tableId, store); } + function registerSchemaInternal() internal { + SchemaLib.registerSchemaInternal(tableId); + } + /** Set the table's data */ function set( bytes32 routeId, diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 3b5d0dec75..6f64b9b9b5 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -23,6 +23,10 @@ library RouteTable { SchemaLib.registerSchema(tableId, store); } + function registerSchemaInternal() internal { + SchemaLib.registerSchemaInternal(tableId); + } + /** Set the table's data */ function set(bytes32 key, string memory value) internal { SchemaLib.set(tableId, key, value); diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 91f08e94f1..7779b7b739 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -23,6 +23,10 @@ library SystemRouteTable { SchemaLib.registerSchema(tableId, store); } + function registerSchemaInternal() internal { + SchemaLib.registerSchemaInternal(tableId); + } + /** Set the table's data */ function set(address system, bytes32 route) internal { SchemaLib.set(tableId, system, route); diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index 6d824d9798..41ce83acda 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -23,6 +23,10 @@ library SystemTable { SchemaLib.registerSchema(tableId, store); } + function registerSchemaInternal() internal { + SchemaLib.registerSchemaInternal(tableId); + } + /** Set the table's data */ function set( bytes32 key, diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol new file mode 100644 index 0000000000..012c750a80 --- /dev/null +++ b/packages/world/test/World.t.sol @@ -0,0 +1,17 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +import "forge-std/Test.sol"; +import { World } from "../src/World.sol"; + +contract WorldTest is Test { + World world; + + function setUp() public { + world = new World(); + } + + function testIsStore() public view { + world.isStore(); + } +} From ce31edd0db8b361e722c04aa93247f827003ecd0 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 18:39:27 -0500 Subject: [PATCH 05/42] feat(store): allow StoreSwitch usage in constructors --- packages/store/src/StoreSwitch.sol | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/store/src/StoreSwitch.sol b/packages/store/src/StoreSwitch.sol index 594ba54549..fece083bc2 100644 --- a/packages/store/src/StoreSwitch.sol +++ b/packages/store/src/StoreSwitch.sol @@ -23,7 +23,9 @@ library StoreSwitch { assembly { codeSize := extcodesize(address()) } - if (codeSize == 0) revert StoreSwitch_InvalidInsideConstructor(); + + // If the call is from within a constructor, use StoreCore to write to own storage + if (codeSize == 0) return true; // Check whether this contract implements the IStore interface try IStore(address(this)).isStore() { From 9a267f9f298aa1f3958afeaaee323c047a2215fb Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 18:39:54 -0500 Subject: [PATCH 06/42] feat(world): add registerRoute --- packages/world/src/World.sol | 64 +++++++++++++++++-- packages/world/src/schemas/Address.sol | 4 -- packages/world/src/schemas/AddressArray.sol | 4 -- .../world/src/schemas/AddressToBytes32.sol | 4 -- packages/world/src/schemas/Bool.sol | 4 -- packages/world/src/schemas/RouteAccess.sol | 4 -- packages/world/src/schemas/String.sol | 12 ++-- packages/world/src/schemas/System.sol | 4 -- packages/world/src/tables/OwnerTable.sol | 8 +-- .../world/src/tables/RouteAccessTable.sol | 4 -- packages/world/src/tables/RouteTable.sol | 12 ++-- .../world/src/tables/SystemRouteTable.sol | 4 -- packages/world/src/tables/SystemTable.sol | 4 -- packages/world/test/World.t.sol | 35 ++++++++++ 14 files changed, 109 insertions(+), 58 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 8353b7de86..5cc612b6a8 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -1,19 +1,71 @@ // SPDX-License-Identifier: MIT pragma solidity >=0.8.0; +import { console } from "forge-std/console.sol"; import { StoreView } from "store/StoreView.sol"; -import { OwnerTable } from "./tables/OwnerTable.sol"; +import { OwnerTable, tableId as OwnerTableId } from "./tables/OwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; import { SystemTable } from "./tables/SystemTable.sol"; +import { StoreCore } from "store/StoreCore.sol"; + +bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); contract World is StoreView { + error RouteInvalid(string route); + error RouteExists(string route); + constructor() { - SystemTable.registerSchemaInternal(); - RouteTable.registerSchemaInternal(); - RouteAccessTable.registerSchemaInternal(); - SystemRouteTable.registerSchemaInternal(); - OwnerTable.registerSchemaInternal(); + SystemTable.registerSchema(); + RouteTable.registerSchema(); + RouteAccessTable.registerSchema(); + SystemRouteTable.registerSchema(); + OwnerTable.registerSchema(); + + // Register root route and give ownership to msg.sender + RouteTable.set({ routeId: ROOT_ROUTE_ID, route: "" }); // Storing this explicitly to trigger the event for indexers + OwnerTable.set({ key: ROOT_ROUTE_ID, owner: msg.sender }); + RouteAccessTable.set({ routeId: ROOT_ROUTE_ID, caller: msg.sender, access: true }); + } + + /************************************************************************ + * + * REGISTRATION METHODS + * + ************************************************************************/ + + /** + * Register a new route by extending an existing route + */ + function registerRoute(string calldata baseRoute, string calldata subRoute) public returns (bytes32 routeId) { + // Require subroute to be a valid route fragment (ie don't contain any `/`) + if (!_isRouteFragment(subRoute)) revert RouteInvalid(subRoute); + + // Require base route to exist (with a special check for the root route because it's empty and fails the `has` check) + if (!(keccak256(bytes(baseRoute)) == ROOT_ROUTE_ID || RouteTable.has(keccak256(bytes(baseRoute))))) + revert RouteInvalid(baseRoute); + + // Construct the new route + string memory route = string(abi.encodePacked(baseRoute, "/", subRoute)); + routeId = keccak256(bytes(route)); + + // Require route to not exist yet + if (RouteTable.has(routeId)) revert RouteExists(route); + + // Store the route + RouteTable.set({ routeId: routeId, route: route }); + + // Add caller as owner of the new route + OwnerTable.set({ key: routeId, owner: msg.sender }); + + // Give caller access to the route + RouteAccessTable.set({ routeId: routeId, caller: msg.sender, access: true }); } } + +// Require route fragment to end with `/` and not contain any other `/` +function _isRouteFragment(string calldata) pure returns (bool) { + // TODO: implement + return true; +} diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/Address.sol index 295c585bc7..46584b4a8e 100644 --- a/packages/world/src/schemas/Address.sol +++ b/packages/world/src/schemas/Address.sol @@ -33,10 +33,6 @@ library AddressSchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index 6167b46c1a..e1b4ab8546 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -35,10 +35,6 @@ library AddressArraySchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol index 23965dc0ea..f43979996b 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -33,10 +33,6 @@ library AddressToBytes32SchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index 36ccad8491..b9bd7b0dc4 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -34,10 +34,6 @@ library BoolSchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index e6a1be3e43..3e1795305c 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -34,10 +34,6 @@ library RouteAccessSchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index 5847533ccb..3304e124c0 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -34,10 +34,6 @@ library StringSchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, @@ -67,4 +63,12 @@ library StringSchemaLib { bytes memory blob = store.getRecord(tableId, keyTuple); return SliceLib.getSubslice(blob, 32).toString(); } + + function has(bytes32 tableId, bytes32 key) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); + console.log("blob length %s", blob.length); + return blob.length > 0; + } } diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index c872feb7da..e5eb9b6e85 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -35,10 +35,6 @@ library SystemSchemaLib { store.registerSchema(tableId, getSchema()); } - function registerSchemaInternal(bytes32 tableId) internal { - StoreCore.registerSchema(tableId, getSchema()); - } - /** Set the table's data */ function set( bytes32 tableId, diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/OwnerTable.sol index d2f850004d..bb1d795869 100644 --- a/packages/world/src/tables/OwnerTable.sol +++ b/packages/world/src/tables/OwnerTable.sol @@ -23,13 +23,9 @@ library OwnerTable { SchemaLib.registerSchema(tableId, store); } - function registerSchemaInternal() internal { - SchemaLib.registerSchemaInternal(tableId); - } - /** Set the table's data */ - function set(bytes32 key, address value) internal { - SchemaLib.set(tableId, key, value); + function set(bytes32 key, address owner) internal { + SchemaLib.set(tableId, key, owner); } /** Get the table's data */ diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index b8d6cfa4f0..10ace843ca 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -23,10 +23,6 @@ library RouteAccessTable { SchemaLib.registerSchema(tableId, store); } - function registerSchemaInternal() internal { - SchemaLib.registerSchemaInternal(tableId); - } - /** Set the table's data */ function set( bytes32 routeId, diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 6f64b9b9b5..218cd7b549 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -23,13 +23,9 @@ library RouteTable { SchemaLib.registerSchema(tableId, store); } - function registerSchemaInternal() internal { - SchemaLib.registerSchemaInternal(tableId); - } - /** Set the table's data */ - function set(bytes32 key, string memory value) internal { - SchemaLib.set(tableId, key, value); + function set(bytes32 routeId, string memory route) internal { + SchemaLib.set(tableId, routeId, route); } /** Get the table's data */ @@ -40,4 +36,8 @@ library RouteTable { function get(IStore store, bytes32 key) internal view returns (string memory) { return SchemaLib.get(tableId, store, key); } + + function has(bytes32 key) internal view returns (bool) { + return SchemaLib.has(tableId, key); + } } diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 7779b7b739..91f08e94f1 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -23,10 +23,6 @@ library SystemRouteTable { SchemaLib.registerSchema(tableId, store); } - function registerSchemaInternal() internal { - SchemaLib.registerSchemaInternal(tableId); - } - /** Set the table's data */ function set(address system, bytes32 route) internal { SchemaLib.set(tableId, system, route); diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index 41ce83acda..6d824d9798 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -23,10 +23,6 @@ library SystemTable { SchemaLib.registerSchema(tableId, store); } - function registerSchemaInternal() internal { - SchemaLib.registerSchemaInternal(tableId); - } - /** Set the table's data */ function set( bytes32 key, diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 012c750a80..0f1133f0f2 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -3,6 +3,8 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; import { World } from "../src/World.sol"; +import { OwnerTable } from "../src/tables/OwnerTable.sol"; +import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; contract WorldTest is Test { World world; @@ -11,7 +13,40 @@ contract WorldTest is Test { world = new World(); } + function testConstructor() public { + // Owner of root route should be the creator of the World + address rootOwner = OwnerTable.get(world, keccak256("")); + assertEq(rootOwner, address(this)); + } + function testIsStore() public view { world.isStore(); } + + function testRegisterRoute() public { + // Register a new route (by extending the root route) + world.registerRoute("", "test"); + + // Owner of the new route should be the caller of the method + address routeOwner = OwnerTable.get(world, keccak256("/test")); + assertEq(routeOwner, address(this)); + + // The new route should be accessible by the caller + assertTrue(RouteAccessTable.get({ store: world, routeId: keccak256("/test"), caller: address(this) })); + + // The new route should not be accessible by another address + assertFalse(RouteAccessTable.get({ store: world, routeId: keccak256("/test"), caller: address(0x01) })); + + // Expect an error when registering an existing route + vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/test")); + world.registerRoute("", "test"); + + // TODO: Expect an error when registering an invalid route + // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); + // world.registerRoute("", "invalid/route"); + + // Expect an error when extending a route that doesn't exist + vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); + world.registerRoute("/invalid", "test"); + } } From 43b70704967acb9be1b6c073d3f4ae2a4fd70d63 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 19:49:54 -0500 Subject: [PATCH 07/42] feat(world): add registerTable --- packages/world/src/World.sol | 19 ++++++++++++++++- packages/world/src/schemas/String.sol | 1 - packages/world/test/World.t.sol | 30 +++++++++++++++++++++++++++ 3 files changed, 48 insertions(+), 2 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 5cc612b6a8..1d59487ebe 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -3,12 +3,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; import { StoreView } from "store/StoreView.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { Schema } from "store/Schema.sol"; + import { OwnerTable, tableId as OwnerTableId } from "./tables/OwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; import { SystemTable } from "./tables/SystemTable.sol"; -import { StoreCore } from "store/StoreCore.sol"; bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); @@ -62,6 +64,21 @@ contract World is StoreView { // Give caller access to the route RouteAccessTable.set({ routeId: routeId, caller: msg.sender, access: true }); } + + /** + * Register register a table with given schema at the given route + */ + function registerTable( + string calldata baseRoute, + string calldata tableRoute, + Schema schema + ) public returns (bytes32 routeId) { + // Register table route + routeId = registerRoute(baseRoute, tableRoute); + + // StoreCore handles checking for existence + StoreCore.registerSchema(routeId, schema); + } } // Require route fragment to end with `/` and not contain any other `/` diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index 3304e124c0..c6cf004b0a 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -68,7 +68,6 @@ library StringSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - console.log("blob length %s", blob.length); return blob.length > 0; } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 0f1133f0f2..9958847022 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -5,6 +5,7 @@ import "forge-std/Test.sol"; import { World } from "../src/World.sol"; import { OwnerTable } from "../src/tables/OwnerTable.sol"; import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; +import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; contract WorldTest is Test { World world; @@ -49,4 +50,33 @@ contract WorldTest is Test { vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); world.registerRoute("/invalid", "test"); } + + function testRegisterTable() public { + bytes32 tableId = world.registerTable("", "testRouteAccess", RouteAccessSchemaLib.getSchema()); + + // Expect the table to be registered + assertEq(world.getSchema(tableId).unwrap(), RouteAccessSchemaLib.getSchema().unwrap()); + + // Expect the table's route to be owned by the caller + address routeOwner = OwnerTable.get(world, tableId); + assertEq(routeOwner, address(this)); + + // The new table should be accessible by the caller + assertTrue(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(this) })); + + // The new table should not be accessible by another address + assertFalse(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(0x01) })); + + // Expect an error when registering an existing table + vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testRouteAccess")); + world.registerTable("", "testRouteAccess", RouteAccessSchemaLib.getSchema()); + + // TODO: Expect an error when registering an invalid table route + // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); + // world.registerTable("", "invalid/route", RouteAccessSchemaLib.getSchema())); + + // Expect an error when extending a route that doesn't exist + vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); + world.registerTable("/invalid", "test", RouteAccessSchemaLib.getSchema()); + } } From a3f5e68fc7171b7c6c68d8c8027a29d6039de020 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 20:37:00 -0500 Subject: [PATCH 08/42] feat(world): add registerSystem --- packages/world/src/World.sol | 38 ++++++++++++-- .../world/src/schemas/AddressToBytes32.sol | 6 +++ packages/world/src/schemas/System.sol | 2 +- .../world/src/tables/SystemRouteTable.sol | 8 ++- packages/world/src/tables/SystemTable.sol | 12 ++--- packages/world/test/World.t.sol | 52 +++++++++++++++++++ 6 files changed, 106 insertions(+), 12 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 1d59487ebe..ac92e81109 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -11,12 +11,15 @@ import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; import { SystemTable } from "./tables/SystemTable.sol"; +import { System } from "./System.sol"; bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); contract World is StoreView { error RouteInvalid(string route); error RouteExists(string route); + error RouteAccessDenied(string route, address caller); + error SystemExists(address system); constructor() { SystemTable.registerSchema(); @@ -72,12 +75,41 @@ contract World is StoreView { string calldata baseRoute, string calldata tableRoute, Schema schema - ) public returns (bytes32 routeId) { + ) public returns (bytes32 tableRouteId) { // Register table route - routeId = registerRoute(baseRoute, tableRoute); + tableRouteId = registerRoute(baseRoute, tableRoute); // StoreCore handles checking for existence - StoreCore.registerSchema(routeId, schema); + StoreCore.registerSchema(tableRouteId, schema); + } + + /** + * Register a system at the given route + */ + function registerSystem( + string calldata baseRoute, + string calldata systemRoute, + System system, + bool publicAccess + ) public returns (bytes32 systemRouteId) { + // Require the system to not exist yet + if (SystemRouteTable.has(address(system))) revert SystemExists(address(system)); + + // Require the caller to own the base route + bytes32 baseRouteId = keccak256(bytes(baseRoute)); + if (OwnerTable.get(baseRouteId) != msg.sender) revert RouteAccessDenied(baseRoute, msg.sender); + + // Register system route + systemRouteId = registerRoute(baseRoute, systemRoute); + + // Store the system address in the system table + SystemTable.set({ routeId: systemRouteId, system: address(system), publicAccess: publicAccess }); + + // Store the system's route in the SystemToRoute table + SystemRouteTable.set({ system: address(system), routeId: systemRouteId }); + + // Give the system access to its base route + RouteAccessTable.set({ routeId: baseRouteId, caller: address(system), access: true }); } } diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol index f43979996b..d6d792534a 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -62,4 +62,10 @@ library AddressToBytes32SchemaLib { bytes memory blob = store.getRecord(tableId, keyTuple); return bytes32(blob); } + + function has(bytes32 tableId, address key) internal view returns (bool) { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = bytes20(key); + return bytes32(StoreSwitch.getRecord(tableId, keyTuple)) != 0; + } } diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index e5eb9b6e85..66d85ab6d8 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -52,7 +52,7 @@ library SystemSchemaLib { ) internal { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; - StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(system, publicAccess)); + StoreSwitch.setRecord(tableId, keyTuple, abi.encodePacked(system, publicAccess)); } function get(bytes32 tableId, bytes32 key) internal view returns (address system, bool publicAccess) { diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 91f08e94f1..002bfad75f 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -24,8 +24,8 @@ library SystemRouteTable { } /** Set the table's data */ - function set(address system, bytes32 route) internal { - SchemaLib.set(tableId, system, route); + function set(address system, bytes32 routeId) internal { + SchemaLib.set(tableId, system, routeId); } /** Get the table's data */ @@ -36,4 +36,8 @@ library SystemRouteTable { function get(IStore store, address system) internal view returns (bytes32) { return SchemaLib.get(tableId, store, system); } + + function has(address system) internal view returns (bool) { + return SchemaLib.has(tableId, system); + } } diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index 6d824d9798..da7d1f26ea 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -25,19 +25,19 @@ library SystemTable { /** Set the table's data */ function set( - bytes32 key, + bytes32 routeId, address system, bool publicAccess ) internal { - SchemaLib.set(tableId, key, system, publicAccess); + SchemaLib.set(tableId, routeId, system, publicAccess); } /** Get the table's data */ - function get(bytes32 key) internal view returns (address, bool) { - return SchemaLib.get(tableId, key); + function get(bytes32 routeId) internal view returns (address, bool) { + return SchemaLib.get(tableId, routeId); } - function get(IStore store, bytes32 key) internal view returns (address, bool) { - return SchemaLib.get(tableId, store, key); + function get(IStore store, bytes32 routeId) internal view returns (address, bool) { + return SchemaLib.get(tableId, store, routeId); } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 9958847022..ce03ecfb64 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -3,9 +3,11 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; import { World } from "../src/World.sol"; +import { System } from "../src/System.sol"; import { OwnerTable } from "../src/tables/OwnerTable.sol"; import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; +import { SystemTable } from "../src/tables/SystemTable.sol"; contract WorldTest is Test { World world; @@ -79,4 +81,54 @@ contract WorldTest is Test { vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); world.registerTable("/invalid", "test", RouteAccessSchemaLib.getSchema()); } + + function testRegisterSystem() public { + System system = new System(); + bytes32 systemRouteId = world.registerSystem("", "testSystem", system, false); + + // Expect the system to be registered + (address registeredAddress, bool publicAccess) = SystemTable.get(world, systemRouteId); + assertEq(registeredAddress, address(system)); + + // Expect the system route to be owned by the caller + address routeOwner = OwnerTable.get(world, systemRouteId); + assertEq(routeOwner, address(this)); + + // Expect the system to not be publicly accessible + assertFalse(publicAccess); + + // Expect the system to be accessible by the caller + assertTrue(RouteAccessTable.get({ store: world, routeId: systemRouteId, caller: address(this) })); + + // Expect the system to not be accessible by another address + assertFalse(RouteAccessTable.get({ store: world, routeId: systemRouteId, caller: address(0x01) })); + + // Expect the system to have access to its own base route + assertTrue(RouteAccessTable.get({ store: world, routeId: keccak256(bytes("")), caller: address(system) })); + + // Expect an error when registering an existing system + vm.expectRevert(abi.encodeWithSelector(World.SystemExists.selector, address(system))); + world.registerSystem("", "newRoute", system, true); + + // Expect an error when registering a system at an existing route + System newSystem = new System(); + vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testSystem")); + world.registerSystem("", "testSystem", newSystem, true); + + // TODO: Expect an error when registering an invalid system route + // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); + // world.registerSystem("", "invalid/route", new System(), true); + + // Expect an error when extending a route that doesn't exist + System anotherSystem = new System(); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/invalid", address(this))); + world.registerSystem("/invalid", "test", anotherSystem, true); + + // Expect an error when registering a system at a route that is not owned by the caller + System yetAnotherSystem = new System(); + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x01))); + world.registerSystem("", "rootSystem", yetAnotherSystem, true); + vm.stopPrank(); + } } From d0f8e12cf5b8b31c466da408e6e8e6868620b043 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 20:49:36 -0500 Subject: [PATCH 09/42] feat(world): add grantAccess and retractAccess --- packages/world/src/World.sol | 24 +++++++++++++++++++ packages/world/src/schemas/RouteAccess.sol | 11 +++++++++ .../world/src/tables/RouteAccessTable.sol | 4 ++++ packages/world/test/World.t.sol | 8 +++++++ 4 files changed, 47 insertions(+) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index ac92e81109..464e881f4e 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -111,6 +111,30 @@ contract World is StoreView { // Give the system access to its base route RouteAccessTable.set({ routeId: baseRouteId, caller: address(system), access: true }); } + + /** + * Grant access to a given route + */ + function grantAccess(string calldata route, address grantee) public { + // Require the caller to own the route + bytes32 routeId = keccak256(bytes(route)); + if (OwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); + + // Grant access to the given route + RouteAccessTable.set({ routeId: routeId, caller: grantee, access: true }); + } + + /** + * Retract access to a given route + */ + function retractAccess(string calldata route, address grantee) public { + // Require the caller to own the route + bytes32 routeId = keccak256(bytes(route)); + if (OwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); + + // Retract access to the given route + RouteAccessTable.deleteRecord({ routeId: routeId, caller: grantee }); + } } // Require route fragment to end with `/` and not contain any other `/` diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index 3e1795305c..10e36781c5 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -72,4 +72,15 @@ library RouteAccessSchemaLib { bytes memory blob = store.getRecord(tableId, keyTuple); return SliceLib.fromBytes(blob).toBool(); } + + function deleteRecord( + bytes32 tableId, + bytes32 routeId, + address caller + ) internal { + bytes32[] memory keyTuple = new bytes32[](2); + keyTuple[0] = routeId; + keyTuple[1] = bytes32(bytes20(caller)); + StoreSwitch.deleteRecord(tableId, keyTuple); + } } diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index 10ace843ca..719096324e 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -44,4 +44,8 @@ library RouteAccessTable { ) internal view returns (bool) { return SchemaLib.get(tableId, store, routeId, caller); } + + function deleteRecord(bytes32 routeId, address caller) internal { + SchemaLib.deleteRecord(tableId, routeId, caller); + } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index ce03ecfb64..9b86f06c3b 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -131,4 +131,12 @@ contract WorldTest is Test { world.registerSystem("", "rootSystem", yetAnotherSystem, true); vm.stopPrank(); } + + function testGrantAccess() public { + // TODO + } + + function testRetractAccess() public { + // TODO + } } From cdad26db15dd0f058b463737a31c1872cf8ade7e Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 22:06:50 -0500 Subject: [PATCH 10/42] feat(store): change IStore to use calldata --- packages/store/src/IStore.sol | 12 ++++++------ packages/store/src/Store.sol | 6 +++--- packages/store/src/StoreView.sol | 8 ++++---- 3 files changed, 13 insertions(+), 13 deletions(-) diff --git a/packages/store/src/IStore.sol b/packages/store/src/IStore.sol index 430b0f4a90..2ed1535790 100644 --- a/packages/store/src/IStore.sol +++ b/packages/store/src/IStore.sol @@ -16,16 +16,16 @@ interface IStore { // Set full record (including full dynamic data) function setRecord( uint256 table, - bytes32[] memory key, - bytes memory data + bytes32[] calldata key, + bytes calldata data ) external; // Set partial data at schema index function setField( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, uint8 schemaIndex, - bytes memory data + bytes calldata data ) external; // Register hooks to be called when a record or field is set or deleted @@ -40,14 +40,14 @@ interface IStore { // Get full record (including full array) function getRecord( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, Schema schema ) external view returns (bytes memory data); // Get partial data at schema index function getField( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, uint8 schemaIndex ) external view returns (bytes memory data); diff --git a/packages/store/src/Store.sol b/packages/store/src/Store.sol index b1f6d4dab7..09afc3c2a6 100644 --- a/packages/store/src/Store.sol +++ b/packages/store/src/Store.sol @@ -16,14 +16,14 @@ abstract contract Store is IStore { } // Get full record (including full array, load schema from storage) - function getRecord(uint256 table, bytes32[] memory key) public view virtual returns (bytes memory data) { + function getRecord(uint256 table, bytes32[] calldata key) public view virtual returns (bytes memory data) { data = StoreCore.getRecord(table, key); } // Get full record (including full array) function getRecord( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, Schema schema ) public view virtual returns (bytes memory data) { data = StoreCore.getRecord(table, key, schema); @@ -32,7 +32,7 @@ abstract contract Store is IStore { // Get partial data at schema index function getField( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, uint8 schemaIndex ) public view virtual returns (bytes memory data) { data = StoreCore.getField(table, key, schemaIndex); diff --git a/packages/store/src/StoreView.sol b/packages/store/src/StoreView.sol index a35375b86e..478b350647 100644 --- a/packages/store/src/StoreView.sol +++ b/packages/store/src/StoreView.sol @@ -17,8 +17,8 @@ contract StoreView is Store { function setRecord( uint256, - bytes32[] memory, - bytes memory + bytes32[] calldata, + bytes calldata ) public virtual { revert StoreView_NotImplemented(); } @@ -26,9 +26,9 @@ contract StoreView is Store { // Set partial data at schema index function setField( uint256, - bytes32[] memory, + bytes32[] calldata, uint8, - bytes memory + bytes calldata ) public virtual { revert StoreView_NotImplemented(); } From 4e216e0b840d263e83573c5606268ddaa37c9ed3 Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 22:07:34 -0500 Subject: [PATCH 11/42] feat(world): add setRecord with access control based on route --- packages/world/src/World.sol | 47 +++++++++++++++++++++++++++++ packages/world/src/schemas/Bool.sol | 13 +++++++- packages/world/test/World.t.sol | 34 +++++++++++++++++++++ 3 files changed, 93 insertions(+), 1 deletion(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 464e881f4e..a77468c9c4 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -135,6 +135,53 @@ contract World is StoreView { // Retract access to the given route RouteAccessTable.deleteRecord({ routeId: routeId, caller: grantee }); } + + /************************************************************************ + * + * STORE METHODS + * + ************************************************************************/ + + /** + * Write to a table based on a parent route access right. + * We check for access based on `accessRoute`, and write to `accessRoute/tableRoute` + * because access to a route also grants access to all sub routes. + */ + function setRecord( + string calldata accessRoute, + string calldata tableRoute, + bytes32[] calldata key, + bytes calldata data + ) public { + // Check access control based on the `accessRoute` + bytes32 accessRouteId = keccak256(bytes(accessRoute)); + if (!RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender })) + revert RouteAccessDenied(accessRoute, msg.sender); + + // Construct the table route id by concatenating accessRoute and tableRoute + bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, "/", tableRoute)); + + // Set the record + StoreCore.setRecord(tableRouteId, key, data); + } + + /** + * Write to a table based on specific access rights. + * This overload exists to conform with the `IStore` interface. + */ + function setRecord( + bytes32 tableRouteId, + bytes32[] calldata key, + bytes calldata data + ) public override { + // Check access based on the tableRoute + if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + + // Set the record + StoreCore.setRecord(tableRouteId, key, data); + } + + // TODO: add functions for `setField` and `deleteRecord` akin to `setRecord` } // Require route fragment to end with `/` and not contain any other `/` diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index b9bd7b0dc4..376a795a2a 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -42,7 +42,18 @@ library BoolSchemaLib { ) internal { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; - StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(value)); + StoreSwitch.setRecord(tableId, keyTuple, abi.encodePacked(value)); + } + + function set( + bytes32 tableId, + IStore store, + bytes32 key, + bool value + ) internal { + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + store.setRecord(tableId, keyTuple, abi.encodePacked(value)); } /** Get the table's data */ diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 9b86f06c3b..1b3a9281be 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -8,6 +8,7 @@ import { OwnerTable } from "../src/tables/OwnerTable.sol"; import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; import { SystemTable } from "../src/tables/SystemTable.sol"; +import { BoolSchemaLib } from "../src/schemas/Bool.sol"; contract WorldTest is Test { World world; @@ -139,4 +140,37 @@ contract WorldTest is Test { function testRetractAccess() public { // TODO } + + function testSetRecord() public { + // Register a new route + world.registerRoute("", "testSetRecord"); + + // Register a new table + bytes32 tableRouteId = world.registerTable("/testSetRecord", "testTable", BoolSchemaLib.getSchema()); + + // Write data to the table + bytes32 key = keccak256("testKey"); + BoolSchemaLib.set({ store: world, tableId: tableRouteId, key: key, value: true }); + + // Expect the data to be written + assertTrue(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Expect an error when trying to write from an address that doesn't have access + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x01))); + BoolSchemaLib.set({ store: world, tableId: tableRouteId, key: key, value: true }); + vm.stopPrank(); + + // Expect to be able to write via the base route + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + world.setRecord("/testSetRecord", "testTable", keyTuple, abi.encodePacked(false)); + assertFalse(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Expect an error when trying to write from an address that doesn't have access to the base route + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSetRecord", address(0x01))); + world.setRecord("/testSetRecord", "testTable", keyTuple, abi.encodePacked(false)); + vm.stopPrank(); + } } From d1ecc42cc7333a78fa181ff96d072c1e74f8d1ea Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 15 Feb 2023 22:52:14 -0500 Subject: [PATCH 12/42] feat(world): add call entry point --- packages/world/src/World.sol | 97 ++++++++++++++++++++++++++++++--- packages/world/test/World.t.sol | 68 ++++++++++++++++++----- 2 files changed, 142 insertions(+), 23 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index a77468c9c4..817feb083b 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -44,15 +44,15 @@ contract World is StoreView { * Register a new route by extending an existing route */ function registerRoute(string calldata baseRoute, string calldata subRoute) public returns (bytes32 routeId) { - // Require subroute to be a valid route fragment (ie don't contain any `/`) - if (!_isRouteFragment(subRoute)) revert RouteInvalid(subRoute); + // Require subroute to be a valid route fragment (start with `/` and don't contain any further `/`) + if (!_isSingleLevelRoute(subRoute)) revert RouteInvalid(subRoute); // Require base route to exist (with a special check for the root route because it's empty and fails the `has` check) if (!(keccak256(bytes(baseRoute)) == ROOT_ROUTE_ID || RouteTable.has(keccak256(bytes(baseRoute))))) revert RouteInvalid(baseRoute); // Construct the new route - string memory route = string(abi.encodePacked(baseRoute, "/", subRoute)); + string memory route = string(abi.encodePacked(baseRoute, subRoute)); routeId = keccak256(bytes(route)); // Require route to not exist yet @@ -144,12 +144,12 @@ contract World is StoreView { /** * Write to a table based on a parent route access right. - * We check for access based on `accessRoute`, and write to `accessRoute/tableRoute` + * We check for access based on `accessRoute`, and write to `accessRoute/subRoute` * because access to a route also grants access to all sub routes. */ function setRecord( string calldata accessRoute, - string calldata tableRoute, + string calldata subRoute, bytes32[] calldata key, bytes calldata data ) public { @@ -158,8 +158,11 @@ contract World is StoreView { if (!RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender })) revert RouteAccessDenied(accessRoute, msg.sender); + // Require subRoute to be a valid route + if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); + // Construct the table route id by concatenating accessRoute and tableRoute - bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, "/", tableRoute)); + bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); // Set the record StoreCore.setRecord(tableRouteId, key, data); @@ -182,10 +185,88 @@ contract World is StoreView { } // TODO: add functions for `setField` and `deleteRecord` akin to `setRecord` + + /************************************************************************ + * + * SYSTEM CALLS + * + ************************************************************************/ + + /** + * Call a system based on a parent route access right + * We check for access based on `accessRoute`, and execute `accessRoute/subRoute` + * because access to a route also grants access to all sub routes + */ + function call( + string calldata accessRoute, + string memory subRoute, + bytes calldata funcSelectorAndArgs + ) public returns (bytes memory) { + // Check if the system is a public system and get its address + string memory systemRoute = string(abi.encodePacked(accessRoute, subRoute)); + bytes32 systemRouteId = keccak256(bytes(systemRoute)); + (address systemAddress, bool publicAccess) = SystemTable.get(systemRouteId); + + // If the system is not public, check for individual access + if (!publicAccess) { + bytes32 accessRouteId = keccak256(bytes(accessRoute)); + bool access = RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender }); + if (!access) revert RouteAccessDenied(accessRoute, msg.sender); + + // Require subRoute to be a valid route + if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); + } + + // Call the system and forward any return data + return + _call({ + msgSender: msg.sender, + systemAddress: systemAddress, + funcSelectorAndArgs: funcSelectorAndArgs, + delegate: _isSingleLevelRoute(systemRoute) + }); + } + + /** + * Overload for the function above to check access based on the full system route instead of a parent route (better devex for public systems) + */ + function call(string calldata systemRoute, bytes calldata funcSelectorAndArgs) public returns (bytes memory) { + return call(systemRoute, "", funcSelectorAndArgs); + } + + /** + * Internal function to call system with delegatecall/call, without access control + */ + function _call( + address msgSender, + address systemAddress, + bytes calldata funcSelectorAndArgs, + bool delegate + ) internal returns (bytes memory) { + // Append msg.sender to the calldata + bytes memory callData = abi.encodePacked(funcSelectorAndArgs, msgSender); + + // Call the system using `delegatecall` for root systems and `call` for others + (bool success, bytes memory data) = delegate + ? systemAddress.delegatecall(callData) // root system + : systemAddress.call(callData); // non-root system + + // Forward returndata + if (success) return data; + + // Forward error if the call failed + revert("Call failed"); // TODO forward originlal error + } +} + +// A route is a string starting with `/` or an empty string +function _isRoute(string memory) pure returns (bool) { + // TODO: implement + return true; } -// Require route fragment to end with `/` and not contain any other `/` -function _isRouteFragment(string calldata) pure returns (bool) { +// A top level route contains exactly one `/` at the start +function _isSingleLevelRoute(string memory) pure returns (bool) { // TODO: implement return true; } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 1b3a9281be..103a81f8fd 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -10,6 +10,16 @@ import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; import { SystemTable } from "../src/tables/SystemTable.sol"; import { BoolSchemaLib } from "../src/schemas/Bool.sol"; +contract WorldTestSystem is System { + function msgSender() public pure returns (address) { + return _msgSender(); + } + + function execute(bytes32) public pure returns (address) { + return _msgSender(); + } +} + contract WorldTest is Test { World world; @@ -29,7 +39,7 @@ contract WorldTest is Test { function testRegisterRoute() public { // Register a new route (by extending the root route) - world.registerRoute("", "test"); + world.registerRoute("", "/test"); // Owner of the new route should be the caller of the method address routeOwner = OwnerTable.get(world, keccak256("/test")); @@ -43,7 +53,7 @@ contract WorldTest is Test { // Expect an error when registering an existing route vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/test")); - world.registerRoute("", "test"); + world.registerRoute("", "/test"); // TODO: Expect an error when registering an invalid route // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); @@ -51,11 +61,11 @@ contract WorldTest is Test { // Expect an error when extending a route that doesn't exist vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); - world.registerRoute("/invalid", "test"); + world.registerRoute("/invalid", "/test"); } function testRegisterTable() public { - bytes32 tableId = world.registerTable("", "testRouteAccess", RouteAccessSchemaLib.getSchema()); + bytes32 tableId = world.registerTable("", "/testRouteAccess", RouteAccessSchemaLib.getSchema()); // Expect the table to be registered assertEq(world.getSchema(tableId).unwrap(), RouteAccessSchemaLib.getSchema().unwrap()); @@ -72,7 +82,7 @@ contract WorldTest is Test { // Expect an error when registering an existing table vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testRouteAccess")); - world.registerTable("", "testRouteAccess", RouteAccessSchemaLib.getSchema()); + world.registerTable("", "/testRouteAccess", RouteAccessSchemaLib.getSchema()); // TODO: Expect an error when registering an invalid table route // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); @@ -80,12 +90,12 @@ contract WorldTest is Test { // Expect an error when extending a route that doesn't exist vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); - world.registerTable("/invalid", "test", RouteAccessSchemaLib.getSchema()); + world.registerTable("/invalid", "/test", RouteAccessSchemaLib.getSchema()); } function testRegisterSystem() public { System system = new System(); - bytes32 systemRouteId = world.registerSystem("", "testSystem", system, false); + bytes32 systemRouteId = world.registerSystem("", "/testSystem", system, false); // Expect the system to be registered (address registeredAddress, bool publicAccess) = SystemTable.get(world, systemRouteId); @@ -109,12 +119,12 @@ contract WorldTest is Test { // Expect an error when registering an existing system vm.expectRevert(abi.encodeWithSelector(World.SystemExists.selector, address(system))); - world.registerSystem("", "newRoute", system, true); + world.registerSystem("", "/newRoute", system, true); // Expect an error when registering a system at an existing route System newSystem = new System(); vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testSystem")); - world.registerSystem("", "testSystem", newSystem, true); + world.registerSystem("", "/testSystem", newSystem, true); // TODO: Expect an error when registering an invalid system route // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); @@ -123,13 +133,13 @@ contract WorldTest is Test { // Expect an error when extending a route that doesn't exist System anotherSystem = new System(); vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/invalid", address(this))); - world.registerSystem("/invalid", "test", anotherSystem, true); + world.registerSystem("/invalid", "/test", anotherSystem, true); // Expect an error when registering a system at a route that is not owned by the caller System yetAnotherSystem = new System(); vm.startPrank(address(0x01)); vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x01))); - world.registerSystem("", "rootSystem", yetAnotherSystem, true); + world.registerSystem("", "/rootSystem", yetAnotherSystem, true); vm.stopPrank(); } @@ -143,10 +153,10 @@ contract WorldTest is Test { function testSetRecord() public { // Register a new route - world.registerRoute("", "testSetRecord"); + world.registerRoute("", "/testSetRecord"); // Register a new table - bytes32 tableRouteId = world.registerTable("/testSetRecord", "testTable", BoolSchemaLib.getSchema()); + bytes32 tableRouteId = world.registerTable("/testSetRecord", "/testTable", BoolSchemaLib.getSchema()); // Write data to the table bytes32 key = keccak256("testKey"); @@ -164,13 +174,41 @@ contract WorldTest is Test { // Expect to be able to write via the base route bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; - world.setRecord("/testSetRecord", "testTable", keyTuple, abi.encodePacked(false)); + world.setRecord("/testSetRecord", "/testTable", keyTuple, abi.encodePacked(false)); assertFalse(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); // Expect an error when trying to write from an address that doesn't have access to the base route vm.startPrank(address(0x01)); vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSetRecord", address(0x01))); - world.setRecord("/testSetRecord", "testTable", keyTuple, abi.encodePacked(false)); + world.setRecord("/testSetRecord", "/testTable", keyTuple, abi.encodePacked(false)); + vm.stopPrank(); + } + + function testCall() public { + // Register a new system + WorldTestSystem system = new WorldTestSystem(); + world.registerSystem("", "/testSystem", system, false); + + // Call a system function without arguments via the World + bytes memory result = world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.msgSender.selector)); + + // Expect the system to have received the caller's address + assertEq(address(uint160(uint256(bytes32(result)))), address(this)); + + // Call a system function with arguments via the World + result = world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.execute.selector, bytes32(0))); + + // Expect the system to have received the caller's address + assertEq(address(uint160(uint256(bytes32(result)))), address(this)); + + // Expect an error when trying to call from an address that doesn't have access + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSystem", address(0x01))); + world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.msgSender.selector)); vm.stopPrank(); + + // TODO: register a system at a non-root route and expect calling to to work as well } + + // TODO: add a test for systems writing to tables via the World } From b1bda3ecaa3e8301132720a57aaefe7bb79c7a44 Mon Sep 17 00:00:00 2001 From: alvrs Date: Thu, 16 Feb 2023 17:12:40 -0500 Subject: [PATCH 13/42] feat(world): return errors to caller via _call --- packages/world/src/World.sol | 33 +++++++++++++++++++++++---------- 1 file changed, 23 insertions(+), 10 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 817feb083b..40d2462e61 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -246,16 +246,29 @@ contract World is StoreView { // Append msg.sender to the calldata bytes memory callData = abi.encodePacked(funcSelectorAndArgs, msgSender); - // Call the system using `delegatecall` for root systems and `call` for others - (bool success, bytes memory data) = delegate - ? systemAddress.delegatecall(callData) // root system - : systemAddress.call(callData); // non-root system - - // Forward returndata - if (success) return data; - - // Forward error if the call failed - revert("Call failed"); // TODO forward originlal error + assembly { + // execute function call on the system usig `delegatecall` or `call` depending on the `delegate` flag + let result + switch delegate + case 0 { + result := call(gas(), systemAddress, callvalue(), callData, mload(callData), 0, 0) // non-root system + } + default { + result := delegatecall(gas(), systemAddress, callData, mload(callData), 0, 0) // root system + } + + // get any return value + returndatacopy(0, 0, returndatasize()) + + // return any return value or error back to the caller + switch result + case 0 { + revert(0, returndatasize()) + } + default { + return(0, returndatasize()) + } + } } } From d2b54a98512367ab3f18b04a63045c7b18660e3e Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 11:21:39 -0500 Subject: [PATCH 14/42] fix(store): update Store interfaces to use calldata instead of memory --- packages/store/src/World.sol | 8 ++++---- packages/store/test/StoreCore.t.sol | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/packages/store/src/World.sol b/packages/store/src/World.sol index 6c430eeb2c..b189f0101c 100644 --- a/packages/store/src/World.sol +++ b/packages/store/src/World.sol @@ -25,17 +25,17 @@ contract World is StoreView { function setRecord( uint256 table, - bytes32[] memory key, - bytes memory data + bytes32[] calldata key, + bytes calldata data ) public override { StoreCore.setRecord(table, key, data); } function setField( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, uint8 schemaIndex, - bytes memory data + bytes calldata data ) public override { StoreCore.setField(table, key, schemaIndex, data); } diff --git a/packages/store/test/StoreCore.t.sol b/packages/store/test/StoreCore.t.sol index 85db224ae5..e16d4cf8a4 100644 --- a/packages/store/test/StoreCore.t.sol +++ b/packages/store/test/StoreCore.t.sol @@ -28,8 +28,8 @@ contract StoreCoreTest is Test, StoreView { // Expose an external setRecord function for testing purposes of indexers (see testHooks) function setRecord( uint256 table, - bytes32[] memory key, - bytes memory data + bytes32[] calldata key, + bytes calldata data ) public override { StoreCore.setRecord(table, key, data); } @@ -37,9 +37,9 @@ contract StoreCoreTest is Test, StoreView { // Expose an external setField function for testing purposes of indexers (see testHooks) function setField( uint256 table, - bytes32[] memory key, + bytes32[] calldata key, uint8 schemaIndex, - bytes memory data + bytes calldata data ) public override { StoreCore.setField(table, key, schemaIndex, data); } From 177d98d1c7f02cf116fe7dcbbdd5b6df57953293 Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 11:22:07 -0500 Subject: [PATCH 15/42] feat(world): forward error from system calls via World --- packages/world/src/World.sol | 32 +++++-------- packages/world/test/World.t.sol | 82 +++++++++++++++++++++++++++++---- 2 files changed, 85 insertions(+), 29 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 40d2462e61..ab326be0f9 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -246,28 +246,18 @@ contract World is StoreView { // Append msg.sender to the calldata bytes memory callData = abi.encodePacked(funcSelectorAndArgs, msgSender); + // Call the system using `delegatecall` for root systems and `call` for others + (bool success, bytes memory data) = delegate + ? systemAddress.delegatecall(callData) // root system + : systemAddress.call(callData); // non-root system + + // Forward returned data if the call succeeded + if (success) return data; + + // Forward error if the call failed assembly { - // execute function call on the system usig `delegatecall` or `call` depending on the `delegate` flag - let result - switch delegate - case 0 { - result := call(gas(), systemAddress, callvalue(), callData, mload(callData), 0, 0) // non-root system - } - default { - result := delegatecall(gas(), systemAddress, callData, mload(callData), 0, 0) // root system - } - - // get any return value - returndatacopy(0, 0, returndatasize()) - - // return any return value or error back to the caller - switch result - case 0 { - revert(0, returndatasize()) - } - default { - return(0, returndatasize()) - } + // data+32 is a pointer to the error message, mload(data) is the length of the error message + revert(add(data, 0x20), mload(data)) } } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 103a81f8fd..198ee0441b 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -10,13 +10,38 @@ import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; import { SystemTable } from "../src/tables/SystemTable.sol"; import { BoolSchemaLib } from "../src/schemas/Bool.sol"; +struct WorldTestSystemReturn { + address sender; + bytes32 input; +} + contract WorldTestSystem is System { - function msgSender() public pure returns (address) { + error WorldTestSystemError(string err); + + function msgSender() public view returns (address) { + console.log("msgsender", _msgSender()); return _msgSender(); } - function execute(bytes32) public pure returns (address) { - return _msgSender(); + function echo(bytes32 input) public pure returns (WorldTestSystemReturn memory) { + return WorldTestSystemReturn(_msgSender(), input); + } + + function err(string memory input) public pure { + revert WorldTestSystemError(input); + } + + function delegateCallSubSystem(address subSystem, bytes memory funcSelectorAndCalldata) + public + returns (bytes memory) + { + (bool success, bytes memory returndata) = subSystem.delegatecall(funcSelectorAndCalldata); + if (!success) { + assembly { + revert(add(32, returndata), mload(returndata)) + } + } + return returndata; } } @@ -191,24 +216,65 @@ contract WorldTest is Test { // Call a system function without arguments via the World bytes memory result = world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.msgSender.selector)); + // assertEq(result, address(this)); // Expect the system to have received the caller's address assertEq(address(uint160(uint256(bytes32(result)))), address(this)); // Call a system function with arguments via the World - result = world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.execute.selector, bytes32(0))); + result = world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.echo.selector, bytes32(uint256(0x123)))); - // Expect the system to have received the caller's address - assertEq(address(uint160(uint256(bytes32(result)))), address(this)); + // Expect the return data to be decodable as a tuple + (address returnedAddress, bytes32 returnedBytes32) = abi.decode(result, (address, bytes32)); + assertEq(returnedAddress, address(this)); + assertEq(returnedBytes32, bytes32(uint256(0x123))); - // Expect an error when trying to call from an address that doesn't have access + // Expect the return data to be decodable as a tuple + WorldTestSystemReturn memory returnStruct = abi.decode(result, (WorldTestSystemReturn)); + assertEq(returnStruct.sender, address(this)); + assertEq(returnStruct.input, bytes32(uint256(0x123))); + + // Expect an error when trying to call a private system from an address that doesn't have access vm.startPrank(address(0x01)); vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSystem", address(0x01))); world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.msgSender.selector)); vm.stopPrank(); - // TODO: register a system at a non-root route and expect calling to to work as well + // Expect errors from the system to be forwarded + vm.expectRevert(abi.encodeWithSelector(WorldTestSystem.WorldTestSystemError.selector, "test error")); + world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.err.selector, "test error")); + + // Register a system at a subroute + WorldTestSystem subSystem = new WorldTestSystem(); + world.registerSystem("/testSystem", "/testSubSystem", subSystem, false); + + // Call the subsystem via the World (with access to the base route) + returnedAddress = abi.decode( + world.call("/testSystem", "/testSubSystem", abi.encodeWithSelector(WorldTestSystem.msgSender.selector)), + (address) + ); + assertEq(returnedAddress, address(this)); + + // Call the subsystem via delegatecall from the system + // (Note: just for testing purposes, in reality systems can call subsystems directly instead of via two indirections like here) + bytes memory nestedReturndata = world.call( + "/testSystem", + abi.encodeWithSelector( + WorldTestSystem.delegateCallSubSystem.selector, // Function in system + address(subSystem), // Address of subsystem + abi.encodePacked(WorldTestSystem.msgSender.selector, address(this)) // Function in subsystem + ) + ); + + returnedAddress = abi.decode(abi.decode(nestedReturndata, (bytes)), (address)); + assertEq(returnedAddress, address(this), "subsystem returned wrong address"); } // TODO: add a test for systems writing to tables via the World + + function testHashEquality() public { + // bytes32 h1 = keccak256("testHashEquality"); + // bytes32 h2 = keccak256(abi.encodePacked(bytes32("testHashEquality"))); + // assertEq(h1, h2); + } } From a466e62c3c036115747686dc99ab8e49b83a6115 Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 12:55:11 -0500 Subject: [PATCH 16/42] fix(store): update deleteRecord to use calldata --- packages/store/src/StoreView.sol | 2 +- packages/store/test/StoreCore.t.sol | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/store/src/StoreView.sol b/packages/store/src/StoreView.sol index 478b350647..29476c7523 100644 --- a/packages/store/src/StoreView.sol +++ b/packages/store/src/StoreView.sol @@ -37,7 +37,7 @@ contract StoreView is Store { revert StoreView_NotImplemented(); } - function deleteRecord(uint256, bytes32[] memory) public virtual { + function deleteRecord(uint256, bytes32[] calldata) public virtual { revert StoreView_NotImplemented(); } } diff --git a/packages/store/test/StoreCore.t.sol b/packages/store/test/StoreCore.t.sol index e16d4cf8a4..cfe97cecf1 100644 --- a/packages/store/test/StoreCore.t.sol +++ b/packages/store/test/StoreCore.t.sol @@ -45,7 +45,7 @@ contract StoreCoreTest is Test, StoreView { } // Expose an external deleteRecord function for testing purposes of indexers (see testHooks) - function deleteRecord(uint256 table, bytes32[] memory key) public override { + function deleteRecord(uint256 table, bytes32[] calldata key) public override { StoreCore.deleteRecord(table, key); } From 29c15587258d08370b1f00c4c7f8082fabfe987c Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 13:02:05 -0500 Subject: [PATCH 17/42] feat(world): add setField, deleteRecord, _isRoute, _isSingleLevelRoute --- packages/world/src/World.sol | 136 ++++++++++++++++++++++++++++---- packages/world/test/World.t.sol | 76 +++++++++++++++++- 2 files changed, 196 insertions(+), 16 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index ab326be0f9..d042906c9f 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -14,6 +14,7 @@ import { SystemTable } from "./tables/SystemTable.sol"; import { System } from "./System.sol"; bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); +bytes32 constant SINGLE_SLASH = "/"; contract World is StoreView { error RouteInvalid(string route); @@ -143,7 +144,7 @@ contract World is StoreView { ************************************************************************/ /** - * Write to a table based on a parent route access right. + * Write a record in a table based on a parent route access right. * We check for access based on `accessRoute`, and write to `accessRoute/subRoute` * because access to a route also grants access to all sub routes. */ @@ -153,13 +154,9 @@ contract World is StoreView { bytes32[] calldata key, bytes calldata data ) public { - // Check access control based on the `accessRoute` - bytes32 accessRouteId = keccak256(bytes(accessRoute)); - if (!RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender })) - revert RouteAccessDenied(accessRoute, msg.sender); - - // Require subRoute to be a valid route - if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); + // Require access to accessRoute and a valid subRoute + _requireAccess(accessRoute); + _requireValidRoute(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); @@ -169,7 +166,7 @@ contract World is StoreView { } /** - * Write to a table based on specific access rights. + * Write a record in a table based on specific access rights. * This overload exists to conform with the `IStore` interface. */ function setRecord( @@ -184,7 +181,78 @@ contract World is StoreView { StoreCore.setRecord(tableRouteId, key, data); } - // TODO: add functions for `setField` and `deleteRecord` akin to `setRecord` + /** + * Write a field in a table based on a parent route access right. + * We check for access based on `accessRoute`, and write to `accessRoute/subRoute` + * because access to a route also grants access to all sub routes. + */ + function setField( + string calldata accessRoute, + string calldata subRoute, + bytes32[] calldata key, + uint8 schemaIndex, + bytes calldata data + ) public { + // Require access to accessRoute and a valid subRoute + _requireAccess(accessRoute); + _requireValidRoute(subRoute); + + // Construct the table route id by concatenating accessRoute and tableRoute + bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); + + // Set the field + StoreCore.setField(tableRouteId, key, schemaIndex, data); + } + + /** + * Write a field in a table based on specific access rights. + * This overload exists to conform with the `IStore` interface. + */ + function setField( + bytes32 tableRouteId, + bytes32[] calldata key, + uint8 schemaIndex, + bytes calldata data + ) public override { + // Check access based on the tableRoute + if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + + // Set the field + StoreCore.setField(tableRouteId, key, schemaIndex, data); + } + + /** + * Delete a record in a table based on a parent route access right. + * We check for access based on `accessRoute`, and write to `accessRoute/subRoute` + * because access to a route also grants access to all sub routes. + */ + function deleteRecord( + string calldata accessRoute, + string calldata subRoute, + bytes32[] calldata key + ) public { + // Require access to accessRoute and a valid subRoute + _requireAccess(accessRoute); + _requireValidRoute(subRoute); + + // Construct the table route id by concatenating accessRoute and tableRoute + bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); + + // Delete the record + StoreCore.deleteRecord(tableRouteId, key); + } + + /** + * Delete a record in a table based on specific access rights. + * This overload exists to conform with the `IStore` interface. + */ + function deleteRecord(bytes32 tableRouteId, bytes32[] calldata key) public override { + // Check access based on the tableRoute + if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + + // Delete the record + StoreCore.deleteRecord(tableRouteId, key); + } /************************************************************************ * @@ -260,16 +328,54 @@ contract World is StoreView { revert(add(data, 0x20), mload(data)) } } + + /** + * Revert if msg.sender does not have access to accessRoute + */ + function _requireAccess(string calldata accessRoute) internal view { + // Check access control based on the `accessRoute` + bytes32 accessRouteId = keccak256(bytes(accessRoute)); + if (!RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender })) + revert RouteAccessDenied(accessRoute, msg.sender); + } + + /** + * Revert if the route is not valid + */ + function _requireValidRoute(string calldata route) internal pure { + if (!_isRoute(route)) revert RouteInvalid(route); + } } // A route is a string starting with `/` or an empty string -function _isRoute(string memory) pure returns (bool) { - // TODO: implement - return true; +function _isRoute(string memory route) pure returns (bool result) { + assembly { + // If the route is empty, return true + if eq(mload(route), 0) { + result := 1 + } + + // If the first byte is `/` (ascii 0x2f), return true + if eq(byte(0, mload(add(route, 0x20))), 0x2f) { + result := 1 + } + } } // A top level route contains exactly one `/` at the start -function _isSingleLevelRoute(string memory) pure returns (bool) { - // TODO: implement +function _isSingleLevelRoute(string memory route) pure returns (bool result) { + // Verify the route is empty or starts with `/` + if (!_isRoute(route)) return false; + + // Loop through the string and return false if another `/` is found + bytes memory routeBytes = bytes(route); + for (uint256 i = 1; i < routeBytes.length; ) { + if (routeBytes[i] == 0x2f) return false; + unchecked { + i++; + } + } + + // Return true if no `/` was found return true; } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 198ee0441b..335759109d 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -2,7 +2,7 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; -import { World } from "../src/World.sol"; +import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; import { OwnerTable } from "../src/tables/OwnerTable.sol"; import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; @@ -62,6 +62,40 @@ contract WorldTest is Test { world.isStore(); } + function testIsRoute() public { + // !gasreport validate route (empty string) + assertTrue(_isRoute(""), "empty string"); + + // !gasreport validate route (single slash) + assertTrue(_isRoute("/"), "single slash"); + + // !gasreport validate route (single level) + assertTrue(_isRoute("/topLevel"), "single level"); + + // !gasreport validate route (multi level) + assertTrue(_isRoute("/topLevel/subLevel"), "multi level"); + + // !gasreport validate route (no leading slash) + assertFalse(_isRoute("noLeadingSlash"), "no leading slash"); + } + + function testIsSingleLevelRoute() public { + // !gasreport validate single level route (empty string) + assertTrue(_isSingleLevelRoute(""), "empty string"); + + // !gasreport validate single level route (single slash) + assertTrue(_isSingleLevelRoute("/"), "single slash"); + + // !gasreport validate single level route (single level) + assertTrue(_isSingleLevelRoute("/topLevel"), "single level"); + + // !gasreport validate single level route (multi level) + assertFalse(_isSingleLevelRoute("/topLevel/subLevel"), "multi level"); + + // !gasreport validate single level route (no leading slash) + assertFalse(_isSingleLevelRoute("noLeadingSlash"), "no leading slash"); + } + function testRegisterRoute() public { // Register a new route (by extending the root route) world.registerRoute("", "/test"); @@ -209,6 +243,46 @@ contract WorldTest is Test { vm.stopPrank(); } + function testSetField() public { + // Register a new route + world.registerRoute("", "/testSetField"); + + // Register a new table + bytes32 tableRouteId = world.registerTable("/testSetField", "/testTable", BoolSchemaLib.getSchema()); + + bytes32 key = keccak256("testKey"); + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + + // Write data to the table via access route + world.setField("/testSetField", "/testTable", keyTuple, 0, abi.encodePacked(true)); + + // Expect the data to be written + assertTrue(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Write data to the table via direct access + world.setField(tableRouteId, keyTuple, 0, abi.encodePacked(false)); + + // Expect the data to be written + assertFalse(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Expect an error when trying to write from an address that doesn't have access + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSetField", address(0x01))); + world.setField("/testSetField", "/testTable", keyTuple, 0, abi.encodePacked(true)); + vm.stopPrank(); + + // Expect an error when trying to write from an address that doesn't have direct access + vm.startPrank(address(0x02)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x02))); + world.setField(tableRouteId, keyTuple, 0, abi.encodePacked(true)); + vm.stopPrank(); + } + + function testDeleteField() public { + // TODO + } + function testCall() public { // Register a new system WorldTestSystem system = new WorldTestSystem(); From accef115a929fc99467e69966152631d9bf655c7 Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 13:16:24 -0500 Subject: [PATCH 18/42] test(world): add test for deleteRecord --- packages/world/test/World.t.sol | 45 ++++++++++++++++++++++++++++++--- 1 file changed, 42 insertions(+), 3 deletions(-) diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 335759109d..5ae6220c8c 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -19,7 +19,6 @@ contract WorldTestSystem is System { error WorldTestSystemError(string err); function msgSender() public view returns (address) { - console.log("msgsender", _msgSender()); return _msgSender(); } @@ -279,8 +278,48 @@ contract WorldTest is Test { vm.stopPrank(); } - function testDeleteField() public { - // TODO + function testDeleteRecord() public { + // Register a new route + world.registerRoute("", "/testDeleteRecord"); + + // Register a new table + bytes32 tableRouteId = world.registerTable("/testDeleteRecord", "/testTable", BoolSchemaLib.getSchema()); + + bytes32 key = keccak256("testKey"); + bytes32[] memory keyTuple = new bytes32[](1); + keyTuple[0] = key; + + // Write data to the table via the access route and expect it to be written + world.setRecord("/testDeleteRecord", "/testTable", keyTuple, abi.encodePacked(true)); + assertTrue(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Delete the record via the access route and expect it to be deleted + world.deleteRecord("/testDeleteRecord", "/testTable", keyTuple); + assertFalse(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Write data to the table via the access route and expect it to be written + world.setRecord("/testDeleteRecord", "/testTable", keyTuple, abi.encodePacked(true)); + assertTrue(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Delete the record via direct access and expect it to be deleted + world.deleteRecord(tableRouteId, keyTuple); + assertFalse(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Write data to the table via the access route and expect it to be written + world.setRecord("/testDeleteRecord", "/testTable", keyTuple, abi.encodePacked(true)); + assertTrue(BoolSchemaLib.get({ store: world, tableId: tableRouteId, key: key })); + + // Expect an error when trying to delete from an address that doesn't have access + vm.startPrank(address(0x01)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testDeleteRecord", address(0x01))); + world.deleteRecord("/testDeleteRecord", "/testTable", keyTuple); + vm.stopPrank(); + + // Expect an error when trying to delete from an address that doesn't have direct access + vm.startPrank(address(0x02)); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x02))); + world.deleteRecord(tableRouteId, keyTuple); + vm.stopPrank(); } function testCall() public { From 416288df11db09ac393711bb41facbaf7dcabb5f Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 17:08:21 -0500 Subject: [PATCH 19/42] feat(store): rename registerHook to registerStoreHook --- packages/store/src/IStore.sol | 2 +- packages/store/src/Slice.sol | 7 ++++--- packages/store/src/StoreCore.sol | 2 +- packages/store/src/StoreView.sol | 2 +- packages/store/test/StoreCore.t.sol | 4 ++-- 5 files changed, 9 insertions(+), 8 deletions(-) diff --git a/packages/store/src/IStore.sol b/packages/store/src/IStore.sol index 2ed1535790..df00ca4b2c 100644 --- a/packages/store/src/IStore.sol +++ b/packages/store/src/IStore.sol @@ -29,7 +29,7 @@ interface IStore { ) external; // Register hooks to be called when a record or field is set or deleted - function registerHook(uint256 table, IStoreHook hooks) external; + function registerStoreHook(uint256 table, IStoreHook hooks) external; // Set full record (including full dynamic data) function deleteRecord(uint256 table, bytes32[] memory key) external; diff --git a/packages/store/src/Slice.sol b/packages/store/src/Slice.sol index 8516ef72db..4841933be5 100644 --- a/packages/store/src/Slice.sol +++ b/packages/store/src/Slice.sol @@ -18,7 +18,7 @@ using DecodeSlice for Slice global; * @title Static functions for Slice */ library SliceLib { - error Slice_OutOfBounds(); + error Slice_OutOfBounds(bytes data, uint256 start, uint256 end); uint256 constant MASK_LEN = uint256(type(uint128).max); uint256 constant MASK_PTR = uint256(type(uint128).max) << 128; @@ -40,11 +40,12 @@ library SliceLib { * @dev Subslice a bytes array using the given start index until the end of the array (without copying data) */ function getSubslice(bytes memory data, uint256 start) internal pure returns (Slice) { - return getSubslice(data, start, data.length - 1); + return getSubslice(data, start, data.length); } /** * @dev Subslice a bytes array using the given indexes (without copying data) + * The start index is inclusive, the end index is exclusive */ function getSubslice( bytes memory data, @@ -52,7 +53,7 @@ library SliceLib { uint256 end ) internal pure returns (Slice) { // TODO this check helps catch bugs and can eventually be removed - if (!(start <= end && end <= data.length)) revert Slice_OutOfBounds(); + if (!(start <= end && end <= data.length)) revert Slice_OutOfBounds(data, start, end); uint256 _pointer; assembly { diff --git a/packages/store/src/StoreCore.sol b/packages/store/src/StoreCore.sol index 8398103144..5d9aea9d74 100644 --- a/packages/store/src/StoreCore.sol +++ b/packages/store/src/StoreCore.sol @@ -78,7 +78,7 @@ library StoreCore { /* * Register hooks to be called when a record or field is set or deleted */ - function registerHook(uint256 table, IStoreHook hook) external { + function registerStoreHook(uint256 table, IStoreHook hook) external { HooksTable.push(table, address(hook)); } diff --git a/packages/store/src/StoreView.sol b/packages/store/src/StoreView.sol index 29476c7523..5d9fbb35c9 100644 --- a/packages/store/src/StoreView.sol +++ b/packages/store/src/StoreView.sol @@ -33,7 +33,7 @@ contract StoreView is Store { revert StoreView_NotImplemented(); } - function registerHook(uint256, IStoreHook) public virtual { + function registerStoreHook(uint256, IStoreHook) public virtual { revert StoreView_NotImplemented(); } diff --git a/packages/store/test/StoreCore.t.sol b/packages/store/test/StoreCore.t.sol index cfe97cecf1..3bf67d031f 100644 --- a/packages/store/test/StoreCore.t.sol +++ b/packages/store/test/StoreCore.t.sol @@ -539,7 +539,7 @@ contract StoreCoreTest is Test, StoreView { MirrorSubscriber subscriber = new MirrorSubscriber(table, schema); // !gasreport register subscriber - StoreCore.registerHook(table, subscriber); + StoreCore.registerStoreHook(table, subscriber); bytes memory data = abi.encodePacked(bytes16(0x0102030405060708090a0b0c0d0e0f10)); @@ -580,7 +580,7 @@ contract StoreCoreTest is Test, StoreView { MirrorSubscriber subscriber = new MirrorSubscriber(table, schema); // !gasreport register subscriber - StoreCore.registerHook(table, subscriber); + StoreCore.registerStoreHook(table, subscriber); uint32[] memory arrayData = new uint32[](1); arrayData[0] = 0x01020304; From c38bfc4f39d85d1786d4704b80411ce31e54e897 Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 17:09:33 -0500 Subject: [PATCH 20/42] feat(world): add registerTableHook and prepare for registerSystemHook --- packages/world/src/ISystemHook.sol | 10 +++ packages/world/src/World.sol | 103 ++++++++++++++++++++--------- packages/world/test/World.t.sol | 79 +++++++++++++++++++--- 3 files changed, 149 insertions(+), 43 deletions(-) create mode 100644 packages/world/src/ISystemHook.sol diff --git a/packages/world/src/ISystemHook.sol b/packages/world/src/ISystemHook.sol new file mode 100644 index 0000000000..3130ab973f --- /dev/null +++ b/packages/world/src/ISystemHook.sol @@ -0,0 +1,10 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +interface ISystemHook { + function onCallSystem( + address msgSender, + address systemAddress, + bytes memory funcSelectorAndArgs + ) external; +} diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index d042906c9f..2554815a67 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -2,7 +2,7 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { StoreView } from "store/StoreView.sol"; +import { Store, IStoreHook } from "store/Store.sol"; import { StoreCore } from "store/StoreCore.sol"; import { Schema } from "store/Schema.sol"; @@ -12,11 +12,12 @@ import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; import { SystemTable } from "./tables/SystemTable.sol"; import { System } from "./System.sol"; +import { ISystemHook } from "./ISystemHook.sol"; bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); bytes32 constant SINGLE_SLASH = "/"; -contract World is StoreView { +contract World is Store { error RouteInvalid(string route); error RouteExists(string route); error RouteAccessDenied(string route, address caller); @@ -84,6 +85,45 @@ contract World is StoreView { StoreCore.registerSchema(tableRouteId, schema); } + /** + * Register a schema for a given table id + * This overload exists to conform to the Store interface, + * but it requires the caller to register a route using `registerRoute` first + */ + function registerSchema(bytes32 tableId, Schema schema) public override { + // Require caller to own the given tableId + if (OwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); + + // Register the schema + StoreCore.registerSchema(tableId, schema); + } + + /** + * Register a hook for a given table route + */ + function registerTableHook(string calldata tableRoute, IStoreHook hook) public { + registerStoreHook(keccak256(bytes(tableRoute)), hook); + } + + /** + * Register a hook for a given table route id + * This overload exists to conform with the `IStore` interface. + */ + function registerStoreHook(bytes32 tableId, IStoreHook hook) public override { + // Require caller to own the given tableId + if (OwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); + + // Register the hook + StoreCore.registerStoreHook(tableId, hook); + } + + /** + * Register a hook for a given system route + */ + function registerSystemHook(string calldata systemRoute, ISystemHook hook) public { + // TODO + } + /** * Register a system at the given route */ @@ -154,9 +194,11 @@ contract World is StoreView { bytes32[] calldata key, bytes calldata data ) public { - // Require access to accessRoute and a valid subRoute - _requireAccess(accessRoute); - _requireValidRoute(subRoute); + // Require access to accessRoute + if (!_hasAccess(accessRoute, msg.sender)) revert RouteAccessDenied(accessRoute, msg.sender); + + // Require a valid subRoute + if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); @@ -166,16 +208,17 @@ contract World is StoreView { } /** - * Write a record in a table based on specific access rights. + * Write a record in a table based on access right to the table route id. * This overload exists to conform with the `IStore` interface. */ function setRecord( bytes32 tableRouteId, bytes32[] calldata key, bytes calldata data - ) public override { + ) public { // Check access based on the tableRoute - if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) + revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); // Set the record StoreCore.setRecord(tableRouteId, key, data); @@ -193,9 +236,11 @@ contract World is StoreView { uint8 schemaIndex, bytes calldata data ) public { - // Require access to accessRoute and a valid subRoute - _requireAccess(accessRoute); - _requireValidRoute(subRoute); + // Require access to accessRoute + if (!_hasAccess(accessRoute, msg.sender)) revert RouteAccessDenied(accessRoute, msg.sender); + + // Require a valid subRoute + if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); @@ -215,7 +260,7 @@ contract World is StoreView { bytes calldata data ) public override { // Check access based on the tableRoute - if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); // Set the field StoreCore.setField(tableRouteId, key, schemaIndex, data); @@ -231,9 +276,11 @@ contract World is StoreView { string calldata subRoute, bytes32[] calldata key ) public { - // Require access to accessRoute and a valid subRoute - _requireAccess(accessRoute); - _requireValidRoute(subRoute); + // Require access to accessRoute + if (!_hasAccess(accessRoute, msg.sender)) revert RouteAccessDenied(accessRoute, msg.sender); + + // Require a valid subRoute + if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); @@ -248,7 +295,7 @@ contract World is StoreView { */ function deleteRecord(bytes32 tableRouteId, bytes32[] calldata key) public override { // Check access based on the tableRoute - if (!RouteAccessTable.get({ routeId: tableRouteId, caller: msg.sender })) revert RouteAccessDenied("", msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); // Delete the record StoreCore.deleteRecord(tableRouteId, key); @@ -277,11 +324,10 @@ contract World is StoreView { // If the system is not public, check for individual access if (!publicAccess) { - bytes32 accessRouteId = keccak256(bytes(accessRoute)); - bool access = RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender }); - if (!access) revert RouteAccessDenied(accessRoute, msg.sender); + // Require access to accessRoute + if (!_hasAccess(accessRoute, msg.sender)) revert RouteAccessDenied(accessRoute, msg.sender); - // Require subRoute to be a valid route + // Require a valid subRoute if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); } @@ -329,21 +375,12 @@ contract World is StoreView { } } - /** - * Revert if msg.sender does not have access to accessRoute - */ - function _requireAccess(string calldata accessRoute) internal view { - // Check access control based on the `accessRoute` - bytes32 accessRouteId = keccak256(bytes(accessRoute)); - if (!RouteAccessTable.get({ routeId: accessRouteId, caller: msg.sender })) - revert RouteAccessDenied(accessRoute, msg.sender); + function _hasAccess(string calldata route, address caller) internal view returns (bool) { + return _hasAccess(keccak256(bytes(route)), caller); } - /** - * Revert if the route is not valid - */ - function _requireValidRoute(string calldata route) internal pure { - if (!_isRoute(route)) revert RouteInvalid(route); + function _hasAccess(bytes32 routeId, address caller) internal view returns (bool) { + return RouteAccessTable.get(routeId, caller); } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 5ae6220c8c..bf457ad115 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -2,6 +2,8 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; +import { IStoreHook } from "store/IStore.sol"; + import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; import { OwnerTable } from "../src/tables/OwnerTable.sol"; @@ -18,7 +20,7 @@ struct WorldTestSystemReturn { contract WorldTestSystem is System { error WorldTestSystemError(string err); - function msgSender() public view returns (address) { + function msgSender() public pure returns (address) { return _msgSender(); } @@ -44,7 +46,33 @@ contract WorldTestSystem is System { } } +contract WorldTestTableHook is IStoreHook { + event HookCalled(bytes data); + + function onSetRecord( + bytes32 table, + bytes32[] memory key, + bytes memory data + ) public { + emit HookCalled(abi.encode(table, key, data)); + } + + function onSetField( + bytes32 table, + bytes32[] memory key, + uint8 schemaIndex, + bytes memory data + ) public { + emit HookCalled(abi.encode(table, key, schemaIndex, data)); + } + + function onDeleteRecord(bytes32 table, bytes32[] memory key) public { + emit HookCalled(abi.encode(table, key)); + } +} + contract WorldTest is Test { + event HookCalled(bytes data); World world; function setUp() public { @@ -93,6 +121,9 @@ contract WorldTest is Test { // !gasreport validate single level route (no leading slash) assertFalse(_isSingleLevelRoute("noLeadingSlash"), "no leading slash"); + + // !gasreport validate single level route (no leading slash but contains slash) + assertFalse(_isSingleLevelRoute("noLeadingSlash/butContainsSlash"), "no leading slash"); } function testRegisterRoute() public { @@ -142,9 +173,9 @@ contract WorldTest is Test { vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testRouteAccess")); world.registerTable("", "/testRouteAccess", RouteAccessSchemaLib.getSchema()); - // TODO: Expect an error when registering an invalid table route - // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); - // world.registerTable("", "invalid/route", RouteAccessSchemaLib.getSchema())); + // Expect an error when registering an invalid table route + vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); + world.registerTable("", "invalid/route", RouteAccessSchemaLib.getSchema()); // Expect an error when extending a route that doesn't exist vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "/invalid")); @@ -184,9 +215,10 @@ contract WorldTest is Test { vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testSystem")); world.registerSystem("", "/testSystem", newSystem, true); - // TODO: Expect an error when registering an invalid system route - // vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); - // world.registerSystem("", "invalid/route", new System(), true); + // Expect an error when registering an invalid system route + System oneMoreSystem = new System(); + vm.expectRevert(abi.encodeWithSelector(World.RouteInvalid.selector, "invalid/route")); + world.registerSystem("", "invalid/route", oneMoreSystem, true); // Expect an error when extending a route that doesn't exist System anotherSystem = new System(); @@ -225,7 +257,9 @@ contract WorldTest is Test { // Expect an error when trying to write from an address that doesn't have access vm.startPrank(address(0x01)); - vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x01))); + vm.expectRevert( + abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSetRecord/testTable", address(0x01)) + ); BoolSchemaLib.set({ store: world, tableId: tableRouteId, key: key, value: true }); vm.stopPrank(); @@ -273,7 +307,7 @@ contract WorldTest is Test { // Expect an error when trying to write from an address that doesn't have direct access vm.startPrank(address(0x02)); - vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x02))); + vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testSetField/testTable", address(0x02))); world.setField(tableRouteId, keyTuple, 0, abi.encodePacked(true)); vm.stopPrank(); } @@ -317,7 +351,9 @@ contract WorldTest is Test { // Expect an error when trying to delete from an address that doesn't have direct access vm.startPrank(address(0x02)); - vm.expectRevert(abi.encodeWithSelector(World.RouteAccessDenied.selector, "", address(0x02))); + vm.expectRevert( + abi.encodeWithSelector(World.RouteAccessDenied.selector, "/testDeleteRecord/testTable", address(0x02)) + ); world.deleteRecord(tableRouteId, keyTuple); vm.stopPrank(); } @@ -383,6 +419,29 @@ contract WorldTest is Test { assertEq(returnedAddress, address(this), "subsystem returned wrong address"); } + function testRegisterTableHook() public { + // Register a new table + bytes32 tableId = world.registerTable("", "/testTable", BoolSchemaLib.getSchema()); + + // Register a new hook + IStoreHook tableHook = new WorldTestTableHook(); + world.registerTableHook("/testTable", tableHook); + + // Prepare data to write to the table + bytes32[] memory key = new bytes32[](1); + key[0] = "someKey"; + bytes memory value = abi.encodePacked(true); + + // Expect the hook to be notified when a record is written + vm.expectEmit(true, true, true, true); + emit HookCalled(abi.encode(tableId, key, value)); + world.setRecord(tableId, key, value); + } + + function testRegisterSystemHook() public view { + // TODO + } + // TODO: add a test for systems writing to tables via the World function testHashEquality() public { From 2cc28af5bccf6791477bd0ad322a3f9f9a08b4fd Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 17:49:06 -0500 Subject: [PATCH 21/42] refactor(world): change tableId type from bytes32 to uint256 --- packages/world/src/World.sol | 36 ++++++++++--------- packages/world/src/schemas/Address.sol | 12 +++---- packages/world/src/schemas/AddressArray.sol | 14 ++++---- .../world/src/schemas/AddressToBytes32.sol | 14 ++++---- packages/world/src/schemas/Bool.sol | 14 ++++---- packages/world/src/schemas/RouteAccess.sol | 14 ++++---- packages/world/src/schemas/String.sol | 14 ++++---- packages/world/src/schemas/System.sol | 14 ++++---- packages/world/src/tables/OwnerTable.sol | 2 +- .../world/src/tables/RouteAccessTable.sol | 2 +- packages/world/src/tables/RouteTable.sol | 2 +- .../world/src/tables/SystemRouteTable.sol | 2 +- packages/world/src/tables/SystemTable.sol | 2 +- packages/world/test/World.t.sol | 22 ++++++------ 14 files changed, 84 insertions(+), 80 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 2554815a67..f932aa9009 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -77,9 +77,9 @@ contract World is Store { string calldata baseRoute, string calldata tableRoute, Schema schema - ) public returns (bytes32 tableRouteId) { + ) public returns (uint256 tableRouteId) { // Register table route - tableRouteId = registerRoute(baseRoute, tableRoute); + tableRouteId = uint256(registerRoute(baseRoute, tableRoute)); // StoreCore handles checking for existence StoreCore.registerSchema(tableRouteId, schema); @@ -90,9 +90,10 @@ contract World is Store { * This overload exists to conform to the Store interface, * but it requires the caller to register a route using `registerRoute` first */ - function registerSchema(bytes32 tableId, Schema schema) public override { + function registerSchema(uint256 tableId, Schema schema) public override { // Require caller to own the given tableId - if (OwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); + if (OwnerTable.get(bytes32(tableId)) != msg.sender) + revert RouteAccessDenied(RouteTable.get(bytes32(tableId)), msg.sender); // Register the schema StoreCore.registerSchema(tableId, schema); @@ -102,16 +103,17 @@ contract World is Store { * Register a hook for a given table route */ function registerTableHook(string calldata tableRoute, IStoreHook hook) public { - registerStoreHook(keccak256(bytes(tableRoute)), hook); + registerStoreHook(uint256(keccak256(bytes(tableRoute))), hook); } /** * Register a hook for a given table route id * This overload exists to conform with the `IStore` interface. */ - function registerStoreHook(bytes32 tableId, IStoreHook hook) public override { + function registerStoreHook(uint256 tableId, IStoreHook hook) public override { // Require caller to own the given tableId - if (OwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); + if (OwnerTable.get(bytes32(tableId)) != msg.sender) + revert RouteAccessDenied(RouteTable.get(bytes32(tableId)), msg.sender); // Register the hook StoreCore.registerStoreHook(tableId, hook); @@ -201,7 +203,7 @@ contract World is Store { if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute - bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); + uint256 tableRouteId = uint256(keccak256(abi.encodePacked(accessRoute, subRoute))); // Set the record StoreCore.setRecord(tableRouteId, key, data); @@ -212,12 +214,12 @@ contract World is Store { * This overload exists to conform with the `IStore` interface. */ function setRecord( - bytes32 tableRouteId, + uint256 tableRouteId, bytes32[] calldata key, bytes calldata data ) public { // Check access based on the tableRoute - if (!_hasAccess(tableRouteId, msg.sender)) + if (!_hasAccess(bytes32(tableRouteId), msg.sender)) revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); // Set the record @@ -243,7 +245,7 @@ contract World is Store { if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute - bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); + uint256 tableRouteId = uint256(keccak256(abi.encodePacked(accessRoute, subRoute))); // Set the field StoreCore.setField(tableRouteId, key, schemaIndex, data); @@ -254,13 +256,14 @@ contract World is Store { * This overload exists to conform with the `IStore` interface. */ function setField( - bytes32 tableRouteId, + uint256 tableRouteId, bytes32[] calldata key, uint8 schemaIndex, bytes calldata data ) public override { // Check access based on the tableRoute - if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); + if (!_hasAccess(bytes32(tableRouteId), msg.sender)) + revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); // Set the field StoreCore.setField(tableRouteId, key, schemaIndex, data); @@ -283,7 +286,7 @@ contract World is Store { if (!_isRoute(subRoute)) revert RouteInvalid(subRoute); // Construct the table route id by concatenating accessRoute and tableRoute - bytes32 tableRouteId = keccak256(abi.encodePacked(accessRoute, subRoute)); + uint256 tableRouteId = uint256(keccak256(abi.encodePacked(accessRoute, subRoute))); // Delete the record StoreCore.deleteRecord(tableRouteId, key); @@ -293,9 +296,10 @@ contract World is Store { * Delete a record in a table based on specific access rights. * This overload exists to conform with the `IStore` interface. */ - function deleteRecord(bytes32 tableRouteId, bytes32[] calldata key) public override { + function deleteRecord(uint256 tableRouteId, bytes32[] calldata key) public override { // Check access based on the tableRoute - if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); + if (!_hasAccess(bytes32(tableRouteId), msg.sender)) + revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); // Delete the record StoreCore.deleteRecord(tableRouteId, key); diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/Address.sol index 46584b4a8e..2a64eec899 100644 --- a/packages/world/src/schemas/Address.sol +++ b/packages/world/src/schemas/Address.sol @@ -21,21 +21,21 @@ struct AddressSchema { library AddressSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.Address); + schema = SchemaLib.encode(SchemaType.ADDRESS); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 key, address addr ) internal { @@ -45,7 +45,7 @@ library AddressSchemaLib { } /** Get the table's data */ - function get(bytes32 tableId, bytes32 key) internal view returns (address) { + function get(uint256 tableId, bytes32 key) internal view returns (address) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -53,7 +53,7 @@ library AddressSchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key ) internal view returns (address) { diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index e1b4ab8546..7642e142be 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -23,21 +23,21 @@ struct AddressArraySchema { library AddressArraySchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.AddressArray); + schema = SchemaLib.encode(SchemaType.ADDRESS_ARRAY); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 key, address[] memory addresses ) internal { @@ -52,7 +52,7 @@ library AddressArraySchemaLib { * TODO: this is super inefficient right now, need to add support for pushing to arrays to the store core library to avoid reading/writing the entire array */ function push( - bytes32 tableId, + uint256 tableId, bytes32 key, address addr ) internal { @@ -63,7 +63,7 @@ library AddressArraySchemaLib { } /** Get the table's data */ - function get(bytes32 tableId, bytes32 key) internal view returns (address[] memory addresses) { + function get(uint256 tableId, bytes32 key) internal view returns (address[] memory addresses) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -71,7 +71,7 @@ library AddressArraySchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key ) internal view returns (address[] memory addresses) { diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol index d6d792534a..60f9ad1984 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -21,21 +21,21 @@ struct AddressToBytes32Schema { library AddressToBytes32SchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.Bytes32); + schema = SchemaLib.encode(SchemaType.BYTES32); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, address key, bytes32 value ) internal { @@ -45,7 +45,7 @@ library AddressToBytes32SchemaLib { } /** Get the table's data */ - function get(bytes32 tableId, address key) internal view returns (bytes32) { + function get(uint256 tableId, address key) internal view returns (bytes32) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = bytes20(key); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -53,7 +53,7 @@ library AddressToBytes32SchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, address key ) internal view returns (bytes32) { @@ -63,7 +63,7 @@ library AddressToBytes32SchemaLib { return bytes32(blob); } - function has(bytes32 tableId, address key) internal view returns (bool) { + function has(uint256 tableId, address key) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = bytes20(key); return bytes32(StoreSwitch.getRecord(tableId, keyTuple)) != 0; diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index 376a795a2a..679d2eb41d 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -22,21 +22,21 @@ struct BoolSchema { library BoolSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.Bool); + schema = SchemaLib.encode(SchemaType.BOOL); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 key, bool value ) internal { @@ -46,7 +46,7 @@ library BoolSchemaLib { } function set( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key, bool value @@ -57,7 +57,7 @@ library BoolSchemaLib { } /** Get the table's data */ - function get(bytes32 tableId, bytes32 key) internal view returns (bool) { + function get(uint256 tableId, bytes32 key) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -65,7 +65,7 @@ library BoolSchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key ) internal view returns (bool) { diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index 10e36781c5..bd98123645 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -22,21 +22,21 @@ struct RouteAccessSchema { library RouteAccessSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.Bool); + schema = SchemaLib.encode(SchemaType.BOOL); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 routeId, address caller, bool access @@ -49,7 +49,7 @@ library RouteAccessSchemaLib { /** Get the table's data */ function get( - bytes32 tableId, + uint256 tableId, bytes32 routeId, address caller ) internal view returns (bool) { @@ -61,7 +61,7 @@ library RouteAccessSchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 routeId, address caller @@ -74,7 +74,7 @@ library RouteAccessSchemaLib { } function deleteRecord( - bytes32 tableId, + uint256 tableId, bytes32 routeId, address caller ) internal { diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index c6cf004b0a..1c28e36ec4 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -22,21 +22,21 @@ struct StringSchema { library StringSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.String); + schema = SchemaLib.encode(SchemaType.STRING); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 key, string memory value ) internal { @@ -46,7 +46,7 @@ library StringSchemaLib { } /** Get the table's data */ - function get(bytes32 tableId, bytes32 key) internal view returns (string memory) { + function get(uint256 tableId, bytes32 key) internal view returns (string memory) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -54,7 +54,7 @@ library StringSchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key ) internal view returns (string memory) { @@ -64,7 +64,7 @@ library StringSchemaLib { return SliceLib.getSubslice(blob, 32).toString(); } - function has(bytes32 tableId, bytes32 key) internal view returns (bool) { + function has(uint256 tableId, bytes32 key) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index 66d85ab6d8..ebcdd86bba 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -23,21 +23,21 @@ struct SystemSchema { library SystemSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.Bool, SchemaType.Address); + schema = SchemaLib.encode(SchemaType.BOOL, SchemaType.ADDRESS); } /** Register the table's schema */ - function registerSchema(bytes32 tableId) internal { + function registerSchema(uint256 tableId) internal { StoreSwitch.registerSchema(tableId, getSchema()); } - function registerSchema(bytes32 tableId, IStore store) internal { + function registerSchema(uint256 tableId, IStore store) internal { store.registerSchema(tableId, getSchema()); } /** Set the table's data */ function set( - bytes32 tableId, + uint256 tableId, bytes32 key, SystemSchema memory value ) internal { @@ -45,7 +45,7 @@ library SystemSchemaLib { } function set( - bytes32 tableId, + uint256 tableId, bytes32 key, address system, bool publicAccess @@ -55,7 +55,7 @@ library SystemSchemaLib { StoreSwitch.setRecord(tableId, keyTuple, abi.encodePacked(system, publicAccess)); } - function get(bytes32 tableId, bytes32 key) internal view returns (address system, bool publicAccess) { + function get(uint256 tableId, bytes32 key) internal view returns (address system, bool publicAccess) { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); @@ -64,7 +64,7 @@ library SystemSchemaLib { } function get( - bytes32 tableId, + uint256 tableId, IStore store, bytes32 key ) internal view returns (address system, bool publicAccess) { diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/OwnerTable.sol index bb1d795869..99b351fcb2 100644 --- a/packages/world/src/tables/OwnerTable.sol +++ b/packages/world/src/tables/OwnerTable.sol @@ -8,7 +8,7 @@ import { Schema } from "store/Schema.sol"; import { AddressSchemaLib as SchemaLib } from "../schemas/Address.sol"; // -- User defined schema and tableId -- -bytes32 constant tableId = keccak256("mud.world.table.address"); +uint256 constant tableId = uint256(keccak256("mud.world.table.address")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index 719096324e..08232074d2 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -8,7 +8,7 @@ import { Schema } from "store/Schema.sol"; import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccess.sol"; // -- User defined schema and tableId -- -bytes32 constant tableId = keccak256("mud.world.table.routeAccess"); +uint256 constant tableId = uint256(keccak256("mud.world.table.routeAccess")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 218cd7b549..7dbfbbec8c 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -8,7 +8,7 @@ import { Schema } from "store/Schema.sol"; import { StringSchemaLib as SchemaLib } from "../schemas/String.sol"; // -- User defined schema and tableId -- -bytes32 constant tableId = keccak256("mud.world.table.route"); +uint256 constant tableId = uint256(keccak256("mud.world.table.route")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 002bfad75f..840fb5313a 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -8,7 +8,7 @@ import { Schema } from "store/Schema.sol"; import { AddressToBytes32SchemaLib as SchemaLib } from "../schemas/AddressToBytes32.sol"; // -- User defined schema and tableId -- -bytes32 constant tableId = keccak256("mud.world.table.systemRoute"); +uint256 constant tableId = uint256(keccak256("mud.world.table.systemRoute")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index da7d1f26ea..5a01fcf8f4 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -8,7 +8,7 @@ import { Schema } from "store/Schema.sol"; import { SystemSchemaLib as SchemaLib } from "../schemas/System.sol"; // -- User defined schema and tableId -- -bytes32 constant tableId = keccak256("mud.world.table.system"); +uint256 constant tableId = uint256(keccak256("mud.world.table.system")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index bf457ad115..52de5adf26 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -50,7 +50,7 @@ contract WorldTestTableHook is IStoreHook { event HookCalled(bytes data); function onSetRecord( - bytes32 table, + uint256 table, bytes32[] memory key, bytes memory data ) public { @@ -58,7 +58,7 @@ contract WorldTestTableHook is IStoreHook { } function onSetField( - bytes32 table, + uint256 table, bytes32[] memory key, uint8 schemaIndex, bytes memory data @@ -66,7 +66,7 @@ contract WorldTestTableHook is IStoreHook { emit HookCalled(abi.encode(table, key, schemaIndex, data)); } - function onDeleteRecord(bytes32 table, bytes32[] memory key) public { + function onDeleteRecord(uint256 table, bytes32[] memory key) public { emit HookCalled(abi.encode(table, key)); } } @@ -154,20 +154,20 @@ contract WorldTest is Test { } function testRegisterTable() public { - bytes32 tableId = world.registerTable("", "/testRouteAccess", RouteAccessSchemaLib.getSchema()); + uint256 tableId = world.registerTable("", "/testRouteAccess", RouteAccessSchemaLib.getSchema()); // Expect the table to be registered assertEq(world.getSchema(tableId).unwrap(), RouteAccessSchemaLib.getSchema().unwrap()); // Expect the table's route to be owned by the caller - address routeOwner = OwnerTable.get(world, tableId); + address routeOwner = OwnerTable.get(world, bytes32(tableId)); assertEq(routeOwner, address(this)); // The new table should be accessible by the caller - assertTrue(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(this) })); + assertTrue(RouteAccessTable.get({ store: world, routeId: bytes32(tableId), caller: address(this) })); // The new table should not be accessible by another address - assertFalse(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(0x01) })); + assertFalse(RouteAccessTable.get({ store: world, routeId: bytes32(tableId), caller: address(0x01) })); // Expect an error when registering an existing table vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testRouteAccess")); @@ -246,7 +246,7 @@ contract WorldTest is Test { world.registerRoute("", "/testSetRecord"); // Register a new table - bytes32 tableRouteId = world.registerTable("/testSetRecord", "/testTable", BoolSchemaLib.getSchema()); + uint256 tableRouteId = world.registerTable("/testSetRecord", "/testTable", BoolSchemaLib.getSchema()); // Write data to the table bytes32 key = keccak256("testKey"); @@ -281,7 +281,7 @@ contract WorldTest is Test { world.registerRoute("", "/testSetField"); // Register a new table - bytes32 tableRouteId = world.registerTable("/testSetField", "/testTable", BoolSchemaLib.getSchema()); + uint256 tableRouteId = world.registerTable("/testSetField", "/testTable", BoolSchemaLib.getSchema()); bytes32 key = keccak256("testKey"); bytes32[] memory keyTuple = new bytes32[](1); @@ -317,7 +317,7 @@ contract WorldTest is Test { world.registerRoute("", "/testDeleteRecord"); // Register a new table - bytes32 tableRouteId = world.registerTable("/testDeleteRecord", "/testTable", BoolSchemaLib.getSchema()); + uint256 tableRouteId = world.registerTable("/testDeleteRecord", "/testTable", BoolSchemaLib.getSchema()); bytes32 key = keccak256("testKey"); bytes32[] memory keyTuple = new bytes32[](1); @@ -421,7 +421,7 @@ contract WorldTest is Test { function testRegisterTableHook() public { // Register a new table - bytes32 tableId = world.registerTable("", "/testTable", BoolSchemaLib.getSchema()); + uint256 tableId = world.registerTable("", "/testTable", BoolSchemaLib.getSchema()); // Register a new hook IStoreHook tableHook = new WorldTestTableHook(); From 7fc68d0f576e7044cd1d7bbda7edd71beb1e8c83 Mon Sep 17 00:00:00 2001 From: alvrs Date: Fri, 17 Feb 2023 18:34:44 -0500 Subject: [PATCH 22/42] test(world): add tests for systems writing to the world --- packages/world/test/World.t.sol | 89 +++++++++++++++++++++++++++++++++ 1 file changed, 89 insertions(+) diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 52de5adf26..78beeff50d 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -3,6 +3,8 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; import { IStoreHook } from "store/IStore.sol"; +import { StoreCore } from "store/StoreCore.sol"; +import { StoreSwitch } from "store/StoreSwitch.sol"; import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; @@ -19,6 +21,7 @@ struct WorldTestSystemReturn { contract WorldTestSystem is System { error WorldTestSystemError(string err); + event WorldTestSystemLog(string log); function msgSender() public pure returns (address) { return _msgSender(); @@ -44,6 +47,30 @@ contract WorldTestSystem is System { } return returndata; } + + function writeData( + string calldata accessRoute, + string calldata subRoute, + bool data + ) public { + bytes32[] memory key = new bytes32[](1); + key[0] = "testKey"; + + if (StoreSwitch.isDelegateCall()) { + uint256 tableId = uint256(keccak256(abi.encodePacked(accessRoute, subRoute))); + StoreCore.setRecord(tableId, key, abi.encodePacked(data)); + } else { + World(msg.sender).setRecord(accessRoute, subRoute, key, abi.encodePacked(data)); + } + } + + function emitCallType() public { + if (StoreSwitch.isDelegateCall()) { + emit WorldTestSystemLog("delegatecall"); + } else { + emit WorldTestSystemLog("call"); + } + } } contract WorldTestTableHook is IStoreHook { @@ -73,6 +100,8 @@ contract WorldTestTableHook is IStoreHook { contract WorldTest is Test { event HookCalled(bytes data); + event WorldTestSystemLog(string log); + World world; function setUp() public { @@ -442,6 +471,66 @@ contract WorldTest is Test { // TODO } + function testWriteRootSystem() public { + // Register a new table + uint256 tableId = world.registerTable("", "/testTable", BoolSchemaLib.getSchema()); + + // Register a new system + WorldTestSystem system = new WorldTestSystem(); + world.registerSystem("", "/testSystem", system, false); + + // Call a system function that write data to the World + world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.writeData.selector, "", "/testTable", true)); + + // Expect the data to be written + assertTrue(BoolSchemaLib.get(tableId, world, "testKey")); + } + + function testWriteAutonomousSystem() public { + // Register a new subroute + world.registerRoute("", "/testRoute"); + + // Register a new table + uint256 tableId = world.registerTable("/testRoute", "/testTable", BoolSchemaLib.getSchema()); + + // Register a new system + WorldTestSystem system = new WorldTestSystem(); + world.registerSystem("/testRoute", "/testSystem", system, false); + + // Call a system function that writes data to the World + world.call( + "/testRoute/testSystem", + abi.encodeWithSelector(WorldTestSystem.writeData.selector, "/testRoute", "/testTable", true) + ); + + // Expect the data to be written + assertTrue(BoolSchemaLib.get(tableId, world, "testKey")); + } + + function testDelegatecallRootSystem() public { + // Register a new root system + WorldTestSystem system = new WorldTestSystem(); + world.registerSystem("", "/testSystem", system, false); + + // Call the root sysyem + vm.expectEmit(true, true, true, true); + emit WorldTestSystemLog("delegatecall"); + world.call("/testSystem", abi.encodeWithSelector(WorldTestSystem.emitCallType.selector)); + } + + function testCallAutonomousSystem() public { + world.registerRoute("", "/testRoute"); + + // Register a new non-root system + WorldTestSystem system = new WorldTestSystem(); + world.registerSystem("/testRoute", "/testSystem", system, false); + + // Call the root sysyem + vm.expectEmit(true, true, true, true); + emit WorldTestSystemLog("call"); + world.call("/testRoute/testSystem", abi.encodeWithSelector(WorldTestSystem.emitCallType.selector)); + } + // TODO: add a test for systems writing to tables via the World function testHashEquality() public { From 270f1936e45421ae579fa980648d3e3adf0a026d Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 09:56:19 -0500 Subject: [PATCH 23/42] docs(store): update comment for clarity --- packages/store/src/Store.sol | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/store/src/Store.sol b/packages/store/src/Store.sol index 09afc3c2a6..35e278f6cd 100644 --- a/packages/store/src/Store.sol +++ b/packages/store/src/Store.sol @@ -15,12 +15,12 @@ abstract contract Store is IStore { schema = StoreCore.getSchema(table); } - // Get full record (including full array, load schema from storage) + // Get full record (static and dynamic data, load schema from storage) function getRecord(uint256 table, bytes32[] calldata key) public view virtual returns (bytes memory data) { data = StoreCore.getRecord(table, key); } - // Get full record (including full array) + // Get full record (static and dynamic data) function getRecord( uint256 table, bytes32[] calldata key, From f25f3beaa8f35e03fc865480529be7d90fa9ab1c Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 10:00:17 -0500 Subject: [PATCH 24/42] build(world): remove explicit --out from forge build command --- packages/world/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/world/package.json b/packages/world/package.json index 3c59128a82..40fa1f57a6 100644 --- a/packages/world/package.json +++ b/packages/world/package.json @@ -13,7 +13,7 @@ "prepare": "yarn build && chmod u+x git-install.sh", "git:install": "bash git-install.sh", "test": "forge test", - "build": "rimraf out && forge build --out out && yarn dist && yarn types", + "build": "rimraf out && forge build && yarn dist && yarn types", "dist": "rimraf abi && mkdir abi && cp -rf out/*.sol/*.json abi/ && yarn rimraf abi/*.metadata.json", "types": "rimraf types && typechain --target=ethers-v5 abi/*.json", "prettier": "prettier --write 'src/**/*.sol'", From ba8ed1095b31859530efdcc2f4e2bed379255970 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 10:05:43 -0500 Subject: [PATCH 25/42] chore(world): update imports from store to @latticexyz/store --- .vscode/settings.json | 2 +- packages/world/remappings.txt | 2 +- packages/world/src/World.sol | 6 +++--- packages/world/src/schemas/Address.sol | 14 +++++++------- packages/world/src/schemas/AddressArray.sol | 18 +++++++++--------- .../world/src/schemas/AddressToBytes32.sol | 14 +++++++------- packages/world/src/schemas/Bool.sol | 16 ++++++++-------- packages/world/src/schemas/RouteAccess.sol | 16 ++++++++-------- packages/world/src/schemas/String.sol | 16 ++++++++-------- packages/world/src/schemas/System.sol | 16 ++++++++-------- packages/world/src/tables/OwnerTable.sol | 6 +++--- packages/world/src/tables/RouteAccessTable.sol | 6 +++--- packages/world/src/tables/RouteTable.sol | 6 +++--- packages/world/src/tables/SystemRouteTable.sol | 6 +++--- packages/world/src/tables/SystemTable.sol | 6 +++--- packages/world/test/World.t.sol | 6 +++--- 16 files changed, 78 insertions(+), 78 deletions(-) diff --git a/.vscode/settings.json b/.vscode/settings.json index db9181bbc5..6d67e32743 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -10,6 +10,6 @@ "solecs/=node_modules/@latticexyz/solecs/src/", "royalty-registry/=node_modules/@manifoldxzy/royalty-registry/contracts/", "std-contracts/=node_modules/@latticexyz/std-contracts/src/", - "store/=node_modules/@latticexyz/store/src/" + "@latticexyz/store/=node_modules/@latticexyz/store/src/" ] } diff --git a/packages/world/remappings.txt b/packages/world/remappings.txt index 764dfe470c..d72d703e66 100644 --- a/packages/world/remappings.txt +++ b/packages/world/remappings.txt @@ -1,3 +1,3 @@ ds-test/=../../node_modules/ds-test/src/ forge-std/=../../node_modules/forge-std/src/ -store/=../../node_modules/@latticexyz/store/src/ +@latticexyz/store/=../../node_modules/@latticexyz/store/src/ diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index f932aa9009..81e0ddabee 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { Store, IStoreHook } from "store/Store.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { Schema } from "store/Schema.sol"; +import { Store, IStoreHook } from "@latticexyz/store/Store.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { OwnerTable, tableId as OwnerTableId } from "./tables/OwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/Address.sol index 2a64eec899..1bdf7037e3 100644 --- a/packages/world/src/schemas/Address.sol +++ b/packages/world/src/schemas/Address.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- struct AddressSchema { diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index 7642e142be..9cc8cbb09c 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -2,15 +2,15 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { SliceLib } from "store/Slice.sol"; -import { EncodeArray } from "store/tightcoder/EncodeArray.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { EncodeArray } from "@latticexyz/store/tightcoder/EncodeArray.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- struct AddressArraySchema { diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/AddressToBytes32.sol index 60f9ad1984..44bd7c6eaf 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/AddressToBytes32.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- struct AddressToBytes32Schema { diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index 679d2eb41d..b2267041d8 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; -import { SliceLib } from "store/Slice.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { SliceLib } from "@latticexyz/store/Slice.sol"; // -- User defined schema and tableId -- struct BoolSchema { diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index bd98123645..1242a8ea68 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; -import { SliceLib } from "store/Slice.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { SliceLib } from "@latticexyz/store/Slice.sol"; // -- User defined schema and tableId -- struct RouteAccessSchema { diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index 1c28e36ec4..111c5f01c5 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { SliceLib } from "store/Slice.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- struct StringSchema { diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index ebcdd86bba..bbe63e7b13 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Bytes } from "store/Bytes.sol"; -import { Schema, SchemaLib } from "store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "store/PackedCounter.sol"; -import { SliceLib } from "store/Slice.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Bytes } from "@latticexyz/store/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { SliceLib } from "@latticexyz/store/Slice.sol"; // -- User defined schema and tableId -- struct SystemSchema { diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/OwnerTable.sol index 99b351fcb2..87440f1c83 100644 --- a/packages/world/src/tables/OwnerTable.sol +++ b/packages/world/src/tables/OwnerTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Schema } from "store/Schema.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { AddressSchemaLib as SchemaLib } from "../schemas/Address.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index 08232074d2..64c4e7088a 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Schema } from "store/Schema.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccess.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 7dbfbbec8c..600bded21a 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Schema } from "store/Schema.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { StringSchemaLib as SchemaLib } from "../schemas/String.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 840fb5313a..cd86c098fc 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Schema } from "store/Schema.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { AddressToBytes32SchemaLib as SchemaLib } from "../schemas/AddressToBytes32.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index 5a01fcf8f4..bdad8c837a 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "store/IStore.sol"; -import { SchemaType } from "store/Types.sol"; -import { Schema } from "store/Schema.sol"; +import { IStore } from "@latticexyz/store/IStore.sol"; +import { SchemaType } from "@latticexyz/store/Types.sol"; +import { Schema } from "@latticexyz/store/Schema.sol"; import { SystemSchemaLib as SchemaLib } from "../schemas/System.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index 78beeff50d..d86c0e4bbc 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; -import { IStoreHook } from "store/IStore.sol"; -import { StoreCore } from "store/StoreCore.sol"; -import { StoreSwitch } from "store/StoreSwitch.sol"; +import { IStoreHook } from "@latticexyz/store/IStore.sol"; +import { StoreCore } from "@latticexyz/store/StoreCore.sol"; +import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; From f37a289a82c3fde0c207658fd6f925fac572ab6d Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 10:19:07 -0500 Subject: [PATCH 26/42] chore(world): remove unused import --- packages/world/src/World.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 81e0ddabee..38617d01ca 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -6,7 +6,7 @@ import { Store, IStoreHook } from "@latticexyz/store/Store.sol"; import { StoreCore } from "@latticexyz/store/StoreCore.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { OwnerTable, tableId as OwnerTableId } from "./tables/OwnerTable.sol"; +import { OwnerTable } from "./tables/OwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; From f010ea2bf21ba910b6a52fee7b9307b99f63d6aa Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 10:23:01 -0500 Subject: [PATCH 27/42] refactor(world): save baseRouteId in memory --- packages/world/src/World.sol | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 38617d01ca..4ceaebff33 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -50,8 +50,8 @@ contract World is Store { if (!_isSingleLevelRoute(subRoute)) revert RouteInvalid(subRoute); // Require base route to exist (with a special check for the root route because it's empty and fails the `has` check) - if (!(keccak256(bytes(baseRoute)) == ROOT_ROUTE_ID || RouteTable.has(keccak256(bytes(baseRoute))))) - revert RouteInvalid(baseRoute); + bytes32 baseRouteId = keccak256(bytes(baseRoute)); + if (!(baseRouteId == ROOT_ROUTE_ID || RouteTable.has(baseRouteId))) revert RouteInvalid(baseRoute); // Construct the new route string memory route = string(abi.encodePacked(baseRoute, subRoute)); From da48c0fcc345831407313e30a87b3488af73c47a Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 11:29:00 -0500 Subject: [PATCH 28/42] refactor(world): use bytes32ToBool util instead of Slice.toBool --- packages/world/src/Utils.sol | 8 ++++++++ packages/world/src/schemas/Bool.sol | 6 +++--- packages/world/src/schemas/RouteAccess.sol | 6 +++--- packages/world/src/schemas/String.sol | 4 ++-- packages/world/src/schemas/System.sol | 5 +++-- 5 files changed, 19 insertions(+), 10 deletions(-) create mode 100644 packages/world/src/Utils.sol diff --git a/packages/world/src/Utils.sol b/packages/world/src/Utils.sol new file mode 100644 index 0000000000..666edbd4cb --- /dev/null +++ b/packages/world/src/Utils.sol @@ -0,0 +1,8 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.0; + +function bytes32ToBool(bytes32 input) pure returns (bool output) { + assembly { + output := input + } +} diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index b2267041d8..a952f08479 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -9,7 +9,7 @@ import { SchemaType } from "@latticexyz/store/Types.sol"; import { Bytes } from "@latticexyz/store/Bytes.sol"; import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; -import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- struct BoolSchema { @@ -61,7 +61,7 @@ library BoolSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - return SliceLib.fromBytes(blob).toBool(); + return bytes32ToBool(bytes32(blob)); } function get( @@ -72,6 +72,6 @@ library BoolSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = store.getRecord(tableId, keyTuple); - return SliceLib.fromBytes(blob).toBool(); + return bytes32ToBool(bytes32(blob)); } } diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccess.sol index 1242a8ea68..edd64bb57b 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccess.sol @@ -9,7 +9,7 @@ import { SchemaType } from "@latticexyz/store/Types.sol"; import { Bytes } from "@latticexyz/store/Bytes.sol"; import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; -import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- struct RouteAccessSchema { @@ -57,7 +57,7 @@ library RouteAccessSchemaLib { keyTuple[0] = routeId; keyTuple[1] = bytes32(bytes20(caller)); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - return SliceLib.fromBytes(blob).toBool(); + return bytes32ToBool(bytes32(blob)); } function get( @@ -70,7 +70,7 @@ library RouteAccessSchemaLib { keyTuple[0] = routeId; keyTuple[1] = bytes32(bytes20(caller)); bytes memory blob = store.getRecord(tableId, keyTuple); - return SliceLib.fromBytes(blob).toBool(); + return bytes32ToBool(bytes32(blob)); } function deleteRecord( diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/String.sol index 111c5f01c5..50ff63ee24 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/String.sol @@ -50,7 +50,7 @@ library StringSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - return SliceLib.getSubslice(blob, 32).toString(); + return string(SliceLib.getSubslice(blob, 32).toBytes()); } function get( @@ -61,7 +61,7 @@ library StringSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = key; bytes memory blob = store.getRecord(tableId, keyTuple); - return SliceLib.getSubslice(blob, 32).toString(); + return string(SliceLib.getSubslice(blob, 32).toBytes()); } function has(uint256 tableId, bytes32 key) internal view returns (bool) { diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/System.sol index bbe63e7b13..2a65a61c19 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/System.sol @@ -10,6 +10,7 @@ import { Bytes } from "@latticexyz/store/Bytes.sol"; import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- struct SystemSchema { @@ -60,7 +61,7 @@ library SystemSchemaLib { keyTuple[0] = key; bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); system = SliceLib.fromBytes(blob).toAddress(); - publicAccess = SliceLib.getSubslice(blob, 20).toBool(); + publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); } function get( @@ -72,6 +73,6 @@ library SystemSchemaLib { keyTuple[0] = key; bytes memory blob = store.getRecord(tableId, keyTuple); system = SliceLib.fromBytes(blob).toAddress(); - publicAccess = SliceLib.getSubslice(blob, 20).toBool(); + publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); } } From 9901b6516f710a4d16b7aa154585bc7c343f078d Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 11:29:18 -0500 Subject: [PATCH 29/42] refactor(store): remove unused toBool and toString methods --- packages/store/src/tightcoder/DecodeSlice.sol | 4 ---- 1 file changed, 4 deletions(-) diff --git a/packages/store/src/tightcoder/DecodeSlice.sol b/packages/store/src/tightcoder/DecodeSlice.sol index 27e3f1ed5c..260aa668a4 100644 --- a/packages/store/src/tightcoder/DecodeSlice.sol +++ b/packages/store/src/tightcoder/DecodeSlice.sol @@ -468,10 +468,6 @@ library DecodeSlice { } } - function toString(Slice self) internal view returns (string memory output) { - return string(self.toBytes()); - } - /************************************************************************ * * bytes1 - bytes32 From bcfcf68fe2ff037e4dfffb49348dbc87873909cf Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 11:34:54 -0500 Subject: [PATCH 30/42] docs(store): add comments to StoreView --- packages/store/src/StoreView.sol | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/packages/store/src/StoreView.sol b/packages/store/src/StoreView.sol index 5d9fbb35c9..4f48ab6f5e 100644 --- a/packages/store/src/StoreView.sol +++ b/packages/store/src/StoreView.sol @@ -11,10 +11,16 @@ import { Store } from "./Store.sol"; contract StoreView is Store { error StoreView_NotImplemented(); + /** + * Not implemented in StoreView + */ function registerSchema(uint256, Schema) public virtual { revert StoreView_NotImplemented(); } + /** + * Not implemented in StoreView + */ function setRecord( uint256, bytes32[] calldata, @@ -23,7 +29,9 @@ contract StoreView is Store { revert StoreView_NotImplemented(); } - // Set partial data at schema index + /** + * Not implemented in StoreView + */ function setField( uint256, bytes32[] calldata, @@ -33,10 +41,16 @@ contract StoreView is Store { revert StoreView_NotImplemented(); } + /** + * Not implemented in StoreView + */ function registerStoreHook(uint256, IStoreHook) public virtual { revert StoreView_NotImplemented(); } + /** + * Not implemented in StoreView + */ function deleteRecord(uint256, bytes32[] calldata) public virtual { revert StoreView_NotImplemented(); } From 0c91fbaaaf1d0b56a3c122d3c38079826960ab51 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 11:44:27 -0500 Subject: [PATCH 31/42] build(world): reduce forge optimizer runs to 3000 --- packages/world/foundry.toml | 2 +- packages/world/gas-report.txt | 11 +++++++++++ 2 files changed, 12 insertions(+), 1 deletion(-) create mode 100644 packages/world/gas-report.txt diff --git a/packages/world/foundry.toml b/packages/world/foundry.toml index 5847f2b9a7..4711ce8e0a 100644 --- a/packages/world/foundry.toml +++ b/packages/world/foundry.toml @@ -2,7 +2,7 @@ ffi = false fuzz_runs = 256 optimizer = true -optimizer_runs = 1000000 +optimizer_runs = 3000 verbosity = 1 libs = ["../../node_modules", "../store"] src = "src" diff --git a/packages/world/gas-report.txt b/packages/world/gas-report.txt new file mode 100644 index 0000000000..9f0df47cee --- /dev/null +++ b/packages/world/gas-report.txt @@ -0,0 +1,11 @@ +(test/World.t.sol) | validate route (empty string) [assertTrue(_isRoute(""), "empty string")]: 250 +(test/World.t.sol) | validate route (single slash) [assertTrue(_isRoute("/"), "single slash")]: 265 +(test/World.t.sol) | validate route (single level) [assertTrue(_isRoute("/topLevel"), "single level")]: 264 +(test/World.t.sol) | validate route (multi level) [assertTrue(_isRoute("/topLevel/subLevel"), "multi level")]: 262 +(test/World.t.sol) | validate route (no leading slash) [assertFalse(_isRoute("noLeadingSlash"), "no leading slash")]: 298 +(test/World.t.sol) | validate single level route (empty string) [assertTrue(_isSingleLevelRoute(""), "empty string")]: 347 +(test/World.t.sol) | validate single level route (single slash) [assertTrue(_isSingleLevelRoute("/"), "single slash")]: 362 +(test/World.t.sol) | validate single level route (single level) [assertTrue(_isSingleLevelRoute("/topLevel"), "single level")]: 1290 +(test/World.t.sol) | validate single level route (multi level) [assertFalse(_isSingleLevelRoute("/topLevel/subLevel"), "multi level")]: 1391 +(test/World.t.sol) | validate single level route (no leading slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash"), "no leading slash")]: 351 +(test/World.t.sol) | validate single level route (no leading slash but contains slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash/butContainsSlash"), "no leading slash")]: 354 \ No newline at end of file From 26642b3dcae04e54718d9c37ca89c576229c59ee Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 12:42:05 -0500 Subject: [PATCH 32/42] fix(world): prevent empty routes --- packages/world/src/World.sol | 5 +++++ packages/world/test/World.t.sol | 10 ++++++++-- 2 files changed, 13 insertions(+), 2 deletions(-) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 4ceaebff33..1fe95c30a8 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -400,6 +400,11 @@ function _isRoute(string memory route) pure returns (bool result) { if eq(byte(0, mload(add(route, 0x20))), 0x2f) { result := 1 } + + // If the route is only `/`, return false + if eq(mload(route), 1) { + result := 0 + } } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index d86c0e4bbc..aac16b0287 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -123,7 +123,10 @@ contract WorldTest is Test { assertTrue(_isRoute(""), "empty string"); // !gasreport validate route (single slash) - assertTrue(_isRoute("/"), "single slash"); + assertFalse(_isRoute("/"), "single slash"); + + // !gasreport validate route (single character) + assertTrue(_isRoute("/a"), "single character"); // !gasreport validate route (single level) assertTrue(_isRoute("/topLevel"), "single level"); @@ -140,7 +143,10 @@ contract WorldTest is Test { assertTrue(_isSingleLevelRoute(""), "empty string"); // !gasreport validate single level route (single slash) - assertTrue(_isSingleLevelRoute("/"), "single slash"); + assertFalse(_isSingleLevelRoute("/"), "single slash"); + + // !gasreport validate route (single character) + assertTrue(_isRoute("/a"), "single character"); // !gasreport validate single level route (single level) assertTrue(_isSingleLevelRoute("/topLevel"), "single level"); From 0278f0ac80fcfafdc35ccf130378bf924594cd2a Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 14:15:41 -0500 Subject: [PATCH 33/42] refactor(world): use uint256 for routeId instead of bytes32 --- packages/world/src/World.sol | 57 +++++++++---------- ...{RouteAccess.sol => RouteAccessSchema.sol} | 16 +++--- .../{Address.sol => RouteOwnerSchema.sol} | 16 +++--- .../schemas/{String.sol => RouteSchema.sol} | 20 +++---- ...essToBytes32.sol => SystemRouteSchema.sol} | 32 +++++------ .../schemas/{System.sol => SystemSchema.sol} | 16 +++--- .../world/src/tables/RouteAccessTable.sol | 10 ++-- .../{OwnerTable.sol => RouteOwnerTable.sol} | 18 +++--- packages/world/src/tables/RouteTable.sol | 10 ++-- .../world/src/tables/SystemRouteTable.sol | 8 +-- packages/world/src/tables/SystemTable.sol | 8 +-- packages/world/test/World.t.sol | 30 +++++----- 12 files changed, 120 insertions(+), 121 deletions(-) rename packages/world/src/schemas/{RouteAccess.sol => RouteAccessSchema.sol} (91%) rename packages/world/src/schemas/{Address.sol => RouteOwnerSchema.sol} (86%) rename packages/world/src/schemas/{String.sol => RouteSchema.sol} (83%) rename packages/world/src/schemas/{AddressToBytes32.sol => SystemRouteSchema.sol} (74%) rename packages/world/src/schemas/{System.sol => SystemSchema.sol} (87%) rename packages/world/src/tables/{OwnerTable.sol => RouteOwnerTable.sol} (57%) diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 1fe95c30a8..5b34fe4e6b 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -6,7 +6,7 @@ import { Store, IStoreHook } from "@latticexyz/store/Store.sol"; import { StoreCore } from "@latticexyz/store/StoreCore.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { OwnerTable } from "./tables/OwnerTable.sol"; +import { RouteOwnerTable } from "./tables/RouteOwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; import { RouteTable } from "./tables/RouteTable.sol"; import { SystemRouteTable } from "./tables/SystemRouteTable.sol"; @@ -14,7 +14,7 @@ import { SystemTable } from "./tables/SystemTable.sol"; import { System } from "./System.sol"; import { ISystemHook } from "./ISystemHook.sol"; -bytes32 constant ROOT_ROUTE_ID = keccak256(bytes("")); +uint256 constant ROOT_ROUTE_ID = uint256(keccak256(bytes(""))); bytes32 constant SINGLE_SLASH = "/"; contract World is Store { @@ -28,11 +28,11 @@ contract World is Store { RouteTable.registerSchema(); RouteAccessTable.registerSchema(); SystemRouteTable.registerSchema(); - OwnerTable.registerSchema(); + RouteOwnerTable.registerSchema(); // Register root route and give ownership to msg.sender RouteTable.set({ routeId: ROOT_ROUTE_ID, route: "" }); // Storing this explicitly to trigger the event for indexers - OwnerTable.set({ key: ROOT_ROUTE_ID, owner: msg.sender }); + RouteOwnerTable.set({ routeId: ROOT_ROUTE_ID, owner: msg.sender }); RouteAccessTable.set({ routeId: ROOT_ROUTE_ID, caller: msg.sender, access: true }); } @@ -45,17 +45,17 @@ contract World is Store { /** * Register a new route by extending an existing route */ - function registerRoute(string calldata baseRoute, string calldata subRoute) public returns (bytes32 routeId) { + function registerRoute(string calldata baseRoute, string calldata subRoute) public returns (uint256 routeId) { // Require subroute to be a valid route fragment (start with `/` and don't contain any further `/`) if (!_isSingleLevelRoute(subRoute)) revert RouteInvalid(subRoute); // Require base route to exist (with a special check for the root route because it's empty and fails the `has` check) - bytes32 baseRouteId = keccak256(bytes(baseRoute)); + uint256 baseRouteId = _toRouteId(baseRoute); if (!(baseRouteId == ROOT_ROUTE_ID || RouteTable.has(baseRouteId))) revert RouteInvalid(baseRoute); // Construct the new route string memory route = string(abi.encodePacked(baseRoute, subRoute)); - routeId = keccak256(bytes(route)); + routeId = _toRouteId(route); // Require route to not exist yet if (RouteTable.has(routeId)) revert RouteExists(route); @@ -64,7 +64,7 @@ contract World is Store { RouteTable.set({ routeId: routeId, route: route }); // Add caller as owner of the new route - OwnerTable.set({ key: routeId, owner: msg.sender }); + RouteOwnerTable.set({ routeId: routeId, owner: msg.sender }); // Give caller access to the route RouteAccessTable.set({ routeId: routeId, caller: msg.sender, access: true }); @@ -92,8 +92,7 @@ contract World is Store { */ function registerSchema(uint256 tableId, Schema schema) public override { // Require caller to own the given tableId - if (OwnerTable.get(bytes32(tableId)) != msg.sender) - revert RouteAccessDenied(RouteTable.get(bytes32(tableId)), msg.sender); + if (RouteOwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); // Register the schema StoreCore.registerSchema(tableId, schema); @@ -103,7 +102,7 @@ contract World is Store { * Register a hook for a given table route */ function registerTableHook(string calldata tableRoute, IStoreHook hook) public { - registerStoreHook(uint256(keccak256(bytes(tableRoute))), hook); + registerStoreHook(_toRouteId(tableRoute), hook); } /** @@ -112,8 +111,7 @@ contract World is Store { */ function registerStoreHook(uint256 tableId, IStoreHook hook) public override { // Require caller to own the given tableId - if (OwnerTable.get(bytes32(tableId)) != msg.sender) - revert RouteAccessDenied(RouteTable.get(bytes32(tableId)), msg.sender); + if (RouteOwnerTable.get(tableId) != msg.sender) revert RouteAccessDenied(RouteTable.get(tableId), msg.sender); // Register the hook StoreCore.registerStoreHook(tableId, hook); @@ -134,13 +132,13 @@ contract World is Store { string calldata systemRoute, System system, bool publicAccess - ) public returns (bytes32 systemRouteId) { + ) public returns (uint256 systemRouteId) { // Require the system to not exist yet if (SystemRouteTable.has(address(system))) revert SystemExists(address(system)); // Require the caller to own the base route - bytes32 baseRouteId = keccak256(bytes(baseRoute)); - if (OwnerTable.get(baseRouteId) != msg.sender) revert RouteAccessDenied(baseRoute, msg.sender); + uint256 baseRouteId = _toRouteId(baseRoute); + if (RouteOwnerTable.get(baseRouteId) != msg.sender) revert RouteAccessDenied(baseRoute, msg.sender); // Register system route systemRouteId = registerRoute(baseRoute, systemRoute); @@ -160,8 +158,8 @@ contract World is Store { */ function grantAccess(string calldata route, address grantee) public { // Require the caller to own the route - bytes32 routeId = keccak256(bytes(route)); - if (OwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); + uint256 routeId = _toRouteId(route); + if (RouteOwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); // Grant access to the given route RouteAccessTable.set({ routeId: routeId, caller: grantee, access: true }); @@ -172,8 +170,8 @@ contract World is Store { */ function retractAccess(string calldata route, address grantee) public { // Require the caller to own the route - bytes32 routeId = keccak256(bytes(route)); - if (OwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); + uint256 routeId = _toRouteId(route); + if (RouteOwnerTable.get(routeId) != msg.sender) revert RouteAccessDenied(route, msg.sender); // Retract access to the given route RouteAccessTable.deleteRecord({ routeId: routeId, caller: grantee }); @@ -219,8 +217,7 @@ contract World is Store { bytes calldata data ) public { // Check access based on the tableRoute - if (!_hasAccess(bytes32(tableRouteId), msg.sender)) - revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); // Set the record StoreCore.setRecord(tableRouteId, key, data); @@ -262,8 +259,7 @@ contract World is Store { bytes calldata data ) public override { // Check access based on the tableRoute - if (!_hasAccess(bytes32(tableRouteId), msg.sender)) - revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); // Set the field StoreCore.setField(tableRouteId, key, schemaIndex, data); @@ -298,8 +294,7 @@ contract World is Store { */ function deleteRecord(uint256 tableRouteId, bytes32[] calldata key) public override { // Check access based on the tableRoute - if (!_hasAccess(bytes32(tableRouteId), msg.sender)) - revert RouteAccessDenied(RouteTable.get(bytes32(tableRouteId)), msg.sender); + if (!_hasAccess(tableRouteId, msg.sender)) revert RouteAccessDenied(RouteTable.get(tableRouteId), msg.sender); // Delete the record StoreCore.deleteRecord(tableRouteId, key); @@ -323,7 +318,7 @@ contract World is Store { ) public returns (bytes memory) { // Check if the system is a public system and get its address string memory systemRoute = string(abi.encodePacked(accessRoute, subRoute)); - bytes32 systemRouteId = keccak256(bytes(systemRoute)); + uint256 systemRouteId = _toRouteId(systemRoute); (address systemAddress, bool publicAccess) = SystemTable.get(systemRouteId); // If the system is not public, check for individual access @@ -380,10 +375,10 @@ contract World is Store { } function _hasAccess(string calldata route, address caller) internal view returns (bool) { - return _hasAccess(keccak256(bytes(route)), caller); + return _hasAccess(_toRouteId(route), caller); } - function _hasAccess(bytes32 routeId, address caller) internal view returns (bool) { + function _hasAccess(uint256 routeId, address caller) internal view returns (bool) { return RouteAccessTable.get(routeId, caller); } } @@ -425,3 +420,7 @@ function _isSingleLevelRoute(string memory route) pure returns (bool result) { // Return true if no `/` was found return true; } + +function _toRouteId(string memory route) pure returns (uint256) { + return uint256(keccak256(bytes(route))); +} diff --git a/packages/world/src/schemas/RouteAccess.sol b/packages/world/src/schemas/RouteAccessSchema.sol similarity index 91% rename from packages/world/src/schemas/RouteAccess.sol rename to packages/world/src/schemas/RouteAccessSchema.sol index edd64bb57b..67b836961a 100644 --- a/packages/world/src/schemas/RouteAccess.sol +++ b/packages/world/src/schemas/RouteAccessSchema.sol @@ -37,12 +37,12 @@ library RouteAccessSchemaLib { /** Set the table's data */ function set( uint256 tableId, - bytes32 routeId, + uint256 routeId, address caller, bool access ) internal { bytes32[] memory keyTuple = new bytes32[](2); - keyTuple[0] = routeId; + keyTuple[0] = bytes32(routeId); keyTuple[1] = bytes32(bytes20(caller)); StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(access)); } @@ -50,11 +50,11 @@ library RouteAccessSchemaLib { /** Get the table's data */ function get( uint256 tableId, - bytes32 routeId, + uint256 routeId, address caller ) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](2); - keyTuple[0] = routeId; + keyTuple[0] = bytes32(routeId); keyTuple[1] = bytes32(bytes20(caller)); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); return bytes32ToBool(bytes32(blob)); @@ -63,11 +63,11 @@ library RouteAccessSchemaLib { function get( uint256 tableId, IStore store, - bytes32 routeId, + uint256 routeId, address caller ) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](2); - keyTuple[0] = routeId; + keyTuple[0] = bytes32(routeId); keyTuple[1] = bytes32(bytes20(caller)); bytes memory blob = store.getRecord(tableId, keyTuple); return bytes32ToBool(bytes32(blob)); @@ -75,11 +75,11 @@ library RouteAccessSchemaLib { function deleteRecord( uint256 tableId, - bytes32 routeId, + uint256 routeId, address caller ) internal { bytes32[] memory keyTuple = new bytes32[](2); - keyTuple[0] = routeId; + keyTuple[0] = bytes32(routeId); keyTuple[1] = bytes32(bytes20(caller)); StoreSwitch.deleteRecord(tableId, keyTuple); } diff --git a/packages/world/src/schemas/Address.sol b/packages/world/src/schemas/RouteOwnerSchema.sol similarity index 86% rename from packages/world/src/schemas/Address.sol rename to packages/world/src/schemas/RouteOwnerSchema.sol index 1bdf7037e3..6e92b438e1 100644 --- a/packages/world/src/schemas/Address.sol +++ b/packages/world/src/schemas/RouteOwnerSchema.sol @@ -11,14 +11,14 @@ import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- -struct AddressSchema { +struct RouteOwnerSchema { address addr; } // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate -library AddressSchemaLib { +library RouteOwnerSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { schema = SchemaLib.encode(SchemaType.ADDRESS); @@ -36,18 +36,18 @@ library AddressSchemaLib { /** Set the table's data */ function set( uint256 tableId, - bytes32 key, + uint256 routeId, address addr ) internal { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(addr)); } /** Get the table's data */ - function get(uint256 tableId, bytes32 key) internal view returns (address) { + function get(uint256 tableId, uint256 routeId) internal view returns (address) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); return address(bytes20(blob)); } @@ -55,10 +55,10 @@ library AddressSchemaLib { function get( uint256 tableId, IStore store, - bytes32 key + uint256 routeId ) internal view returns (address) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = store.getRecord(tableId, keyTuple); return address(bytes20(blob)); } diff --git a/packages/world/src/schemas/String.sol b/packages/world/src/schemas/RouteSchema.sol similarity index 83% rename from packages/world/src/schemas/String.sol rename to packages/world/src/schemas/RouteSchema.sol index 50ff63ee24..1e77c92c02 100644 --- a/packages/world/src/schemas/String.sol +++ b/packages/world/src/schemas/RouteSchema.sol @@ -12,14 +12,14 @@ import { SliceLib } from "@latticexyz/store/Slice.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- -struct StringSchema { +struct RouteSchema { string value; } // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate -library StringSchemaLib { +library RouteSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { schema = SchemaLib.encode(SchemaType.STRING); @@ -37,18 +37,18 @@ library StringSchemaLib { /** Set the table's data */ function set( uint256 tableId, - bytes32 key, + uint256 routeId, string memory value ) internal { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); StoreSwitch.setField(tableId, keyTuple, 0, bytes(value)); } /** Get the table's data */ - function get(uint256 tableId, bytes32 key) internal view returns (string memory) { + function get(uint256 tableId, uint256 routeId) internal view returns (string memory) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); return string(SliceLib.getSubslice(blob, 32).toBytes()); } @@ -56,17 +56,17 @@ library StringSchemaLib { function get( uint256 tableId, IStore store, - bytes32 key + uint256 routeId ) internal view returns (string memory) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = store.getRecord(tableId, keyTuple); return string(SliceLib.getSubslice(blob, 32).toBytes()); } - function has(uint256 tableId, bytes32 key) internal view returns (bool) { + function has(uint256 tableId, uint256 routeId) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); return blob.length > 0; } diff --git a/packages/world/src/schemas/AddressToBytes32.sol b/packages/world/src/schemas/SystemRouteSchema.sol similarity index 74% rename from packages/world/src/schemas/AddressToBytes32.sol rename to packages/world/src/schemas/SystemRouteSchema.sol index 44bd7c6eaf..c6d72fdadd 100644 --- a/packages/world/src/schemas/AddressToBytes32.sol +++ b/packages/world/src/schemas/SystemRouteSchema.sol @@ -11,17 +11,17 @@ import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; // -- User defined schema and tableId -- -struct AddressToBytes32Schema { - bytes32 value; +struct SystemRouteSchema { + uint256 value; } // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate -library AddressToBytes32SchemaLib { +library SystemRouteSchemaLib { /** Get the table's schema */ function getSchema() internal pure returns (Schema schema) { - schema = SchemaLib.encode(SchemaType.BYTES32); + schema = SchemaLib.encode(SchemaType.UINT256); } /** Register the table's schema */ @@ -36,36 +36,36 @@ library AddressToBytes32SchemaLib { /** Set the table's data */ function set( uint256 tableId, - address key, - bytes32 value + address system, + uint256 value ) internal { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = bytes20(key); + keyTuple[0] = bytes20(system); StoreSwitch.setField(tableId, keyTuple, 0, abi.encodePacked(value)); } /** Get the table's data */ - function get(uint256 tableId, address key) internal view returns (bytes32) { + function get(uint256 tableId, address system) internal view returns (uint256) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = bytes20(key); + keyTuple[0] = bytes20(system); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - return bytes32(blob); + return uint256(bytes32(blob)); } function get( uint256 tableId, IStore store, - address key - ) internal view returns (bytes32) { + address system + ) internal view returns (uint256) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = bytes20(key); + keyTuple[0] = bytes20(system); bytes memory blob = store.getRecord(tableId, keyTuple); - return bytes32(blob); + return uint256(bytes32(blob)); } - function has(uint256 tableId, address key) internal view returns (bool) { + function has(uint256 tableId, address system) internal view returns (bool) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = bytes20(key); + keyTuple[0] = bytes20(system); return bytes32(StoreSwitch.getRecord(tableId, keyTuple)) != 0; } } diff --git a/packages/world/src/schemas/System.sol b/packages/world/src/schemas/SystemSchema.sol similarity index 87% rename from packages/world/src/schemas/System.sol rename to packages/world/src/schemas/SystemSchema.sol index 2a65a61c19..b5039b43be 100644 --- a/packages/world/src/schemas/System.sol +++ b/packages/world/src/schemas/SystemSchema.sol @@ -39,26 +39,26 @@ library SystemSchemaLib { /** Set the table's data */ function set( uint256 tableId, - bytes32 key, + uint256 routeId, SystemSchema memory value ) internal { - set(tableId, key, value.system, value.publicAccess); + set(tableId, routeId, value.system, value.publicAccess); } function set( uint256 tableId, - bytes32 key, + uint256 routeId, address system, bool publicAccess ) internal { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); StoreSwitch.setRecord(tableId, keyTuple, abi.encodePacked(system, publicAccess)); } - function get(uint256 tableId, bytes32 key) internal view returns (address system, bool publicAccess) { + function get(uint256 tableId, uint256 routeId) internal view returns (address system, bool publicAccess) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); system = SliceLib.fromBytes(blob).toAddress(); publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); @@ -67,10 +67,10 @@ library SystemSchemaLib { function get( uint256 tableId, IStore store, - bytes32 key + uint256 routeId ) internal view returns (address system, bool publicAccess) { bytes32[] memory keyTuple = new bytes32[](1); - keyTuple[0] = key; + keyTuple[0] = bytes32(routeId); bytes memory blob = store.getRecord(tableId, keyTuple); system = SliceLib.fromBytes(blob).toAddress(); publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index 64c4e7088a..ab2529c5f1 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -5,7 +5,7 @@ import { console } from "forge-std/console.sol"; import { IStore } from "@latticexyz/store/IStore.sol"; import { SchemaType } from "@latticexyz/store/Types.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccess.sol"; +import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccessSchema.sol"; // -- User defined schema and tableId -- uint256 constant tableId = uint256(keccak256("mud.world.table.routeAccess")); @@ -25,7 +25,7 @@ library RouteAccessTable { /** Set the table's data */ function set( - bytes32 routeId, + uint256 routeId, address caller, bool access ) internal { @@ -33,19 +33,19 @@ library RouteAccessTable { } /** Get the table's data */ - function get(bytes32 routeId, address caller) internal view returns (bool) { + function get(uint256 routeId, address caller) internal view returns (bool) { return SchemaLib.get(tableId, routeId, caller); } function get( IStore store, - bytes32 routeId, + uint256 routeId, address caller ) internal view returns (bool) { return SchemaLib.get(tableId, store, routeId, caller); } - function deleteRecord(bytes32 routeId, address caller) internal { + function deleteRecord(uint256 routeId, address caller) internal { SchemaLib.deleteRecord(tableId, routeId, caller); } } diff --git a/packages/world/src/tables/OwnerTable.sol b/packages/world/src/tables/RouteOwnerTable.sol similarity index 57% rename from packages/world/src/tables/OwnerTable.sol rename to packages/world/src/tables/RouteOwnerTable.sol index 87440f1c83..bd5a05ff00 100644 --- a/packages/world/src/tables/OwnerTable.sol +++ b/packages/world/src/tables/RouteOwnerTable.sol @@ -5,15 +5,15 @@ import { console } from "forge-std/console.sol"; import { IStore } from "@latticexyz/store/IStore.sol"; import { SchemaType } from "@latticexyz/store/Types.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { AddressSchemaLib as SchemaLib } from "../schemas/Address.sol"; +import { RouteOwnerSchemaLib as SchemaLib } from "../schemas/RouteOwnerSchema.sol"; // -- User defined schema and tableId -- -uint256 constant tableId = uint256(keccak256("mud.world.table.address")); +uint256 constant tableId = uint256(keccak256("mud.world.table.routeOwner")); // -- Autogenerated library to interact with tables with this schema -- // TODO: autogenerate -library OwnerTable { +library RouteOwnerTable { /** Register the table's schema */ function registerSchema() internal { SchemaLib.registerSchema(tableId); @@ -24,16 +24,16 @@ library OwnerTable { } /** Set the table's data */ - function set(bytes32 key, address owner) internal { - SchemaLib.set(tableId, key, owner); + function set(uint256 routeId, address owner) internal { + SchemaLib.set(tableId, routeId, owner); } /** Get the table's data */ - function get(bytes32 key) internal view returns (address) { - return SchemaLib.get(tableId, key); + function get(uint256 routeId) internal view returns (address) { + return SchemaLib.get(tableId, routeId); } - function get(IStore store, bytes32 key) internal view returns (address) { - return SchemaLib.get(tableId, store, key); + function get(IStore store, uint256 routeId) internal view returns (address) { + return SchemaLib.get(tableId, store, routeId); } } diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 600bded21a..2d398fd8d4 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -5,7 +5,7 @@ import { console } from "forge-std/console.sol"; import { IStore } from "@latticexyz/store/IStore.sol"; import { SchemaType } from "@latticexyz/store/Types.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { StringSchemaLib as SchemaLib } from "../schemas/String.sol"; +import { RouteSchemaLib as SchemaLib } from "../schemas/RouteSchema.sol"; // -- User defined schema and tableId -- uint256 constant tableId = uint256(keccak256("mud.world.table.route")); @@ -24,20 +24,20 @@ library RouteTable { } /** Set the table's data */ - function set(bytes32 routeId, string memory route) internal { + function set(uint256 routeId, string memory route) internal { SchemaLib.set(tableId, routeId, route); } /** Get the table's data */ - function get(bytes32 key) internal view returns (string memory) { + function get(uint256 key) internal view returns (string memory) { return SchemaLib.get(tableId, key); } - function get(IStore store, bytes32 key) internal view returns (string memory) { + function get(IStore store, uint256 key) internal view returns (string memory) { return SchemaLib.get(tableId, store, key); } - function has(bytes32 key) internal view returns (bool) { + function has(uint256 key) internal view returns (bool) { return SchemaLib.has(tableId, key); } } diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index cd86c098fc..90e0ae56d5 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -5,7 +5,7 @@ import { console } from "forge-std/console.sol"; import { IStore } from "@latticexyz/store/IStore.sol"; import { SchemaType } from "@latticexyz/store/Types.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { AddressToBytes32SchemaLib as SchemaLib } from "../schemas/AddressToBytes32.sol"; +import { SystemRouteSchemaLib as SchemaLib } from "../schemas/SystemRouteSchema.sol"; // -- User defined schema and tableId -- uint256 constant tableId = uint256(keccak256("mud.world.table.systemRoute")); @@ -24,16 +24,16 @@ library SystemRouteTable { } /** Set the table's data */ - function set(address system, bytes32 routeId) internal { + function set(address system, uint256 routeId) internal { SchemaLib.set(tableId, system, routeId); } /** Get the table's data */ - function get(address system) internal view returns (bytes32) { + function get(address system) internal view returns (uint256) { return SchemaLib.get(tableId, system); } - function get(IStore store, address system) internal view returns (bytes32) { + function get(IStore store, address system) internal view returns (uint256) { return SchemaLib.get(tableId, store, system); } diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index bdad8c837a..b9eb20e71a 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -5,7 +5,7 @@ import { console } from "forge-std/console.sol"; import { IStore } from "@latticexyz/store/IStore.sol"; import { SchemaType } from "@latticexyz/store/Types.sol"; import { Schema } from "@latticexyz/store/Schema.sol"; -import { SystemSchemaLib as SchemaLib } from "../schemas/System.sol"; +import { SystemSchemaLib as SchemaLib } from "../schemas/SystemSchema.sol"; // -- User defined schema and tableId -- uint256 constant tableId = uint256(keccak256("mud.world.table.system")); @@ -25,7 +25,7 @@ library SystemTable { /** Set the table's data */ function set( - bytes32 routeId, + uint256 routeId, address system, bool publicAccess ) internal { @@ -33,11 +33,11 @@ library SystemTable { } /** Get the table's data */ - function get(bytes32 routeId) internal view returns (address, bool) { + function get(uint256 routeId) internal view returns (address, bool) { return SchemaLib.get(tableId, routeId); } - function get(IStore store, bytes32 routeId) internal view returns (address, bool) { + function get(IStore store, uint256 routeId) internal view returns (address, bool) { return SchemaLib.get(tableId, store, routeId); } } diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index aac16b0287..e14baf5e26 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -8,9 +8,9 @@ import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; -import { OwnerTable } from "../src/tables/OwnerTable.sol"; +import { RouteOwnerTable } from "../src/tables/RouteOwnerTable.sol"; import { RouteAccessTable } from "../src/tables/RouteAccessTable.sol"; -import { RouteAccessSchemaLib } from "../src/schemas/RouteAccess.sol"; +import { RouteAccessSchemaLib } from "../src/schemas/RouteAccessSchema.sol"; import { SystemTable } from "../src/tables/SystemTable.sol"; import { BoolSchemaLib } from "../src/schemas/Bool.sol"; @@ -57,7 +57,7 @@ contract WorldTestSystem is System { key[0] = "testKey"; if (StoreSwitch.isDelegateCall()) { - uint256 tableId = uint256(keccak256(abi.encodePacked(accessRoute, subRoute))); + uint256 tableId = uint256(uint256(keccak256(abi.encodePacked(accessRoute, subRoute)))); StoreCore.setRecord(tableId, key, abi.encodePacked(data)); } else { World(msg.sender).setRecord(accessRoute, subRoute, key, abi.encodePacked(data)); @@ -110,7 +110,7 @@ contract WorldTest is Test { function testConstructor() public { // Owner of root route should be the creator of the World - address rootOwner = OwnerTable.get(world, keccak256("")); + address rootOwner = RouteOwnerTable.get(world, uint256(uint256(keccak256("")))); assertEq(rootOwner, address(this)); } @@ -166,14 +166,14 @@ contract WorldTest is Test { world.registerRoute("", "/test"); // Owner of the new route should be the caller of the method - address routeOwner = OwnerTable.get(world, keccak256("/test")); + address routeOwner = RouteOwnerTable.get(world, uint256(keccak256("/test"))); assertEq(routeOwner, address(this)); // The new route should be accessible by the caller - assertTrue(RouteAccessTable.get({ store: world, routeId: keccak256("/test"), caller: address(this) })); + assertTrue(RouteAccessTable.get({ store: world, routeId: uint256(keccak256("/test")), caller: address(this) })); // The new route should not be accessible by another address - assertFalse(RouteAccessTable.get({ store: world, routeId: keccak256("/test"), caller: address(0x01) })); + assertFalse(RouteAccessTable.get({ store: world, routeId: uint256(keccak256("/test")), caller: address(0x01) })); // Expect an error when registering an existing route vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/test")); @@ -195,14 +195,14 @@ contract WorldTest is Test { assertEq(world.getSchema(tableId).unwrap(), RouteAccessSchemaLib.getSchema().unwrap()); // Expect the table's route to be owned by the caller - address routeOwner = OwnerTable.get(world, bytes32(tableId)); + address routeOwner = RouteOwnerTable.get(world, tableId); assertEq(routeOwner, address(this)); // The new table should be accessible by the caller - assertTrue(RouteAccessTable.get({ store: world, routeId: bytes32(tableId), caller: address(this) })); + assertTrue(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(this) })); // The new table should not be accessible by another address - assertFalse(RouteAccessTable.get({ store: world, routeId: bytes32(tableId), caller: address(0x01) })); + assertFalse(RouteAccessTable.get({ store: world, routeId: tableId, caller: address(0x01) })); // Expect an error when registering an existing table vm.expectRevert(abi.encodeWithSelector(World.RouteExists.selector, "/testRouteAccess")); @@ -219,14 +219,14 @@ contract WorldTest is Test { function testRegisterSystem() public { System system = new System(); - bytes32 systemRouteId = world.registerSystem("", "/testSystem", system, false); + uint256 systemRouteId = world.registerSystem("", "/testSystem", system, false); // Expect the system to be registered (address registeredAddress, bool publicAccess) = SystemTable.get(world, systemRouteId); assertEq(registeredAddress, address(system)); // Expect the system route to be owned by the caller - address routeOwner = OwnerTable.get(world, systemRouteId); + address routeOwner = RouteOwnerTable.get(world, systemRouteId); assertEq(routeOwner, address(this)); // Expect the system to not be publicly accessible @@ -239,7 +239,7 @@ contract WorldTest is Test { assertFalse(RouteAccessTable.get({ store: world, routeId: systemRouteId, caller: address(0x01) })); // Expect the system to have access to its own base route - assertTrue(RouteAccessTable.get({ store: world, routeId: keccak256(bytes("")), caller: address(system) })); + assertTrue(RouteAccessTable.get({ store: world, routeId: uint256(keccak256(bytes(""))), caller: address(system) })); // Expect an error when registering an existing system vm.expectRevert(abi.encodeWithSelector(World.SystemExists.selector, address(system))); @@ -540,8 +540,8 @@ contract WorldTest is Test { // TODO: add a test for systems writing to tables via the World function testHashEquality() public { - // bytes32 h1 = keccak256("testHashEquality"); - // bytes32 h2 = keccak256(abi.encodePacked(bytes32("testHashEquality"))); + // bytes32 h1 = uint256(keccak256("testHashEquality")); + // bytes32 h2 = uint256(keccak256(abi.encodePacked(bytes32("testHashEquality")))); // assertEq(h1, h2); } } From 8247a5456effc5224a60ed54d04ad3bf7c8add5b Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 14:22:25 -0500 Subject: [PATCH 34/42] ci(world): avoid conflicting Store contracts --- packages/store/test/StoreSwitch.t.sol | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/store/test/StoreSwitch.t.sol b/packages/store/test/StoreSwitch.t.sol index 161f1f06cf..2943f52ac8 100644 --- a/packages/store/test/StoreSwitch.t.sol +++ b/packages/store/test/StoreSwitch.t.sol @@ -8,7 +8,7 @@ import { StoreView } from "../src/StoreView.sol"; import { StoreSwitch } from "../src/StoreSwitch.sol"; // Mock Store to call MockSystem -contract Store is StoreView { +contract StoreSwitchTestStore is StoreView { MockSystem mockSystem = new MockSystem(); function callViaDelegateCall() public returns (bool isDelegate) { @@ -33,10 +33,10 @@ contract MockSystem { } contract StoreSwitchTest is Test { - Store store; + StoreSwitchTestStore store; function setUp() public { - store = new Store(); + store = new StoreSwitchTestStore(); } function testIsDelegatecall() public { From fdcc1da5f8a8e1fc34fb3b7424132bb6d8467b5b Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 14:24:18 -0500 Subject: [PATCH 35/42] refactor(store): remove unused World and System contracts and tests --- packages/store/src/System.sol | 12 --- packages/store/src/World.sol | 122 ------------------------------- packages/store/test/System.t.sol | 24 ------ packages/store/test/World.t.sol | 116 ----------------------------- 4 files changed, 274 deletions(-) delete mode 100644 packages/store/src/System.sol delete mode 100644 packages/store/src/World.sol delete mode 100644 packages/store/test/System.t.sol delete mode 100644 packages/store/test/World.t.sol diff --git a/packages/store/src/System.sol b/packages/store/src/System.sol deleted file mode 100644 index 1fce49db82..0000000000 --- a/packages/store/src/System.sol +++ /dev/null @@ -1,12 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity >=0.8.0; - -contract System { - // Extract the trusted msg.sender value appended to the calldata - function _msgSender() internal pure returns (address sender) { - assembly { - // 96 = 256 - 20 * 8 - sender := shr(96, calldataload(sub(calldatasize(), 20))) - } - } -} diff --git a/packages/store/src/World.sol b/packages/store/src/World.sol deleted file mode 100644 index b189f0101c..0000000000 --- a/packages/store/src/World.sol +++ /dev/null @@ -1,122 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity >=0.8.0; - -import { console } from "forge-std/console.sol"; -import { StoreCore } from "./StoreCore.sol"; -import { StoreView } from "./StoreView.sol"; -import { SchemaType, ExecutionMode } from "./Types.sol"; -import { RouteTable, Route, tableId as RouteId } from "./tables/RouteTable.sol"; -import { Bytes } from "./Bytes.sol"; -import { Schema } from "./Schema.sol"; - -/** - * TODO: add access control - */ -contract World is StoreView { - error World_InvalidSystem(); - - constructor() { - registerSchema(RouteId, RouteTable.getSchema()); - } - - function registerSchema(uint256 table, Schema schema) public override { - StoreCore.registerSchema(table, schema); - } - - function setRecord( - uint256 table, - bytes32[] calldata key, - bytes calldata data - ) public override { - StoreCore.setRecord(table, key, data); - } - - function setField( - uint256 table, - bytes32[] calldata key, - uint8 schemaIndex, - bytes calldata data - ) public override { - StoreCore.setField(table, key, schemaIndex, data); - } - - function registerSystem( - address contractAddress, - string memory contractName, - string memory functionSig, - ExecutionMode executionMode - ) public { - // TODO: checks - bytes4 worldSelector = bytes4(keccak256(abi.encodePacked(contractName, "_", functionSig))); - bytes4 funcSelector = bytes4(keccak256(abi.encodePacked(functionSig))); - RouteTable.set(bytes32(worldSelector), contractAddress, funcSelector, uint8(executionMode)); - } - - fallback() external payable { - // Find system by generated function selector - Route memory route = RouteTable.get(bytes32(msg.sig)); - - address addr = route.addr; - bytes4 selector = route.selector; - - if (addr == address(0)) revert World_InvalidSystem(); - - // Call the system function via `call` if the system is autonomous - if (route.executionMode == uint8(ExecutionMode.Autonomous)) { - assembly { - // place system function selector at memory position 0 - mstore(0, selector) - - // place existing calldata (exclusing selector) after system function selector - calldatacopy(4, 4, sub(calldatasize(), 4)) - - // place msg.sender after calldata - mstore(calldatasize(), caller()) - - // execute function call using the system and pass the constructed calldata - let result := call(gas(), addr, callvalue(), 0, add(calldatasize(), 32), 0, 0) - - // place any return value into memory at position 0 - returndatacopy(0, 0, returndatasize()) - - // return any return value or error back to the caller - switch result - case 0 { - revert(0, returndatasize()) - } - default { - return(0, returndatasize()) - } - } - } - - // Call the system function via `delegatecall` if the system is autonomous - if (route.executionMode == uint8(ExecutionMode.Delegate)) { - assembly { - // place system function selector at memory position 0 - mstore(0, selector) - - // place existing calldata (exclusing selector) after system function selector - calldatacopy(4, 4, sub(calldatasize(), 4)) - - // place msg.sender after calldata - mstore(calldatasize(), caller()) - - // execute function call using the system and pass the constructed calldata - let result := delegatecall(gas(), addr, 0, add(calldatasize(), 32), 0, 0) - - // place any return value into memory at position 0 - returndatacopy(0, 0, returndatasize()) - - // return any return value or error back to the caller - switch result - case 0 { - revert(0, returndatasize()) - } - default { - return(0, returndatasize()) - } - } - } - } -} diff --git a/packages/store/test/System.t.sol b/packages/store/test/System.t.sol deleted file mode 100644 index 0a54d5b7cf..0000000000 --- a/packages/store/test/System.t.sol +++ /dev/null @@ -1,24 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity >=0.8.0; - -import "forge-std/Test.sol"; -import { World } from "../src/World.sol"; -import { System } from "../src/System.sol"; - -contract TestSystem is System { - function msgSender() public pure returns (address) { - // !gasreport extract msg.sender from calldata - address sender = _msgSender(); - return sender; - } -} - -contract SystemTest is Test { - function testMsgSender() public { - TestSystem system = new TestSystem(); - address sender = address(0x123); - (bool success, bytes memory returndata) = address(system).call(abi.encodeWithSignature("msgSender()", sender)); - assertTrue(success); - assertEq(abi.decode(returndata, (address)), sender); - } -} diff --git a/packages/store/test/World.t.sol b/packages/store/test/World.t.sol deleted file mode 100644 index f768fc496a..0000000000 --- a/packages/store/test/World.t.sol +++ /dev/null @@ -1,116 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity >=0.8.0; - -import "forge-std/Test.sol"; -import { World } from "../src/World.sol"; -import { System } from "../src/System.sol"; -import { ExecutionMode } from "../src/Types.sol"; -import { Vector2Table, Vector2 } from "../src/tables/Vector2Table.sol"; - -contract WorldTestSystem is System { - function msgSender() public pure returns (address) { - return _msgSender(); - } - - // WorldTestSystem's move function sets state on the Vector2Table of the caller - // (independent of delegatecall or regular call) - function move( - bytes32 entity, - uint32 x, - uint32 y - ) public { - Vector2Table.set({ key: entity, x: x, y: y }); - } -} - -// TODO: auto-generate this interface from registered systems -interface WorldWithWorldTestSystem { - function WorldTestSystem_msgSender() external view returns (address); - - function WorldTestSystem_move( - bytes32 entity, - uint32 x, - uint32 y - ) external; -} - -contract WorldTest is Test { - World internal world; - WorldTestSystem internal system; - - function setUp() public { - world = new World(); - system = new WorldTestSystem(); - } - - function testRegisterAndCallSystem() public { - // Register autonomous system in the world - world.registerSystem(address(system), "WorldTestSystem", "msgSender()", ExecutionMode.Autonomous); - - // Call system via world contract - address msgSender = WorldWithWorldTestSystem(address(world)).WorldTestSystem_msgSender(); - - // msg.sender (this) should have been passed to system - assertEq(msgSender, address(this)); - } - - function testRegisterAndDelegatecallSystem() public { - // Register delegate system in the world - world.registerSystem(address(system), "WorldTestSystem", "msgSender()", ExecutionMode.Delegate); - - // Call system via world contract - address msgSender = WorldWithWorldTestSystem(address(world)).WorldTestSystem_msgSender(); - - // msg.sender (this) should have been passed to system - assertEq(msgSender, address(this)); - } - - function testRegisterVector2Table() public { - // Register table - Vector2Table.registerSchema(world); - } - - // Register WorldTestSystem as autonomous system and call its move function to set state on Vector2Table - function testSetVector2ViaWorldTestSystemAutonomous() public { - // Register autonomous system in the world - world.registerSystem(address(system), "WorldTestSystem", "move(bytes32,uint32,uint32)", ExecutionMode.Autonomous); - - // Register table - Vector2Table.registerSchema(world); - - // Call autonomous system's move function via world contract - bytes32 entity = keccak256("entity"); - - // !gasreport call autonomous system via World contract - WorldWithWorldTestSystem(address(world)).WorldTestSystem_move(entity, 1, 2); - - // Get state from the table (using out-of-system syntax) - Vector2 memory vec2 = Vector2Table.get(world, entity); - - // Verify the state has been set correctly - assertEq(vec2.x, 1); - assertEq(vec2.y, 2); - } - - // Register WorldTestSystem as delegate system and call its move function to set state on Vector2Table - function testSetVector2ViaWorldTestSystemDelegate() public { - // Register delegate system in the world - world.registerSystem(address(system), "WorldTestSystem", "move(bytes32,uint32,uint32)", ExecutionMode.Delegate); - - // Register table - Vector2Table.registerSchema(world); - - // Call delegate system's move function via world contract - bytes32 entity = keccak256("entity"); - - // !gasreport call delegate system via World contract - WorldWithWorldTestSystem(address(world)).WorldTestSystem_move(entity, 1, 2); - - // Get state from the table (using out-of-system syntax) - Vector2 memory vec2 = Vector2Table.get(world, entity); - - // Verify the state has been set correctly - assertEq(vec2.x, 1); - assertEq(vec2.y, 2); - } -} From b6258e5cb1d251f52977087528e7f9ef2ea4927f Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 19:31:11 +0000 Subject: [PATCH 36/42] test: update gas report --- packages/store/gas-report.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/store/gas-report.txt b/packages/store/gas-report.txt index aec8528678..c7ba62cc3b 100644 --- a/packages/store/gas-report.txt +++ b/packages/store/gas-report.txt @@ -89,4 +89,4 @@ (test/Vector2Table.t.sol) | set Vector2Table record [Vector2Table.set({ key: key, x: 1, y: 2 })]: 35773 (test/Vector2Table.t.sol) | get Vector2Table record [Vector2 memory vector = Vector2Table.get(key)]: 3638 (test/World.t.sol) | call autonomous system via World contract [WorldWithWorldTestSystem(address(world)).WorldTestSystem_move(entity, 1, 2)]: 43386 -(test/World.t.sol) | call delegate system via World contract [WorldWithWorldTestSystem(address(world)).WorldTestSystem_move(entity, 1, 2)]: 41226 \ No newline at end of file +(test/World.t.sol) | call delegate system via World contract [WorldWithWorldTestSystem(address(world)).WorldTestSystem_move(entity, 1, 2)]: 41226 From 9a68d83618d51c2fce66b454cbf61d6844113c83 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 16:52:09 -0500 Subject: [PATCH 37/42] refactor(world): update remapping --- .vscode/settings.json | 2 +- packages/world/remappings.txt | 2 +- packages/world/src/World.sol | 6 +++--- packages/world/src/schemas/AddressArray.sol | 18 +++++++++--------- packages/world/src/schemas/Bool.sol | 14 +++++++------- .../world/src/schemas/RouteAccessSchema.sol | 14 +++++++------- .../world/src/schemas/RouteOwnerSchema.sol | 14 +++++++------- packages/world/src/schemas/RouteSchema.sol | 16 ++++++++-------- .../world/src/schemas/SystemRouteSchema.sol | 14 +++++++------- packages/world/src/schemas/SystemSchema.sol | 16 ++++++++-------- packages/world/src/tables/RouteAccessTable.sol | 6 +++--- packages/world/src/tables/RouteOwnerTable.sol | 6 +++--- packages/world/src/tables/RouteTable.sol | 6 +++--- packages/world/src/tables/SystemRouteTable.sol | 6 +++--- packages/world/src/tables/SystemTable.sol | 6 +++--- packages/world/test/World.t.sol | 6 +++--- 16 files changed, 76 insertions(+), 76 deletions(-) diff --git a/.vscode/settings.json b/.vscode/settings.json index 6d67e32743..d20b7a0111 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -10,6 +10,6 @@ "solecs/=node_modules/@latticexyz/solecs/src/", "royalty-registry/=node_modules/@manifoldxzy/royalty-registry/contracts/", "std-contracts/=node_modules/@latticexyz/std-contracts/src/", - "@latticexyz/store/=node_modules/@latticexyz/store/src/" + "@latticexyz/=node_modules/@latticexyz/" ] } diff --git a/packages/world/remappings.txt b/packages/world/remappings.txt index d72d703e66..bb98a1f2b8 100644 --- a/packages/world/remappings.txt +++ b/packages/world/remappings.txt @@ -1,3 +1,3 @@ ds-test/=../../node_modules/ds-test/src/ forge-std/=../../node_modules/forge-std/src/ -@latticexyz/store/=../../node_modules/@latticexyz/store/src/ +@latticexyz/=../../node_modules/@latticexyz/ diff --git a/packages/world/src/World.sol b/packages/world/src/World.sol index 5b34fe4e6b..ed29710557 100644 --- a/packages/world/src/World.sol +++ b/packages/world/src/World.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { Store, IStoreHook } from "@latticexyz/store/Store.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { Store, IStoreHook } from "@latticexyz/store/src/Store.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { RouteOwnerTable } from "./tables/RouteOwnerTable.sol"; import { RouteAccessTable } from "./tables/RouteAccessTable.sol"; diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index 9cc8cbb09c..72f68c2c58 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -2,15 +2,15 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { SliceLib } from "@latticexyz/store/Slice.sol"; -import { EncodeArray } from "@latticexyz/store/tightcoder/EncodeArray.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { SliceLib } from "@latticexyz/store/src/Slice.sol"; +import { EncodeArray } from "@latticexyz/store/src/tightcoder/EncodeArray.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; // -- User defined schema and tableId -- struct AddressArraySchema { diff --git a/packages/world/src/schemas/Bool.sol b/packages/world/src/schemas/Bool.sol index a952f08479..860951b26e 100644 --- a/packages/world/src/schemas/Bool.sol +++ b/packages/world/src/schemas/Bool.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/schemas/RouteAccessSchema.sol b/packages/world/src/schemas/RouteAccessSchema.sol index 67b836961a..c46a25733d 100644 --- a/packages/world/src/schemas/RouteAccessSchema.sol +++ b/packages/world/src/schemas/RouteAccessSchema.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/schemas/RouteOwnerSchema.sol b/packages/world/src/schemas/RouteOwnerSchema.sol index 6e92b438e1..3835183f8e 100644 --- a/packages/world/src/schemas/RouteOwnerSchema.sol +++ b/packages/world/src/schemas/RouteOwnerSchema.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; // -- User defined schema and tableId -- struct RouteOwnerSchema { diff --git a/packages/world/src/schemas/RouteSchema.sol b/packages/world/src/schemas/RouteSchema.sol index 1e77c92c02..a33bc41138 100644 --- a/packages/world/src/schemas/RouteSchema.sol +++ b/packages/world/src/schemas/RouteSchema.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { SliceLib } from "@latticexyz/store/Slice.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { SliceLib } from "@latticexyz/store/src/Slice.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; // -- User defined schema and tableId -- struct RouteSchema { diff --git a/packages/world/src/schemas/SystemRouteSchema.sol b/packages/world/src/schemas/SystemRouteSchema.sol index c6d72fdadd..55384fc66d 100644 --- a/packages/world/src/schemas/SystemRouteSchema.sol +++ b/packages/world/src/schemas/SystemRouteSchema.sol @@ -2,13 +2,13 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; // -- User defined schema and tableId -- struct SystemRouteSchema { diff --git a/packages/world/src/schemas/SystemSchema.sol b/packages/world/src/schemas/SystemSchema.sol index b5039b43be..b3ecafc0d7 100644 --- a/packages/world/src/schemas/SystemSchema.sol +++ b/packages/world/src/schemas/SystemSchema.sol @@ -2,14 +2,14 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Bytes } from "@latticexyz/store/Bytes.sol"; -import { Schema, SchemaLib } from "@latticexyz/store/Schema.sol"; -import { PackedCounter, PackedCounterLib } from "@latticexyz/store/PackedCounter.sol"; -import { SliceLib } from "@latticexyz/store/Slice.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Bytes } from "@latticexyz/store/src/Bytes.sol"; +import { Schema, SchemaLib } from "@latticexyz/store/src/Schema.sol"; +import { PackedCounter, PackedCounterLib } from "@latticexyz/store/src/PackedCounter.sol"; +import { SliceLib } from "@latticexyz/store/src/Slice.sol"; import { bytes32ToBool } from "../Utils.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/RouteAccessTable.sol b/packages/world/src/tables/RouteAccessTable.sol index ab2529c5f1..83071dbde4 100644 --- a/packages/world/src/tables/RouteAccessTable.sol +++ b/packages/world/src/tables/RouteAccessTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { RouteAccessSchemaLib as SchemaLib } from "../schemas/RouteAccessSchema.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/RouteOwnerTable.sol b/packages/world/src/tables/RouteOwnerTable.sol index bd5a05ff00..c0b7a92a50 100644 --- a/packages/world/src/tables/RouteOwnerTable.sol +++ b/packages/world/src/tables/RouteOwnerTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { RouteOwnerSchemaLib as SchemaLib } from "../schemas/RouteOwnerSchema.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/RouteTable.sol b/packages/world/src/tables/RouteTable.sol index 2d398fd8d4..4cbb87510c 100644 --- a/packages/world/src/tables/RouteTable.sol +++ b/packages/world/src/tables/RouteTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { RouteSchemaLib as SchemaLib } from "../schemas/RouteSchema.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/SystemRouteTable.sol b/packages/world/src/tables/SystemRouteTable.sol index 90e0ae56d5..882c967d78 100644 --- a/packages/world/src/tables/SystemRouteTable.sol +++ b/packages/world/src/tables/SystemRouteTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { SystemRouteSchemaLib as SchemaLib } from "../schemas/SystemRouteSchema.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/src/tables/SystemTable.sol b/packages/world/src/tables/SystemTable.sol index b9eb20e71a..46591206ba 100644 --- a/packages/world/src/tables/SystemTable.sol +++ b/packages/world/src/tables/SystemTable.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import { console } from "forge-std/console.sol"; -import { IStore } from "@latticexyz/store/IStore.sol"; -import { SchemaType } from "@latticexyz/store/Types.sol"; -import { Schema } from "@latticexyz/store/Schema.sol"; +import { IStore } from "@latticexyz/store/src/IStore.sol"; +import { SchemaType } from "@latticexyz/store/src/Types.sol"; +import { Schema } from "@latticexyz/store/src/Schema.sol"; import { SystemSchemaLib as SchemaLib } from "../schemas/SystemSchema.sol"; // -- User defined schema and tableId -- diff --git a/packages/world/test/World.t.sol b/packages/world/test/World.t.sol index e14baf5e26..ec383ce5b3 100644 --- a/packages/world/test/World.t.sol +++ b/packages/world/test/World.t.sol @@ -2,9 +2,9 @@ pragma solidity >=0.8.0; import "forge-std/Test.sol"; -import { IStoreHook } from "@latticexyz/store/IStore.sol"; -import { StoreCore } from "@latticexyz/store/StoreCore.sol"; -import { StoreSwitch } from "@latticexyz/store/StoreSwitch.sol"; +import { IStoreHook } from "@latticexyz/store/src/IStore.sol"; +import { StoreCore } from "@latticexyz/store/src/StoreCore.sol"; +import { StoreSwitch } from "@latticexyz/store/src/StoreSwitch.sol"; import { World, _isRoute, _isSingleLevelRoute } from "../src/World.sol"; import { System } from "../src/System.sol"; From 1f2f19ef353ccf93160fffb3692c065b839f590f Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 17:01:44 -0500 Subject: [PATCH 38/42] ci: disable automatic gas-report commit and instead just check if gas report is up to date --- .github/workflows/gasreport.yml | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/.github/workflows/gasreport.yml b/.github/workflows/gasreport.yml index bee09623c9..5ca6f88c3a 100644 --- a/.github/workflows/gasreport.yml +++ b/.github/workflows/gasreport.yml @@ -5,6 +5,7 @@ on: pull_request: paths: - packages/store/** + - packages/world/** jobs: gas-report: @@ -29,9 +30,5 @@ jobs: - name: Install local CLI run: cd packages/cli && yarn build && npm link && cd ../.. - - name: Run gas report - run: yarn workspace @latticexyz/store run gasreport - - - uses: stefanzweifel/git-auto-commit-action@v4 - with: - commit_message: "test: update gas report" + - name: Verify that gas report is up to date + run: yarn workspace @latticexyz/store run gasreport && yarn workspace @latticexyx/world run gasreport && if [ -n "$(git status --porcelain)" ]; then exit 0; fi From 75849f2e2f66a01556ae242f41c7c64acee33db4 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 17:02:51 -0500 Subject: [PATCH 39/42] docs(world): update index.yml --- packages/world/index.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/world/index.yml b/packages/world/index.yml index 67be39bdfd..85c3374156 100644 --- a/packages/world/index.yml +++ b/packages/world/index.yml @@ -1,2 +1,2 @@ -label: store -order: 50 +label: world +order: 45 From 253d8bb4e12e6d03eab8fb32a7a447b06fb7aff8 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 19:33:37 -0500 Subject: [PATCH 40/42] ci: fix gas-report action typo --- .github/workflows/gasreport.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/gasreport.yml b/.github/workflows/gasreport.yml index 5ca6f88c3a..cd530fa6f9 100644 --- a/.github/workflows/gasreport.yml +++ b/.github/workflows/gasreport.yml @@ -31,4 +31,4 @@ jobs: run: cd packages/cli && yarn build && npm link && cd ../.. - name: Verify that gas report is up to date - run: yarn workspace @latticexyz/store run gasreport && yarn workspace @latticexyx/world run gasreport && if [ -n "$(git status --porcelain)" ]; then exit 0; fi + run: yarn workspace @latticexyz/store run gasreport && yarn workspace @latticexyz/world run gasreport && if [ -n "$(git status --porcelain)" ]; then exit 0; fi From 7a9c9f707db78eeff7135f22d2b3d3c5185ff300 Mon Sep 17 00:00:00 2001 From: alvrs Date: Tue, 21 Feb 2023 19:46:31 -0500 Subject: [PATCH 41/42] fix: rebase changes --- packages/world/src/schemas/AddressArray.sol | 2 +- packages/world/src/schemas/SystemSchema.sol | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/world/src/schemas/AddressArray.sol b/packages/world/src/schemas/AddressArray.sol index 72f68c2c58..5203ceb04d 100644 --- a/packages/world/src/schemas/AddressArray.sol +++ b/packages/world/src/schemas/AddressArray.sol @@ -83,6 +83,6 @@ library AddressArraySchemaLib { function decode(bytes memory blob) internal pure returns (address[] memory addresses) { if (blob.length == 0) return new address[](0); - SliceLib.getSubslice(blob, 32).toAddressArray(); + SliceLib.getSubslice(blob, 32).decodeArray_address(); } } diff --git a/packages/world/src/schemas/SystemSchema.sol b/packages/world/src/schemas/SystemSchema.sol index b3ecafc0d7..2ab3a7c410 100644 --- a/packages/world/src/schemas/SystemSchema.sol +++ b/packages/world/src/schemas/SystemSchema.sol @@ -60,7 +60,7 @@ library SystemSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = bytes32(routeId); bytes memory blob = StoreSwitch.getRecord(tableId, keyTuple); - system = SliceLib.fromBytes(blob).toAddress(); + system = address(bytes20(blob)); publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); } @@ -72,7 +72,7 @@ library SystemSchemaLib { bytes32[] memory keyTuple = new bytes32[](1); keyTuple[0] = bytes32(routeId); bytes memory blob = store.getRecord(tableId, keyTuple); - system = SliceLib.fromBytes(blob).toAddress(); + system = address(bytes20(blob)); publicAccess = bytes32ToBool(SliceLib.getSubslice(blob, 20).toBytes32()); } } From 6d349f1624422f24b2027686489674b18fdbd70d Mon Sep 17 00:00:00 2001 From: alvrs Date: Wed, 22 Feb 2023 11:24:17 -0500 Subject: [PATCH 42/42] fix(world): use released mud cli for gas report --- packages/world/gas-report.txt | 24 +++++++++++++----------- packages/world/package.json | 4 ++-- yarn.lock | 4 ++++ 3 files changed, 19 insertions(+), 13 deletions(-) diff --git a/packages/world/gas-report.txt b/packages/world/gas-report.txt index 9f0df47cee..bc9f74f39f 100644 --- a/packages/world/gas-report.txt +++ b/packages/world/gas-report.txt @@ -1,11 +1,13 @@ -(test/World.t.sol) | validate route (empty string) [assertTrue(_isRoute(""), "empty string")]: 250 -(test/World.t.sol) | validate route (single slash) [assertTrue(_isRoute("/"), "single slash")]: 265 -(test/World.t.sol) | validate route (single level) [assertTrue(_isRoute("/topLevel"), "single level")]: 264 -(test/World.t.sol) | validate route (multi level) [assertTrue(_isRoute("/topLevel/subLevel"), "multi level")]: 262 -(test/World.t.sol) | validate route (no leading slash) [assertFalse(_isRoute("noLeadingSlash"), "no leading slash")]: 298 -(test/World.t.sol) | validate single level route (empty string) [assertTrue(_isSingleLevelRoute(""), "empty string")]: 347 -(test/World.t.sol) | validate single level route (single slash) [assertTrue(_isSingleLevelRoute("/"), "single slash")]: 362 -(test/World.t.sol) | validate single level route (single level) [assertTrue(_isSingleLevelRoute("/topLevel"), "single level")]: 1290 -(test/World.t.sol) | validate single level route (multi level) [assertFalse(_isSingleLevelRoute("/topLevel/subLevel"), "multi level")]: 1391 -(test/World.t.sol) | validate single level route (no leading slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash"), "no leading slash")]: 351 -(test/World.t.sol) | validate single level route (no leading slash but contains slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash/butContainsSlash"), "no leading slash")]: 354 \ No newline at end of file +(test/World.t.sol) | validate route (empty string) [assertTrue(_isRoute(""), "empty string")]: 276 +(test/World.t.sol) | validate route (single slash) [assertFalse(_isRoute("/"), "single slash")]: 333 +(test/World.t.sol) | validate route (single character) [assertTrue(_isRoute("/a"), "single character")]: 291 +(test/World.t.sol) | validate route (single level) [assertTrue(_isRoute("/topLevel"), "single level")]: 289 +(test/World.t.sol) | validate route (multi level) [assertTrue(_isRoute("/topLevel/subLevel"), "multi level")]: 289 +(test/World.t.sol) | validate route (no leading slash) [assertFalse(_isRoute("noLeadingSlash"), "no leading slash")]: 325 +(test/World.t.sol) | validate single level route (empty string) [assertTrue(_isSingleLevelRoute(""), "empty string")]: 373 +(test/World.t.sol) | validate single level route (single slash) [assertFalse(_isSingleLevelRoute("/"), "single slash")]: 389 +(test/World.t.sol) | validate route (single character) [assertTrue(_isRoute("/a"), "single character")]: 292 +(test/World.t.sol) | validate single level route (single level) [assertTrue(_isSingleLevelRoute("/topLevel"), "single level")]: 1314 +(test/World.t.sol) | validate single level route (multi level) [assertFalse(_isSingleLevelRoute("/topLevel/subLevel"), "multi level")]: 1419 +(test/World.t.sol) | validate single level route (no leading slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash"), "no leading slash")]: 377 +(test/World.t.sol) | validate single level route (no leading slash but contains slash) [assertFalse(_isSingleLevelRoute("noLeadingSlash/butContainsSlash"), "no leading slash")]: 381 \ No newline at end of file diff --git a/packages/world/package.json b/packages/world/package.json index 40fa1f57a6..d6a846704d 100644 --- a/packages/world/package.json +++ b/packages/world/package.json @@ -22,7 +22,7 @@ "link": "yarn link", "docs": "rimraf API && hardhat docgen && echo 'label: API\norder: 50' > API/index.yml", "release": "npm publish || echo 'version already published'", - "gasreport": " ../cli/dist/index.js gas-report --path test/** --save gas-report.txt" + "gasreport": "mud gas-report --path test/** --save gas-report.txt" }, "devDependencies": { "@typechain/ethers-v5": "^9.0.0", @@ -38,7 +38,7 @@ "ts-node": "10.7", "typechain": "^8.1.1", "typedoc": "^0.23.10", - "@latticexyz/cli": "^1.34.0", + "@latticexyz/cli": "^1.37.1", "@latticexyz/store": "^1.34.0" }, diff --git a/yarn.lock b/yarn.lock index 54ad8696f3..83ffd83335 100644 --- a/yarn.lock +++ b/yarn.lock @@ -8287,6 +8287,10 @@ forever-agent@~0.6.1: version "1.2.0" resolved "https://github.com/foundry-rs/forge-std.git#b4f121555729b3afb3c5ffccb62ff4b6e2818fd3" +"forge-std@https://github.com/foundry-rs/forge-std.git#f36dab24d63d1c1945a05ed375ce341d3c1a49ed": + version "0.1.0" + resolved "https://github.com/foundry-rs/forge-std.git#f36dab24d63d1c1945a05ed375ce341d3c1a49ed" + form-data@^3.0.0: version "3.0.1" resolved "https://registry.yarnpkg.com/form-data/-/form-data-3.0.1.tgz#ebd53791b78356a99af9a300d4282c4d5eb9755f"