diff --git a/.github/workflows/ci-config.yml b/.github/workflows/ci-config.yml index 9081a01..6b6a006 100644 --- a/.github/workflows/ci-config.yml +++ b/.github/workflows/ci-config.yml @@ -66,29 +66,29 @@ jobs: - name: Tests the project run: npm run test - coverage: - runs-on: ubuntu-latest - - needs: test - - # Steps represent a sequence of tasks that will be executed as part of the job - steps: - # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it - - uses: actions/checkout@v2 - - uses: actions/setup-node@v2 - with: - node-version: "14" - - # Runs a single command using the runners shell - - name: Installs needed packages using npm - run: npm i && npm install -g codecov - - # Runs a single command using the runners shell - - name: Tests the project - run: npm run coverage - - # Runs a single command using the runners shell - - name: Tests the project - run: codecov - env: - CODECOV_TOKEN: "9095761f-e37d-44f6-97b2-b123131a342f" + # coverage: + # runs-on: ubuntu-latest + + # needs: test + + # # Steps represent a sequence of tasks that will be executed as part of the job + # steps: + # # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it + # - uses: actions/checkout@v2 + # - uses: actions/setup-node@v2 + # with: + # node-version: "14" + + # # Runs a single command using the runners shell + # - name: Installs needed packages using npm + # run: npm i && npm install -g codecov + + # # Runs a single command using the runners shell + # - name: Tests the project + # run: npm run coverage + + # # Runs a single command using the runners shell + # - name: Tests the project + # run: codecov + # env: + # CODECOV_TOKEN: "9095761f-e37d-44f6-97b2-b123131a342f" diff --git a/contracts/lbp/LBPManagerFactory.sol b/contracts/lbp/LBPManagerFactory.sol index f952159..661e4c8 100644 --- a/contracts/lbp/LBPManagerFactory.sol +++ b/contracts/lbp/LBPManagerFactory.sol @@ -16,13 +16,14 @@ pragma solidity 0.8.17; import "../utils/CloneFactory.sol"; import "@openzeppelin/contracts/access/Ownable.sol"; -import "./LBPManager.sol"; +import "./LBPManagerV1.sol"; /** * @title LBPManager Factory * @dev Governance to create new LBPManager contracts. */ contract LBPManagerFactory is CloneFactory, Ownable { + bytes6 public version = "2.1.0"; address public masterCopy; address public lbpFactory; @@ -134,7 +135,7 @@ contract LBPManagerFactory is CloneFactory, Ownable { address lbpManager = createClone(masterCopy); - LBPManager(lbpManager).initializeLBPManager( + LBPManagerV1(lbpManager).initializeLBPManager( lbpFactory, _beneficiary, _name, @@ -148,7 +149,7 @@ contract LBPManagerFactory is CloneFactory, Ownable { _metadata ); - LBPManager(lbpManager).transferAdminRights(_admin); + LBPManagerV1(lbpManager).transferAdminRights(_admin); emit LBPManagerDeployed(lbpManager, _admin, _metadata); } diff --git a/contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol b/contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol new file mode 100644 index 0000000..68c90b5 --- /dev/null +++ b/contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol @@ -0,0 +1,159 @@ +/* +██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░ +██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗ +██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║ +██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║ +██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝ +╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░ +*/ + +// SPDX-License-Identifier: GPL-3.0-or-later +// LBPManager Factory contract. Governance to create new LBPManager contracts. +// Copyright (C) 2021 PrimeDao + +// solium-disable linebreak-style +pragma solidity 0.8.17; + +import "../utils/CloneFactory.sol"; +import "@openzeppelin/contracts/access/Ownable.sol"; +import "./LBPManagerV1.sol"; + +/** + * @title LBPManager Factory no access control version 1 + * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the + * function deployLBPManager(). By removing the access control, everyone can deploy a + * LBPManager from this contract. This is a temporarly solution in response to the + * flaky Celo Safe. + */ +contract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable { + bytes6 public version = "1.0.0"; + address public masterCopy; + address public lbpFactory; + + event LBPManagerDeployed( + address indexed lbpManager, + address indexed admin, + bytes metadata + ); + + event LBPFactoryChanged( + address indexed oldLBPFactory, + address indexed newLBPFactory + ); + + event MastercopyChanged( + address indexed oldMasterCopy, + address indexed newMasterCopy + ); + + /** + * @dev Constructor. + * @param _lbpFactory The address of Balancers LBP factory. + */ + constructor(address _lbpFactory) { + require(_lbpFactory != address(0), "LBPMFactory: LBPFactory is zero"); + lbpFactory = _lbpFactory; + } + + modifier validAddress(address addressToCheck) { + require(addressToCheck != address(0), "LBPMFactory: address is zero"); + // solhint-disable-next-line reason-string + require( + addressToCheck != address(this), + "LBPMFactory: address same as LBPManagerFactory" + ); + _; + } + + /** + * @dev Set LBPManager contract which works as a base for clones. + * @param _masterCopy The address of the new LBPManager basis. + */ + function setMasterCopy(address _masterCopy) + external + onlyOwner + validAddress(_masterCopy) + { + emit MastercopyChanged(masterCopy, _masterCopy); + masterCopy = _masterCopy; + } + + /** + * @dev Set Balancers LBP Factory contract as basis for deploying LBPs. + * @param _lbpFactory The address of Balancers LBP factory. + */ + function setLBPFactory(address _lbpFactory) + external + onlyOwner + validAddress(_lbpFactory) + { + emit LBPFactoryChanged(lbpFactory, _lbpFactory); + lbpFactory = _lbpFactory; + } + + /** + * @dev Deploy and initialize LBPManager. + * @param _admin The address of the admin of the LBPManager. + * @param _beneficiary The address that receives the _fees. + * @param _name Name of the LBP. + * @param _symbol Symbol of the LBP. + * @param _tokenList Numerically sorted array (ascending) containing two addresses: + - The address of the project token being distributed. + - The address of the funding token being exchanged for the project token. + * @param _amounts Sorted array to match the _tokenList, containing two parameters: + - The amounts of project token to be added as liquidity to the LBP. + - The amounts of funding token to be added as liquidity to the LBP. + * @param _startWeights Sorted array to match the _tokenList, containing two parametes: + - The start weight for the project token in the LBP. + - The start weight for the funding token in the LBP. + * @param _startTimeEndtime Array containing two parameters: + - Start time for the LBP. + - End time for the LBP. + * @param _endWeights Sorted array to match the _tokenList, containing two parametes: + - The end weight for the project token in the LBP. + - The end weight for the funding token in the LBP. + * @param _fees Array containing two parameters: + - Percentage of fee paid for every swap in the LBP. + - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager. + * @param _metadata IPFS Hash of the LBP creation wizard information. + */ + function deployLBPManager( + address _admin, + address _beneficiary, + string memory _name, + string memory _symbol, + IERC20[] memory _tokenList, + uint256[] memory _amounts, + uint256[] memory _startWeights, + uint256[] memory _startTimeEndtime, + uint256[] memory _endWeights, + uint256[] memory _fees, + bytes memory _metadata + ) external { + // solhint-disable-next-line reason-string + require( + masterCopy != address(0), + "LBPMFactory: LBPManager mastercopy not set" + ); + + address lbpManager = createClone(masterCopy); + + LBPManagerV1(lbpManager).initializeLBPManager( + lbpFactory, + _beneficiary, + _name, + _symbol, + _tokenList, + _amounts, + _startWeights, + _startTimeEndtime, + _endWeights, + _fees, + _metadata + ); + + LBPManagerV1(lbpManager).transferAdminRights(_admin); + + emit LBPManagerDeployed(lbpManager, _admin, _metadata); + } +} diff --git a/contracts/lbp/LBPManager.sol b/contracts/lbp/LBPManagerV1.sol similarity index 99% rename from contracts/lbp/LBPManager.sol rename to contracts/lbp/LBPManagerV1.sol index bf539c6..5c5fb05 100644 --- a/contracts/lbp/LBPManager.sol +++ b/contracts/lbp/LBPManagerV1.sol @@ -20,11 +20,12 @@ import "../utils/interface/IVault.sol"; import "../utils/interface/ILBP.sol"; /** - * @title LBPManager contract. + * @title LBPManager contract version 1 * @dev Smart contract for managing interactions with a Balancer LBP. */ // solhint-disable-next-line max-states-count -contract LBPManager { +contract LBPManagerV1 { + bytes6 public version = "1.0.0"; // Constants uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee. diff --git a/deploy/04_deploy_lbpV1NoAccessControl_contracts.js b/deploy/04_deploy_lbpV1NoAccessControl_contracts.js new file mode 100644 index 0000000..3011304 --- /dev/null +++ b/deploy/04_deploy_lbpV1NoAccessControl_contracts.js @@ -0,0 +1,49 @@ +const { getBalancerContractAddress } = require("@balancer-labs/v2-deployments"); + +const deployFunction = async ({ + getNamedAccounts, + deployments, + ethers, + network, +}) => { + const { deploy } = deployments; + const { root } = await getNamedAccounts(); + + const liquidityBootstrappingPoolFactoryTaskId = + "20211202-no-protocol-fee-lbp"; + const contractName = "LiquidityBootstrappingPoolFactory"; + + // Balancer contracts are not deployed on Celo and Alfajores, so we're using Symmetric/root instead + const lbpFactoryAddress = + network.name === "celo" + ? "0xdF87a2369FAa3140613c3C5D008A9F50B3303fD3" // can be found https://docs.symmetric.exchange/general-resources-and-tools/symmetric-contract-addresses#v2-contracts + : network.name === "goerli" + ? "0xb48Cc42C45d262534e46d5965a9Ac496F1B7a830" // can be found https://dev.balancer.fi/references/contracts/deployment-addresses + : // ToDo: Need to be updated to new package + await getBalancerContractAddress( + liquidityBootstrappingPoolFactoryTaskId, + contractName, + network.name + ); + + await deploy("LBPManagerFactoryV1NoAccessControl", { + from: root, + args: [lbpFactoryAddress], + log: true, + }); + + const { address: lbpManagerAddress } = await deploy("LBPManagerV1", { + from: root, + args: [], + log: true, + }); + + const lbpManagerFactoryInstance = await ethers.getContract( + "LBPManagerFactoryV1NoAccessControl" + ); + + await lbpManagerFactoryInstance.setMasterCopy(lbpManagerAddress); +}; + +module.exports = deployFunction; +module.exports.tags = ["LBPNoAccessControl"]; diff --git a/deployments/celo/LBPManager.json b/deployments/celo/LBPManager.json new file mode 100644 index 0000000..7d098fe --- /dev/null +++ b/deployments/celo/LBPManager.json @@ -0,0 +1,785 @@ +{ + "address": "0xd1BFa64799Eae67b6FeC1741889503daD8FEd768", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0xc5c35952d4ed566b5733d22d0735e926b262804fc5cb63f8cf3adfc641847709", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0xd1BFa64799Eae67b6FeC1741889503daD8FEd768", + "transactionIndex": 4, + "gasUsed": "2298135", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0xe48624ee746f9d010b333f73214a39a4fbdccd07ef6f8829deb8f96dff35200a", + "transactionHash": "0xc5c35952d4ed566b5733d22d0735e926b262804fc5cb63f8cf3adfc641847709", + "logs": [], + "blockNumber": 16537460, + "cumulativeGasUsed": "3494835", + "status": 1, + "byzantium": true + }, + "args": [], + "solcInputHash": "bf89fe6a61a7d22f31b24d3cee885a8d", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"beneficiary\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"tokenAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"FeeTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldAdmin\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newAdmin\",\"type\":\"address\"}],\"name\":\"LBPManagerAdminChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"MetadataUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"PoolTokensWithdrawn\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"admin\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"amounts\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"beneficiary\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"endWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"feePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getSwapEnabled\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_sender\",\"type\":\"address\"}],\"name\":\"initializeLBP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndTime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"initializeLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"initialized\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbp\",\"outputs\":[{\"internalType\":\"contract ILBP\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"metadata\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"name\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"poolFunded\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokenIndex\",\"outputs\":[{\"internalType\":\"uint8\",\"name\":\"\",\"type\":\"uint8\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokensRequired\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"projectTokenAmounts\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"removeLiquidity\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bool\",\"name\":\"_swapEnabled\",\"type\":\"bool\"}],\"name\":\"setSwapEnabled\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startTimeEndTime\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"swapFeePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"symbol\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"tokenList\",\"outputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_newAdmin\",\"type\":\"address\"}],\"name\":\"transferAdminRights\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"updateMetadata\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"withdrawPoolTokens\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Smart contract for managing interactions with a Balancer LBP.\",\"kind\":\"dev\",\"methods\":{\"getSwapEnabled()\":{\"details\":\"Tells whether swaps are enabled or not for the LBP\"},\"initializeLBP(address)\":{\"details\":\"Subtracts the fee, deploys the LBP and adds liquidity to it.\",\"params\":{\"_sender\":\"Address of the liquidity provider.\"}},\"initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Initialize LBPManager.\",\"params\":{\"_amounts\":\"Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the feePercentage.\",\"_endWeights\":\"Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_lbpFactory\":\"LBP factory address.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndTime\":\"Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.\",\"_startWeights\":\"Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token.\"}},\"projectTokensRequired()\":{\"details\":\"Get required amount of project tokens to cover for fees and the actual LBP.\"},\"removeLiquidity(address)\":{\"details\":\"Exit pool or remove liquidity from pool.\",\"params\":{\"_receiver\":\"Address of the liquidity receiver, after exiting the LBP.\"}},\"setSwapEnabled(bool)\":{\"details\":\"Can pause/unpause trading.\",\"params\":{\"_swapEnabled\":\"Enables/disables swapping.\"}},\"transferAdminRights(address)\":{\"details\":\"Transfer admin rights.\",\"params\":{\"_newAdmin\":\"Address of the new admin.\"}},\"updateMetadata(bytes)\":{\"details\":\"Updates metadata.\",\"params\":{\"_metadata\":\"LBP wizard contract metadata, that is an IPFS Hash.\"}},\"withdrawPoolTokens(address)\":{\"details\":\"Withdraw pool tokens if available.\",\"params\":{\"_receiver\":\"Address of the BPT tokens receiver.\"}}},\"title\":\"LBPManager contract.\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManager.sol\":\"LBPManager\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"contracts/lbp/LBPManager.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract.\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManager {\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x371ceeb460072a61394db69c3b0f8b0f4c45dd4d1ee0ad19a1c44ba9f61000b4\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x608060405234801561001057600080fd5b5061289d806100206000396000f3fe608060405234801561001057600080fd5b506004361061018e5760003560e01c8063a001ecdd116100de578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461034b578063e01af92c1461035e578063f851a44014610371578063fc582d411461038457600080fd5b8063c9d8616f14610306578063cb209b6c14610319578063cd2055e51461033857600080fd5b8063a001ecdd146102a2578063a4ac0d49146102ab578063a88971fa146102b4578063b5106add146102c8578063bb7bfb0c146102db578063c18b5151146102ee57600080fd5b80633facbb851161014b5780638638fe31116101255780638638fe31146102615780638bfd52891461027457806395d89b41146102875780639ead72221461028f57600080fd5b80633facbb851461023157806345f0a44f1461024657806347bc4d921461025957600080fd5b806306fdde0314610193578063092f7de7146101b1578063158ef93e146101dc5780633281f3ec1461020057806338af3eed14610216578063392f37e914610229575b600080fd5b61019b610397565b6040516101a89190611f07565b60405180910390f35b600b546101c4906001600160a01b031681565b6040516001600160a01b0390911681526020016101a8565b600d546101f090600160b01b900460ff1681565b60405190151581526020016101a8565b610208610425565b6040519081526020016101a8565b6003546101c4906001600160a01b031681565b61019b610464565b61024461023f366004611f49565b610471565b005b610208610254366004611f66565b6107b2565b6101f06107d3565b61024461026f366004612129565b6108a6565b610244610282366004611f49565b610f89565b61019b611716565b6101c461029d366004611f66565b611723565b61020860045481565b61020860055481565b600d546101f090600160a81b900460ff1681565b6102446102d6366004611f49565b61174d565b6102086102e9366004611f66565b611829565b600d546101c49061010090046001600160a01b031681565b610208610314366004611f66565b611839565b600d546103269060ff1681565b60405160ff90911681526020016101a8565b610208610346366004611f66565b611849565b610244610359366004611f49565b611859565b61024461036c3660046122cd565b611cb1565b6002546101c4906001600160a01b031681565b6102446103923660046122ea565b611d3d565b600180546103a490612327565b80601f01602080910402602001604051908101604052809291908181526020018280546103d090612327565b801561041d5780601f106103f25761010080835404028352916020019161041d565b820191906000526020600020905b81548152906001019060200180831161040057829003601f168201915b505050505081565b600061042f611db5565b600d5460078054909160ff1690811061044a5761044a612361565b906000526020600020015461045f919061238d565b905090565b600c80546103a490612327565b6002546001600160a01b031633146104a45760405162461bcd60e51b815260040161049b906123a6565b60405180910390fd5b6001600160a01b0381166104fa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b6000600a60018154811061051057610510612361565b906000526020600020015490508042101561056d5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105b6573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105da91906123dd565b116106275760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b600b546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa158015610693573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106b791906123dd565b60405190815260200160405180910390a2600b546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561071a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061073e91906123dd565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015610789573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ad91906123f6565b505050565b600781815481106107c257600080fd5b600091825260209091200154905081565b600d54600090600160a81b900460ff1661082f5760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e604482015260640161049b565b600b60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa158015610882573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061045f91906123f6565b600d54600160b01b900460ff16156109005760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a656400604482015260640161049b565b6001600160a01b038a166109565760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f604482015260640161049b565b64e8d4a510008260008151811061096f5761096f612361565b602002602001015110156109d15760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b606482015260840161049b565b67016345785d8a0000826000815181106109ed576109ed612361565b60200260200101511115610a515760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b606482015260840161049b565b86516002148015610a63575085516002145b8015610a70575084516002145b8015610a7d575083516002145b8015610a8a575082516002145b8015610a97575081516002145b610ae35760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a65000000604482015260640161049b565b86600181518110610af657610af6612361565b60200260200101516001600160a01b031687600081518110610b1a57610b1a612361565b60200260200101516001600160a01b031603610b785760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d65604482015260640161049b565b83600181518110610b8b57610b8b612361565b602002602001015184600081518110610ba657610ba6612361565b602002602001015110610bfb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d6500604482015260640161049b565b600d805460ff60b01b1916600160b01b179055600280546001600160a01b0319163317905581518290600090610c3357610c33612361565b602002602001015160058190555081600181518110610c5457610c54612361565b6020908102919091010151600455600380546001600160a01b0319166001600160a01b038c16179055600c610c898282612461565b508351610c9d90600a906020870190611e02565b506001610caa8a82612461565b506000610cb78982612461565b50600d8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610ced57610ced612361565b60200260200101516001600160a01b031687600081518110610d1157610d11612361565b60200260200101516001600160a01b03161115610f2157600d805460ff19166001908117909155875160069189918110610d4d57610d4d612361565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516006918991610d9c57610d9c612361565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160079188918110610df057610df0612361565b602090810291909101810151825460018101845560009384529183209091015586516007918891610e2357610e23612361565b60209081029190910181015182546001818101855560009485529290932090920191909155855160089187918110610e5d57610e5d612361565b602090810291909101810151825460018101845560009384529183209091015585516008918791610e9057610e90612361565b60209081029190910181015182546001818101855560009485529290932090920191909155835160099185918110610eca57610eca612361565b602090810291909101810151825460018101845560009384529183209091015583516009918591610efd57610efd612361565b60209081029190910181015182546001810184556000938452919092200155610f7c565b600d805460ff191690558651610f3e9060069060208a0190611e4d565b508551610f52906007906020890190611e02565b508451610f66906008906020880190611e02565b508251610f7a906009906020860190611e02565b505b5050505050505050505050565b6002546001600160a01b03163314610fb35760405162461bcd60e51b815260040161049b906123a6565b600d54600160b01b900460ff1615156001146110205760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b606482015260840161049b565b600d54600160a81b900460ff161561107a5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e64656400604482015260640161049b565b600d8054600160a81b60ff60a81b199091161790819055600554604051632367971960e01b81526101009092046001600160a01b0316916323679719916110d391600191600091600691600891309085906004016125de565b6020604051808303816000875af11580156110f2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611116919061268f565b600b80546001600160a01b0319166001600160a01b03929092169182179055600a8054633e569205919060009061114f5761114f612361565b9060005260206000200154600a60018154811061116e5761116e612361565b906000526020600020015460096040518463ffffffff1660e01b8152600401611199939291906126ac565b600060405180830381600087803b1580156111b357600080fd5b505af11580156111c7573d6000803e3d6000fd5b505050506000600b60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611220573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611244919061268f565b905060045460001461137d57600061125a611db5565b600d54600680549293509160ff90911690811061127957611279612361565b6000918252602090912001546003546040516323b872dd60e01b81526001600160a01b0386811660048301529182166024820152604481018490529116906323b872dd906064016020604051808303816000875af11580156112df573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061130391906123f6565b50600354600d54600680546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff1690811061134e5761134e612361565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60065460ff821610156115475760068160ff16815481106113a3576113a3612361565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060078560ff16815481106113e7576113e7612361565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af1158015611447573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061146b91906123f6565b5060068160ff168154811061148257611482612361565b600091825260209091200154600780546001600160a01b039092169163095ea7b391859160ff86169081106114b9576114b9612361565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611510573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061153491906123f6565b508061153f816126d4565b915050611380565b50604080516006805460a060208202840181019094526080830181815260009484939192908401828280156115a557602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611587575b5050505050815260200160078054806020026020016040519081016040528092919081815260200182805480156115fb57602002820191906000526020600020905b8154815260200190600101908083116115e7575b505050505081526020016000600760405160200161161a9291906126f3565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611699573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906116bd91906123dd565b3030856040518563ffffffff1660e01b81526004016116df94939291906127d6565b600060405180830381600087803b1580156116f957600080fd5b505af115801561170d573d6000803e3d6000fd5b50505050505050565b600080546103a490612327565b6006818154811061173357600080fd5b6000918252602090912001546001600160a01b0316905081565b6002546001600160a01b031633146117775760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166117cd5760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f000000604482015260640161049b565b6002546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600280546001600160a01b0319166001600160a01b0392909216919091179055565b600881815481106107c257600080fd5b600981815481106107c257600080fd5b600a81815481106107c257600080fd5b6002546001600160a01b031633146118835760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166118d95760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611922573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061194691906123dd565b116119935760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b6000600a6001815481106119a9576119a9612361565b9060005260206000200154905080421015611a065760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a50573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a74919061268f565b9050600060405180608001604052806006805480602002602001604051908101604052809291908181526020018280548015611ad957602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611abb575b5050505050815260200160068054905067ffffffffffffffff811115611b0157611b01611f7f565b604051908082528060200260200182016040528015611b2a578160200160208202803683370190505b508152600b546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611b7c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ba091906123dd565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c33573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c5791906123dd565b3087856040518563ffffffff1660e01b8152600401611c7994939291906127d6565b600060405180830381600087803b158015611c9357600080fd5b505af1158015611ca7573d6000803e3d6000fd5b5050505050505050565b6002546001600160a01b03163314611cdb5760405162461bcd60e51b815260040161049b906123a6565b600b54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d2257600080fd5b505af1158015611d36573d6000803e3d6000fd5b5050505050565b6002546001600160a01b03163314611d675760405162461bcd60e51b815260040161049b906123a6565b600c611d738282612461565b5080604051611d829190612812565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600454600d5460078054600093670de0b6b3a76400009390929160ff909116908110611de357611de3612361565b9060005260206000200154611df8919061282e565b61045f9190612845565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d578251825591602001919060010190611e22565b50611e49929150611ea2565b5090565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d57825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611e6d565b5b80821115611e495760008155600101611ea3565b60005b83811015611ed2578181015183820152602001611eba565b50506000910152565b60008151808452611ef3816020860160208601611eb7565b601f01601f19169290920160200192915050565b602081526000611f1a6020830184611edb565b9392505050565b6001600160a01b0381168114611f3657600080fd5b50565b8035611f4481611f21565b919050565b600060208284031215611f5b57600080fd5b8135611f1a81611f21565b600060208284031215611f7857600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715611fbe57611fbe611f7f565b604052919050565b600082601f830112611fd757600080fd5b813567ffffffffffffffff811115611ff157611ff1611f7f565b612004601f8201601f1916602001611f95565b81815284602083860101111561201957600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561205057612050611f7f565b5060051b60200190565b600082601f83011261206b57600080fd5b8135602061208061207b83612036565b611f95565b82815260059290921b8401810191818101908684111561209f57600080fd5b8286015b848110156120c35780356120b681611f21565b83529183019183016120a3565b509695505050505050565b600082601f8301126120df57600080fd5b813560206120ef61207b83612036565b82815260059290921b8401810191818101908684111561210e57600080fd5b8286015b848110156120c35780358352918301918301612112565b60008060008060008060008060008060006101608c8e03121561214b57600080fd5b6121548c611f39565b9a5061216260208d01611f39565b995067ffffffffffffffff8060408e0135111561217e57600080fd5b61218e8e60408f01358f01611fc6565b99508060608e013511156121a157600080fd5b6121b18e60608f01358f01611fc6565b98508060808e013511156121c457600080fd5b6121d48e60808f01358f0161205a565b97508060a08e013511156121e757600080fd5b6121f78e60a08f01358f016120ce565b96508060c08e0135111561220a57600080fd5b61221a8e60c08f01358f016120ce565b95508060e08e0135111561222d57600080fd5b61223d8e60e08f01358f016120ce565b9450806101008e0135111561225157600080fd5b6122628e6101008f01358f016120ce565b9350806101208e0135111561227657600080fd5b6122878e6101208f01358f016120ce565b9250806101408e0135111561229b57600080fd5b506122ad8d6101408e01358e01611fc6565b90509295989b509295989b9093969950565b8015158114611f3657600080fd5b6000602082840312156122df57600080fd5b8135611f1a816122bf565b6000602082840312156122fc57600080fd5b813567ffffffffffffffff81111561231357600080fd5b61231f84828501611fc6565b949350505050565b600181811c9082168061233b57607f821691505b60208210810361235b57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123a0576123a0612377565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b6000602082840312156123ef57600080fd5b5051919050565b60006020828403121561240857600080fd5b8151611f1a816122bf565b601f8211156107ad57600081815260208120601f850160051c8101602086101561243a5750805b601f850160051c820191505b8181101561245957828155600101612446565b505050505050565b815167ffffffffffffffff81111561247b5761247b611f7f565b61248f816124898454612327565b84612413565b602080601f8311600181146124c457600084156124ac5750858301515b600019600386901b1c1916600185901b178555612459565b600085815260208120601f198616915b828110156124f3578886015182559484019460019091019084016124d4565b50858210156125115787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b6000815461252e81612327565b80855260206001838116801561254b576001811461256557612593565b60ff1985168884015283151560051b880183019550612593565b866000528260002060005b8581101561258b5781548a8201860152908301908401612570565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b838110156125d3578154875295820195600191820191016125b7565b509495945050505050565b60e0815260006125f160e083018a612521565b8281036020840152612603818a612521565b8381036040850152885480825260008a815260208082209450909201915b818110156126485783546001600160a01b0316835260019384019360209093019201612621565b5050838103606085015261265c818961259e565b9250505084608083015261267b60a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126a157600080fd5b8151611f1a81611f21565b8381528260208201526060604082015260006126cb606083018461259e565b95945050505050565b600060ff821660ff81036126ea576126ea612377565b60010192915050565b60ff8316815260406020820152600061231f604083018461259e565b600081518084526020808501945080840160005b838110156125d357815187529582019590820190600101612723565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127845783516001600160a01b03168352928401929184019160010161275f565b50508285015191508581038387015261279d818361270f565b92505050604083015184820360408601526127b88282611edb565b91505060608301516127ce606086018215159052565b509392505050565b8481526001600160a01b038481166020830152831660408201526080606082018190526000906128089083018461273f565b9695505050505050565b60008251612824818460208701611eb7565b9190910192915050565b80820281158282048414176123a0576123a0612377565b60008261286257634e487b7160e01b600052601260045260246000fd5b50049056fea26469706673582212206a6fdfb186a671a69ffd99a8246a5da82698e47ac0533c9c48ccb68220dc51c364736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b506004361061018e5760003560e01c8063a001ecdd116100de578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461034b578063e01af92c1461035e578063f851a44014610371578063fc582d411461038457600080fd5b8063c9d8616f14610306578063cb209b6c14610319578063cd2055e51461033857600080fd5b8063a001ecdd146102a2578063a4ac0d49146102ab578063a88971fa146102b4578063b5106add146102c8578063bb7bfb0c146102db578063c18b5151146102ee57600080fd5b80633facbb851161014b5780638638fe31116101255780638638fe31146102615780638bfd52891461027457806395d89b41146102875780639ead72221461028f57600080fd5b80633facbb851461023157806345f0a44f1461024657806347bc4d921461025957600080fd5b806306fdde0314610193578063092f7de7146101b1578063158ef93e146101dc5780633281f3ec1461020057806338af3eed14610216578063392f37e914610229575b600080fd5b61019b610397565b6040516101a89190611f07565b60405180910390f35b600b546101c4906001600160a01b031681565b6040516001600160a01b0390911681526020016101a8565b600d546101f090600160b01b900460ff1681565b60405190151581526020016101a8565b610208610425565b6040519081526020016101a8565b6003546101c4906001600160a01b031681565b61019b610464565b61024461023f366004611f49565b610471565b005b610208610254366004611f66565b6107b2565b6101f06107d3565b61024461026f366004612129565b6108a6565b610244610282366004611f49565b610f89565b61019b611716565b6101c461029d366004611f66565b611723565b61020860045481565b61020860055481565b600d546101f090600160a81b900460ff1681565b6102446102d6366004611f49565b61174d565b6102086102e9366004611f66565b611829565b600d546101c49061010090046001600160a01b031681565b610208610314366004611f66565b611839565b600d546103269060ff1681565b60405160ff90911681526020016101a8565b610208610346366004611f66565b611849565b610244610359366004611f49565b611859565b61024461036c3660046122cd565b611cb1565b6002546101c4906001600160a01b031681565b6102446103923660046122ea565b611d3d565b600180546103a490612327565b80601f01602080910402602001604051908101604052809291908181526020018280546103d090612327565b801561041d5780601f106103f25761010080835404028352916020019161041d565b820191906000526020600020905b81548152906001019060200180831161040057829003601f168201915b505050505081565b600061042f611db5565b600d5460078054909160ff1690811061044a5761044a612361565b906000526020600020015461045f919061238d565b905090565b600c80546103a490612327565b6002546001600160a01b031633146104a45760405162461bcd60e51b815260040161049b906123a6565b60405180910390fd5b6001600160a01b0381166104fa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b6000600a60018154811061051057610510612361565b906000526020600020015490508042101561056d5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105b6573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105da91906123dd565b116106275760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b600b546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa158015610693573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106b791906123dd565b60405190815260200160405180910390a2600b546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561071a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061073e91906123dd565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015610789573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ad91906123f6565b505050565b600781815481106107c257600080fd5b600091825260209091200154905081565b600d54600090600160a81b900460ff1661082f5760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e604482015260640161049b565b600b60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa158015610882573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061045f91906123f6565b600d54600160b01b900460ff16156109005760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a656400604482015260640161049b565b6001600160a01b038a166109565760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f604482015260640161049b565b64e8d4a510008260008151811061096f5761096f612361565b602002602001015110156109d15760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b606482015260840161049b565b67016345785d8a0000826000815181106109ed576109ed612361565b60200260200101511115610a515760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b606482015260840161049b565b86516002148015610a63575085516002145b8015610a70575084516002145b8015610a7d575083516002145b8015610a8a575082516002145b8015610a97575081516002145b610ae35760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a65000000604482015260640161049b565b86600181518110610af657610af6612361565b60200260200101516001600160a01b031687600081518110610b1a57610b1a612361565b60200260200101516001600160a01b031603610b785760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d65604482015260640161049b565b83600181518110610b8b57610b8b612361565b602002602001015184600081518110610ba657610ba6612361565b602002602001015110610bfb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d6500604482015260640161049b565b600d805460ff60b01b1916600160b01b179055600280546001600160a01b0319163317905581518290600090610c3357610c33612361565b602002602001015160058190555081600181518110610c5457610c54612361565b6020908102919091010151600455600380546001600160a01b0319166001600160a01b038c16179055600c610c898282612461565b508351610c9d90600a906020870190611e02565b506001610caa8a82612461565b506000610cb78982612461565b50600d8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610ced57610ced612361565b60200260200101516001600160a01b031687600081518110610d1157610d11612361565b60200260200101516001600160a01b03161115610f2157600d805460ff19166001908117909155875160069189918110610d4d57610d4d612361565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516006918991610d9c57610d9c612361565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160079188918110610df057610df0612361565b602090810291909101810151825460018101845560009384529183209091015586516007918891610e2357610e23612361565b60209081029190910181015182546001818101855560009485529290932090920191909155855160089187918110610e5d57610e5d612361565b602090810291909101810151825460018101845560009384529183209091015585516008918791610e9057610e90612361565b60209081029190910181015182546001818101855560009485529290932090920191909155835160099185918110610eca57610eca612361565b602090810291909101810151825460018101845560009384529183209091015583516009918591610efd57610efd612361565b60209081029190910181015182546001810184556000938452919092200155610f7c565b600d805460ff191690558651610f3e9060069060208a0190611e4d565b508551610f52906007906020890190611e02565b508451610f66906008906020880190611e02565b508251610f7a906009906020860190611e02565b505b5050505050505050505050565b6002546001600160a01b03163314610fb35760405162461bcd60e51b815260040161049b906123a6565b600d54600160b01b900460ff1615156001146110205760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b606482015260840161049b565b600d54600160a81b900460ff161561107a5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e64656400604482015260640161049b565b600d8054600160a81b60ff60a81b199091161790819055600554604051632367971960e01b81526101009092046001600160a01b0316916323679719916110d391600191600091600691600891309085906004016125de565b6020604051808303816000875af11580156110f2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611116919061268f565b600b80546001600160a01b0319166001600160a01b03929092169182179055600a8054633e569205919060009061114f5761114f612361565b9060005260206000200154600a60018154811061116e5761116e612361565b906000526020600020015460096040518463ffffffff1660e01b8152600401611199939291906126ac565b600060405180830381600087803b1580156111b357600080fd5b505af11580156111c7573d6000803e3d6000fd5b505050506000600b60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611220573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611244919061268f565b905060045460001461137d57600061125a611db5565b600d54600680549293509160ff90911690811061127957611279612361565b6000918252602090912001546003546040516323b872dd60e01b81526001600160a01b0386811660048301529182166024820152604481018490529116906323b872dd906064016020604051808303816000875af11580156112df573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061130391906123f6565b50600354600d54600680546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff1690811061134e5761134e612361565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60065460ff821610156115475760068160ff16815481106113a3576113a3612361565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060078560ff16815481106113e7576113e7612361565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af1158015611447573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061146b91906123f6565b5060068160ff168154811061148257611482612361565b600091825260209091200154600780546001600160a01b039092169163095ea7b391859160ff86169081106114b9576114b9612361565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611510573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061153491906123f6565b508061153f816126d4565b915050611380565b50604080516006805460a060208202840181019094526080830181815260009484939192908401828280156115a557602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611587575b5050505050815260200160078054806020026020016040519081016040528092919081815260200182805480156115fb57602002820191906000526020600020905b8154815260200190600101908083116115e7575b505050505081526020016000600760405160200161161a9291906126f3565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611699573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906116bd91906123dd565b3030856040518563ffffffff1660e01b81526004016116df94939291906127d6565b600060405180830381600087803b1580156116f957600080fd5b505af115801561170d573d6000803e3d6000fd5b50505050505050565b600080546103a490612327565b6006818154811061173357600080fd5b6000918252602090912001546001600160a01b0316905081565b6002546001600160a01b031633146117775760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166117cd5760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f000000604482015260640161049b565b6002546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600280546001600160a01b0319166001600160a01b0392909216919091179055565b600881815481106107c257600080fd5b600981815481106107c257600080fd5b600a81815481106107c257600080fd5b6002546001600160a01b031633146118835760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166118d95760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611922573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061194691906123dd565b116119935760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b6000600a6001815481106119a9576119a9612361565b9060005260206000200154905080421015611a065760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a50573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a74919061268f565b9050600060405180608001604052806006805480602002602001604051908101604052809291908181526020018280548015611ad957602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611abb575b5050505050815260200160068054905067ffffffffffffffff811115611b0157611b01611f7f565b604051908082528060200260200182016040528015611b2a578160200160208202803683370190505b508152600b546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611b7c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ba091906123dd565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c33573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c5791906123dd565b3087856040518563ffffffff1660e01b8152600401611c7994939291906127d6565b600060405180830381600087803b158015611c9357600080fd5b505af1158015611ca7573d6000803e3d6000fd5b5050505050505050565b6002546001600160a01b03163314611cdb5760405162461bcd60e51b815260040161049b906123a6565b600b54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d2257600080fd5b505af1158015611d36573d6000803e3d6000fd5b5050505050565b6002546001600160a01b03163314611d675760405162461bcd60e51b815260040161049b906123a6565b600c611d738282612461565b5080604051611d829190612812565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600454600d5460078054600093670de0b6b3a76400009390929160ff909116908110611de357611de3612361565b9060005260206000200154611df8919061282e565b61045f9190612845565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d578251825591602001919060010190611e22565b50611e49929150611ea2565b5090565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d57825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611e6d565b5b80821115611e495760008155600101611ea3565b60005b83811015611ed2578181015183820152602001611eba565b50506000910152565b60008151808452611ef3816020860160208601611eb7565b601f01601f19169290920160200192915050565b602081526000611f1a6020830184611edb565b9392505050565b6001600160a01b0381168114611f3657600080fd5b50565b8035611f4481611f21565b919050565b600060208284031215611f5b57600080fd5b8135611f1a81611f21565b600060208284031215611f7857600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715611fbe57611fbe611f7f565b604052919050565b600082601f830112611fd757600080fd5b813567ffffffffffffffff811115611ff157611ff1611f7f565b612004601f8201601f1916602001611f95565b81815284602083860101111561201957600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561205057612050611f7f565b5060051b60200190565b600082601f83011261206b57600080fd5b8135602061208061207b83612036565b611f95565b82815260059290921b8401810191818101908684111561209f57600080fd5b8286015b848110156120c35780356120b681611f21565b83529183019183016120a3565b509695505050505050565b600082601f8301126120df57600080fd5b813560206120ef61207b83612036565b82815260059290921b8401810191818101908684111561210e57600080fd5b8286015b848110156120c35780358352918301918301612112565b60008060008060008060008060008060006101608c8e03121561214b57600080fd5b6121548c611f39565b9a5061216260208d01611f39565b995067ffffffffffffffff8060408e0135111561217e57600080fd5b61218e8e60408f01358f01611fc6565b99508060608e013511156121a157600080fd5b6121b18e60608f01358f01611fc6565b98508060808e013511156121c457600080fd5b6121d48e60808f01358f0161205a565b97508060a08e013511156121e757600080fd5b6121f78e60a08f01358f016120ce565b96508060c08e0135111561220a57600080fd5b61221a8e60c08f01358f016120ce565b95508060e08e0135111561222d57600080fd5b61223d8e60e08f01358f016120ce565b9450806101008e0135111561225157600080fd5b6122628e6101008f01358f016120ce565b9350806101208e0135111561227657600080fd5b6122878e6101208f01358f016120ce565b9250806101408e0135111561229b57600080fd5b506122ad8d6101408e01358e01611fc6565b90509295989b509295989b9093969950565b8015158114611f3657600080fd5b6000602082840312156122df57600080fd5b8135611f1a816122bf565b6000602082840312156122fc57600080fd5b813567ffffffffffffffff81111561231357600080fd5b61231f84828501611fc6565b949350505050565b600181811c9082168061233b57607f821691505b60208210810361235b57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123a0576123a0612377565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b6000602082840312156123ef57600080fd5b5051919050565b60006020828403121561240857600080fd5b8151611f1a816122bf565b601f8211156107ad57600081815260208120601f850160051c8101602086101561243a5750805b601f850160051c820191505b8181101561245957828155600101612446565b505050505050565b815167ffffffffffffffff81111561247b5761247b611f7f565b61248f816124898454612327565b84612413565b602080601f8311600181146124c457600084156124ac5750858301515b600019600386901b1c1916600185901b178555612459565b600085815260208120601f198616915b828110156124f3578886015182559484019460019091019084016124d4565b50858210156125115787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b6000815461252e81612327565b80855260206001838116801561254b576001811461256557612593565b60ff1985168884015283151560051b880183019550612593565b866000528260002060005b8581101561258b5781548a8201860152908301908401612570565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b838110156125d3578154875295820195600191820191016125b7565b509495945050505050565b60e0815260006125f160e083018a612521565b8281036020840152612603818a612521565b8381036040850152885480825260008a815260208082209450909201915b818110156126485783546001600160a01b0316835260019384019360209093019201612621565b5050838103606085015261265c818961259e565b9250505084608083015261267b60a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126a157600080fd5b8151611f1a81611f21565b8381528260208201526060604082015260006126cb606083018461259e565b95945050505050565b600060ff821660ff81036126ea576126ea612377565b60010192915050565b60ff8316815260406020820152600061231f604083018461259e565b600081518084526020808501945080840160005b838110156125d357815187529582019590820190600101612723565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127845783516001600160a01b03168352928401929184019160010161275f565b50508285015191508581038387015261279d818361270f565b92505050604083015184820360408601526127b88282611edb565b91505060608301516127ce606086018215159052565b509392505050565b8481526001600160a01b038481166020830152831660408201526080606082018190526000906128089083018461273f565b9695505050505050565b60008251612824818460208701611eb7565b9190910192915050565b80820281158282048414176123a0576123a0612377565b60008261286257634e487b7160e01b600052601260045260246000fd5b50049056fea26469706673582212206a6fdfb186a671a69ffd99a8246a5da82698e47ac0533c9c48ccb68220dc51c364736f6c63430008110033", + "devdoc": { + "details": "Smart contract for managing interactions with a Balancer LBP.", + "kind": "dev", + "methods": { + "getSwapEnabled()": { + "details": "Tells whether swaps are enabled or not for the LBP" + }, + "initializeLBP(address)": { + "details": "Subtracts the fee, deploys the LBP and adds liquidity to it.", + "params": { + "_sender": "Address of the liquidity provider." + } + }, + "initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Initialize LBPManager.", + "params": { + "_amounts": "Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the feePercentage.", + "_endWeights": "Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_lbpFactory": "LBP factory address.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndTime": "Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.", + "_startWeights": "Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token." + } + }, + "projectTokensRequired()": { + "details": "Get required amount of project tokens to cover for fees and the actual LBP." + }, + "removeLiquidity(address)": { + "details": "Exit pool or remove liquidity from pool.", + "params": { + "_receiver": "Address of the liquidity receiver, after exiting the LBP." + } + }, + "setSwapEnabled(bool)": { + "details": "Can pause/unpause trading.", + "params": { + "_swapEnabled": "Enables/disables swapping." + } + }, + "transferAdminRights(address)": { + "details": "Transfer admin rights.", + "params": { + "_newAdmin": "Address of the new admin." + } + }, + "updateMetadata(bytes)": { + "details": "Updates metadata.", + "params": { + "_metadata": "LBP wizard contract metadata, that is an IPFS Hash." + } + }, + "withdrawPoolTokens(address)": { + "details": "Withdraw pool tokens if available.", + "params": { + "_receiver": "Address of the BPT tokens receiver." + } + } + }, + "title": "LBPManager contract.", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 4089, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "symbol", + "offset": 0, + "slot": "0", + "type": "t_string_storage" + }, + { + "astId": 4091, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "name", + "offset": 0, + "slot": "1", + "type": "t_string_storage" + }, + { + "astId": 4093, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "admin", + "offset": 0, + "slot": "2", + "type": "t_address" + }, + { + "astId": 4095, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "beneficiary", + "offset": 0, + "slot": "3", + "type": "t_address" + }, + { + "astId": 4097, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "feePercentage", + "offset": 0, + "slot": "4", + "type": "t_uint256" + }, + { + "astId": 4099, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "swapFeePercentage", + "offset": 0, + "slot": "5", + "type": "t_uint256" + }, + { + "astId": 4103, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "tokenList", + "offset": 0, + "slot": "6", + "type": "t_array(t_contract(IERC20)3353)dyn_storage" + }, + { + "astId": 4106, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "amounts", + "offset": 0, + "slot": "7", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4109, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "startWeights", + "offset": 0, + "slot": "8", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4112, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "endWeights", + "offset": 0, + "slot": "9", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4115, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "startTimeEndTime", + "offset": 0, + "slot": "10", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4118, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "lbp", + "offset": 0, + "slot": "11", + "type": "t_contract(ILBP)8837" + }, + { + "astId": 4120, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "metadata", + "offset": 0, + "slot": "12", + "type": "t_bytes_storage" + }, + { + "astId": 4122, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "projectTokenIndex", + "offset": 0, + "slot": "13", + "type": "t_uint8" + }, + { + "astId": 4124, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "lbpFactory", + "offset": 1, + "slot": "13", + "type": "t_address" + }, + { + "astId": 4126, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "poolFunded", + "offset": 21, + "slot": "13", + "type": "t_bool" + }, + { + "astId": 4128, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "initialized", + "offset": 22, + "slot": "13", + "type": "t_bool" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_array(t_contract(IERC20)3353)dyn_storage": { + "base": "t_contract(IERC20)3353", + "encoding": "dynamic_array", + "label": "contract IERC20[]", + "numberOfBytes": "32" + }, + "t_array(t_uint256)dyn_storage": { + "base": "t_uint256", + "encoding": "dynamic_array", + "label": "uint256[]", + "numberOfBytes": "32" + }, + "t_bool": { + "encoding": "inplace", + "label": "bool", + "numberOfBytes": "1" + }, + "t_bytes_storage": { + "encoding": "bytes", + "label": "bytes", + "numberOfBytes": "32" + }, + "t_contract(IERC20)3353": { + "encoding": "inplace", + "label": "contract IERC20", + "numberOfBytes": "20" + }, + "t_contract(ILBP)8837": { + "encoding": "inplace", + "label": "contract ILBP", + "numberOfBytes": "20" + }, + "t_string_storage": { + "encoding": "bytes", + "label": "string", + "numberOfBytes": "32" + }, + "t_uint256": { + "encoding": "inplace", + "label": "uint256", + "numberOfBytes": "32" + }, + "t_uint8": { + "encoding": "inplace", + "label": "uint8", + "numberOfBytes": "1" + } + } + } +} \ No newline at end of file diff --git a/deployments/celo/LBPManagerFactory.json b/deployments/celo/LBPManagerFactory.json new file mode 100644 index 0000000..38e038d --- /dev/null +++ b/deployments/celo/LBPManagerFactory.json @@ -0,0 +1,375 @@ +{ + "address": "0x8717635e4337E4381A2Aed75aFCbc3a6D0998948", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0x16a122c023cf419aae32574f823b6118d31cfed14a93aabef230eca54b797f0a", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0x8717635e4337E4381A2Aed75aFCbc3a6D0998948", + "transactionIndex": 4, + "gasUsed": "765196", + "logsBloom": "0x00000000000000000000000040000000000000000000000000800000000000000002000000000000000000000000400000000000000000000000000800000000000000000000000000000000000000002001000000000000000000002000000000000000020000000000000000000800000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x612f83486ba9a930eb5f0a1ec38689e1715e1a740c8b8f0102f5125f879d44c8", + "transactionHash": "0x16a122c023cf419aae32574f823b6118d31cfed14a93aabef230eca54b797f0a", + "logs": [ + { + "transactionIndex": 4, + "blockNumber": 16537459, + "transactionHash": "0x16a122c023cf419aae32574f823b6118d31cfed14a93aabef230eca54b797f0a", + "address": "0x8717635e4337E4381A2Aed75aFCbc3a6D0998948", + "topics": [ + "0x8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0", + "0x0000000000000000000000000000000000000000000000000000000000000000", + "0x000000000000000000000000c039897ee5a0d14a3d1f212922faf7e159ab619f" + ], + "data": "0x", + "logIndex": 42, + "blockHash": "0x612f83486ba9a930eb5f0a1ec38689e1715e1a740c8b8f0102f5125f879d44c8" + } + ], + "blockNumber": 16537459, + "cumulativeGasUsed": "2163774", + "status": 1, + "byzantium": true + }, + "args": [ + "0xdF87a2369FAa3140613c3C5D008A9F50B3303fD3" + ], + "solcInputHash": "bf89fe6a61a7d22f31b24d3cee885a8d", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldLBPFactory\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newLBPFactory\",\"type\":\"address\"}],\"name\":\"LBPFactoryChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpManager\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"admin\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"LBPManagerDeployed\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldMasterCopy\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newMasterCopy\",\"type\":\"address\"}],\"name\":\"MastercopyChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_admin\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndtime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"deployLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"masterCopy\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"name\":\"setLBPFactory\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_masterCopy\",\"type\":\"address\"}],\"name\":\"setMasterCopy\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Governance to create new LBPManager contracts.\",\"kind\":\"dev\",\"methods\":{\"constructor\":{\"details\":\"Constructor.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Deploy and initialize LBPManager.\",\"params\":{\"_admin\":\"The address of the admin of the LBPManager.\",\"_amounts\":\"Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the _fees.\",\"_endWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndtime\":\"Array containing two parameters: - Start time for the LBP. - End time for the LBP.\",\"_startWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token.\"}},\"owner()\":{\"details\":\"Returns the address of the current owner.\"},\"renounceOwnership()\":{\"details\":\"Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.\"},\"setLBPFactory(address)\":{\"details\":\"Set Balancers LBP Factory contract as basis for deploying LBPs.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"setMasterCopy(address)\":{\"details\":\"Set LBPManager contract which works as a base for clones.\",\"params\":{\"_masterCopy\":\"The address of the new LBPManager basis.\"}},\"transferOwnership(address)\":{\"details\":\"Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.\"}},\"title\":\"LBPManager Factory\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerFactory.sol\":\"LBPManagerFactory\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/access/Ownable.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\\n\\npragma solidity ^0.8.0;\\n\\nimport \\\"../utils/Context.sol\\\";\\n\\n/**\\n * @dev Contract module which provides a basic access control mechanism, where\\n * there is an account (an owner) that can be granted exclusive access to\\n * specific functions.\\n *\\n * By default, the owner account will be the one that deploys the contract. This\\n * can later be changed with {transferOwnership}.\\n *\\n * This module is used through inheritance. It will make available the modifier\\n * `onlyOwner`, which can be applied to your functions to restrict their use to\\n * the owner.\\n */\\nabstract contract Ownable is Context {\\n address private _owner;\\n\\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\\n\\n /**\\n * @dev Initializes the contract setting the deployer as the initial owner.\\n */\\n constructor() {\\n _transferOwnership(_msgSender());\\n }\\n\\n /**\\n * @dev Throws if called by any account other than the owner.\\n */\\n modifier onlyOwner() {\\n _checkOwner();\\n _;\\n }\\n\\n /**\\n * @dev Returns the address of the current owner.\\n */\\n function owner() public view virtual returns (address) {\\n return _owner;\\n }\\n\\n /**\\n * @dev Throws if the sender is not the owner.\\n */\\n function _checkOwner() internal view virtual {\\n require(owner() == _msgSender(), \\\"Ownable: caller is not the owner\\\");\\n }\\n\\n /**\\n * @dev Leaves the contract without owner. It will not be possible to call\\n * `onlyOwner` functions anymore. Can only be called by the current owner.\\n *\\n * NOTE: Renouncing ownership will leave the contract without an owner,\\n * thereby removing any functionality that is only available to the owner.\\n */\\n function renounceOwnership() public virtual onlyOwner {\\n _transferOwnership(address(0));\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Can only be called by the current owner.\\n */\\n function transferOwnership(address newOwner) public virtual onlyOwner {\\n require(newOwner != address(0), \\\"Ownable: new owner is the zero address\\\");\\n _transferOwnership(newOwner);\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Internal function without access restriction.\\n */\\n function _transferOwnership(address newOwner) internal virtual {\\n address oldOwner = _owner;\\n _owner = newOwner;\\n emit OwnershipTransferred(oldOwner, newOwner);\\n }\\n}\\n\",\"keccak256\":\"0xa94b34880e3c1b0b931662cb1c09e5dfa6662f31cba80e07c5ee71cd135c9673\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"@openzeppelin/contracts/utils/Context.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Provides information about the current execution context, including the\\n * sender of the transaction and its data. While these are generally available\\n * via msg.sender and msg.data, they should not be accessed in such a direct\\n * manner, since when dealing with meta-transactions the account sending and\\n * paying for execution may not be the actual sender (as far as an application\\n * is concerned).\\n *\\n * This contract is only required for intermediate, library-like contracts.\\n */\\nabstract contract Context {\\n function _msgSender() internal view virtual returns (address) {\\n return msg.sender;\\n }\\n\\n function _msgData() internal view virtual returns (bytes calldata) {\\n return msg.data;\\n }\\n}\\n\",\"keccak256\":\"0xe2e337e6dde9ef6b680e07338c493ebea1b5fd09b43424112868e9cc1706bca7\",\"license\":\"MIT\"},\"contracts/lbp/LBPManager.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract.\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManager {\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x371ceeb460072a61394db69c3b0f8b0f4c45dd4d1ee0ad19a1c44ba9f61000b4\",\"license\":\"GPL-3.0-or-later\"},\"contracts/lbp/LBPManagerFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"../utils/CloneFactory.sol\\\";\\nimport \\\"@openzeppelin/contracts/access/Ownable.sol\\\";\\nimport \\\"./LBPManager.sol\\\";\\n\\n/**\\n * @title LBPManager Factory\\n * @dev Governance to create new LBPManager contracts.\\n */\\ncontract LBPManagerFactory is CloneFactory, Ownable {\\n address public masterCopy;\\n address public lbpFactory;\\n\\n event LBPManagerDeployed(\\n address indexed lbpManager,\\n address indexed admin,\\n bytes metadata\\n );\\n\\n event LBPFactoryChanged(\\n address indexed oldLBPFactory,\\n address indexed newLBPFactory\\n );\\n\\n event MastercopyChanged(\\n address indexed oldMasterCopy,\\n address indexed newMasterCopy\\n );\\n\\n /**\\n * @dev Constructor.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n constructor(address _lbpFactory) {\\n require(_lbpFactory != address(0), \\\"LBPMFactory: LBPFactory is zero\\\");\\n lbpFactory = _lbpFactory;\\n }\\n\\n modifier validAddress(address addressToCheck) {\\n require(addressToCheck != address(0), \\\"LBPMFactory: address is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(\\n addressToCheck != address(this),\\n \\\"LBPMFactory: address same as LBPManagerFactory\\\"\\n );\\n _;\\n }\\n\\n /**\\n * @dev Set LBPManager contract which works as a base for clones.\\n * @param _masterCopy The address of the new LBPManager basis.\\n */\\n function setMasterCopy(address _masterCopy)\\n external\\n onlyOwner\\n validAddress(_masterCopy)\\n {\\n emit MastercopyChanged(masterCopy, _masterCopy);\\n masterCopy = _masterCopy;\\n }\\n\\n /**\\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n function setLBPFactory(address _lbpFactory)\\n external\\n onlyOwner\\n validAddress(_lbpFactory)\\n {\\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\\n lbpFactory = _lbpFactory;\\n }\\n\\n /**\\n * @dev Deploy and initialize LBPManager.\\n * @param _admin The address of the admin of the LBPManager.\\n * @param _beneficiary The address that receives the _fees.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\\n - The address of the project token being distributed.\\n - The address of the funding token being exchanged for the project token.\\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\\n - The amounts of project token to be added as liquidity to the LBP.\\n - The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\\n - The start weight for the project token in the LBP.\\n - The start weight for the funding token in the LBP.\\n * @param _startTimeEndtime Array containing two parameters:\\n - Start time for the LBP.\\n - End time for the LBP.\\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\\n - The end weight for the project token in the LBP.\\n - The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters:\\n - Percentage of fee paid for every swap in the LBP.\\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function deployLBPManager(\\n address _admin,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndtime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external onlyOwner {\\n // solhint-disable-next-line reason-string\\n require(\\n masterCopy != address(0),\\n \\\"LBPMFactory: LBPManager mastercopy not set\\\"\\n );\\n\\n address lbpManager = createClone(masterCopy);\\n\\n LBPManager(lbpManager).initializeLBPManager(\\n lbpFactory,\\n _beneficiary,\\n _name,\\n _symbol,\\n _tokenList,\\n _amounts,\\n _startWeights,\\n _startTimeEndtime,\\n _endWeights,\\n _fees,\\n _metadata\\n );\\n\\n LBPManager(lbpManager).transferAdminRights(_admin);\\n\\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\\n }\\n}\\n\",\"keccak256\":\"0xabd6bae623ac01e95553811cfb0a117cf260aabcec6b16a7683ee489d514b837\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/CloneFactory.sol\":{\"content\":\"/*\\n\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n \\n*\\n* CloneFactory.sol was originally published under MIT license.\\n* Republished by PrimeDAO under GNU General Public License v3.0.\\n*\\n*/\\n\\n/*\\nThe MIT License (MIT)\\nCopyright (c) 2018 Murray Software, LLC.\\nPermission is hereby granted, free of charge, to any person obtaining\\na copy of this software and associated documentation files (the\\n\\\"Software\\\"), to deal in the Software without restriction, including\\nwithout limitation the rights to use, copy, modify, merge, publish,\\ndistribute, sublicense, and/or sell copies of the Software, and to\\npermit persons to whom the Software is furnished to do so, subject to\\nthe following conditions:\\nThe above copyright notice and this permission notice shall be included\\nin all copies or substantial portions of the Software.\\nTHE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// solium-disable linebreak-style\\n// solhint-disable max-line-length\\n// solhint-disable no-inline-assembly\\n\\npragma solidity 0.8.17;\\n\\ncontract CloneFactory {\\n function createClone(address target) internal returns (address result) {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\\n )\\n mstore(add(clone, 0x14), targetBytes)\\n mstore(\\n add(clone, 0x28),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n result := create(0, clone, 0x37)\\n }\\n }\\n\\n function isClone(address target, address query)\\n internal\\n view\\n returns (bool result)\\n {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\\n )\\n mstore(add(clone, 0xa), targetBytes)\\n mstore(\\n add(clone, 0x1e),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n\\n let other := add(clone, 0x40)\\n extcodecopy(query, other, 0, 0x2d)\\n result := and(\\n eq(mload(clone), mload(other)),\\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\\n )\\n }\\n }\\n}\\n\",\"keccak256\":\"0x80b3d45006df787a887103ca0704f7eed17848ded1c944e494eb2de0274b2f71\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x608060405234801561001057600080fd5b50604051610d47380380610d4783398101604081905261002f91610107565b610038336100b7565b6001600160a01b0381166100925760405162461bcd60e51b815260206004820152601f60248201527f4c42504d466163746f72793a204c4250466163746f7279206973207a65726f00604482015260640160405180910390fd5b600280546001600160a01b0319166001600160a01b0392909216919091179055610137565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006020828403121561011957600080fd5b81516001600160a01b038116811461013057600080fd5b9392505050565b610c01806101466000396000f3fe608060405234801561001057600080fd5b50600436106100885760003560e01c8063c18b51511161005b578063c18b5151146100e6578063cf497e6c146100f9578063f2fde38b1461010c578063fd3bd38a1461011f57600080fd5b8063715018a61461008d5780637679a4c1146100975780638da5cb5b146100aa578063a619486e146100d3575b600080fd5b610095610132565b005b6100956100a5366004610665565b610146565b6000546001600160a01b03165b6040516001600160a01b03909116815260200160405180910390f35b6001546100b7906001600160a01b031681565b6002546100b7906001600160a01b031681565b610095610107366004610665565b61022f565b61009561011a366004610665565b610313565b61009561012d366004610833565b61038c565b61013a610544565b610144600061059e565b565b61014e610544565b806001600160a01b0381166101aa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b038216036101d25760405162461bcd60e51b81526004016101a1906109c9565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610237610544565b806001600160a01b03811661028e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101a1565b306001600160a01b038216036102b65760405162461bcd60e51b81526004016101a1906109c9565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b61031b610544565b6001600160a01b0381166103805760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101a1565b6103898161059e565b50565b610394610544565b6001546001600160a01b03166103ff5760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101a1565b600154600090610417906001600160a01b03166105ee565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261045e9216908f908f908f908f908f908f908f908f908f908f90600401610ad1565b600060405180830381600087803b15801561047857600080fd5b505af115801561048c573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b1580156104d357600080fd5b505af11580156104e7573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161052e9190610bb8565b60405180910390a3505050505050505050505050565b6000546001600160a01b031633146101445760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101a1565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b038116811461038957600080fd5b803561066081610640565b919050565b60006020828403121561067757600080fd5b813561068281610640565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106c8576106c8610689565b604052919050565b600082601f8301126106e157600080fd5b813567ffffffffffffffff8111156106fb576106fb610689565b61070e601f8201601f191660200161069f565b81815284602083860101111561072357600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561075a5761075a610689565b5060051b60200190565b600082601f83011261077557600080fd5b8135602061078a61078583610740565b61069f565b82815260059290921b840181019181810190868411156107a957600080fd5b8286015b848110156107cd5780356107c081610640565b83529183019183016107ad565b509695505050505050565b600082601f8301126107e957600080fd5b813560206107f961078583610740565b82815260059290921b8401810191818101908684111561081857600080fd5b8286015b848110156107cd578035835291830191830161081c565b60008060008060008060008060008060006101608c8e03121561085557600080fd5b61085e8c610655565b9a5061086c60208d01610655565b995067ffffffffffffffff8060408e0135111561088857600080fd5b6108988e60408f01358f016106d0565b99508060608e013511156108ab57600080fd5b6108bb8e60608f01358f016106d0565b98508060808e013511156108ce57600080fd5b6108de8e60808f01358f01610764565b97508060a08e013511156108f157600080fd5b6109018e60a08f01358f016107d8565b96508060c08e0135111561091457600080fd5b6109248e60c08f01358f016107d8565b95508060e08e0135111561093757600080fd5b6109478e60e08f01358f016107d8565b9450806101008e0135111561095b57600080fd5b61096c8e6101008f01358f016107d8565b9350806101208e0135111561098057600080fd5b6109918e6101208f01358f016107d8565b9250806101408e013511156109a557600080fd5b506109b78d6101408e01358e016106d0565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a3d57602081850181015186830182015201610a21565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610a965781516001600160a01b031687529582019590820190600101610a71565b509495945050505050565b600081518084526020808501945080840160005b83811015610a9657815187529582019590820190600101610ab5565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b038184018d610a17565b90508281036060840152610b17818c610a17565b90508281036080840152610b2b818b610a5d565b905082810360a0840152610b3f818a610aa1565b905082810360c0840152610b538189610aa1565b905082810360e0840152610b678188610aa1565b9050828103610100840152610b7c8187610aa1565b9050828103610120840152610b918186610aa1565b9050828103610140840152610ba68185610a17565b9e9d5050505050505050505050505050565b6020815260006106826020830184610a1756fea2646970667358221220ae5e8810a577600a3790682907f2d9f1dcee3d560c0fa5535b5ed0bf67e7803464736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106100885760003560e01c8063c18b51511161005b578063c18b5151146100e6578063cf497e6c146100f9578063f2fde38b1461010c578063fd3bd38a1461011f57600080fd5b8063715018a61461008d5780637679a4c1146100975780638da5cb5b146100aa578063a619486e146100d3575b600080fd5b610095610132565b005b6100956100a5366004610665565b610146565b6000546001600160a01b03165b6040516001600160a01b03909116815260200160405180910390f35b6001546100b7906001600160a01b031681565b6002546100b7906001600160a01b031681565b610095610107366004610665565b61022f565b61009561011a366004610665565b610313565b61009561012d366004610833565b61038c565b61013a610544565b610144600061059e565b565b61014e610544565b806001600160a01b0381166101aa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b038216036101d25760405162461bcd60e51b81526004016101a1906109c9565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610237610544565b806001600160a01b03811661028e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101a1565b306001600160a01b038216036102b65760405162461bcd60e51b81526004016101a1906109c9565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b61031b610544565b6001600160a01b0381166103805760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101a1565b6103898161059e565b50565b610394610544565b6001546001600160a01b03166103ff5760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101a1565b600154600090610417906001600160a01b03166105ee565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261045e9216908f908f908f908f908f908f908f908f908f908f90600401610ad1565b600060405180830381600087803b15801561047857600080fd5b505af115801561048c573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b1580156104d357600080fd5b505af11580156104e7573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161052e9190610bb8565b60405180910390a3505050505050505050505050565b6000546001600160a01b031633146101445760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101a1565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b038116811461038957600080fd5b803561066081610640565b919050565b60006020828403121561067757600080fd5b813561068281610640565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106c8576106c8610689565b604052919050565b600082601f8301126106e157600080fd5b813567ffffffffffffffff8111156106fb576106fb610689565b61070e601f8201601f191660200161069f565b81815284602083860101111561072357600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561075a5761075a610689565b5060051b60200190565b600082601f83011261077557600080fd5b8135602061078a61078583610740565b61069f565b82815260059290921b840181019181810190868411156107a957600080fd5b8286015b848110156107cd5780356107c081610640565b83529183019183016107ad565b509695505050505050565b600082601f8301126107e957600080fd5b813560206107f961078583610740565b82815260059290921b8401810191818101908684111561081857600080fd5b8286015b848110156107cd578035835291830191830161081c565b60008060008060008060008060008060006101608c8e03121561085557600080fd5b61085e8c610655565b9a5061086c60208d01610655565b995067ffffffffffffffff8060408e0135111561088857600080fd5b6108988e60408f01358f016106d0565b99508060608e013511156108ab57600080fd5b6108bb8e60608f01358f016106d0565b98508060808e013511156108ce57600080fd5b6108de8e60808f01358f01610764565b97508060a08e013511156108f157600080fd5b6109018e60a08f01358f016107d8565b96508060c08e0135111561091457600080fd5b6109248e60c08f01358f016107d8565b95508060e08e0135111561093757600080fd5b6109478e60e08f01358f016107d8565b9450806101008e0135111561095b57600080fd5b61096c8e6101008f01358f016107d8565b9350806101208e0135111561098057600080fd5b6109918e6101208f01358f016107d8565b9250806101408e013511156109a557600080fd5b506109b78d6101408e01358e016106d0565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a3d57602081850181015186830182015201610a21565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610a965781516001600160a01b031687529582019590820190600101610a71565b509495945050505050565b600081518084526020808501945080840160005b83811015610a9657815187529582019590820190600101610ab5565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b038184018d610a17565b90508281036060840152610b17818c610a17565b90508281036080840152610b2b818b610a5d565b905082810360a0840152610b3f818a610aa1565b905082810360c0840152610b538189610aa1565b905082810360e0840152610b678188610aa1565b9050828103610100840152610b7c8187610aa1565b9050828103610120840152610b918186610aa1565b9050828103610140840152610ba68185610a17565b9e9d5050505050505050505050505050565b6020815260006106826020830184610a1756fea2646970667358221220ae5e8810a577600a3790682907f2d9f1dcee3d560c0fa5535b5ed0bf67e7803464736f6c63430008110033", + "devdoc": { + "details": "Governance to create new LBPManager contracts.", + "kind": "dev", + "methods": { + "constructor": { + "details": "Constructor.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Deploy and initialize LBPManager.", + "params": { + "_admin": "The address of the admin of the LBPManager.", + "_amounts": "Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the _fees.", + "_endWeights": "Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndtime": "Array containing two parameters: - Start time for the LBP. - End time for the LBP.", + "_startWeights": "Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token." + } + }, + "owner()": { + "details": "Returns the address of the current owner." + }, + "renounceOwnership()": { + "details": "Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner." + }, + "setLBPFactory(address)": { + "details": "Set Balancers LBP Factory contract as basis for deploying LBPs.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "setMasterCopy(address)": { + "details": "Set LBPManager contract which works as a base for clones.", + "params": { + "_masterCopy": "The address of the new LBPManager basis." + } + }, + "transferOwnership(address)": { + "details": "Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner." + } + }, + "title": "LBPManager Factory", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 2584, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "_owner", + "offset": 0, + "slot": "0", + "type": "t_address" + }, + { + "astId": 4898, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "masterCopy", + "offset": 0, + "slot": "1", + "type": "t_address" + }, + { + "astId": 4900, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "lbpFactory", + "offset": 0, + "slot": "2", + "type": "t_address" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + } + } + } +} \ No newline at end of file diff --git a/deployments/celo/LBPManagerFactoryV1NoAccessControl.json b/deployments/celo/LBPManagerFactoryV1NoAccessControl.json new file mode 100644 index 0000000..12401eb --- /dev/null +++ b/deployments/celo/LBPManagerFactoryV1NoAccessControl.json @@ -0,0 +1,401 @@ +{ + "address": "0x8afa40718d5e23Ca7E84b2Cd9F55E11491322a42", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + } + ], + "transactionHash": "0xae617725b6ffca744a1996f077c135a2c52338ee8f25abe4d04be3b528c1421c", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0x8afa40718d5e23Ca7E84b2Cd9F55E11491322a42", + "transactionIndex": 4, + "gasUsed": "776446", + "logsBloom": "0x00000000000000000000000040000000000000000000000000800000000000000010000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000002001000000000080000000000000000000000000020000000000000000000800000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008000000000000000000020000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x9647077313880a17d284db546b54af8e007b7d841aba991f5cbf8c6b1ee00de8", + "transactionHash": "0xae617725b6ffca744a1996f077c135a2c52338ee8f25abe4d04be3b528c1421c", + "logs": [ + { + "transactionIndex": 4, + "blockNumber": 16550843, + "transactionHash": "0xae617725b6ffca744a1996f077c135a2c52338ee8f25abe4d04be3b528c1421c", + "address": "0x8afa40718d5e23Ca7E84b2Cd9F55E11491322a42", + "topics": [ + "0x8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0", + "0x0000000000000000000000000000000000000000000000000000000000000000", + "0x000000000000000000000000c039897ee5a0d14a3d1f212922faf7e159ab619f" + ], + "data": "0x", + "logIndex": 45, + "blockHash": "0x9647077313880a17d284db546b54af8e007b7d841aba991f5cbf8c6b1ee00de8" + } + ], + "blockNumber": 16550843, + "cumulativeGasUsed": "2244711", + "status": 1, + "byzantium": true + }, + "args": [ + "0xdF87a2369FAa3140613c3C5D008A9F50B3303fD3" + ], + "solcInputHash": "752d54b8f64e3608832db5b1be68e60f", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldLBPFactory\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newLBPFactory\",\"type\":\"address\"}],\"name\":\"LBPFactoryChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpManager\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"admin\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"LBPManagerDeployed\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldMasterCopy\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newMasterCopy\",\"type\":\"address\"}],\"name\":\"MastercopyChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_admin\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndtime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"deployLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"masterCopy\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"name\":\"setLBPFactory\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_masterCopy\",\"type\":\"address\"}],\"name\":\"setMasterCopy\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"version\",\"outputs\":[{\"internalType\":\"bytes6\",\"name\":\"\",\"type\":\"bytes6\"}],\"stateMutability\":\"view\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Governance to create new LBPManager contract without the onlyOwner modifer for the function deployLBPManager(). By removing the access control, everyone can deploy a LBPManager from this contract. This is a temporarly solution in response to the flaky Celo Safe.\",\"kind\":\"dev\",\"methods\":{\"constructor\":{\"details\":\"Constructor.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Deploy and initialize LBPManager.\",\"params\":{\"_admin\":\"The address of the admin of the LBPManager.\",\"_amounts\":\"Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the _fees.\",\"_endWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndtime\":\"Array containing two parameters: - Start time for the LBP. - End time for the LBP.\",\"_startWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token.\"}},\"owner()\":{\"details\":\"Returns the address of the current owner.\"},\"renounceOwnership()\":{\"details\":\"Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.\"},\"setLBPFactory(address)\":{\"details\":\"Set Balancers LBP Factory contract as basis for deploying LBPs.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"setMasterCopy(address)\":{\"details\":\"Set LBPManager contract which works as a base for clones.\",\"params\":{\"_masterCopy\":\"The address of the new LBPManager basis.\"}},\"transferOwnership(address)\":{\"details\":\"Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.\"}},\"title\":\"LBPManager Factory no access control version 1\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol\":\"LBPManagerFactoryV1NoAccessControl\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/access/Ownable.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\\n\\npragma solidity ^0.8.0;\\n\\nimport \\\"../utils/Context.sol\\\";\\n\\n/**\\n * @dev Contract module which provides a basic access control mechanism, where\\n * there is an account (an owner) that can be granted exclusive access to\\n * specific functions.\\n *\\n * By default, the owner account will be the one that deploys the contract. This\\n * can later be changed with {transferOwnership}.\\n *\\n * This module is used through inheritance. It will make available the modifier\\n * `onlyOwner`, which can be applied to your functions to restrict their use to\\n * the owner.\\n */\\nabstract contract Ownable is Context {\\n address private _owner;\\n\\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\\n\\n /**\\n * @dev Initializes the contract setting the deployer as the initial owner.\\n */\\n constructor() {\\n _transferOwnership(_msgSender());\\n }\\n\\n /**\\n * @dev Throws if called by any account other than the owner.\\n */\\n modifier onlyOwner() {\\n _checkOwner();\\n _;\\n }\\n\\n /**\\n * @dev Returns the address of the current owner.\\n */\\n function owner() public view virtual returns (address) {\\n return _owner;\\n }\\n\\n /**\\n * @dev Throws if the sender is not the owner.\\n */\\n function _checkOwner() internal view virtual {\\n require(owner() == _msgSender(), \\\"Ownable: caller is not the owner\\\");\\n }\\n\\n /**\\n * @dev Leaves the contract without owner. It will not be possible to call\\n * `onlyOwner` functions anymore. Can only be called by the current owner.\\n *\\n * NOTE: Renouncing ownership will leave the contract without an owner,\\n * thereby removing any functionality that is only available to the owner.\\n */\\n function renounceOwnership() public virtual onlyOwner {\\n _transferOwnership(address(0));\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Can only be called by the current owner.\\n */\\n function transferOwnership(address newOwner) public virtual onlyOwner {\\n require(newOwner != address(0), \\\"Ownable: new owner is the zero address\\\");\\n _transferOwnership(newOwner);\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Internal function without access restriction.\\n */\\n function _transferOwnership(address newOwner) internal virtual {\\n address oldOwner = _owner;\\n _owner = newOwner;\\n emit OwnershipTransferred(oldOwner, newOwner);\\n }\\n}\\n\",\"keccak256\":\"0xa94b34880e3c1b0b931662cb1c09e5dfa6662f31cba80e07c5ee71cd135c9673\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"@openzeppelin/contracts/utils/Context.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Provides information about the current execution context, including the\\n * sender of the transaction and its data. While these are generally available\\n * via msg.sender and msg.data, they should not be accessed in such a direct\\n * manner, since when dealing with meta-transactions the account sending and\\n * paying for execution may not be the actual sender (as far as an application\\n * is concerned).\\n *\\n * This contract is only required for intermediate, library-like contracts.\\n */\\nabstract contract Context {\\n function _msgSender() internal view virtual returns (address) {\\n return msg.sender;\\n }\\n\\n function _msgData() internal view virtual returns (bytes calldata) {\\n return msg.data;\\n }\\n}\\n\",\"keccak256\":\"0xe2e337e6dde9ef6b680e07338c493ebea1b5fd09b43424112868e9cc1706bca7\",\"license\":\"MIT\"},\"contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"../utils/CloneFactory.sol\\\";\\nimport \\\"@openzeppelin/contracts/access/Ownable.sol\\\";\\nimport \\\"./LBPManagerV1.sol\\\";\\n\\n/**\\n * @title LBPManager Factory no access control version 1\\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\\n * function deployLBPManager(). By removing the access control, everyone can deploy a\\n * LBPManager from this contract. This is a temporarly solution in response to the\\n * flaky Celo Safe.\\n */\\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\\n bytes6 public version = \\\"1.0.0\\\";\\n address public masterCopy;\\n address public lbpFactory;\\n\\n event LBPManagerDeployed(\\n address indexed lbpManager,\\n address indexed admin,\\n bytes metadata\\n );\\n\\n event LBPFactoryChanged(\\n address indexed oldLBPFactory,\\n address indexed newLBPFactory\\n );\\n\\n event MastercopyChanged(\\n address indexed oldMasterCopy,\\n address indexed newMasterCopy\\n );\\n\\n /**\\n * @dev Constructor.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n constructor(address _lbpFactory) {\\n require(_lbpFactory != address(0), \\\"LBPMFactory: LBPFactory is zero\\\");\\n lbpFactory = _lbpFactory;\\n }\\n\\n modifier validAddress(address addressToCheck) {\\n require(addressToCheck != address(0), \\\"LBPMFactory: address is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(\\n addressToCheck != address(this),\\n \\\"LBPMFactory: address same as LBPManagerFactory\\\"\\n );\\n _;\\n }\\n\\n /**\\n * @dev Set LBPManager contract which works as a base for clones.\\n * @param _masterCopy The address of the new LBPManager basis.\\n */\\n function setMasterCopy(address _masterCopy)\\n external\\n onlyOwner\\n validAddress(_masterCopy)\\n {\\n emit MastercopyChanged(masterCopy, _masterCopy);\\n masterCopy = _masterCopy;\\n }\\n\\n /**\\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n function setLBPFactory(address _lbpFactory)\\n external\\n onlyOwner\\n validAddress(_lbpFactory)\\n {\\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\\n lbpFactory = _lbpFactory;\\n }\\n\\n /**\\n * @dev Deploy and initialize LBPManager.\\n * @param _admin The address of the admin of the LBPManager.\\n * @param _beneficiary The address that receives the _fees.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\\n - The address of the project token being distributed.\\n - The address of the funding token being exchanged for the project token.\\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\\n - The amounts of project token to be added as liquidity to the LBP.\\n - The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\\n - The start weight for the project token in the LBP.\\n - The start weight for the funding token in the LBP.\\n * @param _startTimeEndtime Array containing two parameters:\\n - Start time for the LBP.\\n - End time for the LBP.\\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\\n - The end weight for the project token in the LBP.\\n - The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters:\\n - Percentage of fee paid for every swap in the LBP.\\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function deployLBPManager(\\n address _admin,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndtime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n // solhint-disable-next-line reason-string\\n require(\\n masterCopy != address(0),\\n \\\"LBPMFactory: LBPManager mastercopy not set\\\"\\n );\\n\\n address lbpManager = createClone(masterCopy);\\n\\n LBPManagerV1(lbpManager).initializeLBPManager(\\n lbpFactory,\\n _beneficiary,\\n _name,\\n _symbol,\\n _tokenList,\\n _amounts,\\n _startWeights,\\n _startTimeEndtime,\\n _endWeights,\\n _fees,\\n _metadata\\n );\\n\\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\\n\\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\\n }\\n}\\n\",\"keccak256\":\"0xe772adf0bbb0cf173f23527df5e6d94773ba5881b775aeb220fd669d0967ec61\",\"license\":\"GPL-3.0-or-later\"},\"contracts/lbp/LBPManagerV1.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract version 1\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManagerV1 {\\n bytes6 public version = \\\"1.0.0\\\";\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x75473a78174d66c360426296446d175f991d8dba1f047b387ce2e25452ca2991\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/CloneFactory.sol\":{\"content\":\"/*\\n\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n \\n*\\n* CloneFactory.sol was originally published under MIT license.\\n* Republished by PrimeDAO under GNU General Public License v3.0.\\n*\\n*/\\n\\n/*\\nThe MIT License (MIT)\\nCopyright (c) 2018 Murray Software, LLC.\\nPermission is hereby granted, free of charge, to any person obtaining\\na copy of this software and associated documentation files (the\\n\\\"Software\\\"), to deal in the Software without restriction, including\\nwithout limitation the rights to use, copy, modify, merge, publish,\\ndistribute, sublicense, and/or sell copies of the Software, and to\\npermit persons to whom the Software is furnished to do so, subject to\\nthe following conditions:\\nThe above copyright notice and this permission notice shall be included\\nin all copies or substantial portions of the Software.\\nTHE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// solium-disable linebreak-style\\n// solhint-disable max-line-length\\n// solhint-disable no-inline-assembly\\n\\npragma solidity 0.8.17;\\n\\ncontract CloneFactory {\\n function createClone(address target) internal returns (address result) {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\\n )\\n mstore(add(clone, 0x14), targetBytes)\\n mstore(\\n add(clone, 0x28),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n result := create(0, clone, 0x37)\\n }\\n }\\n\\n function isClone(address target, address query)\\n internal\\n view\\n returns (bool result)\\n {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\\n )\\n mstore(add(clone, 0xa), targetBytes)\\n mstore(\\n add(clone, 0x1e),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n\\n let other := add(clone, 0x40)\\n extcodecopy(query, other, 0, 0x2d)\\n result := and(\\n eq(mload(clone), mload(other)),\\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\\n )\\n }\\n }\\n}\\n\",\"keccak256\":\"0x80b3d45006df787a887103ca0704f7eed17848ded1c944e494eb2de0274b2f71\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x60806040526000805465ffffffffffff60a01b1916640312e302e360ac1b17905534801561002c57600080fd5b50604051610d94380380610d9483398101604081905261004b91610123565b610054336100d3565b6001600160a01b0381166100ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d466163746f72793a204c4250466163746f7279206973207a65726f00604482015260640160405180910390fd5b600280546001600160a01b0319166001600160a01b0392909216919091179055610153565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006020828403121561013557600080fd5b81516001600160a01b038116811461014c57600080fd5b9392505050565b610c32806101626000396000f3fe608060405234801561001057600080fd5b50600436106100935760003560e01c8063a619486e11610066578063a619486e1461010c578063c18b51511461011f578063cf497e6c14610132578063f2fde38b14610145578063fd3bd38a1461015857600080fd5b806354fd4d5014610098578063715018a6146100ca5780637679a4c1146100d45780638da5cb5b146100e7575b600080fd5b6000546100ac90600160a01b900460d01b81565b6040516001600160d01b031990911681526020015b60405180910390f35b6100d261016b565b005b6100d26100e2366004610696565b61017f565b6000546001600160a01b03165b6040516001600160a01b0390911681526020016100c1565b6001546100f4906001600160a01b031681565b6002546100f4906001600160a01b031681565b6100d2610140366004610696565b610268565b6100d2610153366004610696565b61034c565b6100d2610166366004610864565b6103c5565b610173610575565b61017d60006105cf565b565b610187610575565b806001600160a01b0381166101e35760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b0382160361020b5760405162461bcd60e51b81526004016101da906109fa565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610270610575565b806001600160a01b0381166102c75760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101da565b306001600160a01b038216036102ef5760405162461bcd60e51b81526004016101da906109fa565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b610354610575565b6001600160a01b0381166103b95760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101da565b6103c2816105cf565b50565b6001546001600160a01b03166104305760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101da565b600154600090610448906001600160a01b031661061f565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261048f9216908f908f908f908f908f908f908f908f908f908f90600401610b02565b600060405180830381600087803b1580156104a957600080fd5b505af11580156104bd573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b15801561050457600080fd5b505af1158015610518573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161055f9190610be9565b60405180910390a3505050505050505050505050565b6000546001600160a01b0316331461017d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101da565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b03811681146103c257600080fd5b803561069181610671565b919050565b6000602082840312156106a857600080fd5b81356106b381610671565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106f9576106f96106ba565b604052919050565b600082601f83011261071257600080fd5b813567ffffffffffffffff81111561072c5761072c6106ba565b61073f601f8201601f19166020016106d0565b81815284602083860101111561075457600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561078b5761078b6106ba565b5060051b60200190565b600082601f8301126107a657600080fd5b813560206107bb6107b683610771565b6106d0565b82815260059290921b840181019181810190868411156107da57600080fd5b8286015b848110156107fe5780356107f181610671565b83529183019183016107de565b509695505050505050565b600082601f83011261081a57600080fd5b8135602061082a6107b683610771565b82815260059290921b8401810191818101908684111561084957600080fd5b8286015b848110156107fe578035835291830191830161084d565b60008060008060008060008060008060006101608c8e03121561088657600080fd5b61088f8c610686565b9a5061089d60208d01610686565b995067ffffffffffffffff8060408e013511156108b957600080fd5b6108c98e60408f01358f01610701565b99508060608e013511156108dc57600080fd5b6108ec8e60608f01358f01610701565b98508060808e013511156108ff57600080fd5b61090f8e60808f01358f01610795565b97508060a08e0135111561092257600080fd5b6109328e60a08f01358f01610809565b96508060c08e0135111561094557600080fd5b6109558e60c08f01358f01610809565b95508060e08e0135111561096857600080fd5b6109788e60e08f01358f01610809565b9450806101008e0135111561098c57600080fd5b61099d8e6101008f01358f01610809565b9350806101208e013511156109b157600080fd5b6109c28e6101208f01358f01610809565b9250806101408e013511156109d657600080fd5b506109e88d6101408e01358e01610701565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a6e57602081850181015186830182015201610a52565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610ac75781516001600160a01b031687529582019590820190600101610aa2565b509495945050505050565b600081518084526020808501945080840160005b83811015610ac757815187529582019590820190600101610ae6565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b348184018d610a48565b90508281036060840152610b48818c610a48565b90508281036080840152610b5c818b610a8e565b905082810360a0840152610b70818a610ad2565b905082810360c0840152610b848189610ad2565b905082810360e0840152610b988188610ad2565b9050828103610100840152610bad8187610ad2565b9050828103610120840152610bc28186610ad2565b9050828103610140840152610bd78185610a48565b9e9d5050505050505050505050505050565b6020815260006106b36020830184610a4856fea2646970667358221220889ac78df81d1379d6471d9899757d4a6e816b1390bb99b56cff15fc7aa3073464736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106100935760003560e01c8063a619486e11610066578063a619486e1461010c578063c18b51511461011f578063cf497e6c14610132578063f2fde38b14610145578063fd3bd38a1461015857600080fd5b806354fd4d5014610098578063715018a6146100ca5780637679a4c1146100d45780638da5cb5b146100e7575b600080fd5b6000546100ac90600160a01b900460d01b81565b6040516001600160d01b031990911681526020015b60405180910390f35b6100d261016b565b005b6100d26100e2366004610696565b61017f565b6000546001600160a01b03165b6040516001600160a01b0390911681526020016100c1565b6001546100f4906001600160a01b031681565b6002546100f4906001600160a01b031681565b6100d2610140366004610696565b610268565b6100d2610153366004610696565b61034c565b6100d2610166366004610864565b6103c5565b610173610575565b61017d60006105cf565b565b610187610575565b806001600160a01b0381166101e35760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b0382160361020b5760405162461bcd60e51b81526004016101da906109fa565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610270610575565b806001600160a01b0381166102c75760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101da565b306001600160a01b038216036102ef5760405162461bcd60e51b81526004016101da906109fa565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b610354610575565b6001600160a01b0381166103b95760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101da565b6103c2816105cf565b50565b6001546001600160a01b03166104305760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101da565b600154600090610448906001600160a01b031661061f565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261048f9216908f908f908f908f908f908f908f908f908f908f90600401610b02565b600060405180830381600087803b1580156104a957600080fd5b505af11580156104bd573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b15801561050457600080fd5b505af1158015610518573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161055f9190610be9565b60405180910390a3505050505050505050505050565b6000546001600160a01b0316331461017d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101da565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b03811681146103c257600080fd5b803561069181610671565b919050565b6000602082840312156106a857600080fd5b81356106b381610671565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106f9576106f96106ba565b604052919050565b600082601f83011261071257600080fd5b813567ffffffffffffffff81111561072c5761072c6106ba565b61073f601f8201601f19166020016106d0565b81815284602083860101111561075457600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561078b5761078b6106ba565b5060051b60200190565b600082601f8301126107a657600080fd5b813560206107bb6107b683610771565b6106d0565b82815260059290921b840181019181810190868411156107da57600080fd5b8286015b848110156107fe5780356107f181610671565b83529183019183016107de565b509695505050505050565b600082601f83011261081a57600080fd5b8135602061082a6107b683610771565b82815260059290921b8401810191818101908684111561084957600080fd5b8286015b848110156107fe578035835291830191830161084d565b60008060008060008060008060008060006101608c8e03121561088657600080fd5b61088f8c610686565b9a5061089d60208d01610686565b995067ffffffffffffffff8060408e013511156108b957600080fd5b6108c98e60408f01358f01610701565b99508060608e013511156108dc57600080fd5b6108ec8e60608f01358f01610701565b98508060808e013511156108ff57600080fd5b61090f8e60808f01358f01610795565b97508060a08e0135111561092257600080fd5b6109328e60a08f01358f01610809565b96508060c08e0135111561094557600080fd5b6109558e60c08f01358f01610809565b95508060e08e0135111561096857600080fd5b6109788e60e08f01358f01610809565b9450806101008e0135111561098c57600080fd5b61099d8e6101008f01358f01610809565b9350806101208e013511156109b157600080fd5b6109c28e6101208f01358f01610809565b9250806101408e013511156109d657600080fd5b506109e88d6101408e01358e01610701565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a6e57602081850181015186830182015201610a52565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610ac75781516001600160a01b031687529582019590820190600101610aa2565b509495945050505050565b600081518084526020808501945080840160005b83811015610ac757815187529582019590820190600101610ae6565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b348184018d610a48565b90508281036060840152610b48818c610a48565b90508281036080840152610b5c818b610a8e565b905082810360a0840152610b70818a610ad2565b905082810360c0840152610b848189610ad2565b905082810360e0840152610b988188610ad2565b9050828103610100840152610bad8187610ad2565b9050828103610120840152610bc28186610ad2565b9050828103610140840152610bd78185610a48565b9e9d5050505050505050505050505050565b6020815260006106b36020830184610a4856fea2646970667358221220889ac78df81d1379d6471d9899757d4a6e816b1390bb99b56cff15fc7aa3073464736f6c63430008110033", + "devdoc": { + "details": "Governance to create new LBPManager contract without the onlyOwner modifer for the function deployLBPManager(). By removing the access control, everyone can deploy a LBPManager from this contract. This is a temporarly solution in response to the flaky Celo Safe.", + "kind": "dev", + "methods": { + "constructor": { + "details": "Constructor.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Deploy and initialize LBPManager.", + "params": { + "_admin": "The address of the admin of the LBPManager.", + "_amounts": "Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the _fees.", + "_endWeights": "Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndtime": "Array containing two parameters: - Start time for the LBP. - End time for the LBP.", + "_startWeights": "Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token." + } + }, + "owner()": { + "details": "Returns the address of the current owner." + }, + "renounceOwnership()": { + "details": "Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner." + }, + "setLBPFactory(address)": { + "details": "Set Balancers LBP Factory contract as basis for deploying LBPs.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "setMasterCopy(address)": { + "details": "Set LBPManager contract which works as a base for clones.", + "params": { + "_masterCopy": "The address of the new LBPManager basis." + } + }, + "transferOwnership(address)": { + "details": "Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner." + } + }, + "title": "LBPManager Factory no access control version 1", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 7, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "_owner", + "offset": 0, + "slot": "0", + "type": "t_address" + }, + { + "astId": 434, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "version", + "offset": 20, + "slot": "0", + "type": "t_bytes6" + }, + { + "astId": 436, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "masterCopy", + "offset": 0, + "slot": "1", + "type": "t_address" + }, + { + "astId": 438, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "lbpFactory", + "offset": 0, + "slot": "2", + "type": "t_address" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_bytes6": { + "encoding": "inplace", + "label": "bytes6", + "numberOfBytes": "6" + } + } + } +} \ No newline at end of file diff --git a/deployments/celo/LBPManagerV1.json b/deployments/celo/LBPManagerV1.json new file mode 100644 index 0000000..11ab1f4 --- /dev/null +++ b/deployments/celo/LBPManagerV1.json @@ -0,0 +1,811 @@ +{ + "address": "0x49ED64a98FA5E298384000A92CD4A0B0fECeA9b9", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0x1a47460b1b1c5c910e3b302e90d70121876abfcdd078afdd375055a07cd7fc1a", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0x49ED64a98FA5E298384000A92CD4A0B0fECeA9b9", + "transactionIndex": 5, + "gasUsed": "2334241", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x36e55273b53ece9e9c5de47130ae1a127f84cbbb1d972578936d45affdc47fef", + "transactionHash": "0x1a47460b1b1c5c910e3b302e90d70121876abfcdd078afdd375055a07cd7fc1a", + "logs": [], + "blockNumber": 16550844, + "cumulativeGasUsed": "3452888", + "status": 1, + "byzantium": true + }, + "args": [], + "solcInputHash": "752d54b8f64e3608832db5b1be68e60f", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"beneficiary\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"tokenAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"FeeTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldAdmin\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newAdmin\",\"type\":\"address\"}],\"name\":\"LBPManagerAdminChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"MetadataUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"PoolTokensWithdrawn\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"admin\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"amounts\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"beneficiary\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"endWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"feePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getSwapEnabled\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_sender\",\"type\":\"address\"}],\"name\":\"initializeLBP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndTime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"initializeLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"initialized\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbp\",\"outputs\":[{\"internalType\":\"contract ILBP\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"metadata\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"name\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"poolFunded\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokenIndex\",\"outputs\":[{\"internalType\":\"uint8\",\"name\":\"\",\"type\":\"uint8\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokensRequired\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"projectTokenAmounts\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"removeLiquidity\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bool\",\"name\":\"_swapEnabled\",\"type\":\"bool\"}],\"name\":\"setSwapEnabled\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startTimeEndTime\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"swapFeePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"symbol\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"tokenList\",\"outputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_newAdmin\",\"type\":\"address\"}],\"name\":\"transferAdminRights\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"updateMetadata\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"version\",\"outputs\":[{\"internalType\":\"bytes6\",\"name\":\"\",\"type\":\"bytes6\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"withdrawPoolTokens\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Smart contract for managing interactions with a Balancer LBP.\",\"kind\":\"dev\",\"methods\":{\"getSwapEnabled()\":{\"details\":\"Tells whether swaps are enabled or not for the LBP\"},\"initializeLBP(address)\":{\"details\":\"Subtracts the fee, deploys the LBP and adds liquidity to it.\",\"params\":{\"_sender\":\"Address of the liquidity provider.\"}},\"initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Initialize LBPManager.\",\"params\":{\"_amounts\":\"Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the feePercentage.\",\"_endWeights\":\"Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_lbpFactory\":\"LBP factory address.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndTime\":\"Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.\",\"_startWeights\":\"Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token.\"}},\"projectTokensRequired()\":{\"details\":\"Get required amount of project tokens to cover for fees and the actual LBP.\"},\"removeLiquidity(address)\":{\"details\":\"Exit pool or remove liquidity from pool.\",\"params\":{\"_receiver\":\"Address of the liquidity receiver, after exiting the LBP.\"}},\"setSwapEnabled(bool)\":{\"details\":\"Can pause/unpause trading.\",\"params\":{\"_swapEnabled\":\"Enables/disables swapping.\"}},\"transferAdminRights(address)\":{\"details\":\"Transfer admin rights.\",\"params\":{\"_newAdmin\":\"Address of the new admin.\"}},\"updateMetadata(bytes)\":{\"details\":\"Updates metadata.\",\"params\":{\"_metadata\":\"LBP wizard contract metadata, that is an IPFS Hash.\"}},\"withdrawPoolTokens(address)\":{\"details\":\"Withdraw pool tokens if available.\",\"params\":{\"_receiver\":\"Address of the BPT tokens receiver.\"}}},\"title\":\"LBPManager contract version 1\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerV1.sol\":\"LBPManagerV1\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"contracts/lbp/LBPManagerV1.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract version 1\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManagerV1 {\\n bytes6 public version = \\\"1.0.0\\\";\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x75473a78174d66c360426296446d175f991d8dba1f047b387ce2e25452ca2991\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x60806040526000805465ffffffffffff191665312e302e300017905534801561002757600080fd5b506128e2806100376000396000f3fe608060405234801561001057600080fd5b50600436106101a95760003560e01c80639ead7222116100f9578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461038c578063e01af92c1461039f578063f851a440146103b2578063fc582d41146103c557600080fd5b8063c9d8616f14610347578063cb209b6c1461035a578063cd2055e51461037957600080fd5b8063a88971fa116100d3578063a88971fa146102f5578063b5106add14610309578063bb7bfb0c1461031c578063c18b51511461032f57600080fd5b80639ead7222146102d0578063a001ecdd146102e3578063a4ac0d49146102ec57600080fd5b80633facbb851161016657806354fd4d501161014057806354fd4d501461027c5780638638fe31146102a25780638bfd5289146102b557806395d89b41146102c857600080fd5b80633facbb851461024c57806345f0a44f1461026157806347bc4d921461027457600080fd5b806306fdde03146101ae578063092f7de7146101cc578063158ef93e146101f75780633281f3ec1461021b57806338af3eed14610231578063392f37e914610244575b600080fd5b6101b66103d8565b6040516101c39190611f4c565b60405180910390f35b600c546101df906001600160a01b031681565b6040516001600160a01b0390911681526020016101c3565b600e5461020b90600160b01b900460ff1681565b60405190151581526020016101c3565b610223610466565b6040519081526020016101c3565b6004546101df906001600160a01b031681565b6101b66104a5565b61025f61025a366004611f8e565b6104b2565b005b61022361026f366004611fab565b6107f3565b61020b610814565b6000546102899060d01b81565b6040516001600160d01b031990911681526020016101c3565b61025f6102b036600461216e565b6108e7565b61025f6102c3366004611f8e565b610fca565b6101b661175b565b6101df6102de366004611fab565b611768565b61022360055481565b61022360065481565b600e5461020b90600160a81b900460ff1681565b61025f610317366004611f8e565b611792565b61022361032a366004611fab565b61186e565b600e546101df9061010090046001600160a01b031681565b610223610355366004611fab565b61187e565b600e546103679060ff1681565b60405160ff90911681526020016101c3565b610223610387366004611fab565b61188e565b61025f61039a366004611f8e565b61189e565b61025f6103ad366004612312565b611cf6565b6003546101df906001600160a01b031681565b61025f6103d336600461232f565b611d82565b600280546103e59061236c565b80601f01602080910402602001604051908101604052809291908181526020018280546104119061236c565b801561045e5780601f106104335761010080835404028352916020019161045e565b820191906000526020600020905b81548152906001019060200180831161044157829003601f168201915b505050505081565b6000610470611dfa565b600e5460088054909160ff1690811061048b5761048b6123a6565b90600052602060002001546104a091906123d2565b905090565b600d80546103e59061236c565b6003546001600160a01b031633146104e55760405162461bcd60e51b81526004016104dc906123eb565b60405180910390fd5b6001600160a01b03811661053b5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b6000600b600181548110610551576105516123a6565b90600052602060002001549050804210156105ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105f7573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061061b9190612422565b116106685760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b600c546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa1580156106d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106f89190612422565b60405190815260200160405180910390a2600c546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561075b573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061077f9190612422565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af11580156107ca573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ee919061243b565b505050565b6008818154811061080357600080fd5b600091825260209091200154905081565b600e54600090600160a81b900460ff166108705760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e60448201526064016104dc565b600c60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa1580156108c3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104a0919061243b565b600e54600160b01b900460ff16156109415760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a65640060448201526064016104dc565b6001600160a01b038a166109975760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f60448201526064016104dc565b64e8d4a51000826000815181106109b0576109b06123a6565b60200260200101511015610a125760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b60648201526084016104dc565b67016345785d8a000082600081518110610a2e57610a2e6123a6565b60200260200101511115610a925760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b60648201526084016104dc565b86516002148015610aa4575085516002145b8015610ab1575084516002145b8015610abe575083516002145b8015610acb575082516002145b8015610ad8575081516002145b610b245760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a6500000060448201526064016104dc565b86600181518110610b3757610b376123a6565b60200260200101516001600160a01b031687600081518110610b5b57610b5b6123a6565b60200260200101516001600160a01b031603610bb95760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d6560448201526064016104dc565b83600181518110610bcc57610bcc6123a6565b602002602001015184600081518110610be757610be76123a6565b602002602001015110610c3c5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d650060448201526064016104dc565b600e805460ff60b01b1916600160b01b179055600380546001600160a01b0319163317905581518290600090610c7457610c746123a6565b602002602001015160068190555081600181518110610c9557610c956123a6565b6020908102919091010151600555600480546001600160a01b0319166001600160a01b038c16179055600d610cca82826124a6565b508351610cde90600b906020870190611e47565b506002610ceb8a826124a6565b506001610cf889826124a6565b50600e8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610d2e57610d2e6123a6565b60200260200101516001600160a01b031687600081518110610d5257610d526123a6565b60200260200101516001600160a01b03161115610f6257600e805460ff19166001908117909155875160079189918110610d8e57610d8e6123a6565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516007918991610ddd57610ddd6123a6565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160089188918110610e3157610e316123a6565b602090810291909101810151825460018101845560009384529183209091015586516008918891610e6457610e646123a6565b60209081029190910181015182546001818101855560009485529290932090920191909155855160099187918110610e9e57610e9e6123a6565b602090810291909101810151825460018101845560009384529183209091015585516009918791610ed157610ed16123a6565b602090810291909101810151825460018181018555600094855292909320909201919091558351600a9185918110610f0b57610f0b6123a6565b60209081029190910181015182546001810184556000938452918320909101558351600a918591610f3e57610f3e6123a6565b60209081029190910181015182546001810184556000938452919092200155610fbd565b600e805460ff191690558651610f7f9060079060208a0190611e92565b508551610f93906008906020890190611e47565b508451610fa7906009906020880190611e47565b508251610fbb90600a906020860190611e47565b505b5050505050505050505050565b6003546001600160a01b03163314610ff45760405162461bcd60e51b81526004016104dc906123eb565b600e54600160b01b900460ff1615156001146110615760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b60648201526084016104dc565b600e54600160a81b900460ff16156110bb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e6465640060448201526064016104dc565b600e8054600160a81b60ff60a81b199091161790819055600654604051632367971960e01b81526101009092046001600160a01b031691632367971991611115916002916001916007916009913090600090600401612623565b6020604051808303816000875af1158015611134573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061115891906126d4565b600c80546001600160a01b0319166001600160a01b03929092169182179055600b8054633e5692059190600090611191576111916123a6565b9060005260206000200154600b6001815481106111b0576111b06123a6565b9060005260206000200154600a6040518463ffffffff1660e01b81526004016111db939291906126f1565b600060405180830381600087803b1580156111f557600080fd5b505af1158015611209573d6000803e3d6000fd5b505050506000600c60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611262573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128691906126d4565b90506005546000146113c257600061129c611dfa565b600e54600780549293509160ff9091169081106112bb576112bb6123a6565b600091825260209091200154600480546040516323b872dd60e01b81526001600160a01b03878116938201939093529082166024820152604481018490529116906323b872dd906064016020604051808303816000875af1158015611324573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611348919061243b565b50600454600e54600780546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff16908110611393576113936123a6565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60075460ff8216101561158c5760078160ff16815481106113e8576113e86123a6565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060088560ff168154811061142c5761142c6123a6565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af115801561148c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114b0919061243b565b5060078160ff16815481106114c7576114c76123a6565b600091825260209091200154600880546001600160a01b039092169163095ea7b391859160ff86169081106114fe576114fe6123a6565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611555573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611579919061243b565b508061158481612719565b9150506113c5565b50604080516007805460a060208202840181019094526080830181815260009484939192908401828280156115ea57602002820191906000526020600020905b81546001600160a01b031681526001909101906020018083116115cc575b50505050508152602001600880548060200260200160405190810160405280929190818152602001828054801561164057602002820191906000526020600020905b81548152602001906001019080831161162c575b505050505081526020016000600860405160200161165f929190612738565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa1580156116de573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906117029190612422565b3030856040518563ffffffff1660e01b8152600401611724949392919061281b565b600060405180830381600087803b15801561173e57600080fd5b505af1158015611752573d6000803e3d6000fd5b50505050505050565b600180546103e59061236c565b6007818154811061177857600080fd5b6000918252602090912001546001600160a01b0316905081565b6003546001600160a01b031633146117bc5760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b0381166118125760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f00000060448201526064016104dc565b6003546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b6009818154811061080357600080fd5b600a818154811061080357600080fd5b600b818154811061080357600080fd5b6003546001600160a01b031633146118c85760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b03811661191e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611967573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061198b9190612422565b116119d85760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b6000600b6001815481106119ee576119ee6123a6565b9060005260206000200154905080421015611a4b5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a95573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ab991906126d4565b9050600060405180608001604052806007805480602002602001604051908101604052809291908181526020018280548015611b1e57602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611b00575b5050505050815260200160078054905067ffffffffffffffff811115611b4657611b46611fc4565b604051908082528060200260200182016040528015611b6f578160200160208202803683370190505b508152600c546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190612422565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c78573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c9c9190612422565b3087856040518563ffffffff1660e01b8152600401611cbe949392919061281b565b600060405180830381600087803b158015611cd857600080fd5b505af1158015611cec573d6000803e3d6000fd5b5050505050505050565b6003546001600160a01b03163314611d205760405162461bcd60e51b81526004016104dc906123eb565b600c54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d6757600080fd5b505af1158015611d7b573d6000803e3d6000fd5b5050505050565b6003546001600160a01b03163314611dac5760405162461bcd60e51b81526004016104dc906123eb565b600d611db882826124a6565b5080604051611dc79190612857565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600554600e5460088054600093670de0b6b3a76400009390929160ff909116908110611e2857611e286123a6565b9060005260206000200154611e3d9190612873565b6104a0919061288a565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e82578251825591602001919060010190611e67565b50611e8e929150611ee7565b5090565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e8257825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611eb2565b5b80821115611e8e5760008155600101611ee8565b60005b83811015611f17578181015183820152602001611eff565b50506000910152565b60008151808452611f38816020860160208601611efc565b601f01601f19169290920160200192915050565b602081526000611f5f6020830184611f20565b9392505050565b6001600160a01b0381168114611f7b57600080fd5b50565b8035611f8981611f66565b919050565b600060208284031215611fa057600080fd5b8135611f5f81611f66565b600060208284031215611fbd57600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561200357612003611fc4565b604052919050565b600082601f83011261201c57600080fd5b813567ffffffffffffffff81111561203657612036611fc4565b612049601f8201601f1916602001611fda565b81815284602083860101111561205e57600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561209557612095611fc4565b5060051b60200190565b600082601f8301126120b057600080fd5b813560206120c56120c08361207b565b611fda565b82815260059290921b840181019181810190868411156120e457600080fd5b8286015b848110156121085780356120fb81611f66565b83529183019183016120e8565b509695505050505050565b600082601f83011261212457600080fd5b813560206121346120c08361207b565b82815260059290921b8401810191818101908684111561215357600080fd5b8286015b848110156121085780358352918301918301612157565b60008060008060008060008060008060006101608c8e03121561219057600080fd5b6121998c611f7e565b9a506121a760208d01611f7e565b995067ffffffffffffffff8060408e013511156121c357600080fd5b6121d38e60408f01358f0161200b565b99508060608e013511156121e657600080fd5b6121f68e60608f01358f0161200b565b98508060808e0135111561220957600080fd5b6122198e60808f01358f0161209f565b97508060a08e0135111561222c57600080fd5b61223c8e60a08f01358f01612113565b96508060c08e0135111561224f57600080fd5b61225f8e60c08f01358f01612113565b95508060e08e0135111561227257600080fd5b6122828e60e08f01358f01612113565b9450806101008e0135111561229657600080fd5b6122a78e6101008f01358f01612113565b9350806101208e013511156122bb57600080fd5b6122cc8e6101208f01358f01612113565b9250806101408e013511156122e057600080fd5b506122f28d6101408e01358e0161200b565b90509295989b509295989b9093969950565b8015158114611f7b57600080fd5b60006020828403121561232457600080fd5b8135611f5f81612304565b60006020828403121561234157600080fd5b813567ffffffffffffffff81111561235857600080fd5b6123648482850161200b565b949350505050565b600181811c9082168061238057607f821691505b6020821081036123a057634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123e5576123e56123bc565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b60006020828403121561243457600080fd5b5051919050565b60006020828403121561244d57600080fd5b8151611f5f81612304565b601f8211156107ee57600081815260208120601f850160051c8101602086101561247f5750805b601f850160051c820191505b8181101561249e5782815560010161248b565b505050505050565b815167ffffffffffffffff8111156124c0576124c0611fc4565b6124d4816124ce845461236c565b84612458565b602080601f83116001811461250957600084156124f15750858301515b600019600386901b1c1916600185901b17855561249e565b600085815260208120601f198616915b8281101561253857888601518255948401946001909101908401612519565b50858210156125565787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600081546125738161236c565b80855260206001838116801561259057600181146125aa576125d8565b60ff1985168884015283151560051b8801830195506125d8565b866000528260002060005b858110156125d05781548a82018601529083019084016125b5565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b83811015612618578154875295820195600191820191016125fc565b509495945050505050565b60e08152600061263660e083018a612566565b8281036020840152612648818a612566565b8381036040850152885480825260008a815260208082209450909201915b8181101561268d5783546001600160a01b0316835260019384019360209093019201612666565b505083810360608501526126a181896125e3565b925050508460808301526126c060a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126e657600080fd5b8151611f5f81611f66565b83815282602082015260606040820152600061271060608301846125e3565b95945050505050565b600060ff821660ff810361272f5761272f6123bc565b60010192915050565b60ff8316815260406020820152600061236460408301846125e3565b600081518084526020808501945080840160005b8381101561261857815187529582019590820190600101612768565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127c95783516001600160a01b0316835292840192918401916001016127a4565b5050828501519150858103838701526127e28183612754565b92505050604083015184820360408601526127fd8282611f20565b9150506060830151612813606086018215159052565b509392505050565b8481526001600160a01b0384811660208301528316604082015260806060820181905260009061284d90830184612784565b9695505050505050565b60008251612869818460208701611efc565b9190910192915050565b80820281158282048414176123e5576123e56123bc565b6000826128a757634e487b7160e01b600052601260045260246000fd5b50049056fea2646970667358221220eb6a5eda73e8fe17bd4c717b89e7802172bdb3b8f73914eef5f8c1f8fd93f13664736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106101a95760003560e01c80639ead7222116100f9578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461038c578063e01af92c1461039f578063f851a440146103b2578063fc582d41146103c557600080fd5b8063c9d8616f14610347578063cb209b6c1461035a578063cd2055e51461037957600080fd5b8063a88971fa116100d3578063a88971fa146102f5578063b5106add14610309578063bb7bfb0c1461031c578063c18b51511461032f57600080fd5b80639ead7222146102d0578063a001ecdd146102e3578063a4ac0d49146102ec57600080fd5b80633facbb851161016657806354fd4d501161014057806354fd4d501461027c5780638638fe31146102a25780638bfd5289146102b557806395d89b41146102c857600080fd5b80633facbb851461024c57806345f0a44f1461026157806347bc4d921461027457600080fd5b806306fdde03146101ae578063092f7de7146101cc578063158ef93e146101f75780633281f3ec1461021b57806338af3eed14610231578063392f37e914610244575b600080fd5b6101b66103d8565b6040516101c39190611f4c565b60405180910390f35b600c546101df906001600160a01b031681565b6040516001600160a01b0390911681526020016101c3565b600e5461020b90600160b01b900460ff1681565b60405190151581526020016101c3565b610223610466565b6040519081526020016101c3565b6004546101df906001600160a01b031681565b6101b66104a5565b61025f61025a366004611f8e565b6104b2565b005b61022361026f366004611fab565b6107f3565b61020b610814565b6000546102899060d01b81565b6040516001600160d01b031990911681526020016101c3565b61025f6102b036600461216e565b6108e7565b61025f6102c3366004611f8e565b610fca565b6101b661175b565b6101df6102de366004611fab565b611768565b61022360055481565b61022360065481565b600e5461020b90600160a81b900460ff1681565b61025f610317366004611f8e565b611792565b61022361032a366004611fab565b61186e565b600e546101df9061010090046001600160a01b031681565b610223610355366004611fab565b61187e565b600e546103679060ff1681565b60405160ff90911681526020016101c3565b610223610387366004611fab565b61188e565b61025f61039a366004611f8e565b61189e565b61025f6103ad366004612312565b611cf6565b6003546101df906001600160a01b031681565b61025f6103d336600461232f565b611d82565b600280546103e59061236c565b80601f01602080910402602001604051908101604052809291908181526020018280546104119061236c565b801561045e5780601f106104335761010080835404028352916020019161045e565b820191906000526020600020905b81548152906001019060200180831161044157829003601f168201915b505050505081565b6000610470611dfa565b600e5460088054909160ff1690811061048b5761048b6123a6565b90600052602060002001546104a091906123d2565b905090565b600d80546103e59061236c565b6003546001600160a01b031633146104e55760405162461bcd60e51b81526004016104dc906123eb565b60405180910390fd5b6001600160a01b03811661053b5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b6000600b600181548110610551576105516123a6565b90600052602060002001549050804210156105ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105f7573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061061b9190612422565b116106685760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b600c546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa1580156106d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106f89190612422565b60405190815260200160405180910390a2600c546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561075b573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061077f9190612422565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af11580156107ca573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ee919061243b565b505050565b6008818154811061080357600080fd5b600091825260209091200154905081565b600e54600090600160a81b900460ff166108705760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e60448201526064016104dc565b600c60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa1580156108c3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104a0919061243b565b600e54600160b01b900460ff16156109415760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a65640060448201526064016104dc565b6001600160a01b038a166109975760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f60448201526064016104dc565b64e8d4a51000826000815181106109b0576109b06123a6565b60200260200101511015610a125760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b60648201526084016104dc565b67016345785d8a000082600081518110610a2e57610a2e6123a6565b60200260200101511115610a925760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b60648201526084016104dc565b86516002148015610aa4575085516002145b8015610ab1575084516002145b8015610abe575083516002145b8015610acb575082516002145b8015610ad8575081516002145b610b245760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a6500000060448201526064016104dc565b86600181518110610b3757610b376123a6565b60200260200101516001600160a01b031687600081518110610b5b57610b5b6123a6565b60200260200101516001600160a01b031603610bb95760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d6560448201526064016104dc565b83600181518110610bcc57610bcc6123a6565b602002602001015184600081518110610be757610be76123a6565b602002602001015110610c3c5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d650060448201526064016104dc565b600e805460ff60b01b1916600160b01b179055600380546001600160a01b0319163317905581518290600090610c7457610c746123a6565b602002602001015160068190555081600181518110610c9557610c956123a6565b6020908102919091010151600555600480546001600160a01b0319166001600160a01b038c16179055600d610cca82826124a6565b508351610cde90600b906020870190611e47565b506002610ceb8a826124a6565b506001610cf889826124a6565b50600e8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610d2e57610d2e6123a6565b60200260200101516001600160a01b031687600081518110610d5257610d526123a6565b60200260200101516001600160a01b03161115610f6257600e805460ff19166001908117909155875160079189918110610d8e57610d8e6123a6565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516007918991610ddd57610ddd6123a6565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160089188918110610e3157610e316123a6565b602090810291909101810151825460018101845560009384529183209091015586516008918891610e6457610e646123a6565b60209081029190910181015182546001818101855560009485529290932090920191909155855160099187918110610e9e57610e9e6123a6565b602090810291909101810151825460018101845560009384529183209091015585516009918791610ed157610ed16123a6565b602090810291909101810151825460018181018555600094855292909320909201919091558351600a9185918110610f0b57610f0b6123a6565b60209081029190910181015182546001810184556000938452918320909101558351600a918591610f3e57610f3e6123a6565b60209081029190910181015182546001810184556000938452919092200155610fbd565b600e805460ff191690558651610f7f9060079060208a0190611e92565b508551610f93906008906020890190611e47565b508451610fa7906009906020880190611e47565b508251610fbb90600a906020860190611e47565b505b5050505050505050505050565b6003546001600160a01b03163314610ff45760405162461bcd60e51b81526004016104dc906123eb565b600e54600160b01b900460ff1615156001146110615760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b60648201526084016104dc565b600e54600160a81b900460ff16156110bb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e6465640060448201526064016104dc565b600e8054600160a81b60ff60a81b199091161790819055600654604051632367971960e01b81526101009092046001600160a01b031691632367971991611115916002916001916007916009913090600090600401612623565b6020604051808303816000875af1158015611134573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061115891906126d4565b600c80546001600160a01b0319166001600160a01b03929092169182179055600b8054633e5692059190600090611191576111916123a6565b9060005260206000200154600b6001815481106111b0576111b06123a6565b9060005260206000200154600a6040518463ffffffff1660e01b81526004016111db939291906126f1565b600060405180830381600087803b1580156111f557600080fd5b505af1158015611209573d6000803e3d6000fd5b505050506000600c60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611262573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128691906126d4565b90506005546000146113c257600061129c611dfa565b600e54600780549293509160ff9091169081106112bb576112bb6123a6565b600091825260209091200154600480546040516323b872dd60e01b81526001600160a01b03878116938201939093529082166024820152604481018490529116906323b872dd906064016020604051808303816000875af1158015611324573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611348919061243b565b50600454600e54600780546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff16908110611393576113936123a6565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60075460ff8216101561158c5760078160ff16815481106113e8576113e86123a6565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060088560ff168154811061142c5761142c6123a6565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af115801561148c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114b0919061243b565b5060078160ff16815481106114c7576114c76123a6565b600091825260209091200154600880546001600160a01b039092169163095ea7b391859160ff86169081106114fe576114fe6123a6565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611555573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611579919061243b565b508061158481612719565b9150506113c5565b50604080516007805460a060208202840181019094526080830181815260009484939192908401828280156115ea57602002820191906000526020600020905b81546001600160a01b031681526001909101906020018083116115cc575b50505050508152602001600880548060200260200160405190810160405280929190818152602001828054801561164057602002820191906000526020600020905b81548152602001906001019080831161162c575b505050505081526020016000600860405160200161165f929190612738565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa1580156116de573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906117029190612422565b3030856040518563ffffffff1660e01b8152600401611724949392919061281b565b600060405180830381600087803b15801561173e57600080fd5b505af1158015611752573d6000803e3d6000fd5b50505050505050565b600180546103e59061236c565b6007818154811061177857600080fd5b6000918252602090912001546001600160a01b0316905081565b6003546001600160a01b031633146117bc5760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b0381166118125760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f00000060448201526064016104dc565b6003546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b6009818154811061080357600080fd5b600a818154811061080357600080fd5b600b818154811061080357600080fd5b6003546001600160a01b031633146118c85760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b03811661191e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611967573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061198b9190612422565b116119d85760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b6000600b6001815481106119ee576119ee6123a6565b9060005260206000200154905080421015611a4b5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a95573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ab991906126d4565b9050600060405180608001604052806007805480602002602001604051908101604052809291908181526020018280548015611b1e57602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611b00575b5050505050815260200160078054905067ffffffffffffffff811115611b4657611b46611fc4565b604051908082528060200260200182016040528015611b6f578160200160208202803683370190505b508152600c546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190612422565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c78573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c9c9190612422565b3087856040518563ffffffff1660e01b8152600401611cbe949392919061281b565b600060405180830381600087803b158015611cd857600080fd5b505af1158015611cec573d6000803e3d6000fd5b5050505050505050565b6003546001600160a01b03163314611d205760405162461bcd60e51b81526004016104dc906123eb565b600c54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d6757600080fd5b505af1158015611d7b573d6000803e3d6000fd5b5050505050565b6003546001600160a01b03163314611dac5760405162461bcd60e51b81526004016104dc906123eb565b600d611db882826124a6565b5080604051611dc79190612857565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600554600e5460088054600093670de0b6b3a76400009390929160ff909116908110611e2857611e286123a6565b9060005260206000200154611e3d9190612873565b6104a0919061288a565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e82578251825591602001919060010190611e67565b50611e8e929150611ee7565b5090565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e8257825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611eb2565b5b80821115611e8e5760008155600101611ee8565b60005b83811015611f17578181015183820152602001611eff565b50506000910152565b60008151808452611f38816020860160208601611efc565b601f01601f19169290920160200192915050565b602081526000611f5f6020830184611f20565b9392505050565b6001600160a01b0381168114611f7b57600080fd5b50565b8035611f8981611f66565b919050565b600060208284031215611fa057600080fd5b8135611f5f81611f66565b600060208284031215611fbd57600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561200357612003611fc4565b604052919050565b600082601f83011261201c57600080fd5b813567ffffffffffffffff81111561203657612036611fc4565b612049601f8201601f1916602001611fda565b81815284602083860101111561205e57600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561209557612095611fc4565b5060051b60200190565b600082601f8301126120b057600080fd5b813560206120c56120c08361207b565b611fda565b82815260059290921b840181019181810190868411156120e457600080fd5b8286015b848110156121085780356120fb81611f66565b83529183019183016120e8565b509695505050505050565b600082601f83011261212457600080fd5b813560206121346120c08361207b565b82815260059290921b8401810191818101908684111561215357600080fd5b8286015b848110156121085780358352918301918301612157565b60008060008060008060008060008060006101608c8e03121561219057600080fd5b6121998c611f7e565b9a506121a760208d01611f7e565b995067ffffffffffffffff8060408e013511156121c357600080fd5b6121d38e60408f01358f0161200b565b99508060608e013511156121e657600080fd5b6121f68e60608f01358f0161200b565b98508060808e0135111561220957600080fd5b6122198e60808f01358f0161209f565b97508060a08e0135111561222c57600080fd5b61223c8e60a08f01358f01612113565b96508060c08e0135111561224f57600080fd5b61225f8e60c08f01358f01612113565b95508060e08e0135111561227257600080fd5b6122828e60e08f01358f01612113565b9450806101008e0135111561229657600080fd5b6122a78e6101008f01358f01612113565b9350806101208e013511156122bb57600080fd5b6122cc8e6101208f01358f01612113565b9250806101408e013511156122e057600080fd5b506122f28d6101408e01358e0161200b565b90509295989b509295989b9093969950565b8015158114611f7b57600080fd5b60006020828403121561232457600080fd5b8135611f5f81612304565b60006020828403121561234157600080fd5b813567ffffffffffffffff81111561235857600080fd5b6123648482850161200b565b949350505050565b600181811c9082168061238057607f821691505b6020821081036123a057634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123e5576123e56123bc565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b60006020828403121561243457600080fd5b5051919050565b60006020828403121561244d57600080fd5b8151611f5f81612304565b601f8211156107ee57600081815260208120601f850160051c8101602086101561247f5750805b601f850160051c820191505b8181101561249e5782815560010161248b565b505050505050565b815167ffffffffffffffff8111156124c0576124c0611fc4565b6124d4816124ce845461236c565b84612458565b602080601f83116001811461250957600084156124f15750858301515b600019600386901b1c1916600185901b17855561249e565b600085815260208120601f198616915b8281101561253857888601518255948401946001909101908401612519565b50858210156125565787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600081546125738161236c565b80855260206001838116801561259057600181146125aa576125d8565b60ff1985168884015283151560051b8801830195506125d8565b866000528260002060005b858110156125d05781548a82018601529083019084016125b5565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b83811015612618578154875295820195600191820191016125fc565b509495945050505050565b60e08152600061263660e083018a612566565b8281036020840152612648818a612566565b8381036040850152885480825260008a815260208082209450909201915b8181101561268d5783546001600160a01b0316835260019384019360209093019201612666565b505083810360608501526126a181896125e3565b925050508460808301526126c060a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126e657600080fd5b8151611f5f81611f66565b83815282602082015260606040820152600061271060608301846125e3565b95945050505050565b600060ff821660ff810361272f5761272f6123bc565b60010192915050565b60ff8316815260406020820152600061236460408301846125e3565b600081518084526020808501945080840160005b8381101561261857815187529582019590820190600101612768565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127c95783516001600160a01b0316835292840192918401916001016127a4565b5050828501519150858103838701526127e28183612754565b92505050604083015184820360408601526127fd8282611f20565b9150506060830151612813606086018215159052565b509392505050565b8481526001600160a01b0384811660208301528316604082015260806060820181905260009061284d90830184612784565b9695505050505050565b60008251612869818460208701611efc565b9190910192915050565b80820281158282048414176123e5576123e56123bc565b6000826128a757634e487b7160e01b600052601260045260246000fd5b50049056fea2646970667358221220eb6a5eda73e8fe17bd4c717b89e7802172bdb3b8f73914eef5f8c1f8fd93f13664736f6c63430008110033", + "devdoc": { + "details": "Smart contract for managing interactions with a Balancer LBP.", + "kind": "dev", + "methods": { + "getSwapEnabled()": { + "details": "Tells whether swaps are enabled or not for the LBP" + }, + "initializeLBP(address)": { + "details": "Subtracts the fee, deploys the LBP and adds liquidity to it.", + "params": { + "_sender": "Address of the liquidity provider." + } + }, + "initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Initialize LBPManager.", + "params": { + "_amounts": "Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the feePercentage.", + "_endWeights": "Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_lbpFactory": "LBP factory address.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndTime": "Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.", + "_startWeights": "Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token." + } + }, + "projectTokensRequired()": { + "details": "Get required amount of project tokens to cover for fees and the actual LBP." + }, + "removeLiquidity(address)": { + "details": "Exit pool or remove liquidity from pool.", + "params": { + "_receiver": "Address of the liquidity receiver, after exiting the LBP." + } + }, + "setSwapEnabled(bool)": { + "details": "Can pause/unpause trading.", + "params": { + "_swapEnabled": "Enables/disables swapping." + } + }, + "transferAdminRights(address)": { + "details": "Transfer admin rights.", + "params": { + "_newAdmin": "Address of the new admin." + } + }, + "updateMetadata(bytes)": { + "details": "Updates metadata.", + "params": { + "_metadata": "LBP wizard contract metadata, that is an IPFS Hash." + } + }, + "withdrawPoolTokens(address)": { + "details": "Withdraw pool tokens if available.", + "params": { + "_receiver": "Address of the BPT tokens receiver." + } + } + }, + "title": "LBPManager contract version 1", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 638, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "version", + "offset": 0, + "slot": "0", + "type": "t_bytes6" + }, + { + "astId": 643, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "symbol", + "offset": 0, + "slot": "1", + "type": "t_string_storage" + }, + { + "astId": 645, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "name", + "offset": 0, + "slot": "2", + "type": "t_string_storage" + }, + { + "astId": 647, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "admin", + "offset": 0, + "slot": "3", + "type": "t_address" + }, + { + "astId": 649, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "beneficiary", + "offset": 0, + "slot": "4", + "type": "t_address" + }, + { + "astId": 651, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "feePercentage", + "offset": 0, + "slot": "5", + "type": "t_uint256" + }, + { + "astId": 653, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "swapFeePercentage", + "offset": 0, + "slot": "6", + "type": "t_uint256" + }, + { + "astId": 657, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "tokenList", + "offset": 0, + "slot": "7", + "type": "t_array(t_contract(IERC20)190)dyn_storage" + }, + { + "astId": 660, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "amounts", + "offset": 0, + "slot": "8", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 663, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "startWeights", + "offset": 0, + "slot": "9", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 666, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "endWeights", + "offset": 0, + "slot": "10", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 669, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "startTimeEndTime", + "offset": 0, + "slot": "11", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 672, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "lbp", + "offset": 0, + "slot": "12", + "type": "t_contract(ILBP)1530" + }, + { + "astId": 674, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "metadata", + "offset": 0, + "slot": "13", + "type": "t_bytes_storage" + }, + { + "astId": 676, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "projectTokenIndex", + "offset": 0, + "slot": "14", + "type": "t_uint8" + }, + { + "astId": 678, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "lbpFactory", + "offset": 1, + "slot": "14", + "type": "t_address" + }, + { + "astId": 680, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "poolFunded", + "offset": 21, + "slot": "14", + "type": "t_bool" + }, + { + "astId": 682, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "initialized", + "offset": 22, + "slot": "14", + "type": "t_bool" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_array(t_contract(IERC20)190)dyn_storage": { + "base": "t_contract(IERC20)190", + "encoding": "dynamic_array", + "label": "contract IERC20[]", + "numberOfBytes": "32" + }, + "t_array(t_uint256)dyn_storage": { + "base": "t_uint256", + "encoding": "dynamic_array", + "label": "uint256[]", + "numberOfBytes": "32" + }, + "t_bool": { + "encoding": "inplace", + "label": "bool", + "numberOfBytes": "1" + }, + "t_bytes6": { + "encoding": "inplace", + "label": "bytes6", + "numberOfBytes": "6" + }, + "t_bytes_storage": { + "encoding": "bytes", + "label": "bytes", + "numberOfBytes": "32" + }, + "t_contract(IERC20)190": { + "encoding": "inplace", + "label": "contract IERC20", + "numberOfBytes": "20" + }, + "t_contract(ILBP)1530": { + "encoding": "inplace", + "label": "contract ILBP", + "numberOfBytes": "20" + }, + "t_string_storage": { + "encoding": "bytes", + "label": "string", + "numberOfBytes": "32" + }, + "t_uint256": { + "encoding": "inplace", + "label": "uint256", + "numberOfBytes": "32" + }, + "t_uint8": { + "encoding": "inplace", + "label": "uint8", + "numberOfBytes": "1" + } + } + } +} \ No newline at end of file diff --git a/deployments/celo/solcInputs/0e8303ce972a3975803bfafcc30eb159.json b/deployments/celo/solcInputs/0e8303ce972a3975803bfafcc30eb159.json new file mode 100644 index 0000000..cec4dca --- /dev/null +++ b/deployments/celo/solcInputs/0e8303ce972a3975803bfafcc30eb159.json @@ -0,0 +1,62 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "contracts/lbp/LBPManagerV1.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract version 1\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManagerV1 {\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory no access control version 1\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/deployments/celo/solcInputs/752d54b8f64e3608832db5b1be68e60f.json b/deployments/celo/solcInputs/752d54b8f64e3608832db5b1be68e60f.json new file mode 100644 index 0000000..ee62d81 --- /dev/null +++ b/deployments/celo/solcInputs/752d54b8f64e3608832db5b1be68e60f.json @@ -0,0 +1,62 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "contracts/lbp/LBPManagerV1.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract version 1\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManagerV1 {\n bytes6 public version = \"1.0.0\";\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory no access control version 1\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\n bytes6 public version = \"1.0.0\";\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/deployments/celo/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json b/deployments/celo/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json new file mode 100644 index 0000000..5231e4d --- /dev/null +++ b/deployments/celo/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json @@ -0,0 +1,170 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManager.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract.\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManager {\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "contracts/lbp/LBPManagerFactoryNoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManager.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryNoAccessControl is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManager(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManager(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/ERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (token/ERC20/ERC20.sol)\n\npragma solidity ^0.8.0;\n\nimport \"./IERC20.sol\";\nimport \"./extensions/IERC20Metadata.sol\";\nimport \"../../utils/Context.sol\";\n\n/**\n * @dev Implementation of the {IERC20} interface.\n *\n * This implementation is agnostic to the way tokens are created. This means\n * that a supply mechanism has to be added in a derived contract using {_mint}.\n * For a generic mechanism see {ERC20PresetMinterPauser}.\n *\n * TIP: For a detailed writeup see our guide\n * https://forum.zeppelin.solutions/t/how-to-implement-erc20-supply-mechanisms/226[How\n * to implement supply mechanisms].\n *\n * We have followed general OpenZeppelin Contracts guidelines: functions revert\n * instead returning `false` on failure. This behavior is nonetheless\n * conventional and does not conflict with the expectations of ERC20\n * applications.\n *\n * Additionally, an {Approval} event is emitted on calls to {transferFrom}.\n * This allows applications to reconstruct the allowance for all accounts just\n * by listening to said events. Other implementations of the EIP may not emit\n * these events, as it isn't required by the specification.\n *\n * Finally, the non-standard {decreaseAllowance} and {increaseAllowance}\n * functions have been added to mitigate the well-known issues around setting\n * allowances. See {IERC20-approve}.\n */\ncontract ERC20 is Context, IERC20, IERC20Metadata {\n mapping(address => uint256) private _balances;\n\n mapping(address => mapping(address => uint256)) private _allowances;\n\n uint256 private _totalSupply;\n\n string private _name;\n string private _symbol;\n\n /**\n * @dev Sets the values for {name} and {symbol}.\n *\n * The default value of {decimals} is 18. To select a different value for\n * {decimals} you should overload it.\n *\n * All two of these values are immutable: they can only be set once during\n * construction.\n */\n constructor(string memory name_, string memory symbol_) {\n _name = name_;\n _symbol = symbol_;\n }\n\n /**\n * @dev Returns the name of the token.\n */\n function name() public view virtual override returns (string memory) {\n return _name;\n }\n\n /**\n * @dev Returns the symbol of the token, usually a shorter version of the\n * name.\n */\n function symbol() public view virtual override returns (string memory) {\n return _symbol;\n }\n\n /**\n * @dev Returns the number of decimals used to get its user representation.\n * For example, if `decimals` equals `2`, a balance of `505` tokens should\n * be displayed to a user as `5.05` (`505 / 10 ** 2`).\n *\n * Tokens usually opt for a value of 18, imitating the relationship between\n * Ether and Wei. This is the value {ERC20} uses, unless this function is\n * overridden;\n *\n * NOTE: This information is only used for _display_ purposes: it in\n * no way affects any of the arithmetic of the contract, including\n * {IERC20-balanceOf} and {IERC20-transfer}.\n */\n function decimals() public view virtual override returns (uint8) {\n return 18;\n }\n\n /**\n * @dev See {IERC20-totalSupply}.\n */\n function totalSupply() public view virtual override returns (uint256) {\n return _totalSupply;\n }\n\n /**\n * @dev See {IERC20-balanceOf}.\n */\n function balanceOf(address account) public view virtual override returns (uint256) {\n return _balances[account];\n }\n\n /**\n * @dev See {IERC20-transfer}.\n *\n * Requirements:\n *\n * - `to` cannot be the zero address.\n * - the caller must have a balance of at least `amount`.\n */\n function transfer(address to, uint256 amount) public virtual override returns (bool) {\n address owner = _msgSender();\n _transfer(owner, to, amount);\n return true;\n }\n\n /**\n * @dev See {IERC20-allowance}.\n */\n function allowance(address owner, address spender) public view virtual override returns (uint256) {\n return _allowances[owner][spender];\n }\n\n /**\n * @dev See {IERC20-approve}.\n *\n * NOTE: If `amount` is the maximum `uint256`, the allowance is not updated on\n * `transferFrom`. This is semantically equivalent to an infinite approval.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n */\n function approve(address spender, uint256 amount) public virtual override returns (bool) {\n address owner = _msgSender();\n _approve(owner, spender, amount);\n return true;\n }\n\n /**\n * @dev See {IERC20-transferFrom}.\n *\n * Emits an {Approval} event indicating the updated allowance. This is not\n * required by the EIP. See the note at the beginning of {ERC20}.\n *\n * NOTE: Does not update the allowance if the current allowance\n * is the maximum `uint256`.\n *\n * Requirements:\n *\n * - `from` and `to` cannot be the zero address.\n * - `from` must have a balance of at least `amount`.\n * - the caller must have allowance for ``from``'s tokens of at least\n * `amount`.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) public virtual override returns (bool) {\n address spender = _msgSender();\n _spendAllowance(from, spender, amount);\n _transfer(from, to, amount);\n return true;\n }\n\n /**\n * @dev Atomically increases the allowance granted to `spender` by the caller.\n *\n * This is an alternative to {approve} that can be used as a mitigation for\n * problems described in {IERC20-approve}.\n *\n * Emits an {Approval} event indicating the updated allowance.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n */\n function increaseAllowance(address spender, uint256 addedValue) public virtual returns (bool) {\n address owner = _msgSender();\n _approve(owner, spender, allowance(owner, spender) + addedValue);\n return true;\n }\n\n /**\n * @dev Atomically decreases the allowance granted to `spender` by the caller.\n *\n * This is an alternative to {approve} that can be used as a mitigation for\n * problems described in {IERC20-approve}.\n *\n * Emits an {Approval} event indicating the updated allowance.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n * - `spender` must have allowance for the caller of at least\n * `subtractedValue`.\n */\n function decreaseAllowance(address spender, uint256 subtractedValue) public virtual returns (bool) {\n address owner = _msgSender();\n uint256 currentAllowance = allowance(owner, spender);\n require(currentAllowance >= subtractedValue, \"ERC20: decreased allowance below zero\");\n unchecked {\n _approve(owner, spender, currentAllowance - subtractedValue);\n }\n\n return true;\n }\n\n /**\n * @dev Moves `amount` of tokens from `from` to `to`.\n *\n * This internal function is equivalent to {transfer}, and can be used to\n * e.g. implement automatic token fees, slashing mechanisms, etc.\n *\n * Emits a {Transfer} event.\n *\n * Requirements:\n *\n * - `from` cannot be the zero address.\n * - `to` cannot be the zero address.\n * - `from` must have a balance of at least `amount`.\n */\n function _transfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {\n require(from != address(0), \"ERC20: transfer from the zero address\");\n require(to != address(0), \"ERC20: transfer to the zero address\");\n\n _beforeTokenTransfer(from, to, amount);\n\n uint256 fromBalance = _balances[from];\n require(fromBalance >= amount, \"ERC20: transfer amount exceeds balance\");\n unchecked {\n _balances[from] = fromBalance - amount;\n }\n _balances[to] += amount;\n\n emit Transfer(from, to, amount);\n\n _afterTokenTransfer(from, to, amount);\n }\n\n /** @dev Creates `amount` tokens and assigns them to `account`, increasing\n * the total supply.\n *\n * Emits a {Transfer} event with `from` set to the zero address.\n *\n * Requirements:\n *\n * - `account` cannot be the zero address.\n */\n function _mint(address account, uint256 amount) internal virtual {\n require(account != address(0), \"ERC20: mint to the zero address\");\n\n _beforeTokenTransfer(address(0), account, amount);\n\n _totalSupply += amount;\n _balances[account] += amount;\n emit Transfer(address(0), account, amount);\n\n _afterTokenTransfer(address(0), account, amount);\n }\n\n /**\n * @dev Destroys `amount` tokens from `account`, reducing the\n * total supply.\n *\n * Emits a {Transfer} event with `to` set to the zero address.\n *\n * Requirements:\n *\n * - `account` cannot be the zero address.\n * - `account` must have at least `amount` tokens.\n */\n function _burn(address account, uint256 amount) internal virtual {\n require(account != address(0), \"ERC20: burn from the zero address\");\n\n _beforeTokenTransfer(account, address(0), amount);\n\n uint256 accountBalance = _balances[account];\n require(accountBalance >= amount, \"ERC20: burn amount exceeds balance\");\n unchecked {\n _balances[account] = accountBalance - amount;\n }\n _totalSupply -= amount;\n\n emit Transfer(account, address(0), amount);\n\n _afterTokenTransfer(account, address(0), amount);\n }\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the `owner` s tokens.\n *\n * This internal function is equivalent to `approve`, and can be used to\n * e.g. set automatic allowances for certain subsystems, etc.\n *\n * Emits an {Approval} event.\n *\n * Requirements:\n *\n * - `owner` cannot be the zero address.\n * - `spender` cannot be the zero address.\n */\n function _approve(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual {\n require(owner != address(0), \"ERC20: approve from the zero address\");\n require(spender != address(0), \"ERC20: approve to the zero address\");\n\n _allowances[owner][spender] = amount;\n emit Approval(owner, spender, amount);\n }\n\n /**\n * @dev Updates `owner` s allowance for `spender` based on spent `amount`.\n *\n * Does not update the allowance amount in case of infinite allowance.\n * Revert if not enough allowance is available.\n *\n * Might emit an {Approval} event.\n */\n function _spendAllowance(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual {\n uint256 currentAllowance = allowance(owner, spender);\n if (currentAllowance != type(uint256).max) {\n require(currentAllowance >= amount, \"ERC20: insufficient allowance\");\n unchecked {\n _approve(owner, spender, currentAllowance - amount);\n }\n }\n }\n\n /**\n * @dev Hook that is called before any transfer of tokens. This includes\n * minting and burning.\n *\n * Calling conditions:\n *\n * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens\n * will be transferred to `to`.\n * - when `from` is zero, `amount` tokens will be minted for `to`.\n * - when `to` is zero, `amount` of ``from``'s tokens will be burned.\n * - `from` and `to` are never both zero.\n *\n * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].\n */\n function _beforeTokenTransfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {}\n\n /**\n * @dev Hook that is called after any transfer of tokens. This includes\n * minting and burning.\n *\n * Calling conditions:\n *\n * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens\n * has been transferred to `to`.\n * - when `from` is zero, `amount` tokens have been minted for `to`.\n * - when `to` is zero, `amount` of ``from``'s tokens have been burned.\n * - `from` and `to` are never both zero.\n *\n * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].\n */\n function _afterTokenTransfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {}\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/IERC20Metadata.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/IERC20Metadata.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../IERC20.sol\";\n\n/**\n * @dev Interface for the optional metadata functions from the ERC20 standard.\n *\n * _Available since v4.1._\n */\ninterface IERC20Metadata is IERC20 {\n /**\n * @dev Returns the name of the token.\n */\n function name() external view returns (string memory);\n\n /**\n * @dev Returns the symbol of the token.\n */\n function symbol() external view returns (string memory);\n\n /**\n * @dev Returns the decimals places of the token.\n */\n function decimals() external view returns (uint8);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/ERC20Capped.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../ERC20.sol\";\n\n/**\n * @dev Extension of {ERC20} that adds a cap to the supply of tokens.\n */\nabstract contract ERC20Capped is ERC20 {\n uint256 private immutable _cap;\n\n /**\n * @dev Sets the value of the `cap`. This value is immutable, it can only be\n * set once during construction.\n */\n constructor(uint256 cap_) {\n require(cap_ > 0, \"ERC20Capped: cap is 0\");\n _cap = cap_;\n }\n\n /**\n * @dev Returns the cap on the token's total supply.\n */\n function cap() public view virtual returns (uint256) {\n return _cap;\n }\n\n /**\n * @dev See {ERC20-_mint}.\n */\n function _mint(address account, uint256 amount) internal virtual override {\n require(ERC20.totalSupply() + amount <= cap(), \"ERC20Capped: cap exceeded\");\n super._mint(account, amount);\n }\n}\n" + }, + "contracts/test/PrimeToken.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol\";\n\ncontract PrimeToken is ERC20Capped {\n constructor(\n uint256 initialSupply,\n uint256 cap,\n address genesisMultisig\n ) ERC20(\"PrimeDAO Token\", \"PRIME\") ERC20Capped(cap) {\n require(initialSupply <= cap); // _mint from ERC20 is not protected\n ERC20._mint(genesisMultisig, initialSupply);\n }\n}\n" + }, + "contracts/test/D2D.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol\";\n\ncontract D2D is ERC20Capped {\n uint256 public constant supply = 100000000000000000000000000;\n\n constructor() ERC20(\"Prime\", \"D2D\") ERC20Capped(supply) {\n ERC20._mint(msg.sender, supply);\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (token/ERC20/utils/SafeERC20.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../IERC20.sol\";\nimport \"../extensions/draft-IERC20Permit.sol\";\nimport \"../../../utils/Address.sol\";\n\n/**\n * @title SafeERC20\n * @dev Wrappers around ERC20 operations that throw on failure (when the token\n * contract returns false). Tokens that return no value (and instead revert or\n * throw on failure) are also supported, non-reverting calls are assumed to be\n * successful.\n * To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,\n * which allows you to call the safe operations as `token.safeTransfer(...)`, etc.\n */\nlibrary SafeERC20 {\n using Address for address;\n\n function safeTransfer(\n IERC20 token,\n address to,\n uint256 value\n ) internal {\n _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));\n }\n\n function safeTransferFrom(\n IERC20 token,\n address from,\n address to,\n uint256 value\n ) internal {\n _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));\n }\n\n /**\n * @dev Deprecated. This function has issues similar to the ones found in\n * {IERC20-approve}, and its usage is discouraged.\n *\n * Whenever possible, use {safeIncreaseAllowance} and\n * {safeDecreaseAllowance} instead.\n */\n function safeApprove(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n // safeApprove should only be called when setting an initial allowance,\n // or when resetting it to zero. To increase and decrease it, use\n // 'safeIncreaseAllowance' and 'safeDecreaseAllowance'\n require(\n (value == 0) || (token.allowance(address(this), spender) == 0),\n \"SafeERC20: approve from non-zero to non-zero allowance\"\n );\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));\n }\n\n function safeIncreaseAllowance(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n uint256 newAllowance = token.allowance(address(this), spender) + value;\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));\n }\n\n function safeDecreaseAllowance(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n unchecked {\n uint256 oldAllowance = token.allowance(address(this), spender);\n require(oldAllowance >= value, \"SafeERC20: decreased allowance below zero\");\n uint256 newAllowance = oldAllowance - value;\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));\n }\n }\n\n function safePermit(\n IERC20Permit token,\n address owner,\n address spender,\n uint256 value,\n uint256 deadline,\n uint8 v,\n bytes32 r,\n bytes32 s\n ) internal {\n uint256 nonceBefore = token.nonces(owner);\n token.permit(owner, spender, value, deadline, v, r, s);\n uint256 nonceAfter = token.nonces(owner);\n require(nonceAfter == nonceBefore + 1, \"SafeERC20: permit did not succeed\");\n }\n\n /**\n * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement\n * on the return value: the return value is optional (but if data is returned, it must not be false).\n * @param token The token targeted by the call.\n * @param data The call data (encoded using abi.encode or one of its variants).\n */\n function _callOptionalReturn(IERC20 token, bytes memory data) private {\n // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since\n // we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that\n // the target address contains contract code and also asserts for success in the low-level call.\n\n bytes memory returndata = address(token).functionCall(data, \"SafeERC20: low-level call failed\");\n if (returndata.length > 0) {\n // Return data is optional\n require(abi.decode(returndata, (bool)), \"SafeERC20: ERC20 operation did not succeed\");\n }\n }\n}\n" + }, + "@openzeppelin/contracts/utils/Address.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (utils/Address.sol)\n\npragma solidity ^0.8.1;\n\n/**\n * @dev Collection of functions related to the address type\n */\nlibrary Address {\n /**\n * @dev Returns true if `account` is a contract.\n *\n * [IMPORTANT]\n * ====\n * It is unsafe to assume that an address for which this function returns\n * false is an externally-owned account (EOA) and not a contract.\n *\n * Among others, `isContract` will return false for the following\n * types of addresses:\n *\n * - an externally-owned account\n * - a contract in construction\n * - an address where a contract will be created\n * - an address where a contract lived, but was destroyed\n * ====\n *\n * [IMPORTANT]\n * ====\n * You shouldn't rely on `isContract` to protect against flash loan attacks!\n *\n * Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets\n * like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract\n * constructor.\n * ====\n */\n function isContract(address account) internal view returns (bool) {\n // This method relies on extcodesize/address.code.length, which returns 0\n // for contracts in construction, since the code is only stored at the end\n // of the constructor execution.\n\n return account.code.length > 0;\n }\n\n /**\n * @dev Replacement for Solidity's `transfer`: sends `amount` wei to\n * `recipient`, forwarding all available gas and reverting on errors.\n *\n * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost\n * of certain opcodes, possibly making contracts go over the 2300 gas limit\n * imposed by `transfer`, making them unable to receive funds via\n * `transfer`. {sendValue} removes this limitation.\n *\n * https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].\n *\n * IMPORTANT: because control is transferred to `recipient`, care must be\n * taken to not create reentrancy vulnerabilities. Consider using\n * {ReentrancyGuard} or the\n * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].\n */\n function sendValue(address payable recipient, uint256 amount) internal {\n require(address(this).balance >= amount, \"Address: insufficient balance\");\n\n (bool success, ) = recipient.call{value: amount}(\"\");\n require(success, \"Address: unable to send value, recipient may have reverted\");\n }\n\n /**\n * @dev Performs a Solidity function call using a low level `call`. A\n * plain `call` is an unsafe replacement for a function call: use this\n * function instead.\n *\n * If `target` reverts with a revert reason, it is bubbled up by this\n * function (like regular Solidity function calls).\n *\n * Returns the raw returned data. To convert to the expected return value,\n * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].\n *\n * Requirements:\n *\n * - `target` must be a contract.\n * - calling `target` with `data` must not revert.\n *\n * _Available since v3.1._\n */\n function functionCall(address target, bytes memory data) internal returns (bytes memory) {\n return functionCall(target, data, \"Address: low-level call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with\n * `errorMessage` as a fallback revert reason when `target` reverts.\n *\n * _Available since v3.1._\n */\n function functionCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal returns (bytes memory) {\n return functionCallWithValue(target, data, 0, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but also transferring `value` wei to `target`.\n *\n * Requirements:\n *\n * - the calling contract must have an ETH balance of at least `value`.\n * - the called Solidity function must be `payable`.\n *\n * _Available since v3.1._\n */\n function functionCallWithValue(\n address target,\n bytes memory data,\n uint256 value\n ) internal returns (bytes memory) {\n return functionCallWithValue(target, data, value, \"Address: low-level call with value failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but\n * with `errorMessage` as a fallback revert reason when `target` reverts.\n *\n * _Available since v3.1._\n */\n function functionCallWithValue(\n address target,\n bytes memory data,\n uint256 value,\n string memory errorMessage\n ) internal returns (bytes memory) {\n require(address(this).balance >= value, \"Address: insufficient balance for call\");\n require(isContract(target), \"Address: call to non-contract\");\n\n (bool success, bytes memory returndata) = target.call{value: value}(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but performing a static call.\n *\n * _Available since v3.3._\n */\n function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {\n return functionStaticCall(target, data, \"Address: low-level static call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\n * but performing a static call.\n *\n * _Available since v3.3._\n */\n function functionStaticCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal view returns (bytes memory) {\n require(isContract(target), \"Address: static call to non-contract\");\n\n (bool success, bytes memory returndata) = target.staticcall(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but performing a delegate call.\n *\n * _Available since v3.4._\n */\n function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {\n return functionDelegateCall(target, data, \"Address: low-level delegate call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\n * but performing a delegate call.\n *\n * _Available since v3.4._\n */\n function functionDelegateCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal returns (bytes memory) {\n require(isContract(target), \"Address: delegate call to non-contract\");\n\n (bool success, bytes memory returndata) = target.delegatecall(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Tool to verifies that a low level call was successful, and revert if it wasn't, either by bubbling the\n * revert reason using the provided one.\n *\n * _Available since v4.3._\n */\n function verifyCallResult(\n bool success,\n bytes memory returndata,\n string memory errorMessage\n ) internal pure returns (bytes memory) {\n if (success) {\n return returndata;\n } else {\n // Look for revert reason and bubble it up if present\n if (returndata.length > 0) {\n // The easiest way to bubble the revert reason is using memory via assembly\n /// @solidity memory-safe-assembly\n assembly {\n let returndata_size := mload(returndata)\n revert(add(32, returndata), returndata_size)\n }\n } else {\n revert(errorMessage);\n }\n }\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/draft-IERC20Permit.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/draft-IERC20Permit.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 Permit extension allowing approvals to be made via signatures, as defined in\n * https://eips.ethereum.org/EIPS/eip-2612[EIP-2612].\n *\n * Adds the {permit} method, which can be used to change an account's ERC20 allowance (see {IERC20-allowance}) by\n * presenting a message signed by the account. By not relying on {IERC20-approve}, the token holder account doesn't\n * need to send a transaction, and thus is not required to hold Ether at all.\n */\ninterface IERC20Permit {\n /**\n * @dev Sets `value` as the allowance of `spender` over ``owner``'s tokens,\n * given ``owner``'s signed approval.\n *\n * IMPORTANT: The same issues {IERC20-approve} has related to transaction\n * ordering also apply here.\n *\n * Emits an {Approval} event.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n * - `deadline` must be a timestamp in the future.\n * - `v`, `r` and `s` must be a valid `secp256k1` signature from `owner`\n * over the EIP712-formatted function arguments.\n * - the signature must use ``owner``'s current nonce (see {nonces}).\n *\n * For more information on the signature format, see the\n * https://eips.ethereum.org/EIPS/eip-2612#specification[relevant EIP\n * section].\n */\n function permit(\n address owner,\n address spender,\n uint256 value,\n uint256 deadline,\n uint8 v,\n bytes32 r,\n bytes32 s\n ) external;\n\n /**\n * @dev Returns the current nonce for `owner`. This value must be\n * included whenever a signature is generated for {permit}.\n *\n * Every successful call to {permit} increases ``owner``'s nonce by one. This\n * prevents a signature from being used multiple times.\n */\n function nonces(address owner) external view returns (uint256);\n\n /**\n * @dev Returns the domain separator used in the encoding of the signature for {permit}, as defined by {EIP712}.\n */\n // solhint-disable-next-line func-name-mixedcase\n function DOMAIN_SEPARATOR() external view returns (bytes32);\n}\n" + }, + "contracts/seed/SeedV2.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed contract. Smart contract for seed phases of liquid launch.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable operator-whitespace\n/* solhint-disable space-after-comma */\n/* solhint-disable max-states-count */\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol\";\n\n/**\n * @title PrimeDAO Seed contract version 2.1.0\n * @dev Smart contract for seed phases of Prime Launch.\n */\ncontract SeedV2 {\n bytes6 public version = \"2.1.0\";\n using SafeERC20 for IERC20;\n // Locked parameters\n address public beneficiary; // The address that recieves fees\n address public admin; // The address of the admin of this contract\n address public treasury; // The address that receives the raised funding tokens, and\n // retrievable seed tokens.\n uint256 public softCap; // The minimum to be reached to consider this Seed successful,\n // expressed in Funding tokens\n uint256 public hardCap; // The maximum of Funding tokens to be raised in the Seed\n uint256 public seedAmountRequired; // Amount of seed required for distribution (buyable + tip)\n uint256 public totalBuyableSeed; // Amount of buyable seed tokens\n uint256 public startTime; // Start of the buyable period\n uint256 public endTime; // End of the buyable period\n uint256 public vestingStartTime; // timestamp for when vesting starts, by default == endTime,\n // otherwise when maximumReached is reached\n bool public permissionedSeed; // Set to true if only allowlisted adresses are allowed to participate\n IERC20 public seedToken; // The address of the seed token being distributed\n IERC20 public fundingToken; // The address of the funding token being exchanged for seed token\n bytes public metadata; // IPFS Hash wich has all the Seed parameters stored\n\n uint256 internal constant PRECISION = 10**18; // used for precision e.g. 1 ETH = 10**18 wei; toWei(\"1\") = 10**18\n\n // Contract logic\n bool public closed; // is the distribution closed\n bool public paused; // is the distribution paused\n bool public isFunded; // distribution can only start when required seed tokens have been funded\n bool public initialized; // is this contract initialized [not necessary that it is funded]\n bool public minimumReached; // if the softCap[minimum limit of funding token] is reached\n bool public maximumReached; // if the hardCap[maximum limit of funding token] is reached\n\n uint256 public totalFunderCount; // Total funders that have contributed.\n uint256 public seedRemainder; // Amount of seed tokens remaining to be distributed\n uint256 public seedClaimed; // Amount of seed token claimed by the user.\n uint256 public fundingCollected; // Amount of funding tokens collected by the seed contract.\n uint256 public fundingWithdrawn; // Amount of funding token withdrawn from the seed contract.\n\n uint256 public price; // Price of the Seed token, expressed in Funding token with precision 10**18\n Tip public tip; // State which stores all the Tip parameters\n\n ContributorClass[] public classes; // Array of contributor classes\n\n mapping(address => FunderPortfolio) public funders; // funder address to funder portfolio\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedsPurchased(\n address indexed recipient,\n uint256 indexed amountPurchased,\n uint256 indexed seedRemainder\n );\n event TokensClaimed(address indexed recipient, uint256 indexed amount);\n event FundingReclaimed(\n address indexed recipient,\n uint256 indexed amountReclaimed\n );\n event MetadataUpdated(bytes indexed metadata);\n event TipClaimed(uint256 indexed amountClaimed);\n\n // ----------------------------------------\n // STRUCTS\n // ----------------------------------------\n\n // Struct which stores all the information of a given funder address\n struct FunderPortfolio {\n uint8 class; // Contibutor class id\n uint256 totalClaimed; // Total amount of seed tokens claimed\n uint256 fundingAmount; // Total amount of funding tokens contributed\n bool allowlist; // If permissioned Seed, funder needs to be allowlisted\n }\n // Struct which stores all the parameters of a contributor class\n struct ContributorClass {\n bytes32 className; // Name of the class\n uint256 classCap; // Amount of tokens that can be donated for class\n uint256 individualCap; // Amount of tokens that can be donated by specific contributor\n uint256 vestingCliff; // Cliff after which the vesting starts to get released\n uint256 vestingDuration; // Vesting duration for class\n uint256 classFundingCollected; // Total amount of staked tokens\n }\n // Struct which stores all the parameters related to the Tip\n struct Tip {\n uint256 tipPercentage; // Total amount of tip percentage,\n uint256 vestingCliff; // Tip cliff duration denominated in seconds.\n uint256 vestingDuration; // Tip vesting period duration denominated in seconds.\n uint256 tipAmount; // Tip amount denominated in Seed tokens\n uint256 totalClaimed; // Total amount of Seed tokens already claimed\n }\n\n // ----------------------------------------\n // MODIFIERS\n // ----------------------------------------\n\n modifier claimable() {\n require(\n endTime < block.timestamp || maximumReached || closed,\n \"Seed: Error 346\"\n );\n _;\n }\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"Seed: Error 322\");\n _;\n }\n\n modifier isActive() {\n require(!closed, \"Seed: Error 348\");\n require(!paused, \"Seed: Error 349\");\n _;\n }\n\n modifier isLive() {\n require(\n !closed && block.timestamp < vestingStartTime,\n \"Seed: Error 350\"\n );\n _;\n }\n\n modifier isNotClosed() {\n require(!closed, \"Seed: Error 348\");\n _;\n }\n\n modifier hasNotStarted() {\n require(block.timestamp < startTime, \"Seed: Error 344\");\n _;\n }\n\n modifier classRestriction(uint256 _classCap, uint256 _individualCap) {\n require(\n _individualCap <= _classCap && _classCap <= hardCap,\n \"Seed: Error 303\"\n );\n require(_classCap > 0, \"Seed: Error 101\");\n _;\n }\n\n modifier classBatchRestrictions(\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlist\n ) {\n require(\n _classNames.length == _classCaps.length &&\n _classNames.length == _individualCaps.length &&\n _classNames.length == _vestingCliffs.length &&\n _classNames.length == _vestingDurations.length &&\n _classNames.length == _allowlist.length,\n \"Seed: Error 102\"\n );\n require(_classNames.length <= 100, \"Seed: Error 304\");\n require(classes.length + _classNames.length <= 256, \"Seed: Error 305\");\n _;\n }\n\n /**\n * @dev Initialize Seed.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price Price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t- Tipcliff duration denominated in seconds.\t\n */\n function initialize(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip\n ) external {\n require(!initialized, \"Seed: Error 001\");\n initialized = true;\n\n beneficiary = _beneficiary;\n admin = _projectAddresses[0];\n treasury = _projectAddresses[1];\n softCap = _softAndHardCap[0];\n hardCap = _softAndHardCap[1];\n startTime = _startTimeAndEndTime[0];\n endTime = _startTimeAndEndTime[1];\n vestingStartTime = _startTimeAndEndTime[1] + 1;\n permissionedSeed = _permissionedSeed;\n seedToken = IERC20(_tokens[0]);\n fundingToken = IERC20(_tokens[1]);\n price = _price;\n\n totalBuyableSeed = (_softAndHardCap[1] * PRECISION) / _price;\n // Calculate tip\n uint256 tipAmount = (totalBuyableSeed * _tip[0]) / PRECISION;\n tip = Tip(_tip[0], _tip[1], _tip[2], tipAmount, 0);\n // Add default class\n _addClass(\n bytes32(\"\"),\n _softAndHardCap[1],\n _defaultClassParameters[0],\n _defaultClassParameters[1],\n _defaultClassParameters[2]\n );\n\n // Add allowlist to the default class\n if (_permissionedSeed == true && _allowlistAddresses.length > 0) {\n uint256 arrayLength = _allowlistAddresses.length;\n for (uint256 i; i < arrayLength; ++i) {\n _addToClass(0, _allowlistAddresses[i]); // Value 0 for the default class\n }\n _addAddressesToAllowlist(_allowlistAddresses);\n }\n\n seedRemainder = totalBuyableSeed;\n seedAmountRequired = tipAmount + seedRemainder;\n }\n\n /**\n * @dev Buy seed tokens.\n * @param _fundingAmount The amount of funding tokens to contribute.\n */\n function buy(uint256 _fundingAmount) external isActive returns (uint256) {\n FunderPortfolio storage funder = funders[msg.sender];\n require(!permissionedSeed || funder.allowlist, \"Seed: Error 320\");\n\n ContributorClass memory userClass = classes[funder.class];\n require(!maximumReached, \"Seed: Error 340\");\n require(_fundingAmount > 0, \"Seed: Error 101\");\n\n require(\n endTime >= block.timestamp && startTime <= block.timestamp,\n \"Seed: Error 361\"\n );\n\n if (!isFunded) {\n require(\n seedToken.balanceOf(address(this)) >= seedAmountRequired,\n \"Seed: Error 343\"\n );\n isFunded = true;\n }\n // Update _fundingAmount to reflect the possible buyable amnount\n if ((fundingCollected + _fundingAmount) > hardCap) {\n _fundingAmount = hardCap - fundingCollected;\n }\n if (\n (userClass.classFundingCollected + _fundingAmount) >\n userClass.classCap\n ) {\n _fundingAmount =\n userClass.classCap -\n userClass.classFundingCollected;\n }\n require(\n (funder.fundingAmount + _fundingAmount) <= userClass.individualCap,\n \"Seed: Error 360\"\n );\n\n uint256 seedAmount = (_fundingAmount * PRECISION) / price;\n // total fundingAmount should not be greater than the hardCap\n\n fundingCollected += _fundingAmount;\n classes[funder.class].classFundingCollected += _fundingAmount;\n // the amount of seed tokens still to be distributed\n seedRemainder = seedRemainder - seedAmount;\n if (fundingCollected >= softCap) {\n minimumReached = true;\n }\n\n if (fundingCollected >= hardCap) {\n maximumReached = true;\n vestingStartTime = block.timestamp;\n }\n\n //functionality of addFunder\n if (funder.fundingAmount == 0) {\n totalFunderCount++;\n }\n funder.fundingAmount += _fundingAmount;\n\n // Here we are sending amount of tokens to pay for seed tokens to purchase\n\n fundingToken.safeTransferFrom(\n msg.sender,\n address(this),\n _fundingAmount\n );\n\n emit SeedsPurchased(msg.sender, seedAmount, seedRemainder);\n\n return (seedAmount);\n }\n\n /**\n * @dev Claim vested seed tokens.\n * @param _claimAmount The amount of seed token a users wants to claim.\n */\n function claim(uint256 _claimAmount) external claimable {\n require(minimumReached, \"Seed: Error 341\");\n\n uint256 amountClaimable;\n\n amountClaimable = calculateClaimFunder(msg.sender);\n require(amountClaimable > 0, \"Seed: Error 380\");\n\n require(amountClaimable >= _claimAmount, \"Seed: Error 381\");\n\n funders[msg.sender].totalClaimed += _claimAmount;\n\n seedClaimed += _claimAmount;\n\n seedToken.safeTransfer(msg.sender, _claimAmount);\n\n emit TokensClaimed(msg.sender, _claimAmount);\n }\n\n function claimTip() external claimable returns (uint256) {\n uint256 amountClaimable;\n\n amountClaimable = calculateClaimBeneficiary();\n require(amountClaimable > 0, \"Seed: Error 380\");\n\n tip.totalClaimed += amountClaimable;\n\n seedToken.safeTransfer(beneficiary, amountClaimable);\n\n emit TipClaimed(amountClaimable);\n\n return amountClaimable;\n }\n\n /**\n * @dev Returns funding tokens to user.\n */\n function retrieveFundingTokens() external returns (uint256) {\n require(startTime <= block.timestamp, \"Seed: Error 344\");\n require(!minimumReached, \"Seed: Error 342\");\n FunderPortfolio storage tokenFunder = funders[msg.sender];\n uint256 fundingAmount = tokenFunder.fundingAmount;\n require(fundingAmount > 0, \"Seed: Error 380\");\n seedRemainder += seedAmountForFunder(msg.sender);\n totalFunderCount--;\n tokenFunder.fundingAmount = 0;\n fundingCollected -= fundingAmount;\n classes[tokenFunder.class].classFundingCollected -= fundingAmount;\n\n fundingToken.safeTransfer(msg.sender, fundingAmount);\n\n emit FundingReclaimed(msg.sender, fundingAmount);\n\n return fundingAmount;\n }\n\n // ----------------------------------------\n // ADMIN FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Changes all de classes given in the _classes parameter, editing\n the different parameters of the class, and allowlist addresses\n if applicable.\n * @param _classes Class for changing.\n * @param _classNames The name of the class\n * @param _classCaps The total cap of the contributor class, denominated in Wei.\n * @param _individualCaps The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliffs The cliff duration, denominated in seconds.\n * @param _vestingDurations The vesting duration for this contributors class.\n * @param _allowlists Array of addresses to be allowlisted\n */\n function changeClassesAndAllowlists(\n uint8[] memory _classes,\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlists\n )\n external\n onlyAdmin\n hasNotStarted\n isNotClosed\n classBatchRestrictions(\n _classNames,\n _classCaps,\n _individualCaps,\n _vestingCliffs,\n _vestingDurations,\n _allowlists\n )\n {\n for (uint8 i; i < _classes.length; ++i) {\n _changeClass(\n _classes[i],\n _classNames[i],\n _classCaps[i],\n _individualCaps[i],\n _vestingCliffs[i],\n _vestingDurations[i]\n );\n\n if (permissionedSeed) {\n _addAddressesToAllowlist(_allowlists[i]);\n }\n for (uint256 j; j < _allowlists[i].length; ++j) {\n _addToClass(_classes[i], _allowlists[i][j]);\n }\n }\n }\n\n /**\n * @dev Pause distribution.\n */\n function pause() external onlyAdmin isActive {\n paused = true;\n }\n\n /**\n * @dev Unpause distribution.\n */\n function unpause() external onlyAdmin {\n require(closed != true, \"Seed: Error 348\");\n require(paused == true, \"Seed: Error 351\");\n\n paused = false;\n }\n\n /**\n * @dev Shut down contributions (buying).\n Supersedes the normal logic that eventually shuts down buying anyway.\n Also shuts down the admin's ability to alter the allowlist.\n */\n function close() external onlyAdmin {\n // close seed token distribution\n require(!closed, \"Seed: Error 348\");\n\n if (block.timestamp < vestingStartTime) {\n vestingStartTime = block.timestamp;\n }\n\n closed = true;\n paused = false;\n }\n\n /**\n * @dev retrieve remaining seed tokens back to project.\n */\n function retrieveSeedTokens() external {\n // transfer seed tokens back to treasury\n /*\n Can't withdraw seed tokens until buying has ended and\n therefore the number of distributable seed tokens can no longer change.\n */\n require(\n closed || maximumReached || block.timestamp >= endTime,\n \"Seed: Error 382\"\n );\n uint256 seedTokenBalance = seedToken.balanceOf(address(this));\n if (!minimumReached) {\n require(seedTokenBalance > 0, \"Seed: Error 345\");\n // subtract tip from Seed tokens\n uint256 retrievableSeedAmount = seedTokenBalance -\n (tip.tipAmount - tip.totalClaimed);\n seedToken.safeTransfer(treasury, retrievableSeedAmount);\n } else {\n // seed tokens to transfer = buyable seed tokens - totalSeedDistributed\n uint256 totalSeedDistributed = totalBuyableSeed - seedRemainder;\n uint256 amountToTransfer = seedTokenBalance -\n (totalSeedDistributed - seedClaimed) -\n (tip.tipAmount - tip.totalClaimed);\n seedToken.safeTransfer(treasury, amountToTransfer);\n }\n }\n\n /**\n * @dev Add classes and allowlists to the contract by batching them into one\n function call. It adds allowlists to the created classes if applicable\n * @param _classNames The name of the class\n * @param _classCaps The total cap of the contributor class, denominated in Wei.\n * @param _individualCaps The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliffs The cliff duration, denominated in seconds.\n * @param _vestingDurations The vesting duration for this contributors class.\n * @param _allowlist Array of addresses to be allowlisted\n */\n function addClassesAndAllowlists(\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlist\n )\n external\n onlyAdmin\n hasNotStarted\n isNotClosed\n classBatchRestrictions(\n _classNames,\n _classCaps,\n _individualCaps,\n _vestingCliffs,\n _vestingDurations,\n _allowlist\n )\n {\n uint256 currentClassId = uint256(classes.length);\n for (uint8 i; i < _classNames.length; ++i) {\n _addClass(\n _classNames[i],\n _classCaps[i],\n _individualCaps[i],\n _vestingCliffs[i],\n _vestingDurations[i]\n );\n }\n uint256 arrayLength = _allowlist.length;\n if (permissionedSeed) {\n for (uint256 i; i < arrayLength; ++i) {\n _addAddressesToAllowlist(_allowlist[i]);\n }\n }\n for (uint256 i; i < arrayLength; ++i) {\n uint256 numberOfAddresses = _allowlist[i].length;\n for (uint256 j; j < numberOfAddresses; ++j) {\n _addToClass(uint8(currentClassId), _allowlist[i][j]);\n }\n ++currentClassId;\n }\n }\n\n /**\n * @dev Add multiple addresses to contributor classes, and if applicable\n allowlist them.\n * @param _buyers Array of addresses to be allowlisted\n * @param _classes Array of classes assigned in batch\n */\n function allowlist(address[] memory _buyers, uint8[] memory _classes)\n external\n onlyAdmin\n isLive\n {\n if (permissionedSeed) {\n _addAddressesToAllowlist(_buyers);\n }\n _addMultipleAdressesToClass(_buyers, _classes);\n }\n\n /**\n * @dev Remove address from allowlist.\n * @param _buyer Address which needs to be un-allowlisted\n */\n function unAllowlist(address _buyer) external onlyAdmin isLive {\n require(permissionedSeed == true, \"Seed: Error 347\");\n\n funders[_buyer].allowlist = false;\n }\n\n /**\n * @dev Withdraw funds from the contract\n */\n function withdraw() external {\n /*\n Can't withdraw funding tokens until buying has ended and\n therefore contributors can no longer withdraw their funding tokens.\n */\n require(minimumReached, \"Seed: Error 383\");\n fundingWithdrawn = fundingCollected;\n // Send the entire seed contract balance of the funding token to the sale’s admin\n fundingToken.safeTransfer(\n treasury,\n fundingToken.balanceOf(address(this))\n );\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata Seed contract metadata, that is IPFS Hash\n */\n function updateMetadata(bytes memory _metadata) external {\n require(initialized != true || msg.sender == admin, \"Seed: Error 321\");\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n // ----------------------------------------\n // INTERNAL FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Change parameters in the class given in the _class parameter\n * @param _class Class for changing.\n * @param _className The name of the class\n * @param _classCap The total cap of the contributor class, denominated in Wei.\n * @param _individualCap The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliff The cliff duration, denominated in seconds.\n * @param _vestingDuration The vesting duration for this contributors class.\n */\n function _changeClass(\n uint8 _class,\n bytes32 _className,\n uint256 _classCap,\n uint256 _individualCap,\n uint256 _vestingCliff,\n uint256 _vestingDuration\n ) internal classRestriction(_classCap, _individualCap) {\n require(_class < classes.length, \"Seed: Error 302\");\n\n classes[_class].className = _className;\n classes[_class].classCap = _classCap;\n classes[_class].individualCap = _individualCap;\n classes[_class].vestingCliff = _vestingCliff;\n classes[_class].vestingDuration = _vestingDuration;\n }\n\n /**\n * @dev Internal function that adds a class to the classes array\n * @param _className The name of the class\n * @param _classCap The total cap of the contributor class, denominated in Wei.\n * @param _individualCap The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliff The cliff duration, denominated in seconds.\n * @param _vestingDuration The vesting duration for this contributors class.\n */\n function _addClass(\n bytes32 _className,\n uint256 _classCap,\n uint256 _individualCap,\n uint256 _vestingCliff,\n uint256 _vestingDuration\n ) internal classRestriction(_classCap, _individualCap) {\n classes.push(\n ContributorClass(\n _className,\n _classCap,\n _individualCap,\n _vestingCliff,\n _vestingDuration,\n 0\n )\n );\n }\n\n /**\n * @dev Set contributor class.\n * @param _classId Class of the contributor.\n * @param _buyer Address of the contributor.\n */\n function _addToClass(uint8 _classId, address _buyer) internal {\n require(_classId < classes.length, \"Seed: Error 302\");\n funders[_buyer].class = _classId;\n }\n\n /**\n * @dev Set contributor class.\n * @param _buyers Address of the contributor.\n * @param _classes Class of the contributor.\n */\n function _addMultipleAdressesToClass(\n address[] memory _buyers,\n uint8[] memory _classes\n ) internal {\n uint256 arrayLength = _buyers.length;\n require(_classes.length == arrayLength, \"Seed: Error 102\");\n\n for (uint256 i; i < arrayLength; ++i) {\n _addToClass(_classes[i], _buyers[i]);\n }\n }\n\n /**\n * @dev Add address to allowlist.\n * @param _buyers Address which needs to be allowlisted\n */\n function _addAddressesToAllowlist(address[] memory _buyers) internal {\n uint256 arrayLength = _buyers.length;\n for (uint256 i; i < arrayLength; ++i) {\n funders[_buyers[i]].allowlist = true;\n }\n }\n\n function _calculateClaim(\n uint256 seedAmount,\n uint256 vestingCliff,\n uint256 vestingDuration,\n uint256 totalClaimed\n ) internal view returns (uint256) {\n if (block.timestamp < vestingStartTime) {\n return 0;\n }\n\n // Check cliff was reached\n uint256 elapsedSeconds = block.timestamp - vestingStartTime;\n if (elapsedSeconds < vestingCliff) {\n return 0;\n }\n\n // If over vesting duration, all tokens vested\n if (elapsedSeconds >= vestingDuration) {\n return seedAmount - totalClaimed;\n } else {\n uint256 amountVested = (elapsedSeconds * seedAmount) /\n vestingDuration;\n return amountVested - totalClaimed;\n }\n }\n\n // ----------------------------------------\n // GETTER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Calculates the maximum claim of the funder address\n * @param _funder Address of funder to find the maximum claim\n */\n function calculateClaimFunder(address _funder)\n public\n view\n returns (uint256)\n {\n FunderPortfolio memory tokenFunder = funders[_funder];\n uint8 currentId = tokenFunder.class;\n ContributorClass memory claimed = classes[currentId];\n\n return\n _calculateClaim(\n seedAmountForFunder(_funder),\n claimed.vestingCliff,\n claimed.vestingDuration,\n tokenFunder.totalClaimed\n );\n }\n\n /**\n * @dev Calculates the maximum claim for the beneficiary\n */\n function calculateClaimBeneficiary() public view returns (uint256) {\n return\n _calculateClaim(\n tip.tipAmount,\n tip.vestingCliff,\n tip.vestingDuration,\n tip.totalClaimed\n );\n }\n\n /**\n * @dev Returns arrays with all the parameters of all the classes\n */\n function getAllClasses()\n external\n view\n returns (\n bytes32[] memory classNames,\n uint256[] memory classCaps,\n uint256[] memory individualCaps,\n uint256[] memory vestingCliffs,\n uint256[] memory vestingDurations,\n uint256[] memory classFundingsCollected\n )\n {\n uint256 numberOfClasses = classes.length;\n classNames = new bytes32[](numberOfClasses);\n classCaps = new uint256[](numberOfClasses);\n individualCaps = new uint256[](numberOfClasses);\n vestingCliffs = new uint256[](numberOfClasses);\n vestingDurations = new uint256[](numberOfClasses);\n classFundingsCollected = new uint256[](numberOfClasses);\n for (uint256 i; i < numberOfClasses; ++i) {\n ContributorClass storage class = classes[i];\n classNames[i] = class.className;\n classCaps[i] = class.classCap;\n individualCaps[i] = class.individualCap;\n vestingCliffs[i] = class.vestingCliff;\n vestingDurations[i] = class.vestingDuration;\n classFundingsCollected[i] = class.classFundingCollected;\n }\n }\n\n /**\n * @dev get seed amount for funder\n * @param _funder address of funder to seed amount\n */\n function seedAmountForFunder(address _funder)\n public\n view\n returns (uint256)\n {\n return (funders[_funder].fundingAmount * PRECISION) / price;\n }\n}\n" + }, + "contracts/seed/SeedFactoryV2NoAccessControl.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed Factory version 2 contract. Enable PrimeDAO governance to create new Seed contracts.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable linebreak-style\n/* solhint-disable space-after-comma */\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./SeedV2.sol\";\nimport \"../utils/CloneFactory.sol\";\n\n/**\n * @title PrimeDAO Seed Factory V2\n * @dev SeedFactory version 2 deployed without the onlyOwner modifer for the function deploySeed(). By \n removing the access control, everyone can deploy a seed from this contract. This is\n * a temporarly solution in response to the flaky Celo Safe.\n */\ncontract SeedFactoryV2NoAccessControl is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n SeedV2 public masterCopy; // Seed implementation address, which is used in the cloning pattern\n uint256 internal constant MAX_TIP = (45 / 100) * 10**18; // Max tip expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee)\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedCreated(\n address indexed newSeed,\n address indexed admin,\n address indexed treasury\n );\n\n constructor(SeedV2 _masterCopy) {\n require(address(_masterCopy) != address(0), \"SeedFactory: Error 100\");\n masterCopy = _masterCopy;\n }\n\n // ----------------------------------------\n // ONLY OWNER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Set Seed contract which works as a base for clones.\n * @param _masterCopy The address of the new Seed basis.\n */\n function setMasterCopy(SeedV2 _masterCopy) external onlyOwner {\n require(\n address(_masterCopy) != address(0) &&\n address(_masterCopy) != address(this),\n \"SeedFactory: Error 100\"\n );\n\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Deploys Seed contract.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage, calculated from the total amount of Seed tokens added to the contract, expressed as a % (e.g. 10**18 = 100% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip cliff duration denominated in seconds.\t\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n * @param _metadata Seed contract metadata, that is IPFS URI\n */\n function deploySeed(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip,\n bytes memory _metadata\n ) external returns (address) {\n {\n require(\n _tip.length == 3 &&\n _tokens.length == 2 &&\n _softAndHardCap.length == 2 &&\n _startTimeAndEndTime.length == 2 &&\n _defaultClassParameters.length == 3 &&\n _projectAddresses.length == 2,\n \"SeedFactory: Error 102\"\n );\n require(\n _beneficiary != address(0) &&\n _projectAddresses[0] != address(0) &&\n _projectAddresses[1] != address(0) &&\n _tokens[0] != address(0) &&\n _tokens[1] != address(0),\n \"SeedFactory: Error 100\"\n );\n require(\n _tokens[0] != _tokens[1] &&\n _beneficiary != _projectAddresses[0] &&\n _beneficiary != _projectAddresses[1],\n \"SeedFactory: Error 104\"\n );\n require(\n _softAndHardCap[1] >= _softAndHardCap[0],\n \"SeedFactory: Error 300\"\n );\n require(\n _startTimeAndEndTime[1] > _startTimeAndEndTime[0] &&\n block.timestamp < _startTimeAndEndTime[0],\n \"SeedFactory: Error 106\"\n );\n require(_tip[0] <= MAX_TIP, \"SeedFactory: Error 301\");\n }\n\n // deploy clone\n address _newSeed = createClone(address(masterCopy));\n\n SeedV2(_newSeed).updateMetadata(_metadata);\n\n // initialize\n SeedV2(_newSeed).initialize(\n _beneficiary,\n _projectAddresses,\n _tokens,\n _softAndHardCap,\n _price,\n _startTimeAndEndTime,\n _defaultClassParameters,\n _permissionedSeed,\n _allowlistAddresses,\n _tip\n );\n\n emit SeedCreated(\n address(_newSeed),\n _projectAddresses[0],\n _projectAddresses[1]\n );\n\n return _newSeed;\n }\n}\n" + }, + "contracts/seed/SeedFactoryV2.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed Factory version 2 contract. Enable PrimeDAO governance to create new Seed contracts.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable linebreak-style\n/* solhint-disable space-after-comma */\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./SeedV2.sol\";\nimport \"../utils/CloneFactory.sol\";\n\n/**\n * @title PrimeDAO Seed Factory version 2.1.0\n * @dev Enable PrimeDAO governance to create new Seed contracts.\n */\ncontract SeedFactoryV2 is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n SeedV2 public masterCopy; // Seed implementation address, which is used in the cloning pattern\n uint256 internal constant MAX_TIP = (45 / 100) * 10**18; // Max tip expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee)\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedCreated(\n address indexed newSeed,\n address indexed admin,\n address indexed treasury\n );\n\n constructor(SeedV2 _masterCopy) {\n require(address(_masterCopy) != address(0), \"SeedFactory: Error 100\");\n masterCopy = _masterCopy;\n }\n\n // ----------------------------------------\n // ONLY OWNER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Set Seed contract which works as a base for clones.\n * @param _masterCopy The address of the new Seed basis.\n */\n function setMasterCopy(SeedV2 _masterCopy) external onlyOwner {\n require(\n address(_masterCopy) != address(0) &&\n address(_masterCopy) != address(this),\n \"SeedFactory: Error 100\"\n );\n\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Deploys Seed contract.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage, calculated from the total amount of Seed tokens added to the contract, expressed as a % (e.g. 10**18 = 100% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip cliff duration denominated in seconds.\t\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n * @param _metadata Seed contract metadata, that is IPFS URI\n */\n function deploySeed(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip,\n bytes memory _metadata\n ) external onlyOwner returns (address) {\n {\n require(\n _tip.length == 3 &&\n _tokens.length == 2 &&\n _softAndHardCap.length == 2 &&\n _startTimeAndEndTime.length == 2 &&\n _defaultClassParameters.length == 3 &&\n _projectAddresses.length == 2,\n \"SeedFactory: Error 102\"\n );\n require(\n _beneficiary != address(0) &&\n _projectAddresses[0] != address(0) &&\n _projectAddresses[1] != address(0) &&\n _tokens[0] != address(0) &&\n _tokens[1] != address(0),\n \"SeedFactory: Error 100\"\n );\n require(\n _tokens[0] != _tokens[1] &&\n _beneficiary != _projectAddresses[0] &&\n _beneficiary != _projectAddresses[1],\n \"SeedFactory: Error 104\"\n );\n require(\n _softAndHardCap[1] >= _softAndHardCap[0],\n \"SeedFactory: Error 300\"\n );\n require(\n _startTimeAndEndTime[1] > _startTimeAndEndTime[0] &&\n block.timestamp < _startTimeAndEndTime[0],\n \"SeedFactory: Error 106\"\n );\n require(_tip[0] <= MAX_TIP, \"SeedFactory: Error 301\");\n }\n\n // deploy clone\n address _newSeed = createClone(address(masterCopy));\n\n SeedV2(_newSeed).updateMetadata(_metadata);\n\n // initialize\n SeedV2(_newSeed).initialize(\n _beneficiary,\n _projectAddresses,\n _tokens,\n _softAndHardCap,\n _price,\n _startTimeAndEndTime,\n _defaultClassParameters,\n _permissionedSeed,\n _allowlistAddresses,\n _tip\n );\n\n emit SeedCreated(\n address(_newSeed),\n _projectAddresses[0],\n _projectAddresses[1]\n );\n\n return _newSeed;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManager.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManager(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManager(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/test/ERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\n\ncontract ERC20Mock is ERC20 {\n uint256 public constant initialSupply = 20000000000000000000000;\n\n constructor(string memory _name, string memory _symbol)\n ERC20(_name, _symbol)\n {\n _mint(msg.sender, initialSupply);\n }\n}\n" + }, + "contracts/test/CustomERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\nimport \"hardhat/console.sol\";\n\ncontract CustomERC20Mock is ERC20 {\n mapping(address => uint256) private _balances;\n\n mapping(address => mapping(address => uint256)) private _allowances;\n\n constructor(string memory _name, string memory _symbol)\n ERC20(_name, _symbol)\n {\n _balances[msg.sender] += 20000000000000000000000;\n }\n\n function transfer(address recipient, uint256 amount)\n public\n virtual\n override\n returns (bool)\n {\n bool success = _customTransfer(_msgSender(), recipient, amount);\n return success;\n }\n\n function transferFrom(\n address sender,\n address recipient,\n uint256 amount\n ) public virtual override returns (bool) {\n uint256 currentAllowance = _allowances[sender][_msgSender()];\n if (currentAllowance < amount) {\n return false;\n }\n\n bool success = _customTransfer(sender, recipient, amount);\n if (success) {\n /* solium-disable */\n unchecked {\n _approve(sender, _msgSender(), currentAllowance - amount);\n }\n /* solium-enable */\n }\n return true;\n }\n\n function approve(address spender, uint256 amount)\n public\n virtual\n override\n returns (bool)\n {\n _approve(_msgSender(), spender, amount);\n return true;\n }\n\n function balanceOf(address account)\n public\n view\n virtual\n override\n returns (uint256)\n {\n return _balances[account];\n }\n\n function burn(address account) public {\n _balances[account] = 0;\n }\n\n function mint(address account, uint256 amount) public {\n _balances[account] += amount;\n }\n\n function _customTransfer(\n address sender,\n address recipient,\n uint256 amount\n ) internal virtual returns (bool) {\n uint256 senderBalance = _balances[sender];\n if (\n sender == address(0) ||\n recipient == address(0) ||\n senderBalance < amount\n ) {\n return false;\n }\n unchecked {\n _balances[sender] = senderBalance - amount;\n }\n _balances[recipient] += amount;\n emit Transfer(sender, recipient, amount);\n return true;\n }\n\n function _approve(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual override {\n require(owner != address(0), \"ERC20: approve from the zero address\");\n require(spender != address(0), \"ERC20: approve to the zero address\");\n\n _allowances[owner][spender] = amount;\n emit Approval(owner, spender, amount);\n }\n}\n" + }, + "hardhat/console.sol": { + "content": "// SPDX-License-Identifier: MIT\npragma solidity >= 0.4.22 <0.9.0;\n\nlibrary console {\n\taddress constant CONSOLE_ADDRESS = address(0x000000000000000000636F6e736F6c652e6c6f67);\n\n\tfunction _sendLogPayload(bytes memory payload) private view {\n\t\tuint256 payloadLength = payload.length;\n\t\taddress consoleAddress = CONSOLE_ADDRESS;\n\t\tassembly {\n\t\t\tlet payloadStart := add(payload, 32)\n\t\t\tlet r := staticcall(gas(), consoleAddress, payloadStart, payloadLength, 0, 0)\n\t\t}\n\t}\n\n\tfunction log() internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log()\"));\n\t}\n\n\tfunction logInt(int256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(int256)\", p0));\n\t}\n\n\tfunction logUint(uint256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256)\", p0));\n\t}\n\n\tfunction logString(string memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string)\", p0));\n\t}\n\n\tfunction logBool(bool p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool)\", p0));\n\t}\n\n\tfunction logAddress(address p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address)\", p0));\n\t}\n\n\tfunction logBytes(bytes memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes)\", p0));\n\t}\n\n\tfunction logBytes1(bytes1 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes1)\", p0));\n\t}\n\n\tfunction logBytes2(bytes2 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes2)\", p0));\n\t}\n\n\tfunction logBytes3(bytes3 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes3)\", p0));\n\t}\n\n\tfunction logBytes4(bytes4 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes4)\", p0));\n\t}\n\n\tfunction logBytes5(bytes5 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes5)\", p0));\n\t}\n\n\tfunction logBytes6(bytes6 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes6)\", p0));\n\t}\n\n\tfunction logBytes7(bytes7 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes7)\", p0));\n\t}\n\n\tfunction logBytes8(bytes8 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes8)\", p0));\n\t}\n\n\tfunction logBytes9(bytes9 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes9)\", p0));\n\t}\n\n\tfunction logBytes10(bytes10 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes10)\", p0));\n\t}\n\n\tfunction logBytes11(bytes11 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes11)\", p0));\n\t}\n\n\tfunction logBytes12(bytes12 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes12)\", p0));\n\t}\n\n\tfunction logBytes13(bytes13 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes13)\", p0));\n\t}\n\n\tfunction logBytes14(bytes14 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes14)\", p0));\n\t}\n\n\tfunction logBytes15(bytes15 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes15)\", p0));\n\t}\n\n\tfunction logBytes16(bytes16 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes16)\", p0));\n\t}\n\n\tfunction logBytes17(bytes17 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes17)\", p0));\n\t}\n\n\tfunction logBytes18(bytes18 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes18)\", p0));\n\t}\n\n\tfunction logBytes19(bytes19 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes19)\", p0));\n\t}\n\n\tfunction logBytes20(bytes20 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes20)\", p0));\n\t}\n\n\tfunction logBytes21(bytes21 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes21)\", p0));\n\t}\n\n\tfunction logBytes22(bytes22 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes22)\", p0));\n\t}\n\n\tfunction logBytes23(bytes23 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes23)\", p0));\n\t}\n\n\tfunction logBytes24(bytes24 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes24)\", p0));\n\t}\n\n\tfunction logBytes25(bytes25 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes25)\", p0));\n\t}\n\n\tfunction logBytes26(bytes26 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes26)\", p0));\n\t}\n\n\tfunction logBytes27(bytes27 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes27)\", p0));\n\t}\n\n\tfunction logBytes28(bytes28 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes28)\", p0));\n\t}\n\n\tfunction logBytes29(bytes29 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes29)\", p0));\n\t}\n\n\tfunction logBytes30(bytes30 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes30)\", p0));\n\t}\n\n\tfunction logBytes31(bytes31 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes31)\", p0));\n\t}\n\n\tfunction logBytes32(bytes32 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes32)\", p0));\n\t}\n\n\tfunction log(uint256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256)\", p0));\n\t}\n\n\tfunction log(string memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string)\", p0));\n\t}\n\n\tfunction log(bool p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool)\", p0));\n\t}\n\n\tfunction log(address p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address)\", p0));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address)\", p0, p1));\n\t}\n\n\tfunction log(address p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256)\", p0, p1));\n\t}\n\n\tfunction log(address p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string)\", p0, p1));\n\t}\n\n\tfunction log(address p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool)\", p0, p1));\n\t}\n\n\tfunction log(address p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n}\n" + }, + "contracts/test/CustomDecimalERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\n\ncontract CustomDecimalERC20Mock is ERC20 {\n uint8 private immutable _decimals;\n\n constructor(\n string memory _name,\n string memory _symbol,\n uint8 decimals_\n ) ERC20(_name, _symbol) {\n _mint(msg.sender, 200000000000000000000000000);\n _decimals = decimals_;\n }\n\n function decimals() public view virtual override returns (uint8) {\n return _decimals;\n }\n}\n" + }, + "contracts/test/Imports.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@gnosis.pm/safe-contracts/contracts/GnosisSafe.sol\";\nimport \"@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxyFactory.sol\";\n" + }, + "@gnosis.pm/safe-contracts/contracts/GnosisSafe.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"./base/ModuleManager.sol\";\nimport \"./base/OwnerManager.sol\";\nimport \"./base/FallbackManager.sol\";\nimport \"./base/GuardManager.sol\";\nimport \"./common/EtherPaymentFallback.sol\";\nimport \"./common/Singleton.sol\";\nimport \"./common/SignatureDecoder.sol\";\nimport \"./common/SecuredTokenTransfer.sol\";\nimport \"./common/StorageAccessible.sol\";\nimport \"./interfaces/ISignatureValidator.sol\";\nimport \"./external/GnosisSafeMath.sol\";\n\n/// @title Gnosis Safe - A multisignature wallet with support for confirmations using signed messages based on ERC191.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract GnosisSafe is\n EtherPaymentFallback,\n Singleton,\n ModuleManager,\n OwnerManager,\n SignatureDecoder,\n SecuredTokenTransfer,\n ISignatureValidatorConstants,\n FallbackManager,\n StorageAccessible,\n GuardManager\n{\n using GnosisSafeMath for uint256;\n\n string public constant VERSION = \"1.3.0\";\n\n // keccak256(\n // \"EIP712Domain(uint256 chainId,address verifyingContract)\"\n // );\n bytes32 private constant DOMAIN_SEPARATOR_TYPEHASH = 0x47e79534a245952e8b16893a336b85a3d9ea9fa8c573f3d803afb92a79469218;\n\n // keccak256(\n // \"SafeTx(address to,uint256 value,bytes data,uint8 operation,uint256 safeTxGas,uint256 baseGas,uint256 gasPrice,address gasToken,address refundReceiver,uint256 nonce)\"\n // );\n bytes32 private constant SAFE_TX_TYPEHASH = 0xbb8310d486368db6bd6f849402fdd73ad53d316b5a4b2644ad6efe0f941286d8;\n\n event SafeSetup(address indexed initiator, address[] owners, uint256 threshold, address initializer, address fallbackHandler);\n event ApproveHash(bytes32 indexed approvedHash, address indexed owner);\n event SignMsg(bytes32 indexed msgHash);\n event ExecutionFailure(bytes32 txHash, uint256 payment);\n event ExecutionSuccess(bytes32 txHash, uint256 payment);\n\n uint256 public nonce;\n bytes32 private _deprecatedDomainSeparator;\n // Mapping to keep track of all message hashes that have been approve by ALL REQUIRED owners\n mapping(bytes32 => uint256) public signedMessages;\n // Mapping to keep track of all hashes (message or transaction) that have been approve by ANY owners\n mapping(address => mapping(bytes32 => uint256)) public approvedHashes;\n\n // This constructor ensures that this contract can only be used as a master copy for Proxy contracts\n constructor() {\n // By setting the threshold it is not possible to call setup anymore,\n // so we create a Safe with 0 owners and threshold 1.\n // This is an unusable Safe, perfect for the singleton\n threshold = 1;\n }\n\n /// @dev Setup function sets initial storage of contract.\n /// @param _owners List of Safe owners.\n /// @param _threshold Number of required confirmations for a Safe transaction.\n /// @param to Contract address for optional delegate call.\n /// @param data Data payload for optional delegate call.\n /// @param fallbackHandler Handler for fallback calls to this contract\n /// @param paymentToken Token that should be used for the payment (0 is ETH)\n /// @param payment Value that should be paid\n /// @param paymentReceiver Adddress that should receive the payment (or 0 if tx.origin)\n function setup(\n address[] calldata _owners,\n uint256 _threshold,\n address to,\n bytes calldata data,\n address fallbackHandler,\n address paymentToken,\n uint256 payment,\n address payable paymentReceiver\n ) external {\n // setupOwners checks if the Threshold is already set, therefore preventing that this method is called twice\n setupOwners(_owners, _threshold);\n if (fallbackHandler != address(0)) internalSetFallbackHandler(fallbackHandler);\n // As setupOwners can only be called if the contract has not been initialized we don't need a check for setupModules\n setupModules(to, data);\n\n if (payment > 0) {\n // To avoid running into issues with EIP-170 we reuse the handlePayment function (to avoid adjusting code of that has been verified we do not adjust the method itself)\n // baseGas = 0, gasPrice = 1 and gas = payment => amount = (payment + 0) * 1 = payment\n handlePayment(payment, 0, 1, paymentToken, paymentReceiver);\n }\n emit SafeSetup(msg.sender, _owners, _threshold, to, fallbackHandler);\n }\n\n /// @dev Allows to execute a Safe transaction confirmed by required number of owners and then pays the account that submitted the transaction.\n /// Note: The fees are always transferred, even if the user transaction fails.\n /// @param to Destination address of Safe transaction.\n /// @param value Ether value of Safe transaction.\n /// @param data Data payload of Safe transaction.\n /// @param operation Operation type of Safe transaction.\n /// @param safeTxGas Gas that should be used for the Safe transaction.\n /// @param baseGas Gas costs that are independent of the transaction execution(e.g. base transaction fee, signature check, payment of the refund)\n /// @param gasPrice Gas price that should be used for the payment calculation.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param signatures Packed signature data ({bytes32 r}{bytes32 s}{uint8 v})\n function execTransaction(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver,\n bytes memory signatures\n ) public payable virtual returns (bool success) {\n bytes32 txHash;\n // Use scope here to limit variable lifetime and prevent `stack too deep` errors\n {\n bytes memory txHashData =\n encodeTransactionData(\n // Transaction info\n to,\n value,\n data,\n operation,\n safeTxGas,\n // Payment info\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n // Signature info\n nonce\n );\n // Increase nonce and execute transaction.\n nonce++;\n txHash = keccak256(txHashData);\n checkSignatures(txHash, txHashData, signatures);\n }\n address guard = getGuard();\n {\n if (guard != address(0)) {\n Guard(guard).checkTransaction(\n // Transaction info\n to,\n value,\n data,\n operation,\n safeTxGas,\n // Payment info\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n // Signature info\n signatures,\n msg.sender\n );\n }\n }\n // We require some gas to emit the events (at least 2500) after the execution and some to perform code until the execution (500)\n // We also include the 1/64 in the check that is not send along with a call to counteract potential shortings because of EIP-150\n require(gasleft() >= ((safeTxGas * 64) / 63).max(safeTxGas + 2500) + 500, \"GS010\");\n // Use scope here to limit variable lifetime and prevent `stack too deep` errors\n {\n uint256 gasUsed = gasleft();\n // If the gasPrice is 0 we assume that nearly all available gas can be used (it is always more than safeTxGas)\n // We only substract 2500 (compared to the 3000 before) to ensure that the amount passed is still higher than safeTxGas\n success = execute(to, value, data, operation, gasPrice == 0 ? (gasleft() - 2500) : safeTxGas);\n gasUsed = gasUsed.sub(gasleft());\n // If no safeTxGas and no gasPrice was set (e.g. both are 0), then the internal tx is required to be successful\n // This makes it possible to use `estimateGas` without issues, as it searches for the minimum gas where the tx doesn't revert\n require(success || safeTxGas != 0 || gasPrice != 0, \"GS013\");\n // We transfer the calculated tx costs to the tx.origin to avoid sending it to intermediate contracts that have made calls\n uint256 payment = 0;\n if (gasPrice > 0) {\n payment = handlePayment(gasUsed, baseGas, gasPrice, gasToken, refundReceiver);\n }\n if (success) emit ExecutionSuccess(txHash, payment);\n else emit ExecutionFailure(txHash, payment);\n }\n {\n if (guard != address(0)) {\n Guard(guard).checkAfterExecution(txHash, success);\n }\n }\n }\n\n function handlePayment(\n uint256 gasUsed,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver\n ) private returns (uint256 payment) {\n // solhint-disable-next-line avoid-tx-origin\n address payable receiver = refundReceiver == address(0) ? payable(tx.origin) : refundReceiver;\n if (gasToken == address(0)) {\n // For ETH we will only adjust the gas price to not be higher than the actual used gas price\n payment = gasUsed.add(baseGas).mul(gasPrice < tx.gasprice ? gasPrice : tx.gasprice);\n require(receiver.send(payment), \"GS011\");\n } else {\n payment = gasUsed.add(baseGas).mul(gasPrice);\n require(transferToken(gasToken, receiver, payment), \"GS012\");\n }\n }\n\n /**\n * @dev Checks whether the signature provided is valid for the provided data, hash. Will revert otherwise.\n * @param dataHash Hash of the data (could be either a message hash or transaction hash)\n * @param data That should be signed (this is passed to an external validator contract)\n * @param signatures Signature data that should be verified. Can be ECDSA signature, contract signature (EIP-1271) or approved hash.\n */\n function checkSignatures(\n bytes32 dataHash,\n bytes memory data,\n bytes memory signatures\n ) public view {\n // Load threshold to avoid multiple storage loads\n uint256 _threshold = threshold;\n // Check that a threshold is set\n require(_threshold > 0, \"GS001\");\n checkNSignatures(dataHash, data, signatures, _threshold);\n }\n\n /**\n * @dev Checks whether the signature provided is valid for the provided data, hash. Will revert otherwise.\n * @param dataHash Hash of the data (could be either a message hash or transaction hash)\n * @param data That should be signed (this is passed to an external validator contract)\n * @param signatures Signature data that should be verified. Can be ECDSA signature, contract signature (EIP-1271) or approved hash.\n * @param requiredSignatures Amount of required valid signatures.\n */\n function checkNSignatures(\n bytes32 dataHash,\n bytes memory data,\n bytes memory signatures,\n uint256 requiredSignatures\n ) public view {\n // Check that the provided signature data is not too short\n require(signatures.length >= requiredSignatures.mul(65), \"GS020\");\n // There cannot be an owner with address 0.\n address lastOwner = address(0);\n address currentOwner;\n uint8 v;\n bytes32 r;\n bytes32 s;\n uint256 i;\n for (i = 0; i < requiredSignatures; i++) {\n (v, r, s) = signatureSplit(signatures, i);\n if (v == 0) {\n // If v is 0 then it is a contract signature\n // When handling contract signatures the address of the contract is encoded into r\n currentOwner = address(uint160(uint256(r)));\n\n // Check that signature data pointer (s) is not pointing inside the static part of the signatures bytes\n // This check is not completely accurate, since it is possible that more signatures than the threshold are send.\n // Here we only check that the pointer is not pointing inside the part that is being processed\n require(uint256(s) >= requiredSignatures.mul(65), \"GS021\");\n\n // Check that signature data pointer (s) is in bounds (points to the length of data -> 32 bytes)\n require(uint256(s).add(32) <= signatures.length, \"GS022\");\n\n // Check if the contract signature is in bounds: start of data is s + 32 and end is start + signature length\n uint256 contractSignatureLen;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n contractSignatureLen := mload(add(add(signatures, s), 0x20))\n }\n require(uint256(s).add(32).add(contractSignatureLen) <= signatures.length, \"GS023\");\n\n // Check signature\n bytes memory contractSignature;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // The signature data for contract signatures is appended to the concatenated signatures and the offset is stored in s\n contractSignature := add(add(signatures, s), 0x20)\n }\n require(ISignatureValidator(currentOwner).isValidSignature(data, contractSignature) == EIP1271_MAGIC_VALUE, \"GS024\");\n } else if (v == 1) {\n // If v is 1 then it is an approved hash\n // When handling approved hashes the address of the approver is encoded into r\n currentOwner = address(uint160(uint256(r)));\n // Hashes are automatically approved by the sender of the message or when they have been pre-approved via a separate transaction\n require(msg.sender == currentOwner || approvedHashes[currentOwner][dataHash] != 0, \"GS025\");\n } else if (v > 30) {\n // If v > 30 then default va (27,28) has been adjusted for eth_sign flow\n // To support eth_sign and similar we adjust v and hash the messageHash with the Ethereum message prefix before applying ecrecover\n currentOwner = ecrecover(keccak256(abi.encodePacked(\"\\x19Ethereum Signed Message:\\n32\", dataHash)), v - 4, r, s);\n } else {\n // Default is the ecrecover flow with the provided data hash\n // Use ecrecover with the messageHash for EOA signatures\n currentOwner = ecrecover(dataHash, v, r, s);\n }\n require(currentOwner > lastOwner && owners[currentOwner] != address(0) && currentOwner != SENTINEL_OWNERS, \"GS026\");\n lastOwner = currentOwner;\n }\n }\n\n /// @dev Allows to estimate a Safe transaction.\n /// This method is only meant for estimation purpose, therefore the call will always revert and encode the result in the revert data.\n /// Since the `estimateGas` function includes refunds, call this method to get an estimated of the costs that are deducted from the safe with `execTransaction`\n /// @param to Destination address of Safe transaction.\n /// @param value Ether value of Safe transaction.\n /// @param data Data payload of Safe transaction.\n /// @param operation Operation type of Safe transaction.\n /// @return Estimate without refunds and overhead fees (base transaction and payload data gas costs).\n /// @notice Deprecated in favor of common/StorageAccessible.sol and will be removed in next version.\n function requiredTxGas(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation\n ) external returns (uint256) {\n uint256 startGas = gasleft();\n // We don't provide an error message here, as we use it to return the estimate\n require(execute(to, value, data, operation, gasleft()));\n uint256 requiredGas = startGas - gasleft();\n // Convert response to string and return via error message\n revert(string(abi.encodePacked(requiredGas)));\n }\n\n /**\n * @dev Marks a hash as approved. This can be used to validate a hash that is used by a signature.\n * @param hashToApprove The hash that should be marked as approved for signatures that are verified by this contract.\n */\n function approveHash(bytes32 hashToApprove) external {\n require(owners[msg.sender] != address(0), \"GS030\");\n approvedHashes[msg.sender][hashToApprove] = 1;\n emit ApproveHash(hashToApprove, msg.sender);\n }\n\n /// @dev Returns the chain id used by this contract.\n function getChainId() public view returns (uint256) {\n uint256 id;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n id := chainid()\n }\n return id;\n }\n\n function domainSeparator() public view returns (bytes32) {\n return keccak256(abi.encode(DOMAIN_SEPARATOR_TYPEHASH, getChainId(), this));\n }\n\n /// @dev Returns the bytes that are hashed to be signed by owners.\n /// @param to Destination address.\n /// @param value Ether value.\n /// @param data Data payload.\n /// @param operation Operation type.\n /// @param safeTxGas Gas that should be used for the safe transaction.\n /// @param baseGas Gas costs for that are independent of the transaction execution(e.g. base transaction fee, signature check, payment of the refund)\n /// @param gasPrice Maximum gas price that should be used for this transaction.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param _nonce Transaction nonce.\n /// @return Transaction hash bytes.\n function encodeTransactionData(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) public view returns (bytes memory) {\n bytes32 safeTxHash =\n keccak256(\n abi.encode(\n SAFE_TX_TYPEHASH,\n to,\n value,\n keccak256(data),\n operation,\n safeTxGas,\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n _nonce\n )\n );\n return abi.encodePacked(bytes1(0x19), bytes1(0x01), domainSeparator(), safeTxHash);\n }\n\n /// @dev Returns hash to be signed by owners.\n /// @param to Destination address.\n /// @param value Ether value.\n /// @param data Data payload.\n /// @param operation Operation type.\n /// @param safeTxGas Fas that should be used for the safe transaction.\n /// @param baseGas Gas costs for data used to trigger the safe transaction.\n /// @param gasPrice Maximum gas price that should be used for this transaction.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param _nonce Transaction nonce.\n /// @return Transaction hash.\n function getTransactionHash(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) public view returns (bytes32) {\n return keccak256(encodeTransactionData(to, value, data, operation, safeTxGas, baseGas, gasPrice, gasToken, refundReceiver, _nonce));\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxyFactory.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"./GnosisSafeProxy.sol\";\nimport \"./IProxyCreationCallback.sol\";\n\n/// @title Proxy Factory - Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n/// @author Stefan George - \ncontract GnosisSafeProxyFactory {\n event ProxyCreation(GnosisSafeProxy proxy, address singleton);\n\n /// @dev Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n /// @param singleton Address of singleton contract.\n /// @param data Payload for message call sent to new proxy contract.\n function createProxy(address singleton, bytes memory data) public returns (GnosisSafeProxy proxy) {\n proxy = new GnosisSafeProxy(singleton);\n if (data.length > 0)\n // solhint-disable-next-line no-inline-assembly\n assembly {\n if eq(call(gas(), proxy, 0, add(data, 0x20), mload(data), 0, 0), 0) {\n revert(0, 0)\n }\n }\n emit ProxyCreation(proxy, singleton);\n }\n\n /// @dev Allows to retrieve the runtime code of a deployed Proxy. This can be used to check that the expected Proxy was deployed.\n function proxyRuntimeCode() public pure returns (bytes memory) {\n return type(GnosisSafeProxy).runtimeCode;\n }\n\n /// @dev Allows to retrieve the creation code used for the Proxy deployment. With this it is easily possible to calculate predicted address.\n function proxyCreationCode() public pure returns (bytes memory) {\n return type(GnosisSafeProxy).creationCode;\n }\n\n /// @dev Allows to create new proxy contact using CREATE2 but it doesn't run the initializer.\n /// This method is only meant as an utility to be called from other methods\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function deployProxyWithNonce(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce\n ) internal returns (GnosisSafeProxy proxy) {\n // If the initializer changes the proxy address should change too. Hashing the initializer data is cheaper than just concatinating it\n bytes32 salt = keccak256(abi.encodePacked(keccak256(initializer), saltNonce));\n bytes memory deploymentData = abi.encodePacked(type(GnosisSafeProxy).creationCode, uint256(uint160(_singleton)));\n // solhint-disable-next-line no-inline-assembly\n assembly {\n proxy := create2(0x0, add(0x20, deploymentData), mload(deploymentData), salt)\n }\n require(address(proxy) != address(0), \"Create2 call failed\");\n }\n\n /// @dev Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function createProxyWithNonce(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce\n ) public returns (GnosisSafeProxy proxy) {\n proxy = deployProxyWithNonce(_singleton, initializer, saltNonce);\n if (initializer.length > 0)\n // solhint-disable-next-line no-inline-assembly\n assembly {\n if eq(call(gas(), proxy, 0, add(initializer, 0x20), mload(initializer), 0, 0), 0) {\n revert(0, 0)\n }\n }\n emit ProxyCreation(proxy, _singleton);\n }\n\n /// @dev Allows to create new proxy contact, execute a message call to the new proxy and call a specified callback within one transaction\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n /// @param callback Callback that will be invoced after the new proxy contract has been successfully deployed and initialized.\n function createProxyWithCallback(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce,\n IProxyCreationCallback callback\n ) public returns (GnosisSafeProxy proxy) {\n uint256 saltNonceWithCallback = uint256(keccak256(abi.encodePacked(saltNonce, callback)));\n proxy = createProxyWithNonce(_singleton, initializer, saltNonceWithCallback);\n if (address(callback) != address(0)) callback.proxyCreated(proxy, _singleton, initializer, saltNonce);\n }\n\n /// @dev Allows to get the address for a new proxy contact created via `createProxyWithNonce`\n /// This method is only meant for address calculation purpose when you use an initializer that would revert,\n /// therefore the response is returned with a revert. When calling this method set `from` to the address of the proxy factory.\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function calculateCreateProxyWithNonceAddress(\n address _singleton,\n bytes calldata initializer,\n uint256 saltNonce\n ) external returns (GnosisSafeProxy proxy) {\n proxy = deployProxyWithNonce(_singleton, initializer, saltNonce);\n revert(string(abi.encodePacked(proxy)));\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/GuardManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"../common/Enum.sol\";\nimport \"../common/SelfAuthorized.sol\";\n\ninterface Guard {\n function checkTransaction(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver,\n bytes memory signatures,\n address msgSender\n ) external;\n\n function checkAfterExecution(bytes32 txHash, bool success) external;\n}\n\n/// @title Fallback Manager - A contract that manages fallback calls made to this contract\n/// @author Richard Meissner - \ncontract GuardManager is SelfAuthorized {\n event ChangedGuard(address guard);\n // keccak256(\"guard_manager.guard.address\")\n bytes32 internal constant GUARD_STORAGE_SLOT = 0x4a204f620c8c5ccdca3fd54d003badd85ba500436a431f0cbda4f558c93c34c8;\n\n /// @dev Set a guard that checks transactions before execution\n /// @param guard The address of the guard to be used or the 0 address to disable the guard\n function setGuard(address guard) external authorized {\n bytes32 slot = GUARD_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n sstore(slot, guard)\n }\n emit ChangedGuard(guard);\n }\n\n function getGuard() internal view returns (address guard) {\n bytes32 slot = GUARD_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n guard := sload(slot)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/FallbackManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"../common/SelfAuthorized.sol\";\n\n/// @title Fallback Manager - A contract that manages fallback calls made to this contract\n/// @author Richard Meissner - \ncontract FallbackManager is SelfAuthorized {\n event ChangedFallbackHandler(address handler);\n\n // keccak256(\"fallback_manager.handler.address\")\n bytes32 internal constant FALLBACK_HANDLER_STORAGE_SLOT = 0x6c9a6c4a39284e37ed1cf53d337577d14212a4870fb976a4366c693b939918d5;\n\n function internalSetFallbackHandler(address handler) internal {\n bytes32 slot = FALLBACK_HANDLER_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n sstore(slot, handler)\n }\n }\n\n /// @dev Allows to add a contract to handle fallback calls.\n /// Only fallback calls without value and with data will be forwarded.\n /// This can only be done via a Safe transaction.\n /// @param handler contract to handle fallbacks calls.\n function setFallbackHandler(address handler) public authorized {\n internalSetFallbackHandler(handler);\n emit ChangedFallbackHandler(handler);\n }\n\n // solhint-disable-next-line payable-fallback,no-complex-fallback\n fallback() external {\n bytes32 slot = FALLBACK_HANDLER_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let handler := sload(slot)\n if iszero(handler) {\n return(0, 0)\n }\n calldatacopy(0, 0, calldatasize())\n // The msg.sender address is shifted to the left by 12 bytes to remove the padding\n // Then the address without padding is stored right after the calldata\n mstore(calldatasize(), shl(96, caller()))\n // Add 20 bytes for the address appended add the end\n let success := call(gas(), handler, 0, 0, add(calldatasize(), 20), 0, 0)\n returndatacopy(0, 0, returndatasize())\n if iszero(success) {\n revert(0, returndatasize())\n }\n return(0, returndatasize())\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/ModuleManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/Enum.sol\";\nimport \"../common/SelfAuthorized.sol\";\nimport \"./Executor.sol\";\n\n/// @title Module Manager - A contract that manages modules that can execute transactions via this contract\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract ModuleManager is SelfAuthorized, Executor {\n event EnabledModule(address module);\n event DisabledModule(address module);\n event ExecutionFromModuleSuccess(address indexed module);\n event ExecutionFromModuleFailure(address indexed module);\n\n address internal constant SENTINEL_MODULES = address(0x1);\n\n mapping(address => address) internal modules;\n\n function setupModules(address to, bytes memory data) internal {\n require(modules[SENTINEL_MODULES] == address(0), \"GS100\");\n modules[SENTINEL_MODULES] = SENTINEL_MODULES;\n if (to != address(0))\n // Setup has to complete successfully or transaction fails.\n require(execute(to, 0, data, Enum.Operation.DelegateCall, gasleft()), \"GS000\");\n }\n\n /// @dev Allows to add a module to the whitelist.\n /// This can only be done via a Safe transaction.\n /// @notice Enables the module `module` for the Safe.\n /// @param module Module to be whitelisted.\n function enableModule(address module) public authorized {\n // Module address cannot be null or sentinel.\n require(module != address(0) && module != SENTINEL_MODULES, \"GS101\");\n // Module cannot be added twice.\n require(modules[module] == address(0), \"GS102\");\n modules[module] = modules[SENTINEL_MODULES];\n modules[SENTINEL_MODULES] = module;\n emit EnabledModule(module);\n }\n\n /// @dev Allows to remove a module from the whitelist.\n /// This can only be done via a Safe transaction.\n /// @notice Disables the module `module` for the Safe.\n /// @param prevModule Module that pointed to the module to be removed in the linked list\n /// @param module Module to be removed.\n function disableModule(address prevModule, address module) public authorized {\n // Validate module address and check that it corresponds to module index.\n require(module != address(0) && module != SENTINEL_MODULES, \"GS101\");\n require(modules[prevModule] == module, \"GS103\");\n modules[prevModule] = modules[module];\n modules[module] = address(0);\n emit DisabledModule(module);\n }\n\n /// @dev Allows a Module to execute a Safe transaction without any further confirmations.\n /// @param to Destination address of module transaction.\n /// @param value Ether value of module transaction.\n /// @param data Data payload of module transaction.\n /// @param operation Operation type of module transaction.\n function execTransactionFromModule(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation\n ) public virtual returns (bool success) {\n // Only whitelisted modules are allowed.\n require(msg.sender != SENTINEL_MODULES && modules[msg.sender] != address(0), \"GS104\");\n // Execute transaction without further confirmations.\n success = execute(to, value, data, operation, gasleft());\n if (success) emit ExecutionFromModuleSuccess(msg.sender);\n else emit ExecutionFromModuleFailure(msg.sender);\n }\n\n /// @dev Allows a Module to execute a Safe transaction without any further confirmations and return data\n /// @param to Destination address of module transaction.\n /// @param value Ether value of module transaction.\n /// @param data Data payload of module transaction.\n /// @param operation Operation type of module transaction.\n function execTransactionFromModuleReturnData(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation\n ) public returns (bool success, bytes memory returnData) {\n success = execTransactionFromModule(to, value, data, operation);\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // Load free memory location\n let ptr := mload(0x40)\n // We allocate memory for the return data by setting the free memory location to\n // current free memory location + data size + 32 bytes for data size value\n mstore(0x40, add(ptr, add(returndatasize(), 0x20)))\n // Store the size\n mstore(ptr, returndatasize())\n // Store the data\n returndatacopy(add(ptr, 0x20), 0, returndatasize())\n // Point the return data to the correct memory location\n returnData := ptr\n }\n }\n\n /// @dev Returns if an module is enabled\n /// @return True if the module is enabled\n function isModuleEnabled(address module) public view returns (bool) {\n return SENTINEL_MODULES != module && modules[module] != address(0);\n }\n\n /// @dev Returns array of modules.\n /// @param start Start of the page.\n /// @param pageSize Maximum number of modules that should be returned.\n /// @return array Array of modules.\n /// @return next Start of the next page.\n function getModulesPaginated(address start, uint256 pageSize) external view returns (address[] memory array, address next) {\n // Init array with max page size\n array = new address[](pageSize);\n\n // Populate return array\n uint256 moduleCount = 0;\n address currentModule = modules[start];\n while (currentModule != address(0x0) && currentModule != SENTINEL_MODULES && moduleCount < pageSize) {\n array[moduleCount] = currentModule;\n currentModule = modules[currentModule];\n moduleCount++;\n }\n next = currentModule;\n // Set correct size of returned array\n // solhint-disable-next-line no-inline-assembly\n assembly {\n mstore(array, moduleCount)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/OwnerManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/SelfAuthorized.sol\";\n\n/// @title OwnerManager - Manages a set of owners and a threshold to perform actions.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract OwnerManager is SelfAuthorized {\n event AddedOwner(address owner);\n event RemovedOwner(address owner);\n event ChangedThreshold(uint256 threshold);\n\n address internal constant SENTINEL_OWNERS = address(0x1);\n\n mapping(address => address) internal owners;\n uint256 internal ownerCount;\n uint256 internal threshold;\n\n /// @dev Setup function sets initial storage of contract.\n /// @param _owners List of Safe owners.\n /// @param _threshold Number of required confirmations for a Safe transaction.\n function setupOwners(address[] memory _owners, uint256 _threshold) internal {\n // Threshold can only be 0 at initialization.\n // Check ensures that setup function can only be called once.\n require(threshold == 0, \"GS200\");\n // Validate that threshold is smaller than number of added owners.\n require(_threshold <= _owners.length, \"GS201\");\n // There has to be at least one Safe owner.\n require(_threshold >= 1, \"GS202\");\n // Initializing Safe owners.\n address currentOwner = SENTINEL_OWNERS;\n for (uint256 i = 0; i < _owners.length; i++) {\n // Owner address cannot be null.\n address owner = _owners[i];\n require(owner != address(0) && owner != SENTINEL_OWNERS && owner != address(this) && currentOwner != owner, \"GS203\");\n // No duplicate owners allowed.\n require(owners[owner] == address(0), \"GS204\");\n owners[currentOwner] = owner;\n currentOwner = owner;\n }\n owners[currentOwner] = SENTINEL_OWNERS;\n ownerCount = _owners.length;\n threshold = _threshold;\n }\n\n /// @dev Allows to add a new owner to the Safe and update the threshold at the same time.\n /// This can only be done via a Safe transaction.\n /// @notice Adds the owner `owner` to the Safe and updates the threshold to `_threshold`.\n /// @param owner New owner address.\n /// @param _threshold New threshold.\n function addOwnerWithThreshold(address owner, uint256 _threshold) public authorized {\n // Owner address cannot be null, the sentinel or the Safe itself.\n require(owner != address(0) && owner != SENTINEL_OWNERS && owner != address(this), \"GS203\");\n // No duplicate owners allowed.\n require(owners[owner] == address(0), \"GS204\");\n owners[owner] = owners[SENTINEL_OWNERS];\n owners[SENTINEL_OWNERS] = owner;\n ownerCount++;\n emit AddedOwner(owner);\n // Change threshold if threshold was changed.\n if (threshold != _threshold) changeThreshold(_threshold);\n }\n\n /// @dev Allows to remove an owner from the Safe and update the threshold at the same time.\n /// This can only be done via a Safe transaction.\n /// @notice Removes the owner `owner` from the Safe and updates the threshold to `_threshold`.\n /// @param prevOwner Owner that pointed to the owner to be removed in the linked list\n /// @param owner Owner address to be removed.\n /// @param _threshold New threshold.\n function removeOwner(\n address prevOwner,\n address owner,\n uint256 _threshold\n ) public authorized {\n // Only allow to remove an owner, if threshold can still be reached.\n require(ownerCount - 1 >= _threshold, \"GS201\");\n // Validate owner address and check that it corresponds to owner index.\n require(owner != address(0) && owner != SENTINEL_OWNERS, \"GS203\");\n require(owners[prevOwner] == owner, \"GS205\");\n owners[prevOwner] = owners[owner];\n owners[owner] = address(0);\n ownerCount--;\n emit RemovedOwner(owner);\n // Change threshold if threshold was changed.\n if (threshold != _threshold) changeThreshold(_threshold);\n }\n\n /// @dev Allows to swap/replace an owner from the Safe with another address.\n /// This can only be done via a Safe transaction.\n /// @notice Replaces the owner `oldOwner` in the Safe with `newOwner`.\n /// @param prevOwner Owner that pointed to the owner to be replaced in the linked list\n /// @param oldOwner Owner address to be replaced.\n /// @param newOwner New owner address.\n function swapOwner(\n address prevOwner,\n address oldOwner,\n address newOwner\n ) public authorized {\n // Owner address cannot be null, the sentinel or the Safe itself.\n require(newOwner != address(0) && newOwner != SENTINEL_OWNERS && newOwner != address(this), \"GS203\");\n // No duplicate owners allowed.\n require(owners[newOwner] == address(0), \"GS204\");\n // Validate oldOwner address and check that it corresponds to owner index.\n require(oldOwner != address(0) && oldOwner != SENTINEL_OWNERS, \"GS203\");\n require(owners[prevOwner] == oldOwner, \"GS205\");\n owners[newOwner] = owners[oldOwner];\n owners[prevOwner] = newOwner;\n owners[oldOwner] = address(0);\n emit RemovedOwner(oldOwner);\n emit AddedOwner(newOwner);\n }\n\n /// @dev Allows to update the number of required confirmations by Safe owners.\n /// This can only be done via a Safe transaction.\n /// @notice Changes the threshold of the Safe to `_threshold`.\n /// @param _threshold New threshold.\n function changeThreshold(uint256 _threshold) public authorized {\n // Validate that threshold is smaller than number of owners.\n require(_threshold <= ownerCount, \"GS201\");\n // There has to be at least one Safe owner.\n require(_threshold >= 1, \"GS202\");\n threshold = _threshold;\n emit ChangedThreshold(threshold);\n }\n\n function getThreshold() public view returns (uint256) {\n return threshold;\n }\n\n function isOwner(address owner) public view returns (bool) {\n return owner != SENTINEL_OWNERS && owners[owner] != address(0);\n }\n\n /// @dev Returns array of owners.\n /// @return Array of Safe owners.\n function getOwners() public view returns (address[] memory) {\n address[] memory array = new address[](ownerCount);\n\n // populate return array\n uint256 index = 0;\n address currentOwner = owners[SENTINEL_OWNERS];\n while (currentOwner != SENTINEL_OWNERS) {\n array[index] = currentOwner;\n currentOwner = owners[currentOwner];\n index++;\n }\n return array;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/Singleton.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title Singleton - Base for singleton contracts (should always be first super contract)\n/// This contract is tightly coupled to our proxy contract (see `proxies/GnosisSafeProxy.sol`)\n/// @author Richard Meissner - \ncontract Singleton {\n // singleton always needs to be first declared variable, to ensure that it is at the same location as in the Proxy contract.\n // It should also always be ensured that the address is stored alone (uses a full word)\n address private singleton;\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SignatureDecoder.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SignatureDecoder - Decodes signatures that a encoded as bytes\n/// @author Richard Meissner - \ncontract SignatureDecoder {\n /// @dev divides bytes signature into `uint8 v, bytes32 r, bytes32 s`.\n /// @notice Make sure to peform a bounds check for @param pos, to avoid out of bounds access on @param signatures\n /// @param pos which signature to read. A prior bounds check of this parameter should be performed, to avoid out of bounds access\n /// @param signatures concatenated rsv signatures\n function signatureSplit(bytes memory signatures, uint256 pos)\n internal\n pure\n returns (\n uint8 v,\n bytes32 r,\n bytes32 s\n )\n {\n // The signature format is a compact form of:\n // {bytes32 r}{bytes32 s}{uint8 v}\n // Compact means, uint8 is not padded to 32 bytes.\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let signaturePos := mul(0x41, pos)\n r := mload(add(signatures, add(signaturePos, 0x20)))\n s := mload(add(signatures, add(signaturePos, 0x40)))\n // Here we are loading the last 32 bytes, including 31 bytes\n // of 's'. There is no 'mload8' to do this.\n //\n // 'byte' is not working due to the Solidity parser, so lets\n // use the second best option, 'and'\n v := and(mload(add(signatures, add(signaturePos, 0x41))), 0xff)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/EtherPaymentFallback.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title EtherPaymentFallback - A contract that has a fallback to accept ether payments\n/// @author Richard Meissner - \ncontract EtherPaymentFallback {\n event SafeReceived(address indexed sender, uint256 value);\n\n /// @dev Fallback function accepts Ether transactions.\n receive() external payable {\n emit SafeReceived(msg.sender, msg.value);\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/interfaces/ISignatureValidator.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\ncontract ISignatureValidatorConstants {\n // bytes4(keccak256(\"isValidSignature(bytes,bytes)\")\n bytes4 internal constant EIP1271_MAGIC_VALUE = 0x20c13b0b;\n}\n\nabstract contract ISignatureValidator is ISignatureValidatorConstants {\n /**\n * @dev Should return whether the signature provided is valid for the provided data\n * @param _data Arbitrary length data signed on the behalf of address(this)\n * @param _signature Signature byte array associated with _data\n *\n * MUST return the bytes4 magic value 0x20c13b0b when function passes.\n * MUST NOT modify state (using STATICCALL for solc < 0.5, view modifier for solc > 0.5)\n * MUST allow external calls\n */\n function isValidSignature(bytes memory _data, bytes memory _signature) public view virtual returns (bytes4);\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SecuredTokenTransfer.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SecuredTokenTransfer - Secure token transfer\n/// @author Richard Meissner - \ncontract SecuredTokenTransfer {\n /// @dev Transfers a token and returns if it was a success\n /// @param token Token that should be transferred\n /// @param receiver Receiver to whom the token should be transferred\n /// @param amount The amount of tokens that should be transferred\n function transferToken(\n address token,\n address receiver,\n uint256 amount\n ) internal returns (bool transferred) {\n // 0xa9059cbb - keccack(\"transfer(address,uint256)\")\n bytes memory data = abi.encodeWithSelector(0xa9059cbb, receiver, amount);\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // We write the return value to scratch space.\n // See https://docs.soliditylang.org/en/v0.7.6/internals/layout_in_memory.html#layout-in-memory\n let success := call(sub(gas(), 10000), token, 0, add(data, 0x20), mload(data), 0, 0x20)\n switch returndatasize()\n case 0 {\n transferred := success\n }\n case 0x20 {\n transferred := iszero(or(iszero(success), iszero(mload(0))))\n }\n default {\n transferred := 0\n }\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/StorageAccessible.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title StorageAccessible - generic base contract that allows callers to access all internal storage.\n/// @notice See https://github.com/gnosis/util-contracts/blob/bb5fe5fb5df6d8400998094fb1b32a178a47c3a1/contracts/StorageAccessible.sol\ncontract StorageAccessible {\n /**\n * @dev Reads `length` bytes of storage in the currents contract\n * @param offset - the offset in the current contract's storage in words to start reading from\n * @param length - the number of words (32 bytes) of data to read\n * @return the bytes that were read.\n */\n function getStorageAt(uint256 offset, uint256 length) public view returns (bytes memory) {\n bytes memory result = new bytes(length * 32);\n for (uint256 index = 0; index < length; index++) {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let word := sload(add(offset, index))\n mstore(add(add(result, 0x20), mul(index, 0x20)), word)\n }\n }\n return result;\n }\n\n /**\n * @dev Performs a delegetecall on a targetContract in the context of self.\n * Internally reverts execution to avoid side effects (making it static).\n *\n * This method reverts with data equal to `abi.encode(bool(success), bytes(response))`.\n * Specifically, the `returndata` after a call to this method will be:\n * `success:bool || response.length:uint256 || response:bytes`.\n *\n * @param targetContract Address of the contract containing the code to execute.\n * @param calldataPayload Calldata that should be sent to the target contract (encoded method name and arguments).\n */\n function simulateAndRevert(address targetContract, bytes memory calldataPayload) external {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let success := delegatecall(gas(), targetContract, add(calldataPayload, 0x20), mload(calldataPayload), 0, 0)\n\n mstore(0x00, success)\n mstore(0x20, returndatasize())\n returndatacopy(0x40, 0, returndatasize())\n revert(0, add(returndatasize(), 0x40))\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/external/GnosisSafeMath.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/**\n * @title GnosisSafeMath\n * @dev Math operations with safety checks that revert on error\n * Renamed from SafeMath to GnosisSafeMath to avoid conflicts\n * TODO: remove once open zeppelin update to solc 0.5.0\n */\nlibrary GnosisSafeMath {\n /**\n * @dev Multiplies two numbers, reverts on overflow.\n */\n function mul(uint256 a, uint256 b) internal pure returns (uint256) {\n // Gas optimization: this is cheaper than requiring 'a' not being zero, but the\n // benefit is lost if 'b' is also tested.\n // See: https://github.com/OpenZeppelin/openzeppelin-solidity/pull/522\n if (a == 0) {\n return 0;\n }\n\n uint256 c = a * b;\n require(c / a == b);\n\n return c;\n }\n\n /**\n * @dev Subtracts two numbers, reverts on overflow (i.e. if subtrahend is greater than minuend).\n */\n function sub(uint256 a, uint256 b) internal pure returns (uint256) {\n require(b <= a);\n uint256 c = a - b;\n\n return c;\n }\n\n /**\n * @dev Adds two numbers, reverts on overflow.\n */\n function add(uint256 a, uint256 b) internal pure returns (uint256) {\n uint256 c = a + b;\n require(c >= a);\n\n return c;\n }\n\n /**\n * @dev Returns the largest of two numbers.\n */\n function max(uint256 a, uint256 b) internal pure returns (uint256) {\n return a >= b ? a : b;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SelfAuthorized.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SelfAuthorized - authorizes current contract to perform actions\n/// @author Richard Meissner - \ncontract SelfAuthorized {\n function requireSelfCall() private view {\n require(msg.sender == address(this), \"GS031\");\n }\n\n modifier authorized() {\n // This is a function call as it minimized the bytecode size\n requireSelfCall();\n _;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/Enum.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title Enum - Collection of enums\n/// @author Richard Meissner - \ncontract Enum {\n enum Operation {Call, DelegateCall}\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/Executor.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/Enum.sol\";\n\n/// @title Executor - A contract that can execute transactions\n/// @author Richard Meissner - \ncontract Executor {\n function execute(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation,\n uint256 txGas\n ) internal returns (bool success) {\n if (operation == Enum.Operation.DelegateCall) {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n success := delegatecall(txGas, to, add(data, 0x20), mload(data), 0, 0)\n }\n } else {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n success := call(txGas, to, value, add(data, 0x20), mload(data), 0, 0)\n }\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxy.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title IProxy - Helper interface to access masterCopy of the Proxy on-chain\n/// @author Richard Meissner - \ninterface IProxy {\n function masterCopy() external view returns (address);\n}\n\n/// @title GnosisSafeProxy - Generic proxy contract allows to execute all transactions applying the code of a master contract.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract GnosisSafeProxy {\n // singleton always needs to be first declared variable, to ensure that it is at the same location in the contracts to which calls are delegated.\n // To reduce deployment costs this variable is internal and needs to be retrieved via `getStorageAt`\n address internal singleton;\n\n /// @dev Constructor function sets address of singleton contract.\n /// @param _singleton Singleton address.\n constructor(address _singleton) {\n require(_singleton != address(0), \"Invalid singleton address provided\");\n singleton = _singleton;\n }\n\n /// @dev Fallback function forwards all transactions and returns all received return data.\n fallback() external payable {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let _singleton := and(sload(0), 0xffffffffffffffffffffffffffffffffffffffff)\n // 0xa619486e == keccak(\"masterCopy()\"). The value is right padded to 32-bytes with 0s\n if eq(calldataload(0), 0xa619486e00000000000000000000000000000000000000000000000000000000) {\n mstore(0, _singleton)\n return(0, 0x20)\n }\n calldatacopy(0, 0, calldatasize())\n let success := delegatecall(gas(), _singleton, 0, calldatasize(), 0, 0)\n returndatacopy(0, 0, returndatasize())\n if eq(success, 0) {\n revert(0, returndatasize())\n }\n return(0, returndatasize())\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/IProxyCreationCallback.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"./GnosisSafeProxy.sol\";\n\ninterface IProxyCreationCallback {\n function proxyCreated(\n GnosisSafeProxy proxy,\n address _singleton,\n bytes calldata initializer,\n uint256 saltNonce\n ) external;\n}\n" + }, + "contracts/utils/SignerV2.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// Signer contract. Enables signing transaction before sending it to Gnosis Safe.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"./interface/ISafe.sol\";\nimport \"@gnosis.pm/safe-contracts/contracts/interfaces/ISignatureValidator.sol\";\n\n/**\n * @title PrimeDAO Signer Contract\n * @dev Enables signing approved function signature transaction before sending it to Gnosis Safe.\n */\ncontract SignerV2 is ISignatureValidator {\n bytes32 private constant DOMAIN_SEPARATOR_TYPEHASH =\n 0x7a9f5b2bf4dbb53eb85e012c6094a3d71d76e5bfe821f44ab63ed59311264e35;\n bytes32 private constant MSG_TYPEHASH =\n 0xa1a7ad659422d5fc08fdc481fd7d8af8daf7993bc4e833452b0268ceaab66e5d; // mapping for msg typehash\n\n mapping(bytes32 => bytes32) public approvedSignatures;\n\n /* solium-disable */\n address public safe;\n mapping(address => mapping(bytes4 => bool)) public allowedTransactions;\n /* solium-enable */\n\n event SignatureCreated(bytes signature, bytes32 indexed hash);\n\n modifier onlySafe() {\n require(msg.sender == safe, \"Signer: only safe functionality\");\n _;\n }\n\n /**\n * @dev Signer Constructor\n * @param _safe Gnosis Safe address.\n * @param _contracts array of contract addresses\n * @param _functionSignatures array of function signatures\n */\n constructor(\n address _safe,\n address[] memory _contracts,\n bytes4[] memory _functionSignatures\n ) {\n require(_safe != address(0), \"Signer: Safe address zero\");\n safe = _safe;\n for (uint256 i; i < _contracts.length; i++) {\n require(\n _contracts[i] != address(0),\n \"Signer: contract address zero\"\n );\n require(\n _functionSignatures[i] != bytes4(0),\n \"Signer: function signature zero\"\n );\n allowedTransactions[_contracts[i]][_functionSignatures[i]] = true;\n }\n }\n\n /**\n * @dev Signature generator\n * @param _to receiver address.\n * @param _value value in wei.\n * @param _data encoded transaction data.\n * @param _operation type of operation call.\n * @param _safeTxGas safe transaction gas for gnosis safe.\n * @param _baseGas base gas for gnosis safe.\n * @param _gasPrice gas price for gnosis safe transaction.\n * @param _gasToken token which gas needs to paid for gnosis safe transaction.\n * @param _refundReceiver address account to receive refund for remaining gas.\n * @param _nonce gnosis safe contract nonce.\n */\n function generateSignature(\n address _to,\n uint256 _value,\n bytes calldata _data,\n Enum.Operation _operation,\n uint256 _safeTxGas,\n uint256 _baseGas,\n uint256 _gasPrice,\n address _gasToken,\n address _refundReceiver,\n uint256 _nonce\n ) external returns (bytes memory signature, bytes32 hash) {\n // check if transaction parameters are correct\n require(\n allowedTransactions[_to][_getFunctionHashFromData(_data)],\n \"Signer: invalid function\"\n );\n require(\n _value == 0 &&\n _refundReceiver == address(0) &&\n _operation == Enum.Operation.Call,\n \"Signer: invalid arguments\"\n );\n\n // get contractTransactionHash from gnosis safe\n hash = ISafe(safe).getTransactionHash(\n _to,\n 0,\n _data,\n _operation,\n _safeTxGas,\n _baseGas,\n _gasPrice,\n _gasToken,\n _refundReceiver,\n _nonce\n );\n\n bytes memory paddedAddress = bytes.concat(\n bytes12(0),\n bytes20(address(this))\n );\n bytes memory messageHash = _encodeMessageHash(hash);\n // check if transaction is not signed before\n // solhint-disable-next-line reason-string\n require(\n approvedSignatures[hash] != keccak256(messageHash),\n \"Signer: transaction already signed\"\n );\n\n // generate signature and add it to approvedSignatures mapping\n signature = bytes.concat(\n paddedAddress,\n bytes32(uint256(65)),\n bytes1(0),\n bytes32(uint256(messageHash.length)),\n messageHash\n );\n approvedSignatures[hash] = keccak256(messageHash);\n emit SignatureCreated(signature, hash);\n }\n\n /**\n * @dev Validate signature using EIP1271\n * @param _data Encoded transaction hash supplied to verify signature.\n * @param _signature Signature that needs to be verified.\n */\n function isValidSignature(bytes memory _data, bytes memory _signature)\n public\n view\n override\n returns (bytes4)\n {\n if (_data.length == 32) {\n bytes32 hash;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n hash := mload(add(_data, 32))\n }\n if (approvedSignatures[hash] == keccak256(_signature)) {\n return EIP1271_MAGIC_VALUE;\n }\n } else {\n if (approvedSignatures[keccak256(_data)] == keccak256(_signature)) {\n return EIP1271_MAGIC_VALUE;\n }\n }\n return \"0x\";\n }\n\n /**\n * @dev Get the byte hash of function call i.e. first four bytes of data\n * @param data encoded transaction data.\n */\n function _getFunctionHashFromData(bytes memory data)\n private\n pure\n returns (bytes4 functionHash)\n {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n functionHash := mload(add(data, 32))\n }\n }\n\n /**\n * @dev encode message with contants\n * @param message the message that needs to be encoded\n */\n function _encodeMessageHash(bytes32 message)\n private\n pure\n returns (bytes memory)\n {\n bytes32 safeMessageHash = keccak256(abi.encode(MSG_TYPEHASH, message));\n return\n abi.encodePacked(\n bytes1(0x19),\n bytes1(0x23),\n keccak256(\n abi.encode(DOMAIN_SEPARATOR_TYPEHASH, safeMessageHash)\n )\n );\n }\n\n /**\n * @dev set new safe\n * @param _safe safe address\n */\n function setSafe(address _safe) public onlySafe {\n require(_safe != address(0), \"Signer: Safe zero address\");\n safe = _safe;\n }\n\n /**\n * @dev add new contracts and functions\n * @param _contract contract address\n * @param _functionSignature function signature for the contract\n */\n function approveNewTransaction(address _contract, bytes4 _functionSignature)\n external\n onlySafe\n {\n require(_contract != address(0), \"Signer: contract address zero\");\n require(\n _functionSignature != bytes4(0),\n \"Signer: function signature zero\"\n );\n allowedTransactions[_contract][_functionSignature] = true;\n }\n\n /**\n * @dev add new contracts and functions\n * @param _contract contract address\n * @param _functionSignature function signature for the contract\n */\n function removeAllowedTransaction(\n address _contract,\n bytes4 _functionSignature\n ) external onlySafe {\n // solhint-disable-next-line reason-string\n require(\n allowedTransactions[_contract][_functionSignature] == true,\n \"Signer: only approved transactions can be removed\"\n );\n allowedTransactions[_contract][_functionSignature] = false;\n }\n}\n" + }, + "contracts/utils/interface/ISafe.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\ncontract Enum {\n enum Operation {\n Call,\n DelegateCall\n }\n}\n\ninterface ISafe {\n function getTransactionHash(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) external view returns (bytes32);\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/deployments/goerli/LBPManager.json b/deployments/goerli/LBPManager.json new file mode 100644 index 0000000..65134e4 --- /dev/null +++ b/deployments/goerli/LBPManager.json @@ -0,0 +1,785 @@ +{ + "address": "0xDC624C9f99B1FD33743d162b137838E6032b0486", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0xd10aba8c22b81890fb82d0d9a960e09e1c2fde5d7ccf4aea70772620106b36d5", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0xDC624C9f99B1FD33743d162b137838E6032b0486", + "transactionIndex": 30, + "gasUsed": "2298135", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x105b49764ee7f4ca0a65581ef5a2f2024d1522c015587e7d8ce7cac29d09a73e", + "transactionHash": "0xd10aba8c22b81890fb82d0d9a960e09e1c2fde5d7ccf4aea70772620106b36d5", + "logs": [], + "blockNumber": 8087283, + "cumulativeGasUsed": "5349604", + "status": 1, + "byzantium": true + }, + "args": [], + "solcInputHash": "bf89fe6a61a7d22f31b24d3cee885a8d", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"beneficiary\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"tokenAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"FeeTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldAdmin\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newAdmin\",\"type\":\"address\"}],\"name\":\"LBPManagerAdminChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"MetadataUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"PoolTokensWithdrawn\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"admin\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"amounts\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"beneficiary\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"endWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"feePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getSwapEnabled\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_sender\",\"type\":\"address\"}],\"name\":\"initializeLBP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndTime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"initializeLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"initialized\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbp\",\"outputs\":[{\"internalType\":\"contract ILBP\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"metadata\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"name\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"poolFunded\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokenIndex\",\"outputs\":[{\"internalType\":\"uint8\",\"name\":\"\",\"type\":\"uint8\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokensRequired\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"projectTokenAmounts\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"removeLiquidity\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bool\",\"name\":\"_swapEnabled\",\"type\":\"bool\"}],\"name\":\"setSwapEnabled\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startTimeEndTime\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"swapFeePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"symbol\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"tokenList\",\"outputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_newAdmin\",\"type\":\"address\"}],\"name\":\"transferAdminRights\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"updateMetadata\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"withdrawPoolTokens\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Smart contract for managing interactions with a Balancer LBP.\",\"kind\":\"dev\",\"methods\":{\"getSwapEnabled()\":{\"details\":\"Tells whether swaps are enabled or not for the LBP\"},\"initializeLBP(address)\":{\"details\":\"Subtracts the fee, deploys the LBP and adds liquidity to it.\",\"params\":{\"_sender\":\"Address of the liquidity provider.\"}},\"initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Initialize LBPManager.\",\"params\":{\"_amounts\":\"Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the feePercentage.\",\"_endWeights\":\"Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_lbpFactory\":\"LBP factory address.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndTime\":\"Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.\",\"_startWeights\":\"Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token.\"}},\"projectTokensRequired()\":{\"details\":\"Get required amount of project tokens to cover for fees and the actual LBP.\"},\"removeLiquidity(address)\":{\"details\":\"Exit pool or remove liquidity from pool.\",\"params\":{\"_receiver\":\"Address of the liquidity receiver, after exiting the LBP.\"}},\"setSwapEnabled(bool)\":{\"details\":\"Can pause/unpause trading.\",\"params\":{\"_swapEnabled\":\"Enables/disables swapping.\"}},\"transferAdminRights(address)\":{\"details\":\"Transfer admin rights.\",\"params\":{\"_newAdmin\":\"Address of the new admin.\"}},\"updateMetadata(bytes)\":{\"details\":\"Updates metadata.\",\"params\":{\"_metadata\":\"LBP wizard contract metadata, that is an IPFS Hash.\"}},\"withdrawPoolTokens(address)\":{\"details\":\"Withdraw pool tokens if available.\",\"params\":{\"_receiver\":\"Address of the BPT tokens receiver.\"}}},\"title\":\"LBPManager contract.\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManager.sol\":\"LBPManager\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"contracts/lbp/LBPManager.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract.\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManager {\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x371ceeb460072a61394db69c3b0f8b0f4c45dd4d1ee0ad19a1c44ba9f61000b4\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x608060405234801561001057600080fd5b5061289d806100206000396000f3fe608060405234801561001057600080fd5b506004361061018e5760003560e01c8063a001ecdd116100de578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461034b578063e01af92c1461035e578063f851a44014610371578063fc582d411461038457600080fd5b8063c9d8616f14610306578063cb209b6c14610319578063cd2055e51461033857600080fd5b8063a001ecdd146102a2578063a4ac0d49146102ab578063a88971fa146102b4578063b5106add146102c8578063bb7bfb0c146102db578063c18b5151146102ee57600080fd5b80633facbb851161014b5780638638fe31116101255780638638fe31146102615780638bfd52891461027457806395d89b41146102875780639ead72221461028f57600080fd5b80633facbb851461023157806345f0a44f1461024657806347bc4d921461025957600080fd5b806306fdde0314610193578063092f7de7146101b1578063158ef93e146101dc5780633281f3ec1461020057806338af3eed14610216578063392f37e914610229575b600080fd5b61019b610397565b6040516101a89190611f07565b60405180910390f35b600b546101c4906001600160a01b031681565b6040516001600160a01b0390911681526020016101a8565b600d546101f090600160b01b900460ff1681565b60405190151581526020016101a8565b610208610425565b6040519081526020016101a8565b6003546101c4906001600160a01b031681565b61019b610464565b61024461023f366004611f49565b610471565b005b610208610254366004611f66565b6107b2565b6101f06107d3565b61024461026f366004612129565b6108a6565b610244610282366004611f49565b610f89565b61019b611716565b6101c461029d366004611f66565b611723565b61020860045481565b61020860055481565b600d546101f090600160a81b900460ff1681565b6102446102d6366004611f49565b61174d565b6102086102e9366004611f66565b611829565b600d546101c49061010090046001600160a01b031681565b610208610314366004611f66565b611839565b600d546103269060ff1681565b60405160ff90911681526020016101a8565b610208610346366004611f66565b611849565b610244610359366004611f49565b611859565b61024461036c3660046122cd565b611cb1565b6002546101c4906001600160a01b031681565b6102446103923660046122ea565b611d3d565b600180546103a490612327565b80601f01602080910402602001604051908101604052809291908181526020018280546103d090612327565b801561041d5780601f106103f25761010080835404028352916020019161041d565b820191906000526020600020905b81548152906001019060200180831161040057829003601f168201915b505050505081565b600061042f611db5565b600d5460078054909160ff1690811061044a5761044a612361565b906000526020600020015461045f919061238d565b905090565b600c80546103a490612327565b6002546001600160a01b031633146104a45760405162461bcd60e51b815260040161049b906123a6565b60405180910390fd5b6001600160a01b0381166104fa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b6000600a60018154811061051057610510612361565b906000526020600020015490508042101561056d5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105b6573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105da91906123dd565b116106275760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b600b546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa158015610693573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106b791906123dd565b60405190815260200160405180910390a2600b546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561071a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061073e91906123dd565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015610789573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ad91906123f6565b505050565b600781815481106107c257600080fd5b600091825260209091200154905081565b600d54600090600160a81b900460ff1661082f5760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e604482015260640161049b565b600b60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa158015610882573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061045f91906123f6565b600d54600160b01b900460ff16156109005760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a656400604482015260640161049b565b6001600160a01b038a166109565760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f604482015260640161049b565b64e8d4a510008260008151811061096f5761096f612361565b602002602001015110156109d15760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b606482015260840161049b565b67016345785d8a0000826000815181106109ed576109ed612361565b60200260200101511115610a515760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b606482015260840161049b565b86516002148015610a63575085516002145b8015610a70575084516002145b8015610a7d575083516002145b8015610a8a575082516002145b8015610a97575081516002145b610ae35760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a65000000604482015260640161049b565b86600181518110610af657610af6612361565b60200260200101516001600160a01b031687600081518110610b1a57610b1a612361565b60200260200101516001600160a01b031603610b785760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d65604482015260640161049b565b83600181518110610b8b57610b8b612361565b602002602001015184600081518110610ba657610ba6612361565b602002602001015110610bfb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d6500604482015260640161049b565b600d805460ff60b01b1916600160b01b179055600280546001600160a01b0319163317905581518290600090610c3357610c33612361565b602002602001015160058190555081600181518110610c5457610c54612361565b6020908102919091010151600455600380546001600160a01b0319166001600160a01b038c16179055600c610c898282612461565b508351610c9d90600a906020870190611e02565b506001610caa8a82612461565b506000610cb78982612461565b50600d8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610ced57610ced612361565b60200260200101516001600160a01b031687600081518110610d1157610d11612361565b60200260200101516001600160a01b03161115610f2157600d805460ff19166001908117909155875160069189918110610d4d57610d4d612361565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516006918991610d9c57610d9c612361565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160079188918110610df057610df0612361565b602090810291909101810151825460018101845560009384529183209091015586516007918891610e2357610e23612361565b60209081029190910181015182546001818101855560009485529290932090920191909155855160089187918110610e5d57610e5d612361565b602090810291909101810151825460018101845560009384529183209091015585516008918791610e9057610e90612361565b60209081029190910181015182546001818101855560009485529290932090920191909155835160099185918110610eca57610eca612361565b602090810291909101810151825460018101845560009384529183209091015583516009918591610efd57610efd612361565b60209081029190910181015182546001810184556000938452919092200155610f7c565b600d805460ff191690558651610f3e9060069060208a0190611e4d565b508551610f52906007906020890190611e02565b508451610f66906008906020880190611e02565b508251610f7a906009906020860190611e02565b505b5050505050505050505050565b6002546001600160a01b03163314610fb35760405162461bcd60e51b815260040161049b906123a6565b600d54600160b01b900460ff1615156001146110205760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b606482015260840161049b565b600d54600160a81b900460ff161561107a5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e64656400604482015260640161049b565b600d8054600160a81b60ff60a81b199091161790819055600554604051632367971960e01b81526101009092046001600160a01b0316916323679719916110d391600191600091600691600891309085906004016125de565b6020604051808303816000875af11580156110f2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611116919061268f565b600b80546001600160a01b0319166001600160a01b03929092169182179055600a8054633e569205919060009061114f5761114f612361565b9060005260206000200154600a60018154811061116e5761116e612361565b906000526020600020015460096040518463ffffffff1660e01b8152600401611199939291906126ac565b600060405180830381600087803b1580156111b357600080fd5b505af11580156111c7573d6000803e3d6000fd5b505050506000600b60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611220573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611244919061268f565b905060045460001461137d57600061125a611db5565b600d54600680549293509160ff90911690811061127957611279612361565b6000918252602090912001546003546040516323b872dd60e01b81526001600160a01b0386811660048301529182166024820152604481018490529116906323b872dd906064016020604051808303816000875af11580156112df573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061130391906123f6565b50600354600d54600680546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff1690811061134e5761134e612361565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60065460ff821610156115475760068160ff16815481106113a3576113a3612361565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060078560ff16815481106113e7576113e7612361565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af1158015611447573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061146b91906123f6565b5060068160ff168154811061148257611482612361565b600091825260209091200154600780546001600160a01b039092169163095ea7b391859160ff86169081106114b9576114b9612361565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611510573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061153491906123f6565b508061153f816126d4565b915050611380565b50604080516006805460a060208202840181019094526080830181815260009484939192908401828280156115a557602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611587575b5050505050815260200160078054806020026020016040519081016040528092919081815260200182805480156115fb57602002820191906000526020600020905b8154815260200190600101908083116115e7575b505050505081526020016000600760405160200161161a9291906126f3565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611699573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906116bd91906123dd565b3030856040518563ffffffff1660e01b81526004016116df94939291906127d6565b600060405180830381600087803b1580156116f957600080fd5b505af115801561170d573d6000803e3d6000fd5b50505050505050565b600080546103a490612327565b6006818154811061173357600080fd5b6000918252602090912001546001600160a01b0316905081565b6002546001600160a01b031633146117775760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166117cd5760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f000000604482015260640161049b565b6002546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600280546001600160a01b0319166001600160a01b0392909216919091179055565b600881815481106107c257600080fd5b600981815481106107c257600080fd5b600a81815481106107c257600080fd5b6002546001600160a01b031633146118835760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166118d95760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611922573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061194691906123dd565b116119935760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b6000600a6001815481106119a9576119a9612361565b9060005260206000200154905080421015611a065760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a50573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a74919061268f565b9050600060405180608001604052806006805480602002602001604051908101604052809291908181526020018280548015611ad957602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611abb575b5050505050815260200160068054905067ffffffffffffffff811115611b0157611b01611f7f565b604051908082528060200260200182016040528015611b2a578160200160208202803683370190505b508152600b546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611b7c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ba091906123dd565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c33573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c5791906123dd565b3087856040518563ffffffff1660e01b8152600401611c7994939291906127d6565b600060405180830381600087803b158015611c9357600080fd5b505af1158015611ca7573d6000803e3d6000fd5b5050505050505050565b6002546001600160a01b03163314611cdb5760405162461bcd60e51b815260040161049b906123a6565b600b54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d2257600080fd5b505af1158015611d36573d6000803e3d6000fd5b5050505050565b6002546001600160a01b03163314611d675760405162461bcd60e51b815260040161049b906123a6565b600c611d738282612461565b5080604051611d829190612812565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600454600d5460078054600093670de0b6b3a76400009390929160ff909116908110611de357611de3612361565b9060005260206000200154611df8919061282e565b61045f9190612845565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d578251825591602001919060010190611e22565b50611e49929150611ea2565b5090565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d57825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611e6d565b5b80821115611e495760008155600101611ea3565b60005b83811015611ed2578181015183820152602001611eba565b50506000910152565b60008151808452611ef3816020860160208601611eb7565b601f01601f19169290920160200192915050565b602081526000611f1a6020830184611edb565b9392505050565b6001600160a01b0381168114611f3657600080fd5b50565b8035611f4481611f21565b919050565b600060208284031215611f5b57600080fd5b8135611f1a81611f21565b600060208284031215611f7857600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715611fbe57611fbe611f7f565b604052919050565b600082601f830112611fd757600080fd5b813567ffffffffffffffff811115611ff157611ff1611f7f565b612004601f8201601f1916602001611f95565b81815284602083860101111561201957600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561205057612050611f7f565b5060051b60200190565b600082601f83011261206b57600080fd5b8135602061208061207b83612036565b611f95565b82815260059290921b8401810191818101908684111561209f57600080fd5b8286015b848110156120c35780356120b681611f21565b83529183019183016120a3565b509695505050505050565b600082601f8301126120df57600080fd5b813560206120ef61207b83612036565b82815260059290921b8401810191818101908684111561210e57600080fd5b8286015b848110156120c35780358352918301918301612112565b60008060008060008060008060008060006101608c8e03121561214b57600080fd5b6121548c611f39565b9a5061216260208d01611f39565b995067ffffffffffffffff8060408e0135111561217e57600080fd5b61218e8e60408f01358f01611fc6565b99508060608e013511156121a157600080fd5b6121b18e60608f01358f01611fc6565b98508060808e013511156121c457600080fd5b6121d48e60808f01358f0161205a565b97508060a08e013511156121e757600080fd5b6121f78e60a08f01358f016120ce565b96508060c08e0135111561220a57600080fd5b61221a8e60c08f01358f016120ce565b95508060e08e0135111561222d57600080fd5b61223d8e60e08f01358f016120ce565b9450806101008e0135111561225157600080fd5b6122628e6101008f01358f016120ce565b9350806101208e0135111561227657600080fd5b6122878e6101208f01358f016120ce565b9250806101408e0135111561229b57600080fd5b506122ad8d6101408e01358e01611fc6565b90509295989b509295989b9093969950565b8015158114611f3657600080fd5b6000602082840312156122df57600080fd5b8135611f1a816122bf565b6000602082840312156122fc57600080fd5b813567ffffffffffffffff81111561231357600080fd5b61231f84828501611fc6565b949350505050565b600181811c9082168061233b57607f821691505b60208210810361235b57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123a0576123a0612377565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b6000602082840312156123ef57600080fd5b5051919050565b60006020828403121561240857600080fd5b8151611f1a816122bf565b601f8211156107ad57600081815260208120601f850160051c8101602086101561243a5750805b601f850160051c820191505b8181101561245957828155600101612446565b505050505050565b815167ffffffffffffffff81111561247b5761247b611f7f565b61248f816124898454612327565b84612413565b602080601f8311600181146124c457600084156124ac5750858301515b600019600386901b1c1916600185901b178555612459565b600085815260208120601f198616915b828110156124f3578886015182559484019460019091019084016124d4565b50858210156125115787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b6000815461252e81612327565b80855260206001838116801561254b576001811461256557612593565b60ff1985168884015283151560051b880183019550612593565b866000528260002060005b8581101561258b5781548a8201860152908301908401612570565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b838110156125d3578154875295820195600191820191016125b7565b509495945050505050565b60e0815260006125f160e083018a612521565b8281036020840152612603818a612521565b8381036040850152885480825260008a815260208082209450909201915b818110156126485783546001600160a01b0316835260019384019360209093019201612621565b5050838103606085015261265c818961259e565b9250505084608083015261267b60a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126a157600080fd5b8151611f1a81611f21565b8381528260208201526060604082015260006126cb606083018461259e565b95945050505050565b600060ff821660ff81036126ea576126ea612377565b60010192915050565b60ff8316815260406020820152600061231f604083018461259e565b600081518084526020808501945080840160005b838110156125d357815187529582019590820190600101612723565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127845783516001600160a01b03168352928401929184019160010161275f565b50508285015191508581038387015261279d818361270f565b92505050604083015184820360408601526127b88282611edb565b91505060608301516127ce606086018215159052565b509392505050565b8481526001600160a01b038481166020830152831660408201526080606082018190526000906128089083018461273f565b9695505050505050565b60008251612824818460208701611eb7565b9190910192915050565b80820281158282048414176123a0576123a0612377565b60008261286257634e487b7160e01b600052601260045260246000fd5b50049056fea26469706673582212206a6fdfb186a671a69ffd99a8246a5da82698e47ac0533c9c48ccb68220dc51c364736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b506004361061018e5760003560e01c8063a001ecdd116100de578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461034b578063e01af92c1461035e578063f851a44014610371578063fc582d411461038457600080fd5b8063c9d8616f14610306578063cb209b6c14610319578063cd2055e51461033857600080fd5b8063a001ecdd146102a2578063a4ac0d49146102ab578063a88971fa146102b4578063b5106add146102c8578063bb7bfb0c146102db578063c18b5151146102ee57600080fd5b80633facbb851161014b5780638638fe31116101255780638638fe31146102615780638bfd52891461027457806395d89b41146102875780639ead72221461028f57600080fd5b80633facbb851461023157806345f0a44f1461024657806347bc4d921461025957600080fd5b806306fdde0314610193578063092f7de7146101b1578063158ef93e146101dc5780633281f3ec1461020057806338af3eed14610216578063392f37e914610229575b600080fd5b61019b610397565b6040516101a89190611f07565b60405180910390f35b600b546101c4906001600160a01b031681565b6040516001600160a01b0390911681526020016101a8565b600d546101f090600160b01b900460ff1681565b60405190151581526020016101a8565b610208610425565b6040519081526020016101a8565b6003546101c4906001600160a01b031681565b61019b610464565b61024461023f366004611f49565b610471565b005b610208610254366004611f66565b6107b2565b6101f06107d3565b61024461026f366004612129565b6108a6565b610244610282366004611f49565b610f89565b61019b611716565b6101c461029d366004611f66565b611723565b61020860045481565b61020860055481565b600d546101f090600160a81b900460ff1681565b6102446102d6366004611f49565b61174d565b6102086102e9366004611f66565b611829565b600d546101c49061010090046001600160a01b031681565b610208610314366004611f66565b611839565b600d546103269060ff1681565b60405160ff90911681526020016101a8565b610208610346366004611f66565b611849565b610244610359366004611f49565b611859565b61024461036c3660046122cd565b611cb1565b6002546101c4906001600160a01b031681565b6102446103923660046122ea565b611d3d565b600180546103a490612327565b80601f01602080910402602001604051908101604052809291908181526020018280546103d090612327565b801561041d5780601f106103f25761010080835404028352916020019161041d565b820191906000526020600020905b81548152906001019060200180831161040057829003601f168201915b505050505081565b600061042f611db5565b600d5460078054909160ff1690811061044a5761044a612361565b906000526020600020015461045f919061238d565b905090565b600c80546103a490612327565b6002546001600160a01b031633146104a45760405162461bcd60e51b815260040161049b906123a6565b60405180910390fd5b6001600160a01b0381166104fa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b6000600a60018154811061051057610510612361565b906000526020600020015490508042101561056d5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105b6573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105da91906123dd565b116106275760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b600b546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa158015610693573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106b791906123dd565b60405190815260200160405180910390a2600b546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561071a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061073e91906123dd565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015610789573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ad91906123f6565b505050565b600781815481106107c257600080fd5b600091825260209091200154905081565b600d54600090600160a81b900460ff1661082f5760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e604482015260640161049b565b600b60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa158015610882573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061045f91906123f6565b600d54600160b01b900460ff16156109005760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a656400604482015260640161049b565b6001600160a01b038a166109565760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f604482015260640161049b565b64e8d4a510008260008151811061096f5761096f612361565b602002602001015110156109d15760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b606482015260840161049b565b67016345785d8a0000826000815181106109ed576109ed612361565b60200260200101511115610a515760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b606482015260840161049b565b86516002148015610a63575085516002145b8015610a70575084516002145b8015610a7d575083516002145b8015610a8a575082516002145b8015610a97575081516002145b610ae35760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a65000000604482015260640161049b565b86600181518110610af657610af6612361565b60200260200101516001600160a01b031687600081518110610b1a57610b1a612361565b60200260200101516001600160a01b031603610b785760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d65604482015260640161049b565b83600181518110610b8b57610b8b612361565b602002602001015184600081518110610ba657610ba6612361565b602002602001015110610bfb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d6500604482015260640161049b565b600d805460ff60b01b1916600160b01b179055600280546001600160a01b0319163317905581518290600090610c3357610c33612361565b602002602001015160058190555081600181518110610c5457610c54612361565b6020908102919091010151600455600380546001600160a01b0319166001600160a01b038c16179055600c610c898282612461565b508351610c9d90600a906020870190611e02565b506001610caa8a82612461565b506000610cb78982612461565b50600d8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610ced57610ced612361565b60200260200101516001600160a01b031687600081518110610d1157610d11612361565b60200260200101516001600160a01b03161115610f2157600d805460ff19166001908117909155875160069189918110610d4d57610d4d612361565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516006918991610d9c57610d9c612361565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160079188918110610df057610df0612361565b602090810291909101810151825460018101845560009384529183209091015586516007918891610e2357610e23612361565b60209081029190910181015182546001818101855560009485529290932090920191909155855160089187918110610e5d57610e5d612361565b602090810291909101810151825460018101845560009384529183209091015585516008918791610e9057610e90612361565b60209081029190910181015182546001818101855560009485529290932090920191909155835160099185918110610eca57610eca612361565b602090810291909101810151825460018101845560009384529183209091015583516009918591610efd57610efd612361565b60209081029190910181015182546001810184556000938452919092200155610f7c565b600d805460ff191690558651610f3e9060069060208a0190611e4d565b508551610f52906007906020890190611e02565b508451610f66906008906020880190611e02565b508251610f7a906009906020860190611e02565b505b5050505050505050505050565b6002546001600160a01b03163314610fb35760405162461bcd60e51b815260040161049b906123a6565b600d54600160b01b900460ff1615156001146110205760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b606482015260840161049b565b600d54600160a81b900460ff161561107a5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e64656400604482015260640161049b565b600d8054600160a81b60ff60a81b199091161790819055600554604051632367971960e01b81526101009092046001600160a01b0316916323679719916110d391600191600091600691600891309085906004016125de565b6020604051808303816000875af11580156110f2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611116919061268f565b600b80546001600160a01b0319166001600160a01b03929092169182179055600a8054633e569205919060009061114f5761114f612361565b9060005260206000200154600a60018154811061116e5761116e612361565b906000526020600020015460096040518463ffffffff1660e01b8152600401611199939291906126ac565b600060405180830381600087803b1580156111b357600080fd5b505af11580156111c7573d6000803e3d6000fd5b505050506000600b60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611220573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611244919061268f565b905060045460001461137d57600061125a611db5565b600d54600680549293509160ff90911690811061127957611279612361565b6000918252602090912001546003546040516323b872dd60e01b81526001600160a01b0386811660048301529182166024820152604481018490529116906323b872dd906064016020604051808303816000875af11580156112df573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061130391906123f6565b50600354600d54600680546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff1690811061134e5761134e612361565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60065460ff821610156115475760068160ff16815481106113a3576113a3612361565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060078560ff16815481106113e7576113e7612361565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af1158015611447573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061146b91906123f6565b5060068160ff168154811061148257611482612361565b600091825260209091200154600780546001600160a01b039092169163095ea7b391859160ff86169081106114b9576114b9612361565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611510573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061153491906123f6565b508061153f816126d4565b915050611380565b50604080516006805460a060208202840181019094526080830181815260009484939192908401828280156115a557602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611587575b5050505050815260200160078054806020026020016040519081016040528092919081815260200182805480156115fb57602002820191906000526020600020905b8154815260200190600101908083116115e7575b505050505081526020016000600760405160200161161a9291906126f3565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611699573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906116bd91906123dd565b3030856040518563ffffffff1660e01b81526004016116df94939291906127d6565b600060405180830381600087803b1580156116f957600080fd5b505af115801561170d573d6000803e3d6000fd5b50505050505050565b600080546103a490612327565b6006818154811061173357600080fd5b6000918252602090912001546001600160a01b0316905081565b6002546001600160a01b031633146117775760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166117cd5760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f000000604482015260640161049b565b6002546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600280546001600160a01b0319166001600160a01b0392909216919091179055565b600881815481106107c257600080fd5b600981815481106107c257600080fd5b600a81815481106107c257600080fd5b6002546001600160a01b031633146118835760405162461bcd60e51b815260040161049b906123a6565b6001600160a01b0381166118d95760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f00000000604482015260640161049b565b600b546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611922573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061194691906123dd565b116119935760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e6365604482015260640161049b565b6000600a6001815481106119a9576119a9612361565b9060005260206000200154905080421015611a065760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f74207265616368656400604482015260640161049b565b600b54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a50573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a74919061268f565b9050600060405180608001604052806006805480602002602001604051908101604052809291908181526020018280548015611ad957602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611abb575b5050505050815260200160068054905067ffffffffffffffff811115611b0157611b01611f7f565b604051908082528060200260200182016040528015611b2a578160200160208202803683370190505b508152600b546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611b7c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ba091906123dd565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600b60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c33573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c5791906123dd565b3087856040518563ffffffff1660e01b8152600401611c7994939291906127d6565b600060405180830381600087803b158015611c9357600080fd5b505af1158015611ca7573d6000803e3d6000fd5b5050505050505050565b6002546001600160a01b03163314611cdb5760405162461bcd60e51b815260040161049b906123a6565b600b54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d2257600080fd5b505af1158015611d36573d6000803e3d6000fd5b5050505050565b6002546001600160a01b03163314611d675760405162461bcd60e51b815260040161049b906123a6565b600c611d738282612461565b5080604051611d829190612812565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600454600d5460078054600093670de0b6b3a76400009390929160ff909116908110611de357611de3612361565b9060005260206000200154611df8919061282e565b61045f9190612845565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d578251825591602001919060010190611e22565b50611e49929150611ea2565b5090565b828054828255906000526020600020908101928215611e3d579160200282015b82811115611e3d57825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611e6d565b5b80821115611e495760008155600101611ea3565b60005b83811015611ed2578181015183820152602001611eba565b50506000910152565b60008151808452611ef3816020860160208601611eb7565b601f01601f19169290920160200192915050565b602081526000611f1a6020830184611edb565b9392505050565b6001600160a01b0381168114611f3657600080fd5b50565b8035611f4481611f21565b919050565b600060208284031215611f5b57600080fd5b8135611f1a81611f21565b600060208284031215611f7857600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715611fbe57611fbe611f7f565b604052919050565b600082601f830112611fd757600080fd5b813567ffffffffffffffff811115611ff157611ff1611f7f565b612004601f8201601f1916602001611f95565b81815284602083860101111561201957600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561205057612050611f7f565b5060051b60200190565b600082601f83011261206b57600080fd5b8135602061208061207b83612036565b611f95565b82815260059290921b8401810191818101908684111561209f57600080fd5b8286015b848110156120c35780356120b681611f21565b83529183019183016120a3565b509695505050505050565b600082601f8301126120df57600080fd5b813560206120ef61207b83612036565b82815260059290921b8401810191818101908684111561210e57600080fd5b8286015b848110156120c35780358352918301918301612112565b60008060008060008060008060008060006101608c8e03121561214b57600080fd5b6121548c611f39565b9a5061216260208d01611f39565b995067ffffffffffffffff8060408e0135111561217e57600080fd5b61218e8e60408f01358f01611fc6565b99508060608e013511156121a157600080fd5b6121b18e60608f01358f01611fc6565b98508060808e013511156121c457600080fd5b6121d48e60808f01358f0161205a565b97508060a08e013511156121e757600080fd5b6121f78e60a08f01358f016120ce565b96508060c08e0135111561220a57600080fd5b61221a8e60c08f01358f016120ce565b95508060e08e0135111561222d57600080fd5b61223d8e60e08f01358f016120ce565b9450806101008e0135111561225157600080fd5b6122628e6101008f01358f016120ce565b9350806101208e0135111561227657600080fd5b6122878e6101208f01358f016120ce565b9250806101408e0135111561229b57600080fd5b506122ad8d6101408e01358e01611fc6565b90509295989b509295989b9093969950565b8015158114611f3657600080fd5b6000602082840312156122df57600080fd5b8135611f1a816122bf565b6000602082840312156122fc57600080fd5b813567ffffffffffffffff81111561231357600080fd5b61231f84828501611fc6565b949350505050565b600181811c9082168061233b57607f821691505b60208210810361235b57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123a0576123a0612377565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b6000602082840312156123ef57600080fd5b5051919050565b60006020828403121561240857600080fd5b8151611f1a816122bf565b601f8211156107ad57600081815260208120601f850160051c8101602086101561243a5750805b601f850160051c820191505b8181101561245957828155600101612446565b505050505050565b815167ffffffffffffffff81111561247b5761247b611f7f565b61248f816124898454612327565b84612413565b602080601f8311600181146124c457600084156124ac5750858301515b600019600386901b1c1916600185901b178555612459565b600085815260208120601f198616915b828110156124f3578886015182559484019460019091019084016124d4565b50858210156125115787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b6000815461252e81612327565b80855260206001838116801561254b576001811461256557612593565b60ff1985168884015283151560051b880183019550612593565b866000528260002060005b8581101561258b5781548a8201860152908301908401612570565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b838110156125d3578154875295820195600191820191016125b7565b509495945050505050565b60e0815260006125f160e083018a612521565b8281036020840152612603818a612521565b8381036040850152885480825260008a815260208082209450909201915b818110156126485783546001600160a01b0316835260019384019360209093019201612621565b5050838103606085015261265c818961259e565b9250505084608083015261267b60a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126a157600080fd5b8151611f1a81611f21565b8381528260208201526060604082015260006126cb606083018461259e565b95945050505050565b600060ff821660ff81036126ea576126ea612377565b60010192915050565b60ff8316815260406020820152600061231f604083018461259e565b600081518084526020808501945080840160005b838110156125d357815187529582019590820190600101612723565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127845783516001600160a01b03168352928401929184019160010161275f565b50508285015191508581038387015261279d818361270f565b92505050604083015184820360408601526127b88282611edb565b91505060608301516127ce606086018215159052565b509392505050565b8481526001600160a01b038481166020830152831660408201526080606082018190526000906128089083018461273f565b9695505050505050565b60008251612824818460208701611eb7565b9190910192915050565b80820281158282048414176123a0576123a0612377565b60008261286257634e487b7160e01b600052601260045260246000fd5b50049056fea26469706673582212206a6fdfb186a671a69ffd99a8246a5da82698e47ac0533c9c48ccb68220dc51c364736f6c63430008110033", + "devdoc": { + "details": "Smart contract for managing interactions with a Balancer LBP.", + "kind": "dev", + "methods": { + "getSwapEnabled()": { + "details": "Tells whether swaps are enabled or not for the LBP" + }, + "initializeLBP(address)": { + "details": "Subtracts the fee, deploys the LBP and adds liquidity to it.", + "params": { + "_sender": "Address of the liquidity provider." + } + }, + "initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Initialize LBPManager.", + "params": { + "_amounts": "Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the feePercentage.", + "_endWeights": "Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_lbpFactory": "LBP factory address.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndTime": "Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.", + "_startWeights": "Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token." + } + }, + "projectTokensRequired()": { + "details": "Get required amount of project tokens to cover for fees and the actual LBP." + }, + "removeLiquidity(address)": { + "details": "Exit pool or remove liquidity from pool.", + "params": { + "_receiver": "Address of the liquidity receiver, after exiting the LBP." + } + }, + "setSwapEnabled(bool)": { + "details": "Can pause/unpause trading.", + "params": { + "_swapEnabled": "Enables/disables swapping." + } + }, + "transferAdminRights(address)": { + "details": "Transfer admin rights.", + "params": { + "_newAdmin": "Address of the new admin." + } + }, + "updateMetadata(bytes)": { + "details": "Updates metadata.", + "params": { + "_metadata": "LBP wizard contract metadata, that is an IPFS Hash." + } + }, + "withdrawPoolTokens(address)": { + "details": "Withdraw pool tokens if available.", + "params": { + "_receiver": "Address of the BPT tokens receiver." + } + } + }, + "title": "LBPManager contract.", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 4089, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "symbol", + "offset": 0, + "slot": "0", + "type": "t_string_storage" + }, + { + "astId": 4091, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "name", + "offset": 0, + "slot": "1", + "type": "t_string_storage" + }, + { + "astId": 4093, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "admin", + "offset": 0, + "slot": "2", + "type": "t_address" + }, + { + "astId": 4095, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "beneficiary", + "offset": 0, + "slot": "3", + "type": "t_address" + }, + { + "astId": 4097, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "feePercentage", + "offset": 0, + "slot": "4", + "type": "t_uint256" + }, + { + "astId": 4099, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "swapFeePercentage", + "offset": 0, + "slot": "5", + "type": "t_uint256" + }, + { + "astId": 4103, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "tokenList", + "offset": 0, + "slot": "6", + "type": "t_array(t_contract(IERC20)3353)dyn_storage" + }, + { + "astId": 4106, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "amounts", + "offset": 0, + "slot": "7", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4109, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "startWeights", + "offset": 0, + "slot": "8", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4112, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "endWeights", + "offset": 0, + "slot": "9", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4115, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "startTimeEndTime", + "offset": 0, + "slot": "10", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 4118, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "lbp", + "offset": 0, + "slot": "11", + "type": "t_contract(ILBP)8837" + }, + { + "astId": 4120, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "metadata", + "offset": 0, + "slot": "12", + "type": "t_bytes_storage" + }, + { + "astId": 4122, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "projectTokenIndex", + "offset": 0, + "slot": "13", + "type": "t_uint8" + }, + { + "astId": 4124, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "lbpFactory", + "offset": 1, + "slot": "13", + "type": "t_address" + }, + { + "astId": 4126, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "poolFunded", + "offset": 21, + "slot": "13", + "type": "t_bool" + }, + { + "astId": 4128, + "contract": "contracts/lbp/LBPManager.sol:LBPManager", + "label": "initialized", + "offset": 22, + "slot": "13", + "type": "t_bool" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_array(t_contract(IERC20)3353)dyn_storage": { + "base": "t_contract(IERC20)3353", + "encoding": "dynamic_array", + "label": "contract IERC20[]", + "numberOfBytes": "32" + }, + "t_array(t_uint256)dyn_storage": { + "base": "t_uint256", + "encoding": "dynamic_array", + "label": "uint256[]", + "numberOfBytes": "32" + }, + "t_bool": { + "encoding": "inplace", + "label": "bool", + "numberOfBytes": "1" + }, + "t_bytes_storage": { + "encoding": "bytes", + "label": "bytes", + "numberOfBytes": "32" + }, + "t_contract(IERC20)3353": { + "encoding": "inplace", + "label": "contract IERC20", + "numberOfBytes": "20" + }, + "t_contract(ILBP)8837": { + "encoding": "inplace", + "label": "contract ILBP", + "numberOfBytes": "20" + }, + "t_string_storage": { + "encoding": "bytes", + "label": "string", + "numberOfBytes": "32" + }, + "t_uint256": { + "encoding": "inplace", + "label": "uint256", + "numberOfBytes": "32" + }, + "t_uint8": { + "encoding": "inplace", + "label": "uint8", + "numberOfBytes": "1" + } + } + } +} \ No newline at end of file diff --git a/deployments/goerli/LBPManagerFactory.json b/deployments/goerli/LBPManagerFactory.json new file mode 100644 index 0000000..02980e3 --- /dev/null +++ b/deployments/goerli/LBPManagerFactory.json @@ -0,0 +1,375 @@ +{ + "address": "0x69Eb008641dDcd0092C26C9A143B164F0CCc17DE", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0xb762d71d2e43d553266461e9f51fd3805e6e5dc8cb20fcff32dec78d71a67bb1", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0x69Eb008641dDcd0092C26C9A143B164F0CCc17DE", + "transactionIndex": 65, + "gasUsed": "767808", + "logsBloom": "0x00000000000000000000000040000000000000000000000000800000000000000000000000000000000000000000000000000000000200000000000800000000000000000000000000000000000000002001000000000000000000000000000000000000020000000000000000000800000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x4dac1a1fa88a55c7b48888c0604c03ff86a62bba448c59e000ec85245438b128", + "transactionHash": "0xb762d71d2e43d553266461e9f51fd3805e6e5dc8cb20fcff32dec78d71a67bb1", + "logs": [ + { + "transactionIndex": 65, + "blockNumber": 8087282, + "transactionHash": "0xb762d71d2e43d553266461e9f51fd3805e6e5dc8cb20fcff32dec78d71a67bb1", + "address": "0x69Eb008641dDcd0092C26C9A143B164F0CCc17DE", + "topics": [ + "0x8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0", + "0x0000000000000000000000000000000000000000000000000000000000000000", + "0x000000000000000000000000c039897ee5a0d14a3d1f212922faf7e159ab619f" + ], + "data": "0x", + "logIndex": 141, + "blockHash": "0x4dac1a1fa88a55c7b48888c0604c03ff86a62bba448c59e000ec85245438b128" + } + ], + "blockNumber": 8087282, + "cumulativeGasUsed": "14047849", + "status": 1, + "byzantium": true + }, + "args": [ + "0xb48Cc42C45d262534e46d5965a9Ac496F1B7a830" + ], + "solcInputHash": "bf89fe6a61a7d22f31b24d3cee885a8d", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldLBPFactory\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newLBPFactory\",\"type\":\"address\"}],\"name\":\"LBPFactoryChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpManager\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"admin\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"LBPManagerDeployed\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldMasterCopy\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newMasterCopy\",\"type\":\"address\"}],\"name\":\"MastercopyChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_admin\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndtime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"deployLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"masterCopy\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"name\":\"setLBPFactory\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_masterCopy\",\"type\":\"address\"}],\"name\":\"setMasterCopy\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Governance to create new LBPManager contracts.\",\"kind\":\"dev\",\"methods\":{\"constructor\":{\"details\":\"Constructor.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Deploy and initialize LBPManager.\",\"params\":{\"_admin\":\"The address of the admin of the LBPManager.\",\"_amounts\":\"Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the _fees.\",\"_endWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndtime\":\"Array containing two parameters: - Start time for the LBP. - End time for the LBP.\",\"_startWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token.\"}},\"owner()\":{\"details\":\"Returns the address of the current owner.\"},\"renounceOwnership()\":{\"details\":\"Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.\"},\"setLBPFactory(address)\":{\"details\":\"Set Balancers LBP Factory contract as basis for deploying LBPs.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"setMasterCopy(address)\":{\"details\":\"Set LBPManager contract which works as a base for clones.\",\"params\":{\"_masterCopy\":\"The address of the new LBPManager basis.\"}},\"transferOwnership(address)\":{\"details\":\"Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.\"}},\"title\":\"LBPManager Factory\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerFactory.sol\":\"LBPManagerFactory\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/access/Ownable.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\\n\\npragma solidity ^0.8.0;\\n\\nimport \\\"../utils/Context.sol\\\";\\n\\n/**\\n * @dev Contract module which provides a basic access control mechanism, where\\n * there is an account (an owner) that can be granted exclusive access to\\n * specific functions.\\n *\\n * By default, the owner account will be the one that deploys the contract. This\\n * can later be changed with {transferOwnership}.\\n *\\n * This module is used through inheritance. It will make available the modifier\\n * `onlyOwner`, which can be applied to your functions to restrict their use to\\n * the owner.\\n */\\nabstract contract Ownable is Context {\\n address private _owner;\\n\\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\\n\\n /**\\n * @dev Initializes the contract setting the deployer as the initial owner.\\n */\\n constructor() {\\n _transferOwnership(_msgSender());\\n }\\n\\n /**\\n * @dev Throws if called by any account other than the owner.\\n */\\n modifier onlyOwner() {\\n _checkOwner();\\n _;\\n }\\n\\n /**\\n * @dev Returns the address of the current owner.\\n */\\n function owner() public view virtual returns (address) {\\n return _owner;\\n }\\n\\n /**\\n * @dev Throws if the sender is not the owner.\\n */\\n function _checkOwner() internal view virtual {\\n require(owner() == _msgSender(), \\\"Ownable: caller is not the owner\\\");\\n }\\n\\n /**\\n * @dev Leaves the contract without owner. It will not be possible to call\\n * `onlyOwner` functions anymore. Can only be called by the current owner.\\n *\\n * NOTE: Renouncing ownership will leave the contract without an owner,\\n * thereby removing any functionality that is only available to the owner.\\n */\\n function renounceOwnership() public virtual onlyOwner {\\n _transferOwnership(address(0));\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Can only be called by the current owner.\\n */\\n function transferOwnership(address newOwner) public virtual onlyOwner {\\n require(newOwner != address(0), \\\"Ownable: new owner is the zero address\\\");\\n _transferOwnership(newOwner);\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Internal function without access restriction.\\n */\\n function _transferOwnership(address newOwner) internal virtual {\\n address oldOwner = _owner;\\n _owner = newOwner;\\n emit OwnershipTransferred(oldOwner, newOwner);\\n }\\n}\\n\",\"keccak256\":\"0xa94b34880e3c1b0b931662cb1c09e5dfa6662f31cba80e07c5ee71cd135c9673\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"@openzeppelin/contracts/utils/Context.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Provides information about the current execution context, including the\\n * sender of the transaction and its data. While these are generally available\\n * via msg.sender and msg.data, they should not be accessed in such a direct\\n * manner, since when dealing with meta-transactions the account sending and\\n * paying for execution may not be the actual sender (as far as an application\\n * is concerned).\\n *\\n * This contract is only required for intermediate, library-like contracts.\\n */\\nabstract contract Context {\\n function _msgSender() internal view virtual returns (address) {\\n return msg.sender;\\n }\\n\\n function _msgData() internal view virtual returns (bytes calldata) {\\n return msg.data;\\n }\\n}\\n\",\"keccak256\":\"0xe2e337e6dde9ef6b680e07338c493ebea1b5fd09b43424112868e9cc1706bca7\",\"license\":\"MIT\"},\"contracts/lbp/LBPManager.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract.\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManager {\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x371ceeb460072a61394db69c3b0f8b0f4c45dd4d1ee0ad19a1c44ba9f61000b4\",\"license\":\"GPL-3.0-or-later\"},\"contracts/lbp/LBPManagerFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"../utils/CloneFactory.sol\\\";\\nimport \\\"@openzeppelin/contracts/access/Ownable.sol\\\";\\nimport \\\"./LBPManager.sol\\\";\\n\\n/**\\n * @title LBPManager Factory\\n * @dev Governance to create new LBPManager contracts.\\n */\\ncontract LBPManagerFactory is CloneFactory, Ownable {\\n address public masterCopy;\\n address public lbpFactory;\\n\\n event LBPManagerDeployed(\\n address indexed lbpManager,\\n address indexed admin,\\n bytes metadata\\n );\\n\\n event LBPFactoryChanged(\\n address indexed oldLBPFactory,\\n address indexed newLBPFactory\\n );\\n\\n event MastercopyChanged(\\n address indexed oldMasterCopy,\\n address indexed newMasterCopy\\n );\\n\\n /**\\n * @dev Constructor.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n constructor(address _lbpFactory) {\\n require(_lbpFactory != address(0), \\\"LBPMFactory: LBPFactory is zero\\\");\\n lbpFactory = _lbpFactory;\\n }\\n\\n modifier validAddress(address addressToCheck) {\\n require(addressToCheck != address(0), \\\"LBPMFactory: address is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(\\n addressToCheck != address(this),\\n \\\"LBPMFactory: address same as LBPManagerFactory\\\"\\n );\\n _;\\n }\\n\\n /**\\n * @dev Set LBPManager contract which works as a base for clones.\\n * @param _masterCopy The address of the new LBPManager basis.\\n */\\n function setMasterCopy(address _masterCopy)\\n external\\n onlyOwner\\n validAddress(_masterCopy)\\n {\\n emit MastercopyChanged(masterCopy, _masterCopy);\\n masterCopy = _masterCopy;\\n }\\n\\n /**\\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n function setLBPFactory(address _lbpFactory)\\n external\\n onlyOwner\\n validAddress(_lbpFactory)\\n {\\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\\n lbpFactory = _lbpFactory;\\n }\\n\\n /**\\n * @dev Deploy and initialize LBPManager.\\n * @param _admin The address of the admin of the LBPManager.\\n * @param _beneficiary The address that receives the _fees.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\\n - The address of the project token being distributed.\\n - The address of the funding token being exchanged for the project token.\\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\\n - The amounts of project token to be added as liquidity to the LBP.\\n - The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\\n - The start weight for the project token in the LBP.\\n - The start weight for the funding token in the LBP.\\n * @param _startTimeEndtime Array containing two parameters:\\n - Start time for the LBP.\\n - End time for the LBP.\\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\\n - The end weight for the project token in the LBP.\\n - The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters:\\n - Percentage of fee paid for every swap in the LBP.\\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function deployLBPManager(\\n address _admin,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndtime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external onlyOwner {\\n // solhint-disable-next-line reason-string\\n require(\\n masterCopy != address(0),\\n \\\"LBPMFactory: LBPManager mastercopy not set\\\"\\n );\\n\\n address lbpManager = createClone(masterCopy);\\n\\n LBPManager(lbpManager).initializeLBPManager(\\n lbpFactory,\\n _beneficiary,\\n _name,\\n _symbol,\\n _tokenList,\\n _amounts,\\n _startWeights,\\n _startTimeEndtime,\\n _endWeights,\\n _fees,\\n _metadata\\n );\\n\\n LBPManager(lbpManager).transferAdminRights(_admin);\\n\\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\\n }\\n}\\n\",\"keccak256\":\"0xabd6bae623ac01e95553811cfb0a117cf260aabcec6b16a7683ee489d514b837\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/CloneFactory.sol\":{\"content\":\"/*\\n\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n \\n*\\n* CloneFactory.sol was originally published under MIT license.\\n* Republished by PrimeDAO under GNU General Public License v3.0.\\n*\\n*/\\n\\n/*\\nThe MIT License (MIT)\\nCopyright (c) 2018 Murray Software, LLC.\\nPermission is hereby granted, free of charge, to any person obtaining\\na copy of this software and associated documentation files (the\\n\\\"Software\\\"), to deal in the Software without restriction, including\\nwithout limitation the rights to use, copy, modify, merge, publish,\\ndistribute, sublicense, and/or sell copies of the Software, and to\\npermit persons to whom the Software is furnished to do so, subject to\\nthe following conditions:\\nThe above copyright notice and this permission notice shall be included\\nin all copies or substantial portions of the Software.\\nTHE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// solium-disable linebreak-style\\n// solhint-disable max-line-length\\n// solhint-disable no-inline-assembly\\n\\npragma solidity 0.8.17;\\n\\ncontract CloneFactory {\\n function createClone(address target) internal returns (address result) {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\\n )\\n mstore(add(clone, 0x14), targetBytes)\\n mstore(\\n add(clone, 0x28),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n result := create(0, clone, 0x37)\\n }\\n }\\n\\n function isClone(address target, address query)\\n internal\\n view\\n returns (bool result)\\n {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\\n )\\n mstore(add(clone, 0xa), targetBytes)\\n mstore(\\n add(clone, 0x1e),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n\\n let other := add(clone, 0x40)\\n extcodecopy(query, other, 0, 0x2d)\\n result := and(\\n eq(mload(clone), mload(other)),\\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\\n )\\n }\\n }\\n}\\n\",\"keccak256\":\"0x80b3d45006df787a887103ca0704f7eed17848ded1c944e494eb2de0274b2f71\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x608060405234801561001057600080fd5b50604051610d47380380610d4783398101604081905261002f91610107565b610038336100b7565b6001600160a01b0381166100925760405162461bcd60e51b815260206004820152601f60248201527f4c42504d466163746f72793a204c4250466163746f7279206973207a65726f00604482015260640160405180910390fd5b600280546001600160a01b0319166001600160a01b0392909216919091179055610137565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006020828403121561011957600080fd5b81516001600160a01b038116811461013057600080fd5b9392505050565b610c01806101466000396000f3fe608060405234801561001057600080fd5b50600436106100885760003560e01c8063c18b51511161005b578063c18b5151146100e6578063cf497e6c146100f9578063f2fde38b1461010c578063fd3bd38a1461011f57600080fd5b8063715018a61461008d5780637679a4c1146100975780638da5cb5b146100aa578063a619486e146100d3575b600080fd5b610095610132565b005b6100956100a5366004610665565b610146565b6000546001600160a01b03165b6040516001600160a01b03909116815260200160405180910390f35b6001546100b7906001600160a01b031681565b6002546100b7906001600160a01b031681565b610095610107366004610665565b61022f565b61009561011a366004610665565b610313565b61009561012d366004610833565b61038c565b61013a610544565b610144600061059e565b565b61014e610544565b806001600160a01b0381166101aa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b038216036101d25760405162461bcd60e51b81526004016101a1906109c9565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610237610544565b806001600160a01b03811661028e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101a1565b306001600160a01b038216036102b65760405162461bcd60e51b81526004016101a1906109c9565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b61031b610544565b6001600160a01b0381166103805760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101a1565b6103898161059e565b50565b610394610544565b6001546001600160a01b03166103ff5760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101a1565b600154600090610417906001600160a01b03166105ee565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261045e9216908f908f908f908f908f908f908f908f908f908f90600401610ad1565b600060405180830381600087803b15801561047857600080fd5b505af115801561048c573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b1580156104d357600080fd5b505af11580156104e7573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161052e9190610bb8565b60405180910390a3505050505050505050505050565b6000546001600160a01b031633146101445760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101a1565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b038116811461038957600080fd5b803561066081610640565b919050565b60006020828403121561067757600080fd5b813561068281610640565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106c8576106c8610689565b604052919050565b600082601f8301126106e157600080fd5b813567ffffffffffffffff8111156106fb576106fb610689565b61070e601f8201601f191660200161069f565b81815284602083860101111561072357600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561075a5761075a610689565b5060051b60200190565b600082601f83011261077557600080fd5b8135602061078a61078583610740565b61069f565b82815260059290921b840181019181810190868411156107a957600080fd5b8286015b848110156107cd5780356107c081610640565b83529183019183016107ad565b509695505050505050565b600082601f8301126107e957600080fd5b813560206107f961078583610740565b82815260059290921b8401810191818101908684111561081857600080fd5b8286015b848110156107cd578035835291830191830161081c565b60008060008060008060008060008060006101608c8e03121561085557600080fd5b61085e8c610655565b9a5061086c60208d01610655565b995067ffffffffffffffff8060408e0135111561088857600080fd5b6108988e60408f01358f016106d0565b99508060608e013511156108ab57600080fd5b6108bb8e60608f01358f016106d0565b98508060808e013511156108ce57600080fd5b6108de8e60808f01358f01610764565b97508060a08e013511156108f157600080fd5b6109018e60a08f01358f016107d8565b96508060c08e0135111561091457600080fd5b6109248e60c08f01358f016107d8565b95508060e08e0135111561093757600080fd5b6109478e60e08f01358f016107d8565b9450806101008e0135111561095b57600080fd5b61096c8e6101008f01358f016107d8565b9350806101208e0135111561098057600080fd5b6109918e6101208f01358f016107d8565b9250806101408e013511156109a557600080fd5b506109b78d6101408e01358e016106d0565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a3d57602081850181015186830182015201610a21565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610a965781516001600160a01b031687529582019590820190600101610a71565b509495945050505050565b600081518084526020808501945080840160005b83811015610a9657815187529582019590820190600101610ab5565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b038184018d610a17565b90508281036060840152610b17818c610a17565b90508281036080840152610b2b818b610a5d565b905082810360a0840152610b3f818a610aa1565b905082810360c0840152610b538189610aa1565b905082810360e0840152610b678188610aa1565b9050828103610100840152610b7c8187610aa1565b9050828103610120840152610b918186610aa1565b9050828103610140840152610ba68185610a17565b9e9d5050505050505050505050505050565b6020815260006106826020830184610a1756fea2646970667358221220ae5e8810a577600a3790682907f2d9f1dcee3d560c0fa5535b5ed0bf67e7803464736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106100885760003560e01c8063c18b51511161005b578063c18b5151146100e6578063cf497e6c146100f9578063f2fde38b1461010c578063fd3bd38a1461011f57600080fd5b8063715018a61461008d5780637679a4c1146100975780638da5cb5b146100aa578063a619486e146100d3575b600080fd5b610095610132565b005b6100956100a5366004610665565b610146565b6000546001600160a01b03165b6040516001600160a01b03909116815260200160405180910390f35b6001546100b7906001600160a01b031681565b6002546100b7906001600160a01b031681565b610095610107366004610665565b61022f565b61009561011a366004610665565b610313565b61009561012d366004610833565b61038c565b61013a610544565b610144600061059e565b565b61014e610544565b806001600160a01b0381166101aa5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b038216036101d25760405162461bcd60e51b81526004016101a1906109c9565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610237610544565b806001600160a01b03811661028e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101a1565b306001600160a01b038216036102b65760405162461bcd60e51b81526004016101a1906109c9565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b61031b610544565b6001600160a01b0381166103805760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101a1565b6103898161059e565b50565b610394610544565b6001546001600160a01b03166103ff5760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101a1565b600154600090610417906001600160a01b03166105ee565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261045e9216908f908f908f908f908f908f908f908f908f908f90600401610ad1565b600060405180830381600087803b15801561047857600080fd5b505af115801561048c573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b1580156104d357600080fd5b505af11580156104e7573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161052e9190610bb8565b60405180910390a3505050505050505050505050565b6000546001600160a01b031633146101445760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101a1565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b038116811461038957600080fd5b803561066081610640565b919050565b60006020828403121561067757600080fd5b813561068281610640565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106c8576106c8610689565b604052919050565b600082601f8301126106e157600080fd5b813567ffffffffffffffff8111156106fb576106fb610689565b61070e601f8201601f191660200161069f565b81815284602083860101111561072357600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561075a5761075a610689565b5060051b60200190565b600082601f83011261077557600080fd5b8135602061078a61078583610740565b61069f565b82815260059290921b840181019181810190868411156107a957600080fd5b8286015b848110156107cd5780356107c081610640565b83529183019183016107ad565b509695505050505050565b600082601f8301126107e957600080fd5b813560206107f961078583610740565b82815260059290921b8401810191818101908684111561081857600080fd5b8286015b848110156107cd578035835291830191830161081c565b60008060008060008060008060008060006101608c8e03121561085557600080fd5b61085e8c610655565b9a5061086c60208d01610655565b995067ffffffffffffffff8060408e0135111561088857600080fd5b6108988e60408f01358f016106d0565b99508060608e013511156108ab57600080fd5b6108bb8e60608f01358f016106d0565b98508060808e013511156108ce57600080fd5b6108de8e60808f01358f01610764565b97508060a08e013511156108f157600080fd5b6109018e60a08f01358f016107d8565b96508060c08e0135111561091457600080fd5b6109248e60c08f01358f016107d8565b95508060e08e0135111561093757600080fd5b6109478e60e08f01358f016107d8565b9450806101008e0135111561095b57600080fd5b61096c8e6101008f01358f016107d8565b9350806101208e0135111561098057600080fd5b6109918e6101208f01358f016107d8565b9250806101408e013511156109a557600080fd5b506109b78d6101408e01358e016106d0565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a3d57602081850181015186830182015201610a21565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610a965781516001600160a01b031687529582019590820190600101610a71565b509495945050505050565b600081518084526020808501945080840160005b83811015610a9657815187529582019590820190600101610ab5565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b038184018d610a17565b90508281036060840152610b17818c610a17565b90508281036080840152610b2b818b610a5d565b905082810360a0840152610b3f818a610aa1565b905082810360c0840152610b538189610aa1565b905082810360e0840152610b678188610aa1565b9050828103610100840152610b7c8187610aa1565b9050828103610120840152610b918186610aa1565b9050828103610140840152610ba68185610a17565b9e9d5050505050505050505050505050565b6020815260006106826020830184610a1756fea2646970667358221220ae5e8810a577600a3790682907f2d9f1dcee3d560c0fa5535b5ed0bf67e7803464736f6c63430008110033", + "devdoc": { + "details": "Governance to create new LBPManager contracts.", + "kind": "dev", + "methods": { + "constructor": { + "details": "Constructor.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Deploy and initialize LBPManager.", + "params": { + "_admin": "The address of the admin of the LBPManager.", + "_amounts": "Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the _fees.", + "_endWeights": "Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndtime": "Array containing two parameters: - Start time for the LBP. - End time for the LBP.", + "_startWeights": "Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token." + } + }, + "owner()": { + "details": "Returns the address of the current owner." + }, + "renounceOwnership()": { + "details": "Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner." + }, + "setLBPFactory(address)": { + "details": "Set Balancers LBP Factory contract as basis for deploying LBPs.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "setMasterCopy(address)": { + "details": "Set LBPManager contract which works as a base for clones.", + "params": { + "_masterCopy": "The address of the new LBPManager basis." + } + }, + "transferOwnership(address)": { + "details": "Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner." + } + }, + "title": "LBPManager Factory", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 2584, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "_owner", + "offset": 0, + "slot": "0", + "type": "t_address" + }, + { + "astId": 4898, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "masterCopy", + "offset": 0, + "slot": "1", + "type": "t_address" + }, + { + "astId": 4900, + "contract": "contracts/lbp/LBPManagerFactory.sol:LBPManagerFactory", + "label": "lbpFactory", + "offset": 0, + "slot": "2", + "type": "t_address" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + } + } + } +} \ No newline at end of file diff --git a/deployments/goerli/LBPManagerFactoryV1NoAccessControl.json b/deployments/goerli/LBPManagerFactoryV1NoAccessControl.json new file mode 100644 index 0000000..5e625f7 --- /dev/null +++ b/deployments/goerli/LBPManagerFactoryV1NoAccessControl.json @@ -0,0 +1,401 @@ +{ + "address": "0x5b4C1b1976B0b2D2d1fF26b10913F910D0E18140", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + } + ], + "transactionHash": "0xfac7d007951aa84adaac7e5016648c0ebea50831284684d0a797751ccb4949f8", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0x5b4C1b1976B0b2D2d1fF26b10913F910D0E18140", + "transactionIndex": 96, + "gasUsed": "779058", + "logsBloom": "0x00000000000000000000000040000000000000000000000000800000000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000002001000000000000100000000000000000000000020000000000000000000800000000000000000000000000000000400000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008000000000000020000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x6c8a942d2de4a6f53e8adca5dfc7ddab777166e1cd1c0b1bfcdbca7bdaf4fe06", + "transactionHash": "0xfac7d007951aa84adaac7e5016648c0ebea50831284684d0a797751ccb4949f8", + "logs": [ + { + "transactionIndex": 96, + "blockNumber": 8092116, + "transactionHash": "0xfac7d007951aa84adaac7e5016648c0ebea50831284684d0a797751ccb4949f8", + "address": "0x5b4C1b1976B0b2D2d1fF26b10913F910D0E18140", + "topics": [ + "0x8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0", + "0x0000000000000000000000000000000000000000000000000000000000000000", + "0x000000000000000000000000c039897ee5a0d14a3d1f212922faf7e159ab619f" + ], + "data": "0x", + "logIndex": 214, + "blockHash": "0x6c8a942d2de4a6f53e8adca5dfc7ddab777166e1cd1c0b1bfcdbca7bdaf4fe06" + } + ], + "blockNumber": 8092116, + "cumulativeGasUsed": "18676790", + "status": 1, + "byzantium": true + }, + "args": [ + "0xb48Cc42C45d262534e46d5965a9Ac496F1B7a830" + ], + "solcInputHash": "752d54b8f64e3608832db5b1be68e60f", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldLBPFactory\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newLBPFactory\",\"type\":\"address\"}],\"name\":\"LBPFactoryChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpManager\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"admin\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"LBPManagerDeployed\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldMasterCopy\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newMasterCopy\",\"type\":\"address\"}],\"name\":\"MastercopyChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_admin\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndtime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"deployLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"masterCopy\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"}],\"name\":\"setLBPFactory\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_masterCopy\",\"type\":\"address\"}],\"name\":\"setMasterCopy\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"version\",\"outputs\":[{\"internalType\":\"bytes6\",\"name\":\"\",\"type\":\"bytes6\"}],\"stateMutability\":\"view\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Governance to create new LBPManager contract without the onlyOwner modifer for the function deployLBPManager(). By removing the access control, everyone can deploy a LBPManager from this contract. This is a temporarly solution in response to the flaky Celo Safe.\",\"kind\":\"dev\",\"methods\":{\"constructor\":{\"details\":\"Constructor.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Deploy and initialize LBPManager.\",\"params\":{\"_admin\":\"The address of the admin of the LBPManager.\",\"_amounts\":\"Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the _fees.\",\"_endWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndtime\":\"Array containing two parameters: - Start time for the LBP. - End time for the LBP.\",\"_startWeights\":\"Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token.\"}},\"owner()\":{\"details\":\"Returns the address of the current owner.\"},\"renounceOwnership()\":{\"details\":\"Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.\"},\"setLBPFactory(address)\":{\"details\":\"Set Balancers LBP Factory contract as basis for deploying LBPs.\",\"params\":{\"_lbpFactory\":\"The address of Balancers LBP factory.\"}},\"setMasterCopy(address)\":{\"details\":\"Set LBPManager contract which works as a base for clones.\",\"params\":{\"_masterCopy\":\"The address of the new LBPManager basis.\"}},\"transferOwnership(address)\":{\"details\":\"Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.\"}},\"title\":\"LBPManager Factory no access control version 1\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol\":\"LBPManagerFactoryV1NoAccessControl\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/access/Ownable.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\\n\\npragma solidity ^0.8.0;\\n\\nimport \\\"../utils/Context.sol\\\";\\n\\n/**\\n * @dev Contract module which provides a basic access control mechanism, where\\n * there is an account (an owner) that can be granted exclusive access to\\n * specific functions.\\n *\\n * By default, the owner account will be the one that deploys the contract. This\\n * can later be changed with {transferOwnership}.\\n *\\n * This module is used through inheritance. It will make available the modifier\\n * `onlyOwner`, which can be applied to your functions to restrict their use to\\n * the owner.\\n */\\nabstract contract Ownable is Context {\\n address private _owner;\\n\\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\\n\\n /**\\n * @dev Initializes the contract setting the deployer as the initial owner.\\n */\\n constructor() {\\n _transferOwnership(_msgSender());\\n }\\n\\n /**\\n * @dev Throws if called by any account other than the owner.\\n */\\n modifier onlyOwner() {\\n _checkOwner();\\n _;\\n }\\n\\n /**\\n * @dev Returns the address of the current owner.\\n */\\n function owner() public view virtual returns (address) {\\n return _owner;\\n }\\n\\n /**\\n * @dev Throws if the sender is not the owner.\\n */\\n function _checkOwner() internal view virtual {\\n require(owner() == _msgSender(), \\\"Ownable: caller is not the owner\\\");\\n }\\n\\n /**\\n * @dev Leaves the contract without owner. It will not be possible to call\\n * `onlyOwner` functions anymore. Can only be called by the current owner.\\n *\\n * NOTE: Renouncing ownership will leave the contract without an owner,\\n * thereby removing any functionality that is only available to the owner.\\n */\\n function renounceOwnership() public virtual onlyOwner {\\n _transferOwnership(address(0));\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Can only be called by the current owner.\\n */\\n function transferOwnership(address newOwner) public virtual onlyOwner {\\n require(newOwner != address(0), \\\"Ownable: new owner is the zero address\\\");\\n _transferOwnership(newOwner);\\n }\\n\\n /**\\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\\n * Internal function without access restriction.\\n */\\n function _transferOwnership(address newOwner) internal virtual {\\n address oldOwner = _owner;\\n _owner = newOwner;\\n emit OwnershipTransferred(oldOwner, newOwner);\\n }\\n}\\n\",\"keccak256\":\"0xa94b34880e3c1b0b931662cb1c09e5dfa6662f31cba80e07c5ee71cd135c9673\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"@openzeppelin/contracts/utils/Context.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Provides information about the current execution context, including the\\n * sender of the transaction and its data. While these are generally available\\n * via msg.sender and msg.data, they should not be accessed in such a direct\\n * manner, since when dealing with meta-transactions the account sending and\\n * paying for execution may not be the actual sender (as far as an application\\n * is concerned).\\n *\\n * This contract is only required for intermediate, library-like contracts.\\n */\\nabstract contract Context {\\n function _msgSender() internal view virtual returns (address) {\\n return msg.sender;\\n }\\n\\n function _msgData() internal view virtual returns (bytes calldata) {\\n return msg.data;\\n }\\n}\\n\",\"keccak256\":\"0xe2e337e6dde9ef6b680e07338c493ebea1b5fd09b43424112868e9cc1706bca7\",\"license\":\"MIT\"},\"contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"../utils/CloneFactory.sol\\\";\\nimport \\\"@openzeppelin/contracts/access/Ownable.sol\\\";\\nimport \\\"./LBPManagerV1.sol\\\";\\n\\n/**\\n * @title LBPManager Factory no access control version 1\\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\\n * function deployLBPManager(). By removing the access control, everyone can deploy a\\n * LBPManager from this contract. This is a temporarly solution in response to the\\n * flaky Celo Safe.\\n */\\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\\n bytes6 public version = \\\"1.0.0\\\";\\n address public masterCopy;\\n address public lbpFactory;\\n\\n event LBPManagerDeployed(\\n address indexed lbpManager,\\n address indexed admin,\\n bytes metadata\\n );\\n\\n event LBPFactoryChanged(\\n address indexed oldLBPFactory,\\n address indexed newLBPFactory\\n );\\n\\n event MastercopyChanged(\\n address indexed oldMasterCopy,\\n address indexed newMasterCopy\\n );\\n\\n /**\\n * @dev Constructor.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n constructor(address _lbpFactory) {\\n require(_lbpFactory != address(0), \\\"LBPMFactory: LBPFactory is zero\\\");\\n lbpFactory = _lbpFactory;\\n }\\n\\n modifier validAddress(address addressToCheck) {\\n require(addressToCheck != address(0), \\\"LBPMFactory: address is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(\\n addressToCheck != address(this),\\n \\\"LBPMFactory: address same as LBPManagerFactory\\\"\\n );\\n _;\\n }\\n\\n /**\\n * @dev Set LBPManager contract which works as a base for clones.\\n * @param _masterCopy The address of the new LBPManager basis.\\n */\\n function setMasterCopy(address _masterCopy)\\n external\\n onlyOwner\\n validAddress(_masterCopy)\\n {\\n emit MastercopyChanged(masterCopy, _masterCopy);\\n masterCopy = _masterCopy;\\n }\\n\\n /**\\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\\n * @param _lbpFactory The address of Balancers LBP factory.\\n */\\n function setLBPFactory(address _lbpFactory)\\n external\\n onlyOwner\\n validAddress(_lbpFactory)\\n {\\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\\n lbpFactory = _lbpFactory;\\n }\\n\\n /**\\n * @dev Deploy and initialize LBPManager.\\n * @param _admin The address of the admin of the LBPManager.\\n * @param _beneficiary The address that receives the _fees.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\\n - The address of the project token being distributed.\\n - The address of the funding token being exchanged for the project token.\\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\\n - The amounts of project token to be added as liquidity to the LBP.\\n - The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\\n - The start weight for the project token in the LBP.\\n - The start weight for the funding token in the LBP.\\n * @param _startTimeEndtime Array containing two parameters:\\n - Start time for the LBP.\\n - End time for the LBP.\\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\\n - The end weight for the project token in the LBP.\\n - The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters:\\n - Percentage of fee paid for every swap in the LBP.\\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function deployLBPManager(\\n address _admin,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndtime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n // solhint-disable-next-line reason-string\\n require(\\n masterCopy != address(0),\\n \\\"LBPMFactory: LBPManager mastercopy not set\\\"\\n );\\n\\n address lbpManager = createClone(masterCopy);\\n\\n LBPManagerV1(lbpManager).initializeLBPManager(\\n lbpFactory,\\n _beneficiary,\\n _name,\\n _symbol,\\n _tokenList,\\n _amounts,\\n _startWeights,\\n _startTimeEndtime,\\n _endWeights,\\n _fees,\\n _metadata\\n );\\n\\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\\n\\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\\n }\\n}\\n\",\"keccak256\":\"0xe772adf0bbb0cf173f23527df5e6d94773ba5881b775aeb220fd669d0967ec61\",\"license\":\"GPL-3.0-or-later\"},\"contracts/lbp/LBPManagerV1.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract version 1\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManagerV1 {\\n bytes6 public version = \\\"1.0.0\\\";\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x75473a78174d66c360426296446d175f991d8dba1f047b387ce2e25452ca2991\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/CloneFactory.sol\":{\"content\":\"/*\\n\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n \\n*\\n* CloneFactory.sol was originally published under MIT license.\\n* Republished by PrimeDAO under GNU General Public License v3.0.\\n*\\n*/\\n\\n/*\\nThe MIT License (MIT)\\nCopyright (c) 2018 Murray Software, LLC.\\nPermission is hereby granted, free of charge, to any person obtaining\\na copy of this software and associated documentation files (the\\n\\\"Software\\\"), to deal in the Software without restriction, including\\nwithout limitation the rights to use, copy, modify, merge, publish,\\ndistribute, sublicense, and/or sell copies of the Software, and to\\npermit persons to whom the Software is furnished to do so, subject to\\nthe following conditions:\\nThe above copyright notice and this permission notice shall be included\\nin all copies or substantial portions of the Software.\\nTHE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// solium-disable linebreak-style\\n// solhint-disable max-line-length\\n// solhint-disable no-inline-assembly\\n\\npragma solidity 0.8.17;\\n\\ncontract CloneFactory {\\n function createClone(address target) internal returns (address result) {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\\n )\\n mstore(add(clone, 0x14), targetBytes)\\n mstore(\\n add(clone, 0x28),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n result := create(0, clone, 0x37)\\n }\\n }\\n\\n function isClone(address target, address query)\\n internal\\n view\\n returns (bool result)\\n {\\n bytes20 targetBytes = bytes20(target);\\n assembly {\\n let clone := mload(0x40)\\n mstore(\\n clone,\\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\\n )\\n mstore(add(clone, 0xa), targetBytes)\\n mstore(\\n add(clone, 0x1e),\\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\\n )\\n\\n let other := add(clone, 0x40)\\n extcodecopy(query, other, 0, 0x2d)\\n result := and(\\n eq(mload(clone), mload(other)),\\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\\n )\\n }\\n }\\n}\\n\",\"keccak256\":\"0x80b3d45006df787a887103ca0704f7eed17848ded1c944e494eb2de0274b2f71\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x60806040526000805465ffffffffffff60a01b1916640312e302e360ac1b17905534801561002c57600080fd5b50604051610d94380380610d9483398101604081905261004b91610123565b610054336100d3565b6001600160a01b0381166100ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d466163746f72793a204c4250466163746f7279206973207a65726f00604482015260640160405180910390fd5b600280546001600160a01b0319166001600160a01b0392909216919091179055610153565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006020828403121561013557600080fd5b81516001600160a01b038116811461014c57600080fd5b9392505050565b610c32806101626000396000f3fe608060405234801561001057600080fd5b50600436106100935760003560e01c8063a619486e11610066578063a619486e1461010c578063c18b51511461011f578063cf497e6c14610132578063f2fde38b14610145578063fd3bd38a1461015857600080fd5b806354fd4d5014610098578063715018a6146100ca5780637679a4c1146100d45780638da5cb5b146100e7575b600080fd5b6000546100ac90600160a01b900460d01b81565b6040516001600160d01b031990911681526020015b60405180910390f35b6100d261016b565b005b6100d26100e2366004610696565b61017f565b6000546001600160a01b03165b6040516001600160a01b0390911681526020016100c1565b6001546100f4906001600160a01b031681565b6002546100f4906001600160a01b031681565b6100d2610140366004610696565b610268565b6100d2610153366004610696565b61034c565b6100d2610166366004610864565b6103c5565b610173610575565b61017d60006105cf565b565b610187610575565b806001600160a01b0381166101e35760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b0382160361020b5760405162461bcd60e51b81526004016101da906109fa565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610270610575565b806001600160a01b0381166102c75760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101da565b306001600160a01b038216036102ef5760405162461bcd60e51b81526004016101da906109fa565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b610354610575565b6001600160a01b0381166103b95760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101da565b6103c2816105cf565b50565b6001546001600160a01b03166104305760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101da565b600154600090610448906001600160a01b031661061f565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261048f9216908f908f908f908f908f908f908f908f908f908f90600401610b02565b600060405180830381600087803b1580156104a957600080fd5b505af11580156104bd573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b15801561050457600080fd5b505af1158015610518573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161055f9190610be9565b60405180910390a3505050505050505050505050565b6000546001600160a01b0316331461017d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101da565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b03811681146103c257600080fd5b803561069181610671565b919050565b6000602082840312156106a857600080fd5b81356106b381610671565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106f9576106f96106ba565b604052919050565b600082601f83011261071257600080fd5b813567ffffffffffffffff81111561072c5761072c6106ba565b61073f601f8201601f19166020016106d0565b81815284602083860101111561075457600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561078b5761078b6106ba565b5060051b60200190565b600082601f8301126107a657600080fd5b813560206107bb6107b683610771565b6106d0565b82815260059290921b840181019181810190868411156107da57600080fd5b8286015b848110156107fe5780356107f181610671565b83529183019183016107de565b509695505050505050565b600082601f83011261081a57600080fd5b8135602061082a6107b683610771565b82815260059290921b8401810191818101908684111561084957600080fd5b8286015b848110156107fe578035835291830191830161084d565b60008060008060008060008060008060006101608c8e03121561088657600080fd5b61088f8c610686565b9a5061089d60208d01610686565b995067ffffffffffffffff8060408e013511156108b957600080fd5b6108c98e60408f01358f01610701565b99508060608e013511156108dc57600080fd5b6108ec8e60608f01358f01610701565b98508060808e013511156108ff57600080fd5b61090f8e60808f01358f01610795565b97508060a08e0135111561092257600080fd5b6109328e60a08f01358f01610809565b96508060c08e0135111561094557600080fd5b6109558e60c08f01358f01610809565b95508060e08e0135111561096857600080fd5b6109788e60e08f01358f01610809565b9450806101008e0135111561098c57600080fd5b61099d8e6101008f01358f01610809565b9350806101208e013511156109b157600080fd5b6109c28e6101208f01358f01610809565b9250806101408e013511156109d657600080fd5b506109e88d6101408e01358e01610701565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a6e57602081850181015186830182015201610a52565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610ac75781516001600160a01b031687529582019590820190600101610aa2565b509495945050505050565b600081518084526020808501945080840160005b83811015610ac757815187529582019590820190600101610ae6565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b348184018d610a48565b90508281036060840152610b48818c610a48565b90508281036080840152610b5c818b610a8e565b905082810360a0840152610b70818a610ad2565b905082810360c0840152610b848189610ad2565b905082810360e0840152610b988188610ad2565b9050828103610100840152610bad8187610ad2565b9050828103610120840152610bc28186610ad2565b9050828103610140840152610bd78185610a48565b9e9d5050505050505050505050505050565b6020815260006106b36020830184610a4856fea2646970667358221220889ac78df81d1379d6471d9899757d4a6e816b1390bb99b56cff15fc7aa3073464736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106100935760003560e01c8063a619486e11610066578063a619486e1461010c578063c18b51511461011f578063cf497e6c14610132578063f2fde38b14610145578063fd3bd38a1461015857600080fd5b806354fd4d5014610098578063715018a6146100ca5780637679a4c1146100d45780638da5cb5b146100e7575b600080fd5b6000546100ac90600160a01b900460d01b81565b6040516001600160d01b031990911681526020015b60405180910390f35b6100d261016b565b005b6100d26100e2366004610696565b61017f565b6000546001600160a01b03165b6040516001600160a01b0390911681526020016100c1565b6001546100f4906001600160a01b031681565b6002546100f4906001600160a01b031681565b6100d2610140366004610696565b610268565b6100d2610153366004610696565b61034c565b6100d2610166366004610864565b6103c5565b610173610575565b61017d60006105cf565b565b610187610575565b806001600160a01b0381166101e35760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064015b60405180910390fd5b306001600160a01b0382160361020b5760405162461bcd60e51b81526004016101da906109fa565b6002546040516001600160a01b038085169216907f877e5d562f57d3294803fbbd1e6715a2342eedb560cc540e97a9b77f03d12cbf90600090a350600280546001600160a01b0319166001600160a01b0392909216919091179055565b610270610575565b806001600160a01b0381166102c75760405162461bcd60e51b815260206004820152601c60248201527f4c42504d466163746f72793a2061646472657373206973207a65726f0000000060448201526064016101da565b306001600160a01b038216036102ef5760405162461bcd60e51b81526004016101da906109fa565b6001546040516001600160a01b038085169216907fb8c954c26b96c632ba5e28e879f889c124225199d6787047500b1eef41ff464190600090a350600180546001600160a01b0319166001600160a01b0392909216919091179055565b610354610575565b6001600160a01b0381166103b95760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b60648201526084016101da565b6103c2816105cf565b50565b6001546001600160a01b03166104305760405162461bcd60e51b815260206004820152602a60248201527f4c42504d466163746f72793a204c42504d616e61676572206d6173746572636f6044820152691c1e481b9bdd081cd95d60b21b60648201526084016101da565b600154600090610448906001600160a01b031661061f565b600254604051638638fe3160e01b81529192506001600160a01b0380841692638638fe319261048f9216908f908f908f908f908f908f908f908f908f908f90600401610b02565b600060405180830381600087803b1580156104a957600080fd5b505af11580156104bd573d6000803e3d6000fd5b505060405163b5106add60e01b81526001600160a01b038f811660048301528416925063b5106add9150602401600060405180830381600087803b15801561050457600080fd5b505af1158015610518573d6000803e3d6000fd5b505050508b6001600160a01b0316816001600160a01b03167f8b8a9c158a44eff86c91705dbc9c0479504c8de441156f3c2c21a6ed00e1627a8460405161055f9190610be9565b60405180910390a3505050505050505050505050565b6000546001600160a01b0316331461017d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016101da565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000808260601b9050604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b81528160148201526e5af43d82803e903d91602b57fd5bf360881b60288201526037816000f0949350505050565b6001600160a01b03811681146103c257600080fd5b803561069181610671565b919050565b6000602082840312156106a857600080fd5b81356106b381610671565b9392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff811182821017156106f9576106f96106ba565b604052919050565b600082601f83011261071257600080fd5b813567ffffffffffffffff81111561072c5761072c6106ba565b61073f601f8201601f19166020016106d0565b81815284602083860101111561075457600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561078b5761078b6106ba565b5060051b60200190565b600082601f8301126107a657600080fd5b813560206107bb6107b683610771565b6106d0565b82815260059290921b840181019181810190868411156107da57600080fd5b8286015b848110156107fe5780356107f181610671565b83529183019183016107de565b509695505050505050565b600082601f83011261081a57600080fd5b8135602061082a6107b683610771565b82815260059290921b8401810191818101908684111561084957600080fd5b8286015b848110156107fe578035835291830191830161084d565b60008060008060008060008060008060006101608c8e03121561088657600080fd5b61088f8c610686565b9a5061089d60208d01610686565b995067ffffffffffffffff8060408e013511156108b957600080fd5b6108c98e60408f01358f01610701565b99508060608e013511156108dc57600080fd5b6108ec8e60608f01358f01610701565b98508060808e013511156108ff57600080fd5b61090f8e60808f01358f01610795565b97508060a08e0135111561092257600080fd5b6109328e60a08f01358f01610809565b96508060c08e0135111561094557600080fd5b6109558e60c08f01358f01610809565b95508060e08e0135111561096857600080fd5b6109788e60e08f01358f01610809565b9450806101008e0135111561098c57600080fd5b61099d8e6101008f01358f01610809565b9350806101208e013511156109b157600080fd5b6109c28e6101208f01358f01610809565b9250806101408e013511156109d657600080fd5b506109e88d6101408e01358e01610701565b90509295989b509295989b9093969950565b6020808252602e908201527f4c42504d466163746f72793a20616464726573732073616d65206173204c425060408201526d4d616e61676572466163746f727960901b606082015260800190565b6000815180845260005b81811015610a6e57602081850181015186830182015201610a52565b506000602082860101526020601f19601f83011685010191505092915050565b600081518084526020808501945080840160005b83811015610ac75781516001600160a01b031687529582019590820190600101610aa2565b509495945050505050565b600081518084526020808501945080840160005b83811015610ac757815187529582019590820190600101610ae6565b6001600160a01b038c16815260006101606001600160a01b038d166020840152806040840152610b348184018d610a48565b90508281036060840152610b48818c610a48565b90508281036080840152610b5c818b610a8e565b905082810360a0840152610b70818a610ad2565b905082810360c0840152610b848189610ad2565b905082810360e0840152610b988188610ad2565b9050828103610100840152610bad8187610ad2565b9050828103610120840152610bc28186610ad2565b9050828103610140840152610bd78185610a48565b9e9d5050505050505050505050505050565b6020815260006106b36020830184610a4856fea2646970667358221220889ac78df81d1379d6471d9899757d4a6e816b1390bb99b56cff15fc7aa3073464736f6c63430008110033", + "devdoc": { + "details": "Governance to create new LBPManager contract without the onlyOwner modifer for the function deployLBPManager(). By removing the access control, everyone can deploy a LBPManager from this contract. This is a temporarly solution in response to the flaky Celo Safe.", + "kind": "dev", + "methods": { + "constructor": { + "details": "Constructor.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "deployLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Deploy and initialize LBPManager.", + "params": { + "_admin": "The address of the admin of the LBPManager.", + "_amounts": "Sorted array to match the _tokenList, containing two parameters: - The amounts of project token to be added as liquidity to the LBP. - The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the _fees.", + "_endWeights": "Sorted array to match the _tokenList, containing two parametes: - The end weight for the project token in the LBP. - The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters: - Percentage of fee paid for every swap in the LBP. - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndtime": "Array containing two parameters: - Start time for the LBP. - End time for the LBP.", + "_startWeights": "Sorted array to match the _tokenList, containing two parametes: - The start weight for the project token in the LBP. - The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Numerically sorted array (ascending) containing two addresses: - The address of the project token being distributed. - The address of the funding token being exchanged for the project token." + } + }, + "owner()": { + "details": "Returns the address of the current owner." + }, + "renounceOwnership()": { + "details": "Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner." + }, + "setLBPFactory(address)": { + "details": "Set Balancers LBP Factory contract as basis for deploying LBPs.", + "params": { + "_lbpFactory": "The address of Balancers LBP factory." + } + }, + "setMasterCopy(address)": { + "details": "Set LBPManager contract which works as a base for clones.", + "params": { + "_masterCopy": "The address of the new LBPManager basis." + } + }, + "transferOwnership(address)": { + "details": "Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner." + } + }, + "title": "LBPManager Factory no access control version 1", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 7, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "_owner", + "offset": 0, + "slot": "0", + "type": "t_address" + }, + { + "astId": 434, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "version", + "offset": 20, + "slot": "0", + "type": "t_bytes6" + }, + { + "astId": 436, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "masterCopy", + "offset": 0, + "slot": "1", + "type": "t_address" + }, + { + "astId": 438, + "contract": "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol:LBPManagerFactoryV1NoAccessControl", + "label": "lbpFactory", + "offset": 0, + "slot": "2", + "type": "t_address" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_bytes6": { + "encoding": "inplace", + "label": "bytes6", + "numberOfBytes": "6" + } + } + } +} \ No newline at end of file diff --git a/deployments/goerli/LBPManagerV1.json b/deployments/goerli/LBPManagerV1.json new file mode 100644 index 0000000..9721df6 --- /dev/null +++ b/deployments/goerli/LBPManagerV1.json @@ -0,0 +1,811 @@ +{ + "address": "0xe5864D50764DB0Fa8266912FC6576100e75b35eB", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "transactionHash": "0xb6e6ae0d8f669fad587eca515b3bce5760712d2d565ed40965d5feda5dec3990", + "receipt": { + "to": null, + "from": "0xc039897eE5A0d14A3d1F212922FaF7e159Ab619F", + "contractAddress": "0xe5864D50764DB0Fa8266912FC6576100e75b35eB", + "transactionIndex": 80, + "gasUsed": "2335541", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "blockHash": "0x6d536104c0edc2406c471b79bf9214bf86ef53a4915065b9397c45d79cd1cf79", + "transactionHash": "0xb6e6ae0d8f669fad587eca515b3bce5760712d2d565ed40965d5feda5dec3990", + "logs": [], + "blockNumber": 8092135, + "cumulativeGasUsed": "26591287", + "status": 1, + "byzantium": true + }, + "args": [], + "solcInputHash": "752d54b8f64e3608832db5b1be68e60f", + "metadata": "{\"compiler\":{\"version\":\"0.8.17+commit.8df45f5f\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"beneficiary\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"tokenAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"FeeTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"oldAdmin\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newAdmin\",\"type\":\"address\"}],\"name\":\"LBPManagerAdminChanged\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes\",\"name\":\"metadata\",\"type\":\"bytes\"}],\"name\":\"MetadataUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"lbpAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"PoolTokensWithdrawn\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"admin\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"amounts\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"beneficiary\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"endWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"feePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getSwapEnabled\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_sender\",\"type\":\"address\"}],\"name\":\"initializeLBP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_lbpFactory\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_beneficiary\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"_name\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"_symbol\",\"type\":\"string\"},{\"internalType\":\"contract IERC20[]\",\"name\":\"_tokenList\",\"type\":\"address[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_amounts\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_startTimeEndTime\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_endWeights\",\"type\":\"uint256[]\"},{\"internalType\":\"uint256[]\",\"name\":\"_fees\",\"type\":\"uint256[]\"},{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"initializeLBPManager\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"initialized\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbp\",\"outputs\":[{\"internalType\":\"contract ILBP\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lbpFactory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"metadata\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"name\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"poolFunded\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokenIndex\",\"outputs\":[{\"internalType\":\"uint8\",\"name\":\"\",\"type\":\"uint8\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"projectTokensRequired\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"projectTokenAmounts\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"removeLiquidity\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bool\",\"name\":\"_swapEnabled\",\"type\":\"bool\"}],\"name\":\"setSwapEnabled\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startTimeEndTime\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"startWeights\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"swapFeePercentage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"symbol\",\"outputs\":[{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"tokenList\",\"outputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_newAdmin\",\"type\":\"address\"}],\"name\":\"transferAdminRights\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes\",\"name\":\"_metadata\",\"type\":\"bytes\"}],\"name\":\"updateMetadata\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"version\",\"outputs\":[{\"internalType\":\"bytes6\",\"name\":\"\",\"type\":\"bytes6\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_receiver\",\"type\":\"address\"}],\"name\":\"withdrawPoolTokens\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"details\":\"Smart contract for managing interactions with a Balancer LBP.\",\"kind\":\"dev\",\"methods\":{\"getSwapEnabled()\":{\"details\":\"Tells whether swaps are enabled or not for the LBP\"},\"initializeLBP(address)\":{\"details\":\"Subtracts the fee, deploys the LBP and adds liquidity to it.\",\"params\":{\"_sender\":\"Address of the liquidity provider.\"}},\"initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)\":{\"details\":\"Initialize LBPManager.\",\"params\":{\"_amounts\":\"Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.\",\"_beneficiary\":\"The address that receives the feePercentage.\",\"_endWeights\":\"Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.\",\"_fees\":\"Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\",\"_lbpFactory\":\"LBP factory address.\",\"_metadata\":\"IPFS Hash of the LBP creation wizard information.\",\"_name\":\"Name of the LBP.\",\"_startTimeEndTime\":\"Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.\",\"_startWeights\":\"Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.\",\"_symbol\":\"Symbol of the LBP.\",\"_tokenList\":\"Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token.\"}},\"projectTokensRequired()\":{\"details\":\"Get required amount of project tokens to cover for fees and the actual LBP.\"},\"removeLiquidity(address)\":{\"details\":\"Exit pool or remove liquidity from pool.\",\"params\":{\"_receiver\":\"Address of the liquidity receiver, after exiting the LBP.\"}},\"setSwapEnabled(bool)\":{\"details\":\"Can pause/unpause trading.\",\"params\":{\"_swapEnabled\":\"Enables/disables swapping.\"}},\"transferAdminRights(address)\":{\"details\":\"Transfer admin rights.\",\"params\":{\"_newAdmin\":\"Address of the new admin.\"}},\"updateMetadata(bytes)\":{\"details\":\"Updates metadata.\",\"params\":{\"_metadata\":\"LBP wizard contract metadata, that is an IPFS Hash.\"}},\"withdrawPoolTokens(address)\":{\"details\":\"Withdraw pool tokens if available.\",\"params\":{\"_receiver\":\"Address of the BPT tokens receiver.\"}}},\"title\":\"LBPManager contract version 1\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{},\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/lbp/LBPManagerV1.sol\":\"LBPManagerV1\"},\"evmVersion\":\"london\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":200},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n /**\\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n * another (`to`).\\n *\\n * Note that `value` may be zero.\\n */\\n event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n /**\\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n * a call to {approve}. `value` is the new allowance.\\n */\\n event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n /**\\n * @dev Returns the amount of tokens in existence.\\n */\\n function totalSupply() external view returns (uint256);\\n\\n /**\\n * @dev Returns the amount of tokens owned by `account`.\\n */\\n function balanceOf(address account) external view returns (uint256);\\n\\n /**\\n * @dev Moves `amount` tokens from the caller's account to `to`.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transfer(address to, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Returns the remaining number of tokens that `spender` will be\\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n * zero by default.\\n *\\n * This value changes when {approve} or {transferFrom} are called.\\n */\\n function allowance(address owner, address spender) external view returns (uint256);\\n\\n /**\\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n * that someone may use both the old and the new allowance by unfortunate\\n * transaction ordering. One possible solution to mitigate this race\\n * condition is to first reduce the spender's allowance to 0 and set the\\n * desired value afterwards:\\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n *\\n * Emits an {Approval} event.\\n */\\n function approve(address spender, uint256 amount) external returns (bool);\\n\\n /**\\n * @dev Moves `amount` tokens from `from` to `to` using the\\n * allowance mechanism. `amount` is then deducted from the caller's\\n * allowance.\\n *\\n * Returns a boolean value indicating whether the operation succeeded.\\n *\\n * Emits a {Transfer} event.\\n */\\n function transferFrom(\\n address from,\\n address to,\\n uint256 amount\\n ) external returns (bool);\\n}\\n\",\"keccak256\":\"0x9750c6b834f7b43000631af5cc30001c5f547b3ceb3635488f140f60e897ea6b\",\"license\":\"MIT\"},\"contracts/lbp/LBPManagerV1.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\\n// Copyright (C) 2021 PrimeDao\\n\\n// solium-disable linebreak-style\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"../utils/interface/ILBPFactory.sol\\\";\\nimport \\\"../utils/interface/IVault.sol\\\";\\nimport \\\"../utils/interface/ILBP.sol\\\";\\n\\n/**\\n * @title LBPManager contract version 1\\n * @dev Smart contract for managing interactions with a Balancer LBP.\\n */\\n// solhint-disable-next-line max-states-count\\ncontract LBPManagerV1 {\\n bytes6 public version = \\\"1.0.0\\\";\\n // Constants\\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\\n\\n // Locked parameter\\n string public symbol; // Symbol of the LBP.\\n string public name; // Name of the LBP.\\n address public admin; // Address of the admin of this contract.\\n address public beneficiary; // Address that recieves fees.\\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\\n ILBP public lbp; // Address of LBP that is managed by this contract.\\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\\n address public lbpFactory; // Address of Balancers LBP factory.\\n\\n // Contract logic\\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\\n\\n event LBPManagerAdminChanged(\\n address indexed oldAdmin,\\n address indexed newAdmin\\n );\\n event FeeTransferred(\\n address indexed beneficiary,\\n address tokenAddress,\\n uint256 amount\\n );\\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\\n event MetadataUpdated(bytes indexed metadata);\\n\\n modifier onlyAdmin() {\\n require(msg.sender == admin, \\\"LBPManager: caller is not admin\\\");\\n _;\\n }\\n\\n /**\\n * @dev Transfer admin rights.\\n * @param _newAdmin Address of the new admin.\\n */\\n function transferAdminRights(address _newAdmin) external onlyAdmin {\\n require(_newAdmin != address(0), \\\"LBPManager: new admin is zero\\\");\\n\\n emit LBPManagerAdminChanged(admin, _newAdmin);\\n admin = _newAdmin;\\n }\\n\\n /**\\n * @dev Initialize LBPManager.\\n * @param _lbpFactory LBP factory address.\\n * @param _beneficiary The address that receives the feePercentage.\\n * @param _name Name of the LBP.\\n * @param _symbol Symbol of the LBP.\\n * @param _tokenList Array containing two addresses in order of:\\n 1. The address of the project token being distributed.\\n 2. The address of the funding token being exchanged for the project token.\\n * @param _amounts Array containing two parameters in order of:\\n 1. The amounts of project token to be added as liquidity to the LBP.\\n 2. The amounts of funding token to be added as liquidity to the LBP.\\n * @param _startWeights Array containing two parametes in order of:\\n 1. The start weight for the project token in the LBP.\\n 2. The start weight for the funding token in the LBP.\\n * @param _startTimeEndTime Array containing two parameters in order of:\\n 1. Start time for the LBP.\\n 2. End time for the LBP.\\n * @param _endWeights Array containing two parametes in order of:\\n 1. The end weight for the project token in the LBP.\\n 2. The end weight for the funding token in the LBP.\\n * @param _fees Array containing two parameters in order of:\\n 1. Percentage of fee paid for every swap in the LBP.\\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\\n * @param _metadata IPFS Hash of the LBP creation wizard information.\\n */\\n function initializeLBPManager(\\n address _lbpFactory,\\n address _beneficiary,\\n string memory _name,\\n string memory _symbol,\\n IERC20[] memory _tokenList,\\n uint256[] memory _amounts,\\n uint256[] memory _startWeights,\\n uint256[] memory _startTimeEndTime,\\n uint256[] memory _endWeights,\\n uint256[] memory _fees,\\n bytes memory _metadata\\n ) external {\\n require(!initialized, \\\"LBPManager: already initialized\\\");\\n require(_beneficiary != address(0), \\\"LBPManager: _beneficiary is zero\\\");\\n // solhint-disable-next-line reason-string\\n require(_fees[0] >= 1e12, \\\"LBPManager: swapFeePercentage to low\\\"); // 0.0001%\\n // solhint-disable-next-line reason-string\\n require(_fees[0] <= 1e17, \\\"LBPManager: swapFeePercentage to high\\\"); // 10%\\n require(\\n _tokenList.length == 2 &&\\n _amounts.length == 2 &&\\n _startWeights.length == 2 &&\\n _startTimeEndTime.length == 2 &&\\n _endWeights.length == 2 &&\\n _fees.length == 2,\\n \\\"LBPManager: arrays wrong size\\\"\\n );\\n require(\\n _tokenList[0] != _tokenList[1],\\n \\\"LBPManager: tokens can't be same\\\"\\n );\\n require(\\n _startTimeEndTime[0] < _startTimeEndTime[1],\\n \\\"LBPManager: startTime > endTime\\\"\\n );\\n\\n initialized = true;\\n admin = msg.sender;\\n swapFeePercentage = _fees[0];\\n feePercentage = _fees[1];\\n beneficiary = _beneficiary;\\n metadata = _metadata;\\n startTimeEndTime = _startTimeEndTime;\\n name = _name;\\n symbol = _symbol;\\n lbpFactory = _lbpFactory;\\n\\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\\n if (address(_tokenList[0]) > address(_tokenList[1])) {\\n projectTokenIndex = 1;\\n tokenList.push(_tokenList[1]);\\n tokenList.push(_tokenList[0]);\\n\\n amounts.push(_amounts[1]);\\n amounts.push(_amounts[0]);\\n\\n startWeights.push(_startWeights[1]);\\n startWeights.push(_startWeights[0]);\\n\\n endWeights.push(_endWeights[1]);\\n endWeights.push(_endWeights[0]);\\n } else {\\n projectTokenIndex = 0;\\n tokenList = _tokenList;\\n amounts = _amounts;\\n startWeights = _startWeights;\\n endWeights = _endWeights;\\n }\\n }\\n\\n /**\\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\\n * @param _sender Address of the liquidity provider.\\n */\\n function initializeLBP(address _sender) external onlyAdmin {\\n // solhint-disable-next-line reason-string\\n require(initialized == true, \\\"LBPManager: LBPManager not initialized\\\");\\n require(!poolFunded, \\\"LBPManager: pool already funded\\\");\\n poolFunded = true;\\n\\n lbp = ILBP(\\n ILBPFactory(lbpFactory).create(\\n name,\\n symbol,\\n tokenList,\\n startWeights,\\n swapFeePercentage,\\n address(this),\\n false // SwapEnabled is set to false at pool creation.\\n )\\n );\\n\\n lbp.updateWeightsGradually(\\n startTimeEndTime[0],\\n startTimeEndTime[1],\\n endWeights\\n );\\n\\n IVault vault = lbp.getVault();\\n\\n if (feePercentage != 0) {\\n // Transfer fee to beneficiary.\\n uint256 feeAmountRequired = _feeAmountRequired();\\n tokenList[projectTokenIndex].transferFrom(\\n _sender,\\n beneficiary,\\n feeAmountRequired\\n );\\n emit FeeTransferred(\\n beneficiary,\\n address(tokenList[projectTokenIndex]),\\n feeAmountRequired\\n );\\n }\\n\\n for (uint8 i; i < tokenList.length; i++) {\\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\\n tokenList[i].approve(address(vault), amounts[i]);\\n }\\n\\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\\n maxAmountsIn: amounts,\\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\\n assets: tokenList\\n });\\n\\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\\n }\\n\\n /**\\n * @dev Exit pool or remove liquidity from pool.\\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\\n */\\n function removeLiquidity(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n IVault vault = lbp.getVault();\\n\\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\\n userData: abi.encode(1, lbp.balanceOf(address(this))),\\n toInternalBalance: false,\\n assets: tokenList\\n });\\n\\n vault.exitPool(\\n lbp.getPoolId(),\\n address(this),\\n payable(_receiver),\\n request\\n );\\n }\\n\\n /*\\n DISCLAIMER:\\n The method below is an advanced functionality. By invoking this method, you are withdrawing\\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\\n */\\n /**\\n * @dev Withdraw pool tokens if available.\\n * @param _receiver Address of the BPT tokens receiver.\\n */\\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\\n require(_receiver != address(0), \\\"LBPManager: receiver is zero\\\");\\n\\n uint256 endTime = startTimeEndTime[1];\\n // solhint-disable-next-line not-rely-on-time\\n require(block.timestamp >= endTime, \\\"LBPManager: endtime not reached\\\");\\n\\n require(\\n lbp.balanceOf(address(this)) > 0,\\n \\\"LBPManager: no BPT token balance\\\"\\n );\\n\\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\\n }\\n\\n /**\\n * @dev Can pause/unpause trading.\\n * @param _swapEnabled Enables/disables swapping.\\n */\\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\\n lbp.setSwapEnabled(_swapEnabled);\\n }\\n\\n /**\\n * @dev Tells whether swaps are enabled or not for the LBP\\n */\\n function getSwapEnabled() external view returns (bool) {\\n require(poolFunded, \\\"LBPManager: LBP not initialized.\\\");\\n return lbp.getSwapEnabled();\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\\n */\\n function projectTokensRequired()\\n external\\n view\\n returns (uint256 projectTokenAmounts)\\n {\\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\\n }\\n\\n /**\\n * @dev Updates metadata.\\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\\n */\\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\\n metadata = _metadata;\\n emit MetadataUpdated(_metadata);\\n }\\n\\n /**\\n * @dev Get required amount of project tokens to cover for fees.\\n */\\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\\n feeAmount =\\n (amounts[projectTokenIndex] * feePercentage) /\\n HUNDRED_PERCENT;\\n }\\n}\\n\",\"keccak256\":\"0x75473a78174d66c360426296446d175f991d8dba1f047b387ce2e25452ca2991\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBP.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n/* solium-disable */\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\nimport \\\"./IVault.sol\\\";\\n\\npragma solidity 0.8.17;\\n\\ninterface ILBP is IERC20 {\\n function updateWeightsGradually(\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n ) external;\\n\\n function getGradualWeightUpdateParams()\\n external\\n view\\n returns (\\n uint256 startTime,\\n uint256 endTime,\\n uint256[] memory endWeights\\n );\\n\\n function getPoolId() external view returns (bytes32);\\n\\n function getVault() external view returns (IVault);\\n\\n function setSwapEnabled(bool swapEnabled) external;\\n\\n function getSwapEnabled() external view returns (bool);\\n\\n function getSwapFeePercentage() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0x709fe648167d6d9029c03ac0b20d6b043787de8b7244c44f3c0000c059878753\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/ILBPFactory.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface ILBPFactory {\\n function create(\\n string memory name,\\n string memory symbol,\\n IERC20[] memory tokens,\\n uint256[] memory weights,\\n uint256 swapFeePercentage,\\n address owner,\\n bool swapEnabledOnStart\\n ) external returns (address);\\n}\\n\",\"keccak256\":\"0x9e94580655bdf62157b303a4c295cddeb90655d7f53c27f2d371aeb8a75ab44f\",\"license\":\"GPL-3.0-or-later\"},\"contracts/utils/interface/IVault.sol\":{\"content\":\"/*\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2591\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u2550\\u255d\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\n\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2588\\u2588\\u2588\\u2588\\u2554\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2554\\u2550\\u2550\\u2550\\u255d\\u2591\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2557\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u255d\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2554\\u2550\\u2550\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\n\\u2588\\u2588\\u2551\\u2591\\u2591\\u2591\\u2591\\u2591\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2588\\u2588\\u2551\\u2591\\u255a\\u2550\\u255d\\u2591\\u2588\\u2588\\u2551\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2557\\u2588\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\u2588\\u2588\\u2551\\u2591\\u2591\\u2588\\u2588\\u2551\\u255a\\u2588\\u2588\\u2588\\u2588\\u2588\\u2554\\u255d\\n\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u255a\\u2550\\u255d\\u2591\\u2591\\u2591\\u2591\\u2591\\u255a\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u255a\\u2550\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\u255a\\u2550\\u255d\\u2591\\u2591\\u255a\\u2550\\u255d\\u2591\\u255a\\u2550\\u2550\\u2550\\u2550\\u255d\\u2591\\n*/\\n\\n// SPDX-License-Identifier: GPL-3.0-or-later\\n\\n/* solium-disable */\\npragma solidity 0.8.17;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IVault {\\n struct JoinPoolRequest {\\n IERC20[] assets;\\n uint256[] maxAmountsIn;\\n bytes userData;\\n bool fromInternalBalance;\\n }\\n\\n struct ExitPoolRequest {\\n IERC20[] assets;\\n uint256[] minAmountsOut;\\n bytes userData;\\n bool toInternalBalance;\\n }\\n\\n function joinPool(\\n bytes32 poolId,\\n address sender,\\n address recipient,\\n JoinPoolRequest memory request\\n ) external payable;\\n\\n function exitPool(\\n bytes32 poolId,\\n address sender,\\n address payable recipient,\\n ExitPoolRequest memory request\\n ) external;\\n}\\n\",\"keccak256\":\"0x7e420b91c0b4c2c27c9467335b34522ff2f33622cfe40f6cd66596eab99203b7\",\"license\":\"GPL-3.0-or-later\"}},\"version\":1}", + "bytecode": "0x60806040526000805465ffffffffffff191665312e302e300017905534801561002757600080fd5b506128e2806100376000396000f3fe608060405234801561001057600080fd5b50600436106101a95760003560e01c80639ead7222116100f9578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461038c578063e01af92c1461039f578063f851a440146103b2578063fc582d41146103c557600080fd5b8063c9d8616f14610347578063cb209b6c1461035a578063cd2055e51461037957600080fd5b8063a88971fa116100d3578063a88971fa146102f5578063b5106add14610309578063bb7bfb0c1461031c578063c18b51511461032f57600080fd5b80639ead7222146102d0578063a001ecdd146102e3578063a4ac0d49146102ec57600080fd5b80633facbb851161016657806354fd4d501161014057806354fd4d501461027c5780638638fe31146102a25780638bfd5289146102b557806395d89b41146102c857600080fd5b80633facbb851461024c57806345f0a44f1461026157806347bc4d921461027457600080fd5b806306fdde03146101ae578063092f7de7146101cc578063158ef93e146101f75780633281f3ec1461021b57806338af3eed14610231578063392f37e914610244575b600080fd5b6101b66103d8565b6040516101c39190611f4c565b60405180910390f35b600c546101df906001600160a01b031681565b6040516001600160a01b0390911681526020016101c3565b600e5461020b90600160b01b900460ff1681565b60405190151581526020016101c3565b610223610466565b6040519081526020016101c3565b6004546101df906001600160a01b031681565b6101b66104a5565b61025f61025a366004611f8e565b6104b2565b005b61022361026f366004611fab565b6107f3565b61020b610814565b6000546102899060d01b81565b6040516001600160d01b031990911681526020016101c3565b61025f6102b036600461216e565b6108e7565b61025f6102c3366004611f8e565b610fca565b6101b661175b565b6101df6102de366004611fab565b611768565b61022360055481565b61022360065481565b600e5461020b90600160a81b900460ff1681565b61025f610317366004611f8e565b611792565b61022361032a366004611fab565b61186e565b600e546101df9061010090046001600160a01b031681565b610223610355366004611fab565b61187e565b600e546103679060ff1681565b60405160ff90911681526020016101c3565b610223610387366004611fab565b61188e565b61025f61039a366004611f8e565b61189e565b61025f6103ad366004612312565b611cf6565b6003546101df906001600160a01b031681565b61025f6103d336600461232f565b611d82565b600280546103e59061236c565b80601f01602080910402602001604051908101604052809291908181526020018280546104119061236c565b801561045e5780601f106104335761010080835404028352916020019161045e565b820191906000526020600020905b81548152906001019060200180831161044157829003601f168201915b505050505081565b6000610470611dfa565b600e5460088054909160ff1690811061048b5761048b6123a6565b90600052602060002001546104a091906123d2565b905090565b600d80546103e59061236c565b6003546001600160a01b031633146104e55760405162461bcd60e51b81526004016104dc906123eb565b60405180910390fd5b6001600160a01b03811661053b5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b6000600b600181548110610551576105516123a6565b90600052602060002001549050804210156105ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105f7573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061061b9190612422565b116106685760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b600c546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa1580156106d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106f89190612422565b60405190815260200160405180910390a2600c546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561075b573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061077f9190612422565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af11580156107ca573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ee919061243b565b505050565b6008818154811061080357600080fd5b600091825260209091200154905081565b600e54600090600160a81b900460ff166108705760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e60448201526064016104dc565b600c60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa1580156108c3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104a0919061243b565b600e54600160b01b900460ff16156109415760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a65640060448201526064016104dc565b6001600160a01b038a166109975760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f60448201526064016104dc565b64e8d4a51000826000815181106109b0576109b06123a6565b60200260200101511015610a125760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b60648201526084016104dc565b67016345785d8a000082600081518110610a2e57610a2e6123a6565b60200260200101511115610a925760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b60648201526084016104dc565b86516002148015610aa4575085516002145b8015610ab1575084516002145b8015610abe575083516002145b8015610acb575082516002145b8015610ad8575081516002145b610b245760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a6500000060448201526064016104dc565b86600181518110610b3757610b376123a6565b60200260200101516001600160a01b031687600081518110610b5b57610b5b6123a6565b60200260200101516001600160a01b031603610bb95760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d6560448201526064016104dc565b83600181518110610bcc57610bcc6123a6565b602002602001015184600081518110610be757610be76123a6565b602002602001015110610c3c5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d650060448201526064016104dc565b600e805460ff60b01b1916600160b01b179055600380546001600160a01b0319163317905581518290600090610c7457610c746123a6565b602002602001015160068190555081600181518110610c9557610c956123a6565b6020908102919091010151600555600480546001600160a01b0319166001600160a01b038c16179055600d610cca82826124a6565b508351610cde90600b906020870190611e47565b506002610ceb8a826124a6565b506001610cf889826124a6565b50600e8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610d2e57610d2e6123a6565b60200260200101516001600160a01b031687600081518110610d5257610d526123a6565b60200260200101516001600160a01b03161115610f6257600e805460ff19166001908117909155875160079189918110610d8e57610d8e6123a6565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516007918991610ddd57610ddd6123a6565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160089188918110610e3157610e316123a6565b602090810291909101810151825460018101845560009384529183209091015586516008918891610e6457610e646123a6565b60209081029190910181015182546001818101855560009485529290932090920191909155855160099187918110610e9e57610e9e6123a6565b602090810291909101810151825460018101845560009384529183209091015585516009918791610ed157610ed16123a6565b602090810291909101810151825460018181018555600094855292909320909201919091558351600a9185918110610f0b57610f0b6123a6565b60209081029190910181015182546001810184556000938452918320909101558351600a918591610f3e57610f3e6123a6565b60209081029190910181015182546001810184556000938452919092200155610fbd565b600e805460ff191690558651610f7f9060079060208a0190611e92565b508551610f93906008906020890190611e47565b508451610fa7906009906020880190611e47565b508251610fbb90600a906020860190611e47565b505b5050505050505050505050565b6003546001600160a01b03163314610ff45760405162461bcd60e51b81526004016104dc906123eb565b600e54600160b01b900460ff1615156001146110615760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b60648201526084016104dc565b600e54600160a81b900460ff16156110bb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e6465640060448201526064016104dc565b600e8054600160a81b60ff60a81b199091161790819055600654604051632367971960e01b81526101009092046001600160a01b031691632367971991611115916002916001916007916009913090600090600401612623565b6020604051808303816000875af1158015611134573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061115891906126d4565b600c80546001600160a01b0319166001600160a01b03929092169182179055600b8054633e5692059190600090611191576111916123a6565b9060005260206000200154600b6001815481106111b0576111b06123a6565b9060005260206000200154600a6040518463ffffffff1660e01b81526004016111db939291906126f1565b600060405180830381600087803b1580156111f557600080fd5b505af1158015611209573d6000803e3d6000fd5b505050506000600c60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611262573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128691906126d4565b90506005546000146113c257600061129c611dfa565b600e54600780549293509160ff9091169081106112bb576112bb6123a6565b600091825260209091200154600480546040516323b872dd60e01b81526001600160a01b03878116938201939093529082166024820152604481018490529116906323b872dd906064016020604051808303816000875af1158015611324573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611348919061243b565b50600454600e54600780546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff16908110611393576113936123a6565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60075460ff8216101561158c5760078160ff16815481106113e8576113e86123a6565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060088560ff168154811061142c5761142c6123a6565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af115801561148c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114b0919061243b565b5060078160ff16815481106114c7576114c76123a6565b600091825260209091200154600880546001600160a01b039092169163095ea7b391859160ff86169081106114fe576114fe6123a6565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611555573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611579919061243b565b508061158481612719565b9150506113c5565b50604080516007805460a060208202840181019094526080830181815260009484939192908401828280156115ea57602002820191906000526020600020905b81546001600160a01b031681526001909101906020018083116115cc575b50505050508152602001600880548060200260200160405190810160405280929190818152602001828054801561164057602002820191906000526020600020905b81548152602001906001019080831161162c575b505050505081526020016000600860405160200161165f929190612738565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa1580156116de573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906117029190612422565b3030856040518563ffffffff1660e01b8152600401611724949392919061281b565b600060405180830381600087803b15801561173e57600080fd5b505af1158015611752573d6000803e3d6000fd5b50505050505050565b600180546103e59061236c565b6007818154811061177857600080fd5b6000918252602090912001546001600160a01b0316905081565b6003546001600160a01b031633146117bc5760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b0381166118125760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f00000060448201526064016104dc565b6003546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b6009818154811061080357600080fd5b600a818154811061080357600080fd5b600b818154811061080357600080fd5b6003546001600160a01b031633146118c85760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b03811661191e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611967573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061198b9190612422565b116119d85760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b6000600b6001815481106119ee576119ee6123a6565b9060005260206000200154905080421015611a4b5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a95573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ab991906126d4565b9050600060405180608001604052806007805480602002602001604051908101604052809291908181526020018280548015611b1e57602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611b00575b5050505050815260200160078054905067ffffffffffffffff811115611b4657611b46611fc4565b604051908082528060200260200182016040528015611b6f578160200160208202803683370190505b508152600c546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190612422565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c78573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c9c9190612422565b3087856040518563ffffffff1660e01b8152600401611cbe949392919061281b565b600060405180830381600087803b158015611cd857600080fd5b505af1158015611cec573d6000803e3d6000fd5b5050505050505050565b6003546001600160a01b03163314611d205760405162461bcd60e51b81526004016104dc906123eb565b600c54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d6757600080fd5b505af1158015611d7b573d6000803e3d6000fd5b5050505050565b6003546001600160a01b03163314611dac5760405162461bcd60e51b81526004016104dc906123eb565b600d611db882826124a6565b5080604051611dc79190612857565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600554600e5460088054600093670de0b6b3a76400009390929160ff909116908110611e2857611e286123a6565b9060005260206000200154611e3d9190612873565b6104a0919061288a565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e82578251825591602001919060010190611e67565b50611e8e929150611ee7565b5090565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e8257825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611eb2565b5b80821115611e8e5760008155600101611ee8565b60005b83811015611f17578181015183820152602001611eff565b50506000910152565b60008151808452611f38816020860160208601611efc565b601f01601f19169290920160200192915050565b602081526000611f5f6020830184611f20565b9392505050565b6001600160a01b0381168114611f7b57600080fd5b50565b8035611f8981611f66565b919050565b600060208284031215611fa057600080fd5b8135611f5f81611f66565b600060208284031215611fbd57600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561200357612003611fc4565b604052919050565b600082601f83011261201c57600080fd5b813567ffffffffffffffff81111561203657612036611fc4565b612049601f8201601f1916602001611fda565b81815284602083860101111561205e57600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561209557612095611fc4565b5060051b60200190565b600082601f8301126120b057600080fd5b813560206120c56120c08361207b565b611fda565b82815260059290921b840181019181810190868411156120e457600080fd5b8286015b848110156121085780356120fb81611f66565b83529183019183016120e8565b509695505050505050565b600082601f83011261212457600080fd5b813560206121346120c08361207b565b82815260059290921b8401810191818101908684111561215357600080fd5b8286015b848110156121085780358352918301918301612157565b60008060008060008060008060008060006101608c8e03121561219057600080fd5b6121998c611f7e565b9a506121a760208d01611f7e565b995067ffffffffffffffff8060408e013511156121c357600080fd5b6121d38e60408f01358f0161200b565b99508060608e013511156121e657600080fd5b6121f68e60608f01358f0161200b565b98508060808e0135111561220957600080fd5b6122198e60808f01358f0161209f565b97508060a08e0135111561222c57600080fd5b61223c8e60a08f01358f01612113565b96508060c08e0135111561224f57600080fd5b61225f8e60c08f01358f01612113565b95508060e08e0135111561227257600080fd5b6122828e60e08f01358f01612113565b9450806101008e0135111561229657600080fd5b6122a78e6101008f01358f01612113565b9350806101208e013511156122bb57600080fd5b6122cc8e6101208f01358f01612113565b9250806101408e013511156122e057600080fd5b506122f28d6101408e01358e0161200b565b90509295989b509295989b9093969950565b8015158114611f7b57600080fd5b60006020828403121561232457600080fd5b8135611f5f81612304565b60006020828403121561234157600080fd5b813567ffffffffffffffff81111561235857600080fd5b6123648482850161200b565b949350505050565b600181811c9082168061238057607f821691505b6020821081036123a057634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123e5576123e56123bc565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b60006020828403121561243457600080fd5b5051919050565b60006020828403121561244d57600080fd5b8151611f5f81612304565b601f8211156107ee57600081815260208120601f850160051c8101602086101561247f5750805b601f850160051c820191505b8181101561249e5782815560010161248b565b505050505050565b815167ffffffffffffffff8111156124c0576124c0611fc4565b6124d4816124ce845461236c565b84612458565b602080601f83116001811461250957600084156124f15750858301515b600019600386901b1c1916600185901b17855561249e565b600085815260208120601f198616915b8281101561253857888601518255948401946001909101908401612519565b50858210156125565787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600081546125738161236c565b80855260206001838116801561259057600181146125aa576125d8565b60ff1985168884015283151560051b8801830195506125d8565b866000528260002060005b858110156125d05781548a82018601529083019084016125b5565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b83811015612618578154875295820195600191820191016125fc565b509495945050505050565b60e08152600061263660e083018a612566565b8281036020840152612648818a612566565b8381036040850152885480825260008a815260208082209450909201915b8181101561268d5783546001600160a01b0316835260019384019360209093019201612666565b505083810360608501526126a181896125e3565b925050508460808301526126c060a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126e657600080fd5b8151611f5f81611f66565b83815282602082015260606040820152600061271060608301846125e3565b95945050505050565b600060ff821660ff810361272f5761272f6123bc565b60010192915050565b60ff8316815260406020820152600061236460408301846125e3565b600081518084526020808501945080840160005b8381101561261857815187529582019590820190600101612768565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127c95783516001600160a01b0316835292840192918401916001016127a4565b5050828501519150858103838701526127e28183612754565b92505050604083015184820360408601526127fd8282611f20565b9150506060830151612813606086018215159052565b509392505050565b8481526001600160a01b0384811660208301528316604082015260806060820181905260009061284d90830184612784565b9695505050505050565b60008251612869818460208701611efc565b9190910192915050565b80820281158282048414176123e5576123e56123bc565b6000826128a757634e487b7160e01b600052601260045260246000fd5b50049056fea2646970667358221220eb6a5eda73e8fe17bd4c717b89e7802172bdb3b8f73914eef5f8c1f8fd93f13664736f6c63430008110033", + "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106101a95760003560e01c80639ead7222116100f9578063c9d8616f11610097578063d798f86e11610071578063d798f86e1461038c578063e01af92c1461039f578063f851a440146103b2578063fc582d41146103c557600080fd5b8063c9d8616f14610347578063cb209b6c1461035a578063cd2055e51461037957600080fd5b8063a88971fa116100d3578063a88971fa146102f5578063b5106add14610309578063bb7bfb0c1461031c578063c18b51511461032f57600080fd5b80639ead7222146102d0578063a001ecdd146102e3578063a4ac0d49146102ec57600080fd5b80633facbb851161016657806354fd4d501161014057806354fd4d501461027c5780638638fe31146102a25780638bfd5289146102b557806395d89b41146102c857600080fd5b80633facbb851461024c57806345f0a44f1461026157806347bc4d921461027457600080fd5b806306fdde03146101ae578063092f7de7146101cc578063158ef93e146101f75780633281f3ec1461021b57806338af3eed14610231578063392f37e914610244575b600080fd5b6101b66103d8565b6040516101c39190611f4c565b60405180910390f35b600c546101df906001600160a01b031681565b6040516001600160a01b0390911681526020016101c3565b600e5461020b90600160b01b900460ff1681565b60405190151581526020016101c3565b610223610466565b6040519081526020016101c3565b6004546101df906001600160a01b031681565b6101b66104a5565b61025f61025a366004611f8e565b6104b2565b005b61022361026f366004611fab565b6107f3565b61020b610814565b6000546102899060d01b81565b6040516001600160d01b031990911681526020016101c3565b61025f6102b036600461216e565b6108e7565b61025f6102c3366004611f8e565b610fca565b6101b661175b565b6101df6102de366004611fab565b611768565b61022360055481565b61022360065481565b600e5461020b90600160a81b900460ff1681565b61025f610317366004611f8e565b611792565b61022361032a366004611fab565b61186e565b600e546101df9061010090046001600160a01b031681565b610223610355366004611fab565b61187e565b600e546103679060ff1681565b60405160ff90911681526020016101c3565b610223610387366004611fab565b61188e565b61025f61039a366004611f8e565b61189e565b61025f6103ad366004612312565b611cf6565b6003546101df906001600160a01b031681565b61025f6103d336600461232f565b611d82565b600280546103e59061236c565b80601f01602080910402602001604051908101604052809291908181526020018280546104119061236c565b801561045e5780601f106104335761010080835404028352916020019161045e565b820191906000526020600020905b81548152906001019060200180831161044157829003601f168201915b505050505081565b6000610470611dfa565b600e5460088054909160ff1690811061048b5761048b6123a6565b90600052602060002001546104a091906123d2565b905090565b600d80546103e59061236c565b6003546001600160a01b031633146104e55760405162461bcd60e51b81526004016104dc906123eb565b60405180910390fd5b6001600160a01b03811661053b5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b6000600b600181548110610551576105516123a6565b90600052602060002001549050804210156105ae5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa1580156105f7573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061061b9190612422565b116106685760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b600c546040516370a0823160e01b81523060048201526001600160a01b03909116907fd0b72dd3c0f971f9cf266fee8e4c7660231316a67c88a587fa8dfa398c9e13749082906370a0823190602401602060405180830381865afa1580156106d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106f89190612422565b60405190815260200160405180910390a2600c546040516370a0823160e01b81523060048201526001600160a01b039091169063a9059cbb90849083906370a0823190602401602060405180830381865afa15801561075b573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061077f9190612422565b6040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af11580156107ca573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107ee919061243b565b505050565b6008818154811061080357600080fd5b600091825260209091200154905081565b600e54600090600160a81b900460ff166108705760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a204c4250206e6f7420696e697469616c697a65642e60448201526064016104dc565b600c60009054906101000a90046001600160a01b03166001600160a01b03166347bc4d926040518163ffffffff1660e01b8152600401602060405180830381865afa1580156108c3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104a0919061243b565b600e54600160b01b900460ff16156109415760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20616c726561647920696e697469616c697a65640060448201526064016104dc565b6001600160a01b038a166109975760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a205f62656e6566696369617279206973207a65726f60448201526064016104dc565b64e8d4a51000826000815181106109b0576109b06123a6565b60200260200101511015610a125760405162461bcd60e51b8152602060048201526024808201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015263206c6f7760e01b60648201526084016104dc565b67016345785d8a000082600081518110610a2e57610a2e6123a6565b60200260200101511115610a925760405162461bcd60e51b815260206004820152602560248201527f4c42504d616e616765723a207377617046656550657263656e7461676520746f604482015264040d0d2ced60db1b60648201526084016104dc565b86516002148015610aa4575085516002145b8015610ab1575084516002145b8015610abe575083516002145b8015610acb575082516002145b8015610ad8575081516002145b610b245760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206172726179732077726f6e672073697a6500000060448201526064016104dc565b86600181518110610b3757610b376123a6565b60200260200101516001600160a01b031687600081518110610b5b57610b5b6123a6565b60200260200101516001600160a01b031603610bb95760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a20746f6b656e732063616e27742062652073616d6560448201526064016104dc565b83600181518110610bcc57610bcc6123a6565b602002602001015184600081518110610be757610be76123a6565b602002602001015110610c3c5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20737461727454696d65203e20656e6454696d650060448201526064016104dc565b600e805460ff60b01b1916600160b01b179055600380546001600160a01b0319163317905581518290600090610c7457610c746123a6565b602002602001015160068190555081600181518110610c9557610c956123a6565b6020908102919091010151600555600480546001600160a01b0319166001600160a01b038c16179055600d610cca82826124a6565b508351610cde90600b906020870190611e47565b506002610ceb8a826124a6565b506001610cf889826124a6565b50600e8054610100600160a81b0319166101006001600160a01b038e1602179055865187906001908110610d2e57610d2e6123a6565b60200260200101516001600160a01b031687600081518110610d5257610d526123a6565b60200260200101516001600160a01b03161115610f6257600e805460ff19166001908117909155875160079189918110610d8e57610d8e6123a6565b6020908102919091018101518254600181018455600093845291832090910180546001600160a01b0319166001600160a01b0390921691909117905587516007918991610ddd57610ddd6123a6565b60209081029190910181015182546001808201855560009485529290932090920180546001600160a01b0319166001600160a01b0390931692909217909155865160089188918110610e3157610e316123a6565b602090810291909101810151825460018101845560009384529183209091015586516008918891610e6457610e646123a6565b60209081029190910181015182546001818101855560009485529290932090920191909155855160099187918110610e9e57610e9e6123a6565b602090810291909101810151825460018101845560009384529183209091015585516009918791610ed157610ed16123a6565b602090810291909101810151825460018181018555600094855292909320909201919091558351600a9185918110610f0b57610f0b6123a6565b60209081029190910181015182546001810184556000938452918320909101558351600a918591610f3e57610f3e6123a6565b60209081029190910181015182546001810184556000938452919092200155610fbd565b600e805460ff191690558651610f7f9060079060208a0190611e92565b508551610f93906008906020890190611e47565b508451610fa7906009906020880190611e47565b508251610fbb90600a906020860190611e47565b505b5050505050505050505050565b6003546001600160a01b03163314610ff45760405162461bcd60e51b81526004016104dc906123eb565b600e54600160b01b900460ff1615156001146110615760405162461bcd60e51b815260206004820152602660248201527f4c42504d616e616765723a204c42504d616e61676572206e6f7420696e697469604482015265185b1a5e995960d21b60648201526084016104dc565b600e54600160a81b900460ff16156110bb5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20706f6f6c20616c72656164792066756e6465640060448201526064016104dc565b600e8054600160a81b60ff60a81b199091161790819055600654604051632367971960e01b81526101009092046001600160a01b031691632367971991611115916002916001916007916009913090600090600401612623565b6020604051808303816000875af1158015611134573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061115891906126d4565b600c80546001600160a01b0319166001600160a01b03929092169182179055600b8054633e5692059190600090611191576111916123a6565b9060005260206000200154600b6001815481106111b0576111b06123a6565b9060005260206000200154600a6040518463ffffffff1660e01b81526004016111db939291906126f1565b600060405180830381600087803b1580156111f557600080fd5b505af1158015611209573d6000803e3d6000fd5b505050506000600c60009054906101000a90046001600160a01b03166001600160a01b0316638d928af86040518163ffffffff1660e01b8152600401602060405180830381865afa158015611262573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128691906126d4565b90506005546000146113c257600061129c611dfa565b600e54600780549293509160ff9091169081106112bb576112bb6123a6565b600091825260209091200154600480546040516323b872dd60e01b81526001600160a01b03878116938201939093529082166024820152604481018490529116906323b872dd906064016020604051808303816000875af1158015611324573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611348919061243b565b50600454600e54600780546001600160a01b03909316927f1d6298f49fc15449b78df91fcca6812136edc2972366cb70aa0d9145a308cd319260ff16908110611393576113936123a6565b60009182526020918290200154604080516001600160a01b0390921682529181018590520160405180910390a2505b60005b60075460ff8216101561158c5760078160ff16815481106113e8576113e86123a6565b9060005260206000200160009054906101000a90046001600160a01b03166001600160a01b03166323b872dd843060088560ff168154811061142c5761142c6123a6565b6000918252602090912001546040516001600160e01b031960e086901b1681526001600160a01b03938416600482015292909116602483015260448201526064016020604051808303816000875af115801561148c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114b0919061243b565b5060078160ff16815481106114c7576114c76123a6565b600091825260209091200154600880546001600160a01b039092169163095ea7b391859160ff86169081106114fe576114fe6123a6565b6000918252602090912001546040516001600160e01b031960e085901b1681526001600160a01b03909216600483015260248201526044016020604051808303816000875af1158015611555573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611579919061243b565b508061158481612719565b9150506113c5565b50604080516007805460a060208202840181019094526080830181815260009484939192908401828280156115ea57602002820191906000526020600020905b81546001600160a01b031681526001909101906020018083116115cc575b50505050508152602001600880548060200260200160405190810160405280929190818152602001828054801561164057602002820191906000526020600020905b81548152602001906001019080831161162c575b505050505081526020016000600860405160200161165f929190612738565b6040516020818303038152906040528152602001600015158152509050816001600160a01b031663b95cac28600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa1580156116de573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906117029190612422565b3030856040518563ffffffff1660e01b8152600401611724949392919061281b565b600060405180830381600087803b15801561173e57600080fd5b505af1158015611752573d6000803e3d6000fd5b50505050505050565b600180546103e59061236c565b6007818154811061177857600080fd5b6000918252602090912001546001600160a01b0316905081565b6003546001600160a01b031633146117bc5760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b0381166118125760405162461bcd60e51b815260206004820152601d60248201527f4c42504d616e616765723a206e65772061646d696e206973207a65726f00000060448201526064016104dc565b6003546040516001600160a01b038084169216907f39324b4c6f0dfe086be64dee1dd0fff15f9055828415513052c73d8e178c75f590600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b6009818154811061080357600080fd5b600a818154811061080357600080fd5b600b818154811061080357600080fd5b6003546001600160a01b031633146118c85760405162461bcd60e51b81526004016104dc906123eb565b6001600160a01b03811661191e5760405162461bcd60e51b815260206004820152601c60248201527f4c42504d616e616765723a207265636569766572206973207a65726f0000000060448201526064016104dc565b600c546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a0823190602401602060405180830381865afa158015611967573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061198b9190612422565b116119d85760405162461bcd60e51b815260206004820181905260248201527f4c42504d616e616765723a206e6f2042505420746f6b656e2062616c616e636560448201526064016104dc565b6000600b6001815481106119ee576119ee6123a6565b9060005260206000200154905080421015611a4b5760405162461bcd60e51b815260206004820152601f60248201527f4c42504d616e616765723a20656e6474696d65206e6f7420726561636865640060448201526064016104dc565b600c54604080516311b2515f60e31b815290516000926001600160a01b031691638d928af89160048083019260209291908290030181865afa158015611a95573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611ab991906126d4565b9050600060405180608001604052806007805480602002602001604051908101604052809291908181526020018280548015611b1e57602002820191906000526020600020905b81546001600160a01b03168152600190910190602001808311611b00575b5050505050815260200160078054905067ffffffffffffffff811115611b4657611b46611fc4565b604051908082528060200260200182016040528015611b6f578160200160208202803683370190505b508152600c546040516370a0823160e01b81523060048201526020909201916001916001600160a01b0316906370a0823190602401602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190612422565b6040805160ff90931660208401528201526060016040516020818303038152906040528152602001600015158152509050816001600160a01b0316638bdb3913600c60009054906101000a90046001600160a01b03166001600160a01b03166338fff2d06040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c78573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c9c9190612422565b3087856040518563ffffffff1660e01b8152600401611cbe949392919061281b565b600060405180830381600087803b158015611cd857600080fd5b505af1158015611cec573d6000803e3d6000fd5b5050505050505050565b6003546001600160a01b03163314611d205760405162461bcd60e51b81526004016104dc906123eb565b600c54604051633806be4b60e21b815282151560048201526001600160a01b039091169063e01af92c90602401600060405180830381600087803b158015611d6757600080fd5b505af1158015611d7b573d6000803e3d6000fd5b5050505050565b6003546001600160a01b03163314611dac5760405162461bcd60e51b81526004016104dc906123eb565b600d611db882826124a6565b5080604051611dc79190612857565b604051908190038120907f09f579b21815d3f81581d32e97736ccba1cc89d1918e48da28e6e206acd9686490600090a250565b600554600e5460088054600093670de0b6b3a76400009390929160ff909116908110611e2857611e286123a6565b9060005260206000200154611e3d9190612873565b6104a0919061288a565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e82578251825591602001919060010190611e67565b50611e8e929150611ee7565b5090565b828054828255906000526020600020908101928215611e82579160200282015b82811115611e8257825182546001600160a01b0319166001600160a01b03909116178255602090920191600190910190611eb2565b5b80821115611e8e5760008155600101611ee8565b60005b83811015611f17578181015183820152602001611eff565b50506000910152565b60008151808452611f38816020860160208601611efc565b601f01601f19169290920160200192915050565b602081526000611f5f6020830184611f20565b9392505050565b6001600160a01b0381168114611f7b57600080fd5b50565b8035611f8981611f66565b919050565b600060208284031215611fa057600080fd5b8135611f5f81611f66565b600060208284031215611fbd57600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561200357612003611fc4565b604052919050565b600082601f83011261201c57600080fd5b813567ffffffffffffffff81111561203657612036611fc4565b612049601f8201601f1916602001611fda565b81815284602083860101111561205e57600080fd5b816020850160208301376000918101602001919091529392505050565b600067ffffffffffffffff82111561209557612095611fc4565b5060051b60200190565b600082601f8301126120b057600080fd5b813560206120c56120c08361207b565b611fda565b82815260059290921b840181019181810190868411156120e457600080fd5b8286015b848110156121085780356120fb81611f66565b83529183019183016120e8565b509695505050505050565b600082601f83011261212457600080fd5b813560206121346120c08361207b565b82815260059290921b8401810191818101908684111561215357600080fd5b8286015b848110156121085780358352918301918301612157565b60008060008060008060008060008060006101608c8e03121561219057600080fd5b6121998c611f7e565b9a506121a760208d01611f7e565b995067ffffffffffffffff8060408e013511156121c357600080fd5b6121d38e60408f01358f0161200b565b99508060608e013511156121e657600080fd5b6121f68e60608f01358f0161200b565b98508060808e0135111561220957600080fd5b6122198e60808f01358f0161209f565b97508060a08e0135111561222c57600080fd5b61223c8e60a08f01358f01612113565b96508060c08e0135111561224f57600080fd5b61225f8e60c08f01358f01612113565b95508060e08e0135111561227257600080fd5b6122828e60e08f01358f01612113565b9450806101008e0135111561229657600080fd5b6122a78e6101008f01358f01612113565b9350806101208e013511156122bb57600080fd5b6122cc8e6101208f01358f01612113565b9250806101408e013511156122e057600080fd5b506122f28d6101408e01358e0161200b565b90509295989b509295989b9093969950565b8015158114611f7b57600080fd5b60006020828403121561232457600080fd5b8135611f5f81612304565b60006020828403121561234157600080fd5b813567ffffffffffffffff81111561235857600080fd5b6123648482850161200b565b949350505050565b600181811c9082168061238057607f821691505b6020821081036123a057634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b808201808211156123e5576123e56123bc565b92915050565b6020808252601f908201527f4c42504d616e616765723a2063616c6c6572206973206e6f742061646d696e00604082015260600190565b60006020828403121561243457600080fd5b5051919050565b60006020828403121561244d57600080fd5b8151611f5f81612304565b601f8211156107ee57600081815260208120601f850160051c8101602086101561247f5750805b601f850160051c820191505b8181101561249e5782815560010161248b565b505050505050565b815167ffffffffffffffff8111156124c0576124c0611fc4565b6124d4816124ce845461236c565b84612458565b602080601f83116001811461250957600084156124f15750858301515b600019600386901b1c1916600185901b17855561249e565b600085815260208120601f198616915b8281101561253857888601518255948401946001909101908401612519565b50858210156125565787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600081546125738161236c565b80855260206001838116801561259057600181146125aa576125d8565b60ff1985168884015283151560051b8801830195506125d8565b866000528260002060005b858110156125d05781548a82018601529083019084016125b5565b890184019650505b505050505092915050565b6000815480845260208085019450836000528060002060005b83811015612618578154875295820195600191820191016125fc565b509495945050505050565b60e08152600061263660e083018a612566565b8281036020840152612648818a612566565b8381036040850152885480825260008a815260208082209450909201915b8181101561268d5783546001600160a01b0316835260019384019360209093019201612666565b505083810360608501526126a181896125e3565b925050508460808301526126c060a08301856001600160a01b03169052565b82151560c083015298975050505050505050565b6000602082840312156126e657600080fd5b8151611f5f81611f66565b83815282602082015260606040820152600061271060608301846125e3565b95945050505050565b600060ff821660ff810361272f5761272f6123bc565b60010192915050565b60ff8316815260406020820152600061236460408301846125e3565b600081518084526020808501945080840160005b8381101561261857815187529582019590820190600101612768565b8051608080845281519084018190526000916020919082019060a0860190845b818110156127c95783516001600160a01b0316835292840192918401916001016127a4565b5050828501519150858103838701526127e28183612754565b92505050604083015184820360408601526127fd8282611f20565b9150506060830151612813606086018215159052565b509392505050565b8481526001600160a01b0384811660208301528316604082015260806060820181905260009061284d90830184612784565b9695505050505050565b60008251612869818460208701611efc565b9190910192915050565b80820281158282048414176123e5576123e56123bc565b6000826128a757634e487b7160e01b600052601260045260246000fd5b50049056fea2646970667358221220eb6a5eda73e8fe17bd4c717b89e7802172bdb3b8f73914eef5f8c1f8fd93f13664736f6c63430008110033", + "devdoc": { + "details": "Smart contract for managing interactions with a Balancer LBP.", + "kind": "dev", + "methods": { + "getSwapEnabled()": { + "details": "Tells whether swaps are enabled or not for the LBP" + }, + "initializeLBP(address)": { + "details": "Subtracts the fee, deploys the LBP and adds liquidity to it.", + "params": { + "_sender": "Address of the liquidity provider." + } + }, + "initializeLBPManager(address,address,string,string,address[],uint256[],uint256[],uint256[],uint256[],uint256[],bytes)": { + "details": "Initialize LBPManager.", + "params": { + "_amounts": "Array containing two parameters in order of: 1. The amounts of project token to be added as liquidity to the LBP. 2. The amounts of funding token to be added as liquidity to the LBP.", + "_beneficiary": "The address that receives the feePercentage.", + "_endWeights": "Array containing two parametes in order of: 1. The end weight for the project token in the LBP. 2. The end weight for the funding token in the LBP.", + "_fees": "Array containing two parameters in order of: 1. Percentage of fee paid for every swap in the LBP. 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.", + "_lbpFactory": "LBP factory address.", + "_metadata": "IPFS Hash of the LBP creation wizard information.", + "_name": "Name of the LBP.", + "_startTimeEndTime": "Array containing two parameters in order of: 1. Start time for the LBP. 2. End time for the LBP.", + "_startWeights": "Array containing two parametes in order of: 1. The start weight for the project token in the LBP. 2. The start weight for the funding token in the LBP.", + "_symbol": "Symbol of the LBP.", + "_tokenList": "Array containing two addresses in order of: 1. The address of the project token being distributed. 2. The address of the funding token being exchanged for the project token." + } + }, + "projectTokensRequired()": { + "details": "Get required amount of project tokens to cover for fees and the actual LBP." + }, + "removeLiquidity(address)": { + "details": "Exit pool or remove liquidity from pool.", + "params": { + "_receiver": "Address of the liquidity receiver, after exiting the LBP." + } + }, + "setSwapEnabled(bool)": { + "details": "Can pause/unpause trading.", + "params": { + "_swapEnabled": "Enables/disables swapping." + } + }, + "transferAdminRights(address)": { + "details": "Transfer admin rights.", + "params": { + "_newAdmin": "Address of the new admin." + } + }, + "updateMetadata(bytes)": { + "details": "Updates metadata.", + "params": { + "_metadata": "LBP wizard contract metadata, that is an IPFS Hash." + } + }, + "withdrawPoolTokens(address)": { + "details": "Withdraw pool tokens if available.", + "params": { + "_receiver": "Address of the BPT tokens receiver." + } + } + }, + "title": "LBPManager contract version 1", + "version": 1 + }, + "userdoc": { + "kind": "user", + "methods": {}, + "version": 1 + }, + "storageLayout": { + "storage": [ + { + "astId": 638, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "version", + "offset": 0, + "slot": "0", + "type": "t_bytes6" + }, + { + "astId": 643, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "symbol", + "offset": 0, + "slot": "1", + "type": "t_string_storage" + }, + { + "astId": 645, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "name", + "offset": 0, + "slot": "2", + "type": "t_string_storage" + }, + { + "astId": 647, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "admin", + "offset": 0, + "slot": "3", + "type": "t_address" + }, + { + "astId": 649, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "beneficiary", + "offset": 0, + "slot": "4", + "type": "t_address" + }, + { + "astId": 651, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "feePercentage", + "offset": 0, + "slot": "5", + "type": "t_uint256" + }, + { + "astId": 653, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "swapFeePercentage", + "offset": 0, + "slot": "6", + "type": "t_uint256" + }, + { + "astId": 657, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "tokenList", + "offset": 0, + "slot": "7", + "type": "t_array(t_contract(IERC20)190)dyn_storage" + }, + { + "astId": 660, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "amounts", + "offset": 0, + "slot": "8", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 663, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "startWeights", + "offset": 0, + "slot": "9", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 666, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "endWeights", + "offset": 0, + "slot": "10", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 669, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "startTimeEndTime", + "offset": 0, + "slot": "11", + "type": "t_array(t_uint256)dyn_storage" + }, + { + "astId": 672, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "lbp", + "offset": 0, + "slot": "12", + "type": "t_contract(ILBP)1530" + }, + { + "astId": 674, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "metadata", + "offset": 0, + "slot": "13", + "type": "t_bytes_storage" + }, + { + "astId": 676, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "projectTokenIndex", + "offset": 0, + "slot": "14", + "type": "t_uint8" + }, + { + "astId": 678, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "lbpFactory", + "offset": 1, + "slot": "14", + "type": "t_address" + }, + { + "astId": 680, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "poolFunded", + "offset": 21, + "slot": "14", + "type": "t_bool" + }, + { + "astId": 682, + "contract": "contracts/lbp/LBPManagerV1.sol:LBPManagerV1", + "label": "initialized", + "offset": 22, + "slot": "14", + "type": "t_bool" + } + ], + "types": { + "t_address": { + "encoding": "inplace", + "label": "address", + "numberOfBytes": "20" + }, + "t_array(t_contract(IERC20)190)dyn_storage": { + "base": "t_contract(IERC20)190", + "encoding": "dynamic_array", + "label": "contract IERC20[]", + "numberOfBytes": "32" + }, + "t_array(t_uint256)dyn_storage": { + "base": "t_uint256", + "encoding": "dynamic_array", + "label": "uint256[]", + "numberOfBytes": "32" + }, + "t_bool": { + "encoding": "inplace", + "label": "bool", + "numberOfBytes": "1" + }, + "t_bytes6": { + "encoding": "inplace", + "label": "bytes6", + "numberOfBytes": "6" + }, + "t_bytes_storage": { + "encoding": "bytes", + "label": "bytes", + "numberOfBytes": "32" + }, + "t_contract(IERC20)190": { + "encoding": "inplace", + "label": "contract IERC20", + "numberOfBytes": "20" + }, + "t_contract(ILBP)1530": { + "encoding": "inplace", + "label": "contract ILBP", + "numberOfBytes": "20" + }, + "t_string_storage": { + "encoding": "bytes", + "label": "string", + "numberOfBytes": "32" + }, + "t_uint256": { + "encoding": "inplace", + "label": "uint256", + "numberOfBytes": "32" + }, + "t_uint8": { + "encoding": "inplace", + "label": "uint8", + "numberOfBytes": "1" + } + } + } +} \ No newline at end of file diff --git a/deployments/goerli/solcInputs/0e8303ce972a3975803bfafcc30eb159.json b/deployments/goerli/solcInputs/0e8303ce972a3975803bfafcc30eb159.json new file mode 100644 index 0000000..cec4dca --- /dev/null +++ b/deployments/goerli/solcInputs/0e8303ce972a3975803bfafcc30eb159.json @@ -0,0 +1,62 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "contracts/lbp/LBPManagerV1.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract version 1\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManagerV1 {\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory no access control version 1\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/deployments/goerli/solcInputs/752d54b8f64e3608832db5b1be68e60f.json b/deployments/goerli/solcInputs/752d54b8f64e3608832db5b1be68e60f.json new file mode 100644 index 0000000..ee62d81 --- /dev/null +++ b/deployments/goerli/solcInputs/752d54b8f64e3608832db5b1be68e60f.json @@ -0,0 +1,62 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "contracts/lbp/LBPManagerV1.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract version 1\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManagerV1 {\n bytes6 public version = \"1.0.0\";\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactoryV1NoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManagerV1.sol\";\n\n/**\n * @title LBPManager Factory no access control version 1\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryV1NoAccessControl is CloneFactory, Ownable {\n bytes6 public version = \"1.0.0\";\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManagerV1(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManagerV1(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/deployments/goerli/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json b/deployments/goerli/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json new file mode 100644 index 0000000..5231e4d --- /dev/null +++ b/deployments/goerli/solcInputs/bf89fe6a61a7d22f31b24d3cee885a8d.json @@ -0,0 +1,170 @@ +{ + "language": "Solidity", + "sources": { + "contracts/lbp/LBPManager.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager contract. Smart contract for managing interactions with a Balancer LBP.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"../utils/interface/ILBPFactory.sol\";\nimport \"../utils/interface/IVault.sol\";\nimport \"../utils/interface/ILBP.sol\";\n\n/**\n * @title LBPManager contract.\n * @dev Smart contract for managing interactions with a Balancer LBP.\n */\n// solhint-disable-next-line max-states-count\ncontract LBPManager {\n // Constants\n uint256 private constant HUNDRED_PERCENT = 1e18; // Used in calculating the fee.\n\n // Locked parameter\n string public symbol; // Symbol of the LBP.\n string public name; // Name of the LBP.\n address public admin; // Address of the admin of this contract.\n address public beneficiary; // Address that recieves fees.\n uint256 public feePercentage; // Fee expressed as a % (e.g. 10**18 = 100% fee, toWei('1') = 100%, 1e18)\n uint256 public swapFeePercentage; // Percentage of fee paid for every swap in the LBP.\n IERC20[] public tokenList; // Tokens that are used in the LBP, sorted by address in numerical order (ascending).\n uint256[] public amounts; // Amount of tokens to be added as liquidity in LBP.\n uint256[] public startWeights; // Array containing the startWeights for the project & funding token.\n uint256[] public endWeights; // Array containing the endWeights for the project & funding token.\n uint256[] public startTimeEndTime; // Array containing the startTime and endTime for the LBP.\n ILBP public lbp; // Address of LBP that is managed by this contract.\n bytes public metadata; // IPFS Hash of the LBP creation wizard information.\n uint8 public projectTokenIndex; // Index repesenting the project token in the tokenList.\n address public lbpFactory; // Address of Balancers LBP factory.\n\n // Contract logic\n bool public poolFunded; // true:- LBP is funded; false:- LBP is not funded.\n bool public initialized; // true:- LBPManager initialized; false:- LBPManager not initialized. Makes sure, only initialized once.\n\n event LBPManagerAdminChanged(\n address indexed oldAdmin,\n address indexed newAdmin\n );\n event FeeTransferred(\n address indexed beneficiary,\n address tokenAddress,\n uint256 amount\n );\n event PoolTokensWithdrawn(address indexed lbpAddress, uint256 amount);\n event MetadataUpdated(bytes indexed metadata);\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"LBPManager: caller is not admin\");\n _;\n }\n\n /**\n * @dev Transfer admin rights.\n * @param _newAdmin Address of the new admin.\n */\n function transferAdminRights(address _newAdmin) external onlyAdmin {\n require(_newAdmin != address(0), \"LBPManager: new admin is zero\");\n\n emit LBPManagerAdminChanged(admin, _newAdmin);\n admin = _newAdmin;\n }\n\n /**\n * @dev Initialize LBPManager.\n * @param _lbpFactory LBP factory address.\n * @param _beneficiary The address that receives the feePercentage.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Array containing two addresses in order of:\n 1. The address of the project token being distributed.\n 2. The address of the funding token being exchanged for the project token.\n * @param _amounts Array containing two parameters in order of:\n 1. The amounts of project token to be added as liquidity to the LBP.\n 2. The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Array containing two parametes in order of:\n 1. The start weight for the project token in the LBP.\n 2. The start weight for the funding token in the LBP.\n * @param _startTimeEndTime Array containing two parameters in order of:\n 1. Start time for the LBP.\n 2. End time for the LBP.\n * @param _endWeights Array containing two parametes in order of:\n 1. The end weight for the project token in the LBP.\n 2. The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters in order of:\n 1. Percentage of fee paid for every swap in the LBP.\n 2. Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function initializeLBPManager(\n address _lbpFactory,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndTime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n require(!initialized, \"LBPManager: already initialized\");\n require(_beneficiary != address(0), \"LBPManager: _beneficiary is zero\");\n // solhint-disable-next-line reason-string\n require(_fees[0] >= 1e12, \"LBPManager: swapFeePercentage to low\"); // 0.0001%\n // solhint-disable-next-line reason-string\n require(_fees[0] <= 1e17, \"LBPManager: swapFeePercentage to high\"); // 10%\n require(\n _tokenList.length == 2 &&\n _amounts.length == 2 &&\n _startWeights.length == 2 &&\n _startTimeEndTime.length == 2 &&\n _endWeights.length == 2 &&\n _fees.length == 2,\n \"LBPManager: arrays wrong size\"\n );\n require(\n _tokenList[0] != _tokenList[1],\n \"LBPManager: tokens can't be same\"\n );\n require(\n _startTimeEndTime[0] < _startTimeEndTime[1],\n \"LBPManager: startTime > endTime\"\n );\n\n initialized = true;\n admin = msg.sender;\n swapFeePercentage = _fees[0];\n feePercentage = _fees[1];\n beneficiary = _beneficiary;\n metadata = _metadata;\n startTimeEndTime = _startTimeEndTime;\n name = _name;\n symbol = _symbol;\n lbpFactory = _lbpFactory;\n\n // Token addresses are sorted in numerical order (ascending) as specified by Balancer\n if (address(_tokenList[0]) > address(_tokenList[1])) {\n projectTokenIndex = 1;\n tokenList.push(_tokenList[1]);\n tokenList.push(_tokenList[0]);\n\n amounts.push(_amounts[1]);\n amounts.push(_amounts[0]);\n\n startWeights.push(_startWeights[1]);\n startWeights.push(_startWeights[0]);\n\n endWeights.push(_endWeights[1]);\n endWeights.push(_endWeights[0]);\n } else {\n projectTokenIndex = 0;\n tokenList = _tokenList;\n amounts = _amounts;\n startWeights = _startWeights;\n endWeights = _endWeights;\n }\n }\n\n /**\n * @dev Subtracts the fee, deploys the LBP and adds liquidity to it.\n * @param _sender Address of the liquidity provider.\n */\n function initializeLBP(address _sender) external onlyAdmin {\n // solhint-disable-next-line reason-string\n require(initialized == true, \"LBPManager: LBPManager not initialized\");\n require(!poolFunded, \"LBPManager: pool already funded\");\n poolFunded = true;\n\n lbp = ILBP(\n ILBPFactory(lbpFactory).create(\n name,\n symbol,\n tokenList,\n startWeights,\n swapFeePercentage,\n address(this),\n false // SwapEnabled is set to false at pool creation.\n )\n );\n\n lbp.updateWeightsGradually(\n startTimeEndTime[0],\n startTimeEndTime[1],\n endWeights\n );\n\n IVault vault = lbp.getVault();\n\n if (feePercentage != 0) {\n // Transfer fee to beneficiary.\n uint256 feeAmountRequired = _feeAmountRequired();\n tokenList[projectTokenIndex].transferFrom(\n _sender,\n beneficiary,\n feeAmountRequired\n );\n emit FeeTransferred(\n beneficiary,\n address(tokenList[projectTokenIndex]),\n feeAmountRequired\n );\n }\n\n for (uint8 i; i < tokenList.length; i++) {\n tokenList[i].transferFrom(_sender, address(this), amounts[i]);\n tokenList[i].approve(address(vault), amounts[i]);\n }\n\n IVault.JoinPoolRequest memory request = IVault.JoinPoolRequest({\n maxAmountsIn: amounts,\n userData: abi.encode(0, amounts), // JOIN_KIND_INIT = 0, used when adding liquidity for the first time.\n fromInternalBalance: false, // It is not possible to add liquidity through the internal Vault balance.\n assets: tokenList\n });\n\n vault.joinPool(lbp.getPoolId(), address(this), address(this), request);\n }\n\n /**\n * @dev Exit pool or remove liquidity from pool.\n * @param _receiver Address of the liquidity receiver, after exiting the LBP.\n */\n function removeLiquidity(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n IVault vault = lbp.getVault();\n\n IVault.ExitPoolRequest memory request = IVault.ExitPoolRequest({\n minAmountsOut: new uint256[](tokenList.length), // To remove all funding from the pool. Initializes to [0, 0]\n userData: abi.encode(1, lbp.balanceOf(address(this))),\n toInternalBalance: false,\n assets: tokenList\n });\n\n vault.exitPool(\n lbp.getPoolId(),\n address(this),\n payable(_receiver),\n request\n );\n }\n\n /*\n DISCLAIMER:\n The method below is an advanced functionality. By invoking this method, you are withdrawing\n the BPT tokens, which are necessary to exit the pool. If you chose to remove the BPT tokens,\n the LBPManager will no longer be able to remove liquidity. By withdrawing the BPT tokens\n you agree on removing all the responsibility from the LBPManger for removing liquidity from\n the pool and transferring this responsibility to the holder of the BPT tokens. Any possible\n loss of funds by choosing to withdraw the BPT tokens is not the responsibility of\n LBPManager or PrimeDao. After withdrawing the BPT tokens, liquidity has to be withdrawn\n directly from Balancer's LBP. LBPManager or PrimeDAO will no longer provide support to do so.\n */\n /**\n * @dev Withdraw pool tokens if available.\n * @param _receiver Address of the BPT tokens receiver.\n */\n function withdrawPoolTokens(address _receiver) external onlyAdmin {\n require(_receiver != address(0), \"LBPManager: receiver is zero\");\n\n uint256 endTime = startTimeEndTime[1];\n // solhint-disable-next-line not-rely-on-time\n require(block.timestamp >= endTime, \"LBPManager: endtime not reached\");\n\n require(\n lbp.balanceOf(address(this)) > 0,\n \"LBPManager: no BPT token balance\"\n );\n\n emit PoolTokensWithdrawn(address(lbp), lbp.balanceOf(address(this)));\n lbp.transfer(_receiver, lbp.balanceOf(address(this)));\n }\n\n /**\n * @dev Can pause/unpause trading.\n * @param _swapEnabled Enables/disables swapping.\n */\n function setSwapEnabled(bool _swapEnabled) external onlyAdmin {\n lbp.setSwapEnabled(_swapEnabled);\n }\n\n /**\n * @dev Tells whether swaps are enabled or not for the LBP\n */\n function getSwapEnabled() external view returns (bool) {\n require(poolFunded, \"LBPManager: LBP not initialized.\");\n return lbp.getSwapEnabled();\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees and the actual LBP.\n */\n function projectTokensRequired()\n external\n view\n returns (uint256 projectTokenAmounts)\n {\n projectTokenAmounts = amounts[projectTokenIndex] + _feeAmountRequired();\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata LBP wizard contract metadata, that is an IPFS Hash.\n */\n function updateMetadata(bytes memory _metadata) external onlyAdmin {\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n /**\n * @dev Get required amount of project tokens to cover for fees.\n */\n function _feeAmountRequired() internal view returns (uint256 feeAmount) {\n feeAmount =\n (amounts[projectTokenIndex] * feePercentage) /\n HUNDRED_PERCENT;\n }\n}\n" + }, + "contracts/utils/interface/ILBPFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface ILBPFactory {\n function create(\n string memory name,\n string memory symbol,\n IERC20[] memory tokens,\n uint256[] memory weights,\n uint256 swapFeePercentage,\n address owner,\n bool swapEnabledOnStart\n ) external returns (address);\n}\n" + }, + "contracts/utils/interface/IVault.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\n\ninterface IVault {\n struct JoinPoolRequest {\n IERC20[] assets;\n uint256[] maxAmountsIn;\n bytes userData;\n bool fromInternalBalance;\n }\n\n struct ExitPoolRequest {\n IERC20[] assets;\n uint256[] minAmountsOut;\n bytes userData;\n bool toInternalBalance;\n }\n\n function joinPool(\n bytes32 poolId,\n address sender,\n address recipient,\n JoinPoolRequest memory request\n ) external payable;\n\n function exitPool(\n bytes32 poolId,\n address sender,\n address payable recipient,\n ExitPoolRequest memory request\n ) external;\n}\n" + }, + "contracts/utils/interface/ILBP.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n/* solium-disable */\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"./IVault.sol\";\n\npragma solidity 0.8.17;\n\ninterface ILBP is IERC20 {\n function updateWeightsGradually(\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n ) external;\n\n function getGradualWeightUpdateParams()\n external\n view\n returns (\n uint256 startTime,\n uint256 endTime,\n uint256[] memory endWeights\n );\n\n function getPoolId() external view returns (bytes32);\n\n function getVault() external view returns (IVault);\n\n function setSwapEnabled(bool swapEnabled) external;\n\n function getSwapEnabled() external view returns (bool);\n\n function getSwapFeePercentage() external view returns (uint256);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/IERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 standard as defined in the EIP.\n */\ninterface IERC20 {\n /**\n * @dev Emitted when `value` tokens are moved from one account (`from`) to\n * another (`to`).\n *\n * Note that `value` may be zero.\n */\n event Transfer(address indexed from, address indexed to, uint256 value);\n\n /**\n * @dev Emitted when the allowance of a `spender` for an `owner` is set by\n * a call to {approve}. `value` is the new allowance.\n */\n event Approval(address indexed owner, address indexed spender, uint256 value);\n\n /**\n * @dev Returns the amount of tokens in existence.\n */\n function totalSupply() external view returns (uint256);\n\n /**\n * @dev Returns the amount of tokens owned by `account`.\n */\n function balanceOf(address account) external view returns (uint256);\n\n /**\n * @dev Moves `amount` tokens from the caller's account to `to`.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transfer(address to, uint256 amount) external returns (bool);\n\n /**\n * @dev Returns the remaining number of tokens that `spender` will be\n * allowed to spend on behalf of `owner` through {transferFrom}. This is\n * zero by default.\n *\n * This value changes when {approve} or {transferFrom} are called.\n */\n function allowance(address owner, address spender) external view returns (uint256);\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * IMPORTANT: Beware that changing an allowance with this method brings the risk\n * that someone may use both the old and the new allowance by unfortunate\n * transaction ordering. One possible solution to mitigate this race\n * condition is to first reduce the spender's allowance to 0 and set the\n * desired value afterwards:\n * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\n *\n * Emits an {Approval} event.\n */\n function approve(address spender, uint256 amount) external returns (bool);\n\n /**\n * @dev Moves `amount` tokens from `from` to `to` using the\n * allowance mechanism. `amount` is then deducted from the caller's\n * allowance.\n *\n * Returns a boolean value indicating whether the operation succeeded.\n *\n * Emits a {Transfer} event.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) external returns (bool);\n}\n" + }, + "contracts/lbp/LBPManagerFactoryNoAccessControl.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManager.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contract without the onlyOwner modifer for the\n * function deployLBPManager(). By removing the access control, everyone can deploy a\n * LBPManager from this contract. This is a temporarly solution in response to the\n * flaky Celo Safe.\n */\ncontract LBPManagerFactoryNoAccessControl is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManager(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManager(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/utils/CloneFactory.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n \n*\n* CloneFactory.sol was originally published under MIT license.\n* Republished by PrimeDAO under GNU General Public License v3.0.\n*\n*/\n\n/*\nThe MIT License (MIT)\nCopyright (c) 2018 Murray Software, LLC.\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\nThe above copyright notice and this permission notice shall be included\nin all copies or substantial portions of the Software.\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\nOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\nIN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\nCLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\nTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\nSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n// solhint-disable max-line-length\n// solhint-disable no-inline-assembly\n\npragma solidity 0.8.17;\n\ncontract CloneFactory {\n function createClone(address target) internal returns (address result) {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000\n )\n mstore(add(clone, 0x14), targetBytes)\n mstore(\n add(clone, 0x28),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n result := create(0, clone, 0x37)\n }\n }\n\n function isClone(address target, address query)\n internal\n view\n returns (bool result)\n {\n bytes20 targetBytes = bytes20(target);\n assembly {\n let clone := mload(0x40)\n mstore(\n clone,\n 0x363d3d373d3d3d363d7300000000000000000000000000000000000000000000\n )\n mstore(add(clone, 0xa), targetBytes)\n mstore(\n add(clone, 0x1e),\n 0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000\n )\n\n let other := add(clone, 0x40)\n extcodecopy(query, other, 0, 0x2d)\n result := and(\n eq(mload(clone), mload(other)),\n eq(mload(add(clone, 0xd)), mload(add(other, 0xd)))\n )\n }\n }\n}\n" + }, + "@openzeppelin/contracts/access/Ownable.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../utils/Context.sol\";\n\n/**\n * @dev Contract module which provides a basic access control mechanism, where\n * there is an account (an owner) that can be granted exclusive access to\n * specific functions.\n *\n * By default, the owner account will be the one that deploys the contract. This\n * can later be changed with {transferOwnership}.\n *\n * This module is used through inheritance. It will make available the modifier\n * `onlyOwner`, which can be applied to your functions to restrict their use to\n * the owner.\n */\nabstract contract Ownable is Context {\n address private _owner;\n\n event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\n\n /**\n * @dev Initializes the contract setting the deployer as the initial owner.\n */\n constructor() {\n _transferOwnership(_msgSender());\n }\n\n /**\n * @dev Throws if called by any account other than the owner.\n */\n modifier onlyOwner() {\n _checkOwner();\n _;\n }\n\n /**\n * @dev Returns the address of the current owner.\n */\n function owner() public view virtual returns (address) {\n return _owner;\n }\n\n /**\n * @dev Throws if the sender is not the owner.\n */\n function _checkOwner() internal view virtual {\n require(owner() == _msgSender(), \"Ownable: caller is not the owner\");\n }\n\n /**\n * @dev Leaves the contract without owner. It will not be possible to call\n * `onlyOwner` functions anymore. Can only be called by the current owner.\n *\n * NOTE: Renouncing ownership will leave the contract without an owner,\n * thereby removing any functionality that is only available to the owner.\n */\n function renounceOwnership() public virtual onlyOwner {\n _transferOwnership(address(0));\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Can only be called by the current owner.\n */\n function transferOwnership(address newOwner) public virtual onlyOwner {\n require(newOwner != address(0), \"Ownable: new owner is the zero address\");\n _transferOwnership(newOwner);\n }\n\n /**\n * @dev Transfers ownership of the contract to a new account (`newOwner`).\n * Internal function without access restriction.\n */\n function _transferOwnership(address newOwner) internal virtual {\n address oldOwner = _owner;\n _owner = newOwner;\n emit OwnershipTransferred(oldOwner, newOwner);\n }\n}\n" + }, + "@openzeppelin/contracts/utils/Context.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Provides information about the current execution context, including the\n * sender of the transaction and its data. While these are generally available\n * via msg.sender and msg.data, they should not be accessed in such a direct\n * manner, since when dealing with meta-transactions the account sending and\n * paying for execution may not be the actual sender (as far as an application\n * is concerned).\n *\n * This contract is only required for intermediate, library-like contracts.\n */\nabstract contract Context {\n function _msgSender() internal view virtual returns (address) {\n return msg.sender;\n }\n\n function _msgData() internal view virtual returns (bytes calldata) {\n return msg.data;\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/ERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (token/ERC20/ERC20.sol)\n\npragma solidity ^0.8.0;\n\nimport \"./IERC20.sol\";\nimport \"./extensions/IERC20Metadata.sol\";\nimport \"../../utils/Context.sol\";\n\n/**\n * @dev Implementation of the {IERC20} interface.\n *\n * This implementation is agnostic to the way tokens are created. This means\n * that a supply mechanism has to be added in a derived contract using {_mint}.\n * For a generic mechanism see {ERC20PresetMinterPauser}.\n *\n * TIP: For a detailed writeup see our guide\n * https://forum.zeppelin.solutions/t/how-to-implement-erc20-supply-mechanisms/226[How\n * to implement supply mechanisms].\n *\n * We have followed general OpenZeppelin Contracts guidelines: functions revert\n * instead returning `false` on failure. This behavior is nonetheless\n * conventional and does not conflict with the expectations of ERC20\n * applications.\n *\n * Additionally, an {Approval} event is emitted on calls to {transferFrom}.\n * This allows applications to reconstruct the allowance for all accounts just\n * by listening to said events. Other implementations of the EIP may not emit\n * these events, as it isn't required by the specification.\n *\n * Finally, the non-standard {decreaseAllowance} and {increaseAllowance}\n * functions have been added to mitigate the well-known issues around setting\n * allowances. See {IERC20-approve}.\n */\ncontract ERC20 is Context, IERC20, IERC20Metadata {\n mapping(address => uint256) private _balances;\n\n mapping(address => mapping(address => uint256)) private _allowances;\n\n uint256 private _totalSupply;\n\n string private _name;\n string private _symbol;\n\n /**\n * @dev Sets the values for {name} and {symbol}.\n *\n * The default value of {decimals} is 18. To select a different value for\n * {decimals} you should overload it.\n *\n * All two of these values are immutable: they can only be set once during\n * construction.\n */\n constructor(string memory name_, string memory symbol_) {\n _name = name_;\n _symbol = symbol_;\n }\n\n /**\n * @dev Returns the name of the token.\n */\n function name() public view virtual override returns (string memory) {\n return _name;\n }\n\n /**\n * @dev Returns the symbol of the token, usually a shorter version of the\n * name.\n */\n function symbol() public view virtual override returns (string memory) {\n return _symbol;\n }\n\n /**\n * @dev Returns the number of decimals used to get its user representation.\n * For example, if `decimals` equals `2`, a balance of `505` tokens should\n * be displayed to a user as `5.05` (`505 / 10 ** 2`).\n *\n * Tokens usually opt for a value of 18, imitating the relationship between\n * Ether and Wei. This is the value {ERC20} uses, unless this function is\n * overridden;\n *\n * NOTE: This information is only used for _display_ purposes: it in\n * no way affects any of the arithmetic of the contract, including\n * {IERC20-balanceOf} and {IERC20-transfer}.\n */\n function decimals() public view virtual override returns (uint8) {\n return 18;\n }\n\n /**\n * @dev See {IERC20-totalSupply}.\n */\n function totalSupply() public view virtual override returns (uint256) {\n return _totalSupply;\n }\n\n /**\n * @dev See {IERC20-balanceOf}.\n */\n function balanceOf(address account) public view virtual override returns (uint256) {\n return _balances[account];\n }\n\n /**\n * @dev See {IERC20-transfer}.\n *\n * Requirements:\n *\n * - `to` cannot be the zero address.\n * - the caller must have a balance of at least `amount`.\n */\n function transfer(address to, uint256 amount) public virtual override returns (bool) {\n address owner = _msgSender();\n _transfer(owner, to, amount);\n return true;\n }\n\n /**\n * @dev See {IERC20-allowance}.\n */\n function allowance(address owner, address spender) public view virtual override returns (uint256) {\n return _allowances[owner][spender];\n }\n\n /**\n * @dev See {IERC20-approve}.\n *\n * NOTE: If `amount` is the maximum `uint256`, the allowance is not updated on\n * `transferFrom`. This is semantically equivalent to an infinite approval.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n */\n function approve(address spender, uint256 amount) public virtual override returns (bool) {\n address owner = _msgSender();\n _approve(owner, spender, amount);\n return true;\n }\n\n /**\n * @dev See {IERC20-transferFrom}.\n *\n * Emits an {Approval} event indicating the updated allowance. This is not\n * required by the EIP. See the note at the beginning of {ERC20}.\n *\n * NOTE: Does not update the allowance if the current allowance\n * is the maximum `uint256`.\n *\n * Requirements:\n *\n * - `from` and `to` cannot be the zero address.\n * - `from` must have a balance of at least `amount`.\n * - the caller must have allowance for ``from``'s tokens of at least\n * `amount`.\n */\n function transferFrom(\n address from,\n address to,\n uint256 amount\n ) public virtual override returns (bool) {\n address spender = _msgSender();\n _spendAllowance(from, spender, amount);\n _transfer(from, to, amount);\n return true;\n }\n\n /**\n * @dev Atomically increases the allowance granted to `spender` by the caller.\n *\n * This is an alternative to {approve} that can be used as a mitigation for\n * problems described in {IERC20-approve}.\n *\n * Emits an {Approval} event indicating the updated allowance.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n */\n function increaseAllowance(address spender, uint256 addedValue) public virtual returns (bool) {\n address owner = _msgSender();\n _approve(owner, spender, allowance(owner, spender) + addedValue);\n return true;\n }\n\n /**\n * @dev Atomically decreases the allowance granted to `spender` by the caller.\n *\n * This is an alternative to {approve} that can be used as a mitigation for\n * problems described in {IERC20-approve}.\n *\n * Emits an {Approval} event indicating the updated allowance.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n * - `spender` must have allowance for the caller of at least\n * `subtractedValue`.\n */\n function decreaseAllowance(address spender, uint256 subtractedValue) public virtual returns (bool) {\n address owner = _msgSender();\n uint256 currentAllowance = allowance(owner, spender);\n require(currentAllowance >= subtractedValue, \"ERC20: decreased allowance below zero\");\n unchecked {\n _approve(owner, spender, currentAllowance - subtractedValue);\n }\n\n return true;\n }\n\n /**\n * @dev Moves `amount` of tokens from `from` to `to`.\n *\n * This internal function is equivalent to {transfer}, and can be used to\n * e.g. implement automatic token fees, slashing mechanisms, etc.\n *\n * Emits a {Transfer} event.\n *\n * Requirements:\n *\n * - `from` cannot be the zero address.\n * - `to` cannot be the zero address.\n * - `from` must have a balance of at least `amount`.\n */\n function _transfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {\n require(from != address(0), \"ERC20: transfer from the zero address\");\n require(to != address(0), \"ERC20: transfer to the zero address\");\n\n _beforeTokenTransfer(from, to, amount);\n\n uint256 fromBalance = _balances[from];\n require(fromBalance >= amount, \"ERC20: transfer amount exceeds balance\");\n unchecked {\n _balances[from] = fromBalance - amount;\n }\n _balances[to] += amount;\n\n emit Transfer(from, to, amount);\n\n _afterTokenTransfer(from, to, amount);\n }\n\n /** @dev Creates `amount` tokens and assigns them to `account`, increasing\n * the total supply.\n *\n * Emits a {Transfer} event with `from` set to the zero address.\n *\n * Requirements:\n *\n * - `account` cannot be the zero address.\n */\n function _mint(address account, uint256 amount) internal virtual {\n require(account != address(0), \"ERC20: mint to the zero address\");\n\n _beforeTokenTransfer(address(0), account, amount);\n\n _totalSupply += amount;\n _balances[account] += amount;\n emit Transfer(address(0), account, amount);\n\n _afterTokenTransfer(address(0), account, amount);\n }\n\n /**\n * @dev Destroys `amount` tokens from `account`, reducing the\n * total supply.\n *\n * Emits a {Transfer} event with `to` set to the zero address.\n *\n * Requirements:\n *\n * - `account` cannot be the zero address.\n * - `account` must have at least `amount` tokens.\n */\n function _burn(address account, uint256 amount) internal virtual {\n require(account != address(0), \"ERC20: burn from the zero address\");\n\n _beforeTokenTransfer(account, address(0), amount);\n\n uint256 accountBalance = _balances[account];\n require(accountBalance >= amount, \"ERC20: burn amount exceeds balance\");\n unchecked {\n _balances[account] = accountBalance - amount;\n }\n _totalSupply -= amount;\n\n emit Transfer(account, address(0), amount);\n\n _afterTokenTransfer(account, address(0), amount);\n }\n\n /**\n * @dev Sets `amount` as the allowance of `spender` over the `owner` s tokens.\n *\n * This internal function is equivalent to `approve`, and can be used to\n * e.g. set automatic allowances for certain subsystems, etc.\n *\n * Emits an {Approval} event.\n *\n * Requirements:\n *\n * - `owner` cannot be the zero address.\n * - `spender` cannot be the zero address.\n */\n function _approve(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual {\n require(owner != address(0), \"ERC20: approve from the zero address\");\n require(spender != address(0), \"ERC20: approve to the zero address\");\n\n _allowances[owner][spender] = amount;\n emit Approval(owner, spender, amount);\n }\n\n /**\n * @dev Updates `owner` s allowance for `spender` based on spent `amount`.\n *\n * Does not update the allowance amount in case of infinite allowance.\n * Revert if not enough allowance is available.\n *\n * Might emit an {Approval} event.\n */\n function _spendAllowance(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual {\n uint256 currentAllowance = allowance(owner, spender);\n if (currentAllowance != type(uint256).max) {\n require(currentAllowance >= amount, \"ERC20: insufficient allowance\");\n unchecked {\n _approve(owner, spender, currentAllowance - amount);\n }\n }\n }\n\n /**\n * @dev Hook that is called before any transfer of tokens. This includes\n * minting and burning.\n *\n * Calling conditions:\n *\n * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens\n * will be transferred to `to`.\n * - when `from` is zero, `amount` tokens will be minted for `to`.\n * - when `to` is zero, `amount` of ``from``'s tokens will be burned.\n * - `from` and `to` are never both zero.\n *\n * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].\n */\n function _beforeTokenTransfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {}\n\n /**\n * @dev Hook that is called after any transfer of tokens. This includes\n * minting and burning.\n *\n * Calling conditions:\n *\n * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens\n * has been transferred to `to`.\n * - when `from` is zero, `amount` tokens have been minted for `to`.\n * - when `to` is zero, `amount` of ``from``'s tokens have been burned.\n * - `from` and `to` are never both zero.\n *\n * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].\n */\n function _afterTokenTransfer(\n address from,\n address to,\n uint256 amount\n ) internal virtual {}\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/IERC20Metadata.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/IERC20Metadata.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../IERC20.sol\";\n\n/**\n * @dev Interface for the optional metadata functions from the ERC20 standard.\n *\n * _Available since v4.1._\n */\ninterface IERC20Metadata is IERC20 {\n /**\n * @dev Returns the name of the token.\n */\n function name() external view returns (string memory);\n\n /**\n * @dev Returns the symbol of the token.\n */\n function symbol() external view returns (string memory);\n\n /**\n * @dev Returns the decimals places of the token.\n */\n function decimals() external view returns (uint8);\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/ERC20Capped.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../ERC20.sol\";\n\n/**\n * @dev Extension of {ERC20} that adds a cap to the supply of tokens.\n */\nabstract contract ERC20Capped is ERC20 {\n uint256 private immutable _cap;\n\n /**\n * @dev Sets the value of the `cap`. This value is immutable, it can only be\n * set once during construction.\n */\n constructor(uint256 cap_) {\n require(cap_ > 0, \"ERC20Capped: cap is 0\");\n _cap = cap_;\n }\n\n /**\n * @dev Returns the cap on the token's total supply.\n */\n function cap() public view virtual returns (uint256) {\n return _cap;\n }\n\n /**\n * @dev See {ERC20-_mint}.\n */\n function _mint(address account, uint256 amount) internal virtual override {\n require(ERC20.totalSupply() + amount <= cap(), \"ERC20Capped: cap exceeded\");\n super._mint(account, amount);\n }\n}\n" + }, + "contracts/test/PrimeToken.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol\";\n\ncontract PrimeToken is ERC20Capped {\n constructor(\n uint256 initialSupply,\n uint256 cap,\n address genesisMultisig\n ) ERC20(\"PrimeDAO Token\", \"PRIME\") ERC20Capped(cap) {\n require(initialSupply <= cap); // _mint from ERC20 is not protected\n ERC20._mint(genesisMultisig, initialSupply);\n }\n}\n" + }, + "contracts/test/D2D.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol\";\n\ncontract D2D is ERC20Capped {\n uint256 public constant supply = 100000000000000000000000000;\n\n constructor() ERC20(\"Prime\", \"D2D\") ERC20Capped(supply) {\n ERC20._mint(msg.sender, supply);\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (token/ERC20/utils/SafeERC20.sol)\n\npragma solidity ^0.8.0;\n\nimport \"../IERC20.sol\";\nimport \"../extensions/draft-IERC20Permit.sol\";\nimport \"../../../utils/Address.sol\";\n\n/**\n * @title SafeERC20\n * @dev Wrappers around ERC20 operations that throw on failure (when the token\n * contract returns false). Tokens that return no value (and instead revert or\n * throw on failure) are also supported, non-reverting calls are assumed to be\n * successful.\n * To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,\n * which allows you to call the safe operations as `token.safeTransfer(...)`, etc.\n */\nlibrary SafeERC20 {\n using Address for address;\n\n function safeTransfer(\n IERC20 token,\n address to,\n uint256 value\n ) internal {\n _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));\n }\n\n function safeTransferFrom(\n IERC20 token,\n address from,\n address to,\n uint256 value\n ) internal {\n _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));\n }\n\n /**\n * @dev Deprecated. This function has issues similar to the ones found in\n * {IERC20-approve}, and its usage is discouraged.\n *\n * Whenever possible, use {safeIncreaseAllowance} and\n * {safeDecreaseAllowance} instead.\n */\n function safeApprove(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n // safeApprove should only be called when setting an initial allowance,\n // or when resetting it to zero. To increase and decrease it, use\n // 'safeIncreaseAllowance' and 'safeDecreaseAllowance'\n require(\n (value == 0) || (token.allowance(address(this), spender) == 0),\n \"SafeERC20: approve from non-zero to non-zero allowance\"\n );\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));\n }\n\n function safeIncreaseAllowance(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n uint256 newAllowance = token.allowance(address(this), spender) + value;\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));\n }\n\n function safeDecreaseAllowance(\n IERC20 token,\n address spender,\n uint256 value\n ) internal {\n unchecked {\n uint256 oldAllowance = token.allowance(address(this), spender);\n require(oldAllowance >= value, \"SafeERC20: decreased allowance below zero\");\n uint256 newAllowance = oldAllowance - value;\n _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));\n }\n }\n\n function safePermit(\n IERC20Permit token,\n address owner,\n address spender,\n uint256 value,\n uint256 deadline,\n uint8 v,\n bytes32 r,\n bytes32 s\n ) internal {\n uint256 nonceBefore = token.nonces(owner);\n token.permit(owner, spender, value, deadline, v, r, s);\n uint256 nonceAfter = token.nonces(owner);\n require(nonceAfter == nonceBefore + 1, \"SafeERC20: permit did not succeed\");\n }\n\n /**\n * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement\n * on the return value: the return value is optional (but if data is returned, it must not be false).\n * @param token The token targeted by the call.\n * @param data The call data (encoded using abi.encode or one of its variants).\n */\n function _callOptionalReturn(IERC20 token, bytes memory data) private {\n // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since\n // we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that\n // the target address contains contract code and also asserts for success in the low-level call.\n\n bytes memory returndata = address(token).functionCall(data, \"SafeERC20: low-level call failed\");\n if (returndata.length > 0) {\n // Return data is optional\n require(abi.decode(returndata, (bool)), \"SafeERC20: ERC20 operation did not succeed\");\n }\n }\n}\n" + }, + "@openzeppelin/contracts/utils/Address.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts (last updated v4.7.0) (utils/Address.sol)\n\npragma solidity ^0.8.1;\n\n/**\n * @dev Collection of functions related to the address type\n */\nlibrary Address {\n /**\n * @dev Returns true if `account` is a contract.\n *\n * [IMPORTANT]\n * ====\n * It is unsafe to assume that an address for which this function returns\n * false is an externally-owned account (EOA) and not a contract.\n *\n * Among others, `isContract` will return false for the following\n * types of addresses:\n *\n * - an externally-owned account\n * - a contract in construction\n * - an address where a contract will be created\n * - an address where a contract lived, but was destroyed\n * ====\n *\n * [IMPORTANT]\n * ====\n * You shouldn't rely on `isContract` to protect against flash loan attacks!\n *\n * Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets\n * like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract\n * constructor.\n * ====\n */\n function isContract(address account) internal view returns (bool) {\n // This method relies on extcodesize/address.code.length, which returns 0\n // for contracts in construction, since the code is only stored at the end\n // of the constructor execution.\n\n return account.code.length > 0;\n }\n\n /**\n * @dev Replacement for Solidity's `transfer`: sends `amount` wei to\n * `recipient`, forwarding all available gas and reverting on errors.\n *\n * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost\n * of certain opcodes, possibly making contracts go over the 2300 gas limit\n * imposed by `transfer`, making them unable to receive funds via\n * `transfer`. {sendValue} removes this limitation.\n *\n * https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].\n *\n * IMPORTANT: because control is transferred to `recipient`, care must be\n * taken to not create reentrancy vulnerabilities. Consider using\n * {ReentrancyGuard} or the\n * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].\n */\n function sendValue(address payable recipient, uint256 amount) internal {\n require(address(this).balance >= amount, \"Address: insufficient balance\");\n\n (bool success, ) = recipient.call{value: amount}(\"\");\n require(success, \"Address: unable to send value, recipient may have reverted\");\n }\n\n /**\n * @dev Performs a Solidity function call using a low level `call`. A\n * plain `call` is an unsafe replacement for a function call: use this\n * function instead.\n *\n * If `target` reverts with a revert reason, it is bubbled up by this\n * function (like regular Solidity function calls).\n *\n * Returns the raw returned data. To convert to the expected return value,\n * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].\n *\n * Requirements:\n *\n * - `target` must be a contract.\n * - calling `target` with `data` must not revert.\n *\n * _Available since v3.1._\n */\n function functionCall(address target, bytes memory data) internal returns (bytes memory) {\n return functionCall(target, data, \"Address: low-level call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with\n * `errorMessage` as a fallback revert reason when `target` reverts.\n *\n * _Available since v3.1._\n */\n function functionCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal returns (bytes memory) {\n return functionCallWithValue(target, data, 0, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but also transferring `value` wei to `target`.\n *\n * Requirements:\n *\n * - the calling contract must have an ETH balance of at least `value`.\n * - the called Solidity function must be `payable`.\n *\n * _Available since v3.1._\n */\n function functionCallWithValue(\n address target,\n bytes memory data,\n uint256 value\n ) internal returns (bytes memory) {\n return functionCallWithValue(target, data, value, \"Address: low-level call with value failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but\n * with `errorMessage` as a fallback revert reason when `target` reverts.\n *\n * _Available since v3.1._\n */\n function functionCallWithValue(\n address target,\n bytes memory data,\n uint256 value,\n string memory errorMessage\n ) internal returns (bytes memory) {\n require(address(this).balance >= value, \"Address: insufficient balance for call\");\n require(isContract(target), \"Address: call to non-contract\");\n\n (bool success, bytes memory returndata) = target.call{value: value}(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but performing a static call.\n *\n * _Available since v3.3._\n */\n function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {\n return functionStaticCall(target, data, \"Address: low-level static call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\n * but performing a static call.\n *\n * _Available since v3.3._\n */\n function functionStaticCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal view returns (bytes memory) {\n require(isContract(target), \"Address: static call to non-contract\");\n\n (bool success, bytes memory returndata) = target.staticcall(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\n * but performing a delegate call.\n *\n * _Available since v3.4._\n */\n function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {\n return functionDelegateCall(target, data, \"Address: low-level delegate call failed\");\n }\n\n /**\n * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\n * but performing a delegate call.\n *\n * _Available since v3.4._\n */\n function functionDelegateCall(\n address target,\n bytes memory data,\n string memory errorMessage\n ) internal returns (bytes memory) {\n require(isContract(target), \"Address: delegate call to non-contract\");\n\n (bool success, bytes memory returndata) = target.delegatecall(data);\n return verifyCallResult(success, returndata, errorMessage);\n }\n\n /**\n * @dev Tool to verifies that a low level call was successful, and revert if it wasn't, either by bubbling the\n * revert reason using the provided one.\n *\n * _Available since v4.3._\n */\n function verifyCallResult(\n bool success,\n bytes memory returndata,\n string memory errorMessage\n ) internal pure returns (bytes memory) {\n if (success) {\n return returndata;\n } else {\n // Look for revert reason and bubble it up if present\n if (returndata.length > 0) {\n // The easiest way to bubble the revert reason is using memory via assembly\n /// @solidity memory-safe-assembly\n assembly {\n let returndata_size := mload(returndata)\n revert(add(32, returndata), returndata_size)\n }\n } else {\n revert(errorMessage);\n }\n }\n }\n}\n" + }, + "@openzeppelin/contracts/token/ERC20/extensions/draft-IERC20Permit.sol": { + "content": "// SPDX-License-Identifier: MIT\n// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/draft-IERC20Permit.sol)\n\npragma solidity ^0.8.0;\n\n/**\n * @dev Interface of the ERC20 Permit extension allowing approvals to be made via signatures, as defined in\n * https://eips.ethereum.org/EIPS/eip-2612[EIP-2612].\n *\n * Adds the {permit} method, which can be used to change an account's ERC20 allowance (see {IERC20-allowance}) by\n * presenting a message signed by the account. By not relying on {IERC20-approve}, the token holder account doesn't\n * need to send a transaction, and thus is not required to hold Ether at all.\n */\ninterface IERC20Permit {\n /**\n * @dev Sets `value` as the allowance of `spender` over ``owner``'s tokens,\n * given ``owner``'s signed approval.\n *\n * IMPORTANT: The same issues {IERC20-approve} has related to transaction\n * ordering also apply here.\n *\n * Emits an {Approval} event.\n *\n * Requirements:\n *\n * - `spender` cannot be the zero address.\n * - `deadline` must be a timestamp in the future.\n * - `v`, `r` and `s` must be a valid `secp256k1` signature from `owner`\n * over the EIP712-formatted function arguments.\n * - the signature must use ``owner``'s current nonce (see {nonces}).\n *\n * For more information on the signature format, see the\n * https://eips.ethereum.org/EIPS/eip-2612#specification[relevant EIP\n * section].\n */\n function permit(\n address owner,\n address spender,\n uint256 value,\n uint256 deadline,\n uint8 v,\n bytes32 r,\n bytes32 s\n ) external;\n\n /**\n * @dev Returns the current nonce for `owner`. This value must be\n * included whenever a signature is generated for {permit}.\n *\n * Every successful call to {permit} increases ``owner``'s nonce by one. This\n * prevents a signature from being used multiple times.\n */\n function nonces(address owner) external view returns (uint256);\n\n /**\n * @dev Returns the domain separator used in the encoding of the signature for {permit}, as defined by {EIP712}.\n */\n // solhint-disable-next-line func-name-mixedcase\n function DOMAIN_SEPARATOR() external view returns (bytes32);\n}\n" + }, + "contracts/seed/SeedV2.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed contract. Smart contract for seed phases of liquid launch.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable operator-whitespace\n/* solhint-disable space-after-comma */\n/* solhint-disable max-states-count */\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/IERC20.sol\";\nimport \"@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol\";\n\n/**\n * @title PrimeDAO Seed contract version 2.1.0\n * @dev Smart contract for seed phases of Prime Launch.\n */\ncontract SeedV2 {\n bytes6 public version = \"2.1.0\";\n using SafeERC20 for IERC20;\n // Locked parameters\n address public beneficiary; // The address that recieves fees\n address public admin; // The address of the admin of this contract\n address public treasury; // The address that receives the raised funding tokens, and\n // retrievable seed tokens.\n uint256 public softCap; // The minimum to be reached to consider this Seed successful,\n // expressed in Funding tokens\n uint256 public hardCap; // The maximum of Funding tokens to be raised in the Seed\n uint256 public seedAmountRequired; // Amount of seed required for distribution (buyable + tip)\n uint256 public totalBuyableSeed; // Amount of buyable seed tokens\n uint256 public startTime; // Start of the buyable period\n uint256 public endTime; // End of the buyable period\n uint256 public vestingStartTime; // timestamp for when vesting starts, by default == endTime,\n // otherwise when maximumReached is reached\n bool public permissionedSeed; // Set to true if only allowlisted adresses are allowed to participate\n IERC20 public seedToken; // The address of the seed token being distributed\n IERC20 public fundingToken; // The address of the funding token being exchanged for seed token\n bytes public metadata; // IPFS Hash wich has all the Seed parameters stored\n\n uint256 internal constant PRECISION = 10**18; // used for precision e.g. 1 ETH = 10**18 wei; toWei(\"1\") = 10**18\n\n // Contract logic\n bool public closed; // is the distribution closed\n bool public paused; // is the distribution paused\n bool public isFunded; // distribution can only start when required seed tokens have been funded\n bool public initialized; // is this contract initialized [not necessary that it is funded]\n bool public minimumReached; // if the softCap[minimum limit of funding token] is reached\n bool public maximumReached; // if the hardCap[maximum limit of funding token] is reached\n\n uint256 public totalFunderCount; // Total funders that have contributed.\n uint256 public seedRemainder; // Amount of seed tokens remaining to be distributed\n uint256 public seedClaimed; // Amount of seed token claimed by the user.\n uint256 public fundingCollected; // Amount of funding tokens collected by the seed contract.\n uint256 public fundingWithdrawn; // Amount of funding token withdrawn from the seed contract.\n\n uint256 public price; // Price of the Seed token, expressed in Funding token with precision 10**18\n Tip public tip; // State which stores all the Tip parameters\n\n ContributorClass[] public classes; // Array of contributor classes\n\n mapping(address => FunderPortfolio) public funders; // funder address to funder portfolio\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedsPurchased(\n address indexed recipient,\n uint256 indexed amountPurchased,\n uint256 indexed seedRemainder\n );\n event TokensClaimed(address indexed recipient, uint256 indexed amount);\n event FundingReclaimed(\n address indexed recipient,\n uint256 indexed amountReclaimed\n );\n event MetadataUpdated(bytes indexed metadata);\n event TipClaimed(uint256 indexed amountClaimed);\n\n // ----------------------------------------\n // STRUCTS\n // ----------------------------------------\n\n // Struct which stores all the information of a given funder address\n struct FunderPortfolio {\n uint8 class; // Contibutor class id\n uint256 totalClaimed; // Total amount of seed tokens claimed\n uint256 fundingAmount; // Total amount of funding tokens contributed\n bool allowlist; // If permissioned Seed, funder needs to be allowlisted\n }\n // Struct which stores all the parameters of a contributor class\n struct ContributorClass {\n bytes32 className; // Name of the class\n uint256 classCap; // Amount of tokens that can be donated for class\n uint256 individualCap; // Amount of tokens that can be donated by specific contributor\n uint256 vestingCliff; // Cliff after which the vesting starts to get released\n uint256 vestingDuration; // Vesting duration for class\n uint256 classFundingCollected; // Total amount of staked tokens\n }\n // Struct which stores all the parameters related to the Tip\n struct Tip {\n uint256 tipPercentage; // Total amount of tip percentage,\n uint256 vestingCliff; // Tip cliff duration denominated in seconds.\n uint256 vestingDuration; // Tip vesting period duration denominated in seconds.\n uint256 tipAmount; // Tip amount denominated in Seed tokens\n uint256 totalClaimed; // Total amount of Seed tokens already claimed\n }\n\n // ----------------------------------------\n // MODIFIERS\n // ----------------------------------------\n\n modifier claimable() {\n require(\n endTime < block.timestamp || maximumReached || closed,\n \"Seed: Error 346\"\n );\n _;\n }\n\n modifier onlyAdmin() {\n require(msg.sender == admin, \"Seed: Error 322\");\n _;\n }\n\n modifier isActive() {\n require(!closed, \"Seed: Error 348\");\n require(!paused, \"Seed: Error 349\");\n _;\n }\n\n modifier isLive() {\n require(\n !closed && block.timestamp < vestingStartTime,\n \"Seed: Error 350\"\n );\n _;\n }\n\n modifier isNotClosed() {\n require(!closed, \"Seed: Error 348\");\n _;\n }\n\n modifier hasNotStarted() {\n require(block.timestamp < startTime, \"Seed: Error 344\");\n _;\n }\n\n modifier classRestriction(uint256 _classCap, uint256 _individualCap) {\n require(\n _individualCap <= _classCap && _classCap <= hardCap,\n \"Seed: Error 303\"\n );\n require(_classCap > 0, \"Seed: Error 101\");\n _;\n }\n\n modifier classBatchRestrictions(\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlist\n ) {\n require(\n _classNames.length == _classCaps.length &&\n _classNames.length == _individualCaps.length &&\n _classNames.length == _vestingCliffs.length &&\n _classNames.length == _vestingDurations.length &&\n _classNames.length == _allowlist.length,\n \"Seed: Error 102\"\n );\n require(_classNames.length <= 100, \"Seed: Error 304\");\n require(classes.length + _classNames.length <= 256, \"Seed: Error 305\");\n _;\n }\n\n /**\n * @dev Initialize Seed.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price Price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t- Tipcliff duration denominated in seconds.\t\n */\n function initialize(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip\n ) external {\n require(!initialized, \"Seed: Error 001\");\n initialized = true;\n\n beneficiary = _beneficiary;\n admin = _projectAddresses[0];\n treasury = _projectAddresses[1];\n softCap = _softAndHardCap[0];\n hardCap = _softAndHardCap[1];\n startTime = _startTimeAndEndTime[0];\n endTime = _startTimeAndEndTime[1];\n vestingStartTime = _startTimeAndEndTime[1] + 1;\n permissionedSeed = _permissionedSeed;\n seedToken = IERC20(_tokens[0]);\n fundingToken = IERC20(_tokens[1]);\n price = _price;\n\n totalBuyableSeed = (_softAndHardCap[1] * PRECISION) / _price;\n // Calculate tip\n uint256 tipAmount = (totalBuyableSeed * _tip[0]) / PRECISION;\n tip = Tip(_tip[0], _tip[1], _tip[2], tipAmount, 0);\n // Add default class\n _addClass(\n bytes32(\"\"),\n _softAndHardCap[1],\n _defaultClassParameters[0],\n _defaultClassParameters[1],\n _defaultClassParameters[2]\n );\n\n // Add allowlist to the default class\n if (_permissionedSeed == true && _allowlistAddresses.length > 0) {\n uint256 arrayLength = _allowlistAddresses.length;\n for (uint256 i; i < arrayLength; ++i) {\n _addToClass(0, _allowlistAddresses[i]); // Value 0 for the default class\n }\n _addAddressesToAllowlist(_allowlistAddresses);\n }\n\n seedRemainder = totalBuyableSeed;\n seedAmountRequired = tipAmount + seedRemainder;\n }\n\n /**\n * @dev Buy seed tokens.\n * @param _fundingAmount The amount of funding tokens to contribute.\n */\n function buy(uint256 _fundingAmount) external isActive returns (uint256) {\n FunderPortfolio storage funder = funders[msg.sender];\n require(!permissionedSeed || funder.allowlist, \"Seed: Error 320\");\n\n ContributorClass memory userClass = classes[funder.class];\n require(!maximumReached, \"Seed: Error 340\");\n require(_fundingAmount > 0, \"Seed: Error 101\");\n\n require(\n endTime >= block.timestamp && startTime <= block.timestamp,\n \"Seed: Error 361\"\n );\n\n if (!isFunded) {\n require(\n seedToken.balanceOf(address(this)) >= seedAmountRequired,\n \"Seed: Error 343\"\n );\n isFunded = true;\n }\n // Update _fundingAmount to reflect the possible buyable amnount\n if ((fundingCollected + _fundingAmount) > hardCap) {\n _fundingAmount = hardCap - fundingCollected;\n }\n if (\n (userClass.classFundingCollected + _fundingAmount) >\n userClass.classCap\n ) {\n _fundingAmount =\n userClass.classCap -\n userClass.classFundingCollected;\n }\n require(\n (funder.fundingAmount + _fundingAmount) <= userClass.individualCap,\n \"Seed: Error 360\"\n );\n\n uint256 seedAmount = (_fundingAmount * PRECISION) / price;\n // total fundingAmount should not be greater than the hardCap\n\n fundingCollected += _fundingAmount;\n classes[funder.class].classFundingCollected += _fundingAmount;\n // the amount of seed tokens still to be distributed\n seedRemainder = seedRemainder - seedAmount;\n if (fundingCollected >= softCap) {\n minimumReached = true;\n }\n\n if (fundingCollected >= hardCap) {\n maximumReached = true;\n vestingStartTime = block.timestamp;\n }\n\n //functionality of addFunder\n if (funder.fundingAmount == 0) {\n totalFunderCount++;\n }\n funder.fundingAmount += _fundingAmount;\n\n // Here we are sending amount of tokens to pay for seed tokens to purchase\n\n fundingToken.safeTransferFrom(\n msg.sender,\n address(this),\n _fundingAmount\n );\n\n emit SeedsPurchased(msg.sender, seedAmount, seedRemainder);\n\n return (seedAmount);\n }\n\n /**\n * @dev Claim vested seed tokens.\n * @param _claimAmount The amount of seed token a users wants to claim.\n */\n function claim(uint256 _claimAmount) external claimable {\n require(minimumReached, \"Seed: Error 341\");\n\n uint256 amountClaimable;\n\n amountClaimable = calculateClaimFunder(msg.sender);\n require(amountClaimable > 0, \"Seed: Error 380\");\n\n require(amountClaimable >= _claimAmount, \"Seed: Error 381\");\n\n funders[msg.sender].totalClaimed += _claimAmount;\n\n seedClaimed += _claimAmount;\n\n seedToken.safeTransfer(msg.sender, _claimAmount);\n\n emit TokensClaimed(msg.sender, _claimAmount);\n }\n\n function claimTip() external claimable returns (uint256) {\n uint256 amountClaimable;\n\n amountClaimable = calculateClaimBeneficiary();\n require(amountClaimable > 0, \"Seed: Error 380\");\n\n tip.totalClaimed += amountClaimable;\n\n seedToken.safeTransfer(beneficiary, amountClaimable);\n\n emit TipClaimed(amountClaimable);\n\n return amountClaimable;\n }\n\n /**\n * @dev Returns funding tokens to user.\n */\n function retrieveFundingTokens() external returns (uint256) {\n require(startTime <= block.timestamp, \"Seed: Error 344\");\n require(!minimumReached, \"Seed: Error 342\");\n FunderPortfolio storage tokenFunder = funders[msg.sender];\n uint256 fundingAmount = tokenFunder.fundingAmount;\n require(fundingAmount > 0, \"Seed: Error 380\");\n seedRemainder += seedAmountForFunder(msg.sender);\n totalFunderCount--;\n tokenFunder.fundingAmount = 0;\n fundingCollected -= fundingAmount;\n classes[tokenFunder.class].classFundingCollected -= fundingAmount;\n\n fundingToken.safeTransfer(msg.sender, fundingAmount);\n\n emit FundingReclaimed(msg.sender, fundingAmount);\n\n return fundingAmount;\n }\n\n // ----------------------------------------\n // ADMIN FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Changes all de classes given in the _classes parameter, editing\n the different parameters of the class, and allowlist addresses\n if applicable.\n * @param _classes Class for changing.\n * @param _classNames The name of the class\n * @param _classCaps The total cap of the contributor class, denominated in Wei.\n * @param _individualCaps The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliffs The cliff duration, denominated in seconds.\n * @param _vestingDurations The vesting duration for this contributors class.\n * @param _allowlists Array of addresses to be allowlisted\n */\n function changeClassesAndAllowlists(\n uint8[] memory _classes,\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlists\n )\n external\n onlyAdmin\n hasNotStarted\n isNotClosed\n classBatchRestrictions(\n _classNames,\n _classCaps,\n _individualCaps,\n _vestingCliffs,\n _vestingDurations,\n _allowlists\n )\n {\n for (uint8 i; i < _classes.length; ++i) {\n _changeClass(\n _classes[i],\n _classNames[i],\n _classCaps[i],\n _individualCaps[i],\n _vestingCliffs[i],\n _vestingDurations[i]\n );\n\n if (permissionedSeed) {\n _addAddressesToAllowlist(_allowlists[i]);\n }\n for (uint256 j; j < _allowlists[i].length; ++j) {\n _addToClass(_classes[i], _allowlists[i][j]);\n }\n }\n }\n\n /**\n * @dev Pause distribution.\n */\n function pause() external onlyAdmin isActive {\n paused = true;\n }\n\n /**\n * @dev Unpause distribution.\n */\n function unpause() external onlyAdmin {\n require(closed != true, \"Seed: Error 348\");\n require(paused == true, \"Seed: Error 351\");\n\n paused = false;\n }\n\n /**\n * @dev Shut down contributions (buying).\n Supersedes the normal logic that eventually shuts down buying anyway.\n Also shuts down the admin's ability to alter the allowlist.\n */\n function close() external onlyAdmin {\n // close seed token distribution\n require(!closed, \"Seed: Error 348\");\n\n if (block.timestamp < vestingStartTime) {\n vestingStartTime = block.timestamp;\n }\n\n closed = true;\n paused = false;\n }\n\n /**\n * @dev retrieve remaining seed tokens back to project.\n */\n function retrieveSeedTokens() external {\n // transfer seed tokens back to treasury\n /*\n Can't withdraw seed tokens until buying has ended and\n therefore the number of distributable seed tokens can no longer change.\n */\n require(\n closed || maximumReached || block.timestamp >= endTime,\n \"Seed: Error 382\"\n );\n uint256 seedTokenBalance = seedToken.balanceOf(address(this));\n if (!minimumReached) {\n require(seedTokenBalance > 0, \"Seed: Error 345\");\n // subtract tip from Seed tokens\n uint256 retrievableSeedAmount = seedTokenBalance -\n (tip.tipAmount - tip.totalClaimed);\n seedToken.safeTransfer(treasury, retrievableSeedAmount);\n } else {\n // seed tokens to transfer = buyable seed tokens - totalSeedDistributed\n uint256 totalSeedDistributed = totalBuyableSeed - seedRemainder;\n uint256 amountToTransfer = seedTokenBalance -\n (totalSeedDistributed - seedClaimed) -\n (tip.tipAmount - tip.totalClaimed);\n seedToken.safeTransfer(treasury, amountToTransfer);\n }\n }\n\n /**\n * @dev Add classes and allowlists to the contract by batching them into one\n function call. It adds allowlists to the created classes if applicable\n * @param _classNames The name of the class\n * @param _classCaps The total cap of the contributor class, denominated in Wei.\n * @param _individualCaps The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliffs The cliff duration, denominated in seconds.\n * @param _vestingDurations The vesting duration for this contributors class.\n * @param _allowlist Array of addresses to be allowlisted\n */\n function addClassesAndAllowlists(\n bytes32[] memory _classNames,\n uint256[] memory _classCaps,\n uint256[] memory _individualCaps,\n uint256[] memory _vestingCliffs,\n uint256[] memory _vestingDurations,\n address[][] memory _allowlist\n )\n external\n onlyAdmin\n hasNotStarted\n isNotClosed\n classBatchRestrictions(\n _classNames,\n _classCaps,\n _individualCaps,\n _vestingCliffs,\n _vestingDurations,\n _allowlist\n )\n {\n uint256 currentClassId = uint256(classes.length);\n for (uint8 i; i < _classNames.length; ++i) {\n _addClass(\n _classNames[i],\n _classCaps[i],\n _individualCaps[i],\n _vestingCliffs[i],\n _vestingDurations[i]\n );\n }\n uint256 arrayLength = _allowlist.length;\n if (permissionedSeed) {\n for (uint256 i; i < arrayLength; ++i) {\n _addAddressesToAllowlist(_allowlist[i]);\n }\n }\n for (uint256 i; i < arrayLength; ++i) {\n uint256 numberOfAddresses = _allowlist[i].length;\n for (uint256 j; j < numberOfAddresses; ++j) {\n _addToClass(uint8(currentClassId), _allowlist[i][j]);\n }\n ++currentClassId;\n }\n }\n\n /**\n * @dev Add multiple addresses to contributor classes, and if applicable\n allowlist them.\n * @param _buyers Array of addresses to be allowlisted\n * @param _classes Array of classes assigned in batch\n */\n function allowlist(address[] memory _buyers, uint8[] memory _classes)\n external\n onlyAdmin\n isLive\n {\n if (permissionedSeed) {\n _addAddressesToAllowlist(_buyers);\n }\n _addMultipleAdressesToClass(_buyers, _classes);\n }\n\n /**\n * @dev Remove address from allowlist.\n * @param _buyer Address which needs to be un-allowlisted\n */\n function unAllowlist(address _buyer) external onlyAdmin isLive {\n require(permissionedSeed == true, \"Seed: Error 347\");\n\n funders[_buyer].allowlist = false;\n }\n\n /**\n * @dev Withdraw funds from the contract\n */\n function withdraw() external {\n /*\n Can't withdraw funding tokens until buying has ended and\n therefore contributors can no longer withdraw their funding tokens.\n */\n require(minimumReached, \"Seed: Error 383\");\n fundingWithdrawn = fundingCollected;\n // Send the entire seed contract balance of the funding token to the sale’s admin\n fundingToken.safeTransfer(\n treasury,\n fundingToken.balanceOf(address(this))\n );\n }\n\n /**\n * @dev Updates metadata.\n * @param _metadata Seed contract metadata, that is IPFS Hash\n */\n function updateMetadata(bytes memory _metadata) external {\n require(initialized != true || msg.sender == admin, \"Seed: Error 321\");\n metadata = _metadata;\n emit MetadataUpdated(_metadata);\n }\n\n // ----------------------------------------\n // INTERNAL FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Change parameters in the class given in the _class parameter\n * @param _class Class for changing.\n * @param _className The name of the class\n * @param _classCap The total cap of the contributor class, denominated in Wei.\n * @param _individualCap The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliff The cliff duration, denominated in seconds.\n * @param _vestingDuration The vesting duration for this contributors class.\n */\n function _changeClass(\n uint8 _class,\n bytes32 _className,\n uint256 _classCap,\n uint256 _individualCap,\n uint256 _vestingCliff,\n uint256 _vestingDuration\n ) internal classRestriction(_classCap, _individualCap) {\n require(_class < classes.length, \"Seed: Error 302\");\n\n classes[_class].className = _className;\n classes[_class].classCap = _classCap;\n classes[_class].individualCap = _individualCap;\n classes[_class].vestingCliff = _vestingCliff;\n classes[_class].vestingDuration = _vestingDuration;\n }\n\n /**\n * @dev Internal function that adds a class to the classes array\n * @param _className The name of the class\n * @param _classCap The total cap of the contributor class, denominated in Wei.\n * @param _individualCap The personal cap of each contributor in this class, denominated in Wei.\n * @param _vestingCliff The cliff duration, denominated in seconds.\n * @param _vestingDuration The vesting duration for this contributors class.\n */\n function _addClass(\n bytes32 _className,\n uint256 _classCap,\n uint256 _individualCap,\n uint256 _vestingCliff,\n uint256 _vestingDuration\n ) internal classRestriction(_classCap, _individualCap) {\n classes.push(\n ContributorClass(\n _className,\n _classCap,\n _individualCap,\n _vestingCliff,\n _vestingDuration,\n 0\n )\n );\n }\n\n /**\n * @dev Set contributor class.\n * @param _classId Class of the contributor.\n * @param _buyer Address of the contributor.\n */\n function _addToClass(uint8 _classId, address _buyer) internal {\n require(_classId < classes.length, \"Seed: Error 302\");\n funders[_buyer].class = _classId;\n }\n\n /**\n * @dev Set contributor class.\n * @param _buyers Address of the contributor.\n * @param _classes Class of the contributor.\n */\n function _addMultipleAdressesToClass(\n address[] memory _buyers,\n uint8[] memory _classes\n ) internal {\n uint256 arrayLength = _buyers.length;\n require(_classes.length == arrayLength, \"Seed: Error 102\");\n\n for (uint256 i; i < arrayLength; ++i) {\n _addToClass(_classes[i], _buyers[i]);\n }\n }\n\n /**\n * @dev Add address to allowlist.\n * @param _buyers Address which needs to be allowlisted\n */\n function _addAddressesToAllowlist(address[] memory _buyers) internal {\n uint256 arrayLength = _buyers.length;\n for (uint256 i; i < arrayLength; ++i) {\n funders[_buyers[i]].allowlist = true;\n }\n }\n\n function _calculateClaim(\n uint256 seedAmount,\n uint256 vestingCliff,\n uint256 vestingDuration,\n uint256 totalClaimed\n ) internal view returns (uint256) {\n if (block.timestamp < vestingStartTime) {\n return 0;\n }\n\n // Check cliff was reached\n uint256 elapsedSeconds = block.timestamp - vestingStartTime;\n if (elapsedSeconds < vestingCliff) {\n return 0;\n }\n\n // If over vesting duration, all tokens vested\n if (elapsedSeconds >= vestingDuration) {\n return seedAmount - totalClaimed;\n } else {\n uint256 amountVested = (elapsedSeconds * seedAmount) /\n vestingDuration;\n return amountVested - totalClaimed;\n }\n }\n\n // ----------------------------------------\n // GETTER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Calculates the maximum claim of the funder address\n * @param _funder Address of funder to find the maximum claim\n */\n function calculateClaimFunder(address _funder)\n public\n view\n returns (uint256)\n {\n FunderPortfolio memory tokenFunder = funders[_funder];\n uint8 currentId = tokenFunder.class;\n ContributorClass memory claimed = classes[currentId];\n\n return\n _calculateClaim(\n seedAmountForFunder(_funder),\n claimed.vestingCliff,\n claimed.vestingDuration,\n tokenFunder.totalClaimed\n );\n }\n\n /**\n * @dev Calculates the maximum claim for the beneficiary\n */\n function calculateClaimBeneficiary() public view returns (uint256) {\n return\n _calculateClaim(\n tip.tipAmount,\n tip.vestingCliff,\n tip.vestingDuration,\n tip.totalClaimed\n );\n }\n\n /**\n * @dev Returns arrays with all the parameters of all the classes\n */\n function getAllClasses()\n external\n view\n returns (\n bytes32[] memory classNames,\n uint256[] memory classCaps,\n uint256[] memory individualCaps,\n uint256[] memory vestingCliffs,\n uint256[] memory vestingDurations,\n uint256[] memory classFundingsCollected\n )\n {\n uint256 numberOfClasses = classes.length;\n classNames = new bytes32[](numberOfClasses);\n classCaps = new uint256[](numberOfClasses);\n individualCaps = new uint256[](numberOfClasses);\n vestingCliffs = new uint256[](numberOfClasses);\n vestingDurations = new uint256[](numberOfClasses);\n classFundingsCollected = new uint256[](numberOfClasses);\n for (uint256 i; i < numberOfClasses; ++i) {\n ContributorClass storage class = classes[i];\n classNames[i] = class.className;\n classCaps[i] = class.classCap;\n individualCaps[i] = class.individualCap;\n vestingCliffs[i] = class.vestingCliff;\n vestingDurations[i] = class.vestingDuration;\n classFundingsCollected[i] = class.classFundingCollected;\n }\n }\n\n /**\n * @dev get seed amount for funder\n * @param _funder address of funder to seed amount\n */\n function seedAmountForFunder(address _funder)\n public\n view\n returns (uint256)\n {\n return (funders[_funder].fundingAmount * PRECISION) / price;\n }\n}\n" + }, + "contracts/seed/SeedFactoryV2NoAccessControl.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed Factory version 2 contract. Enable PrimeDAO governance to create new Seed contracts.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable linebreak-style\n/* solhint-disable space-after-comma */\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./SeedV2.sol\";\nimport \"../utils/CloneFactory.sol\";\n\n/**\n * @title PrimeDAO Seed Factory V2\n * @dev SeedFactory version 2 deployed without the onlyOwner modifer for the function deploySeed(). By \n removing the access control, everyone can deploy a seed from this contract. This is\n * a temporarly solution in response to the flaky Celo Safe.\n */\ncontract SeedFactoryV2NoAccessControl is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n SeedV2 public masterCopy; // Seed implementation address, which is used in the cloning pattern\n uint256 internal constant MAX_TIP = (45 / 100) * 10**18; // Max tip expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee)\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedCreated(\n address indexed newSeed,\n address indexed admin,\n address indexed treasury\n );\n\n constructor(SeedV2 _masterCopy) {\n require(address(_masterCopy) != address(0), \"SeedFactory: Error 100\");\n masterCopy = _masterCopy;\n }\n\n // ----------------------------------------\n // ONLY OWNER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Set Seed contract which works as a base for clones.\n * @param _masterCopy The address of the new Seed basis.\n */\n function setMasterCopy(SeedV2 _masterCopy) external onlyOwner {\n require(\n address(_masterCopy) != address(0) &&\n address(_masterCopy) != address(this),\n \"SeedFactory: Error 100\"\n );\n\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Deploys Seed contract.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage, calculated from the total amount of Seed tokens added to the contract, expressed as a % (e.g. 10**18 = 100% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip cliff duration denominated in seconds.\t\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n * @param _metadata Seed contract metadata, that is IPFS URI\n */\n function deploySeed(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip,\n bytes memory _metadata\n ) external returns (address) {\n {\n require(\n _tip.length == 3 &&\n _tokens.length == 2 &&\n _softAndHardCap.length == 2 &&\n _startTimeAndEndTime.length == 2 &&\n _defaultClassParameters.length == 3 &&\n _projectAddresses.length == 2,\n \"SeedFactory: Error 102\"\n );\n require(\n _beneficiary != address(0) &&\n _projectAddresses[0] != address(0) &&\n _projectAddresses[1] != address(0) &&\n _tokens[0] != address(0) &&\n _tokens[1] != address(0),\n \"SeedFactory: Error 100\"\n );\n require(\n _tokens[0] != _tokens[1] &&\n _beneficiary != _projectAddresses[0] &&\n _beneficiary != _projectAddresses[1],\n \"SeedFactory: Error 104\"\n );\n require(\n _softAndHardCap[1] >= _softAndHardCap[0],\n \"SeedFactory: Error 300\"\n );\n require(\n _startTimeAndEndTime[1] > _startTimeAndEndTime[0] &&\n block.timestamp < _startTimeAndEndTime[0],\n \"SeedFactory: Error 106\"\n );\n require(_tip[0] <= MAX_TIP, \"SeedFactory: Error 301\");\n }\n\n // deploy clone\n address _newSeed = createClone(address(masterCopy));\n\n SeedV2(_newSeed).updateMetadata(_metadata);\n\n // initialize\n SeedV2(_newSeed).initialize(\n _beneficiary,\n _projectAddresses,\n _tokens,\n _softAndHardCap,\n _price,\n _startTimeAndEndTime,\n _defaultClassParameters,\n _permissionedSeed,\n _allowlistAddresses,\n _tip\n );\n\n emit SeedCreated(\n address(_newSeed),\n _projectAddresses[0],\n _projectAddresses[1]\n );\n\n return _newSeed;\n }\n}\n" + }, + "contracts/seed/SeedFactoryV2.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0\n// PrimeDAO Seed Factory version 2 contract. Enable PrimeDAO governance to create new Seed contracts.\n// Copyright (C) 2022 PrimeDao\n\n// solium-disable linebreak-style\n/* solhint-disable space-after-comma */\n\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./SeedV2.sol\";\nimport \"../utils/CloneFactory.sol\";\n\n/**\n * @title PrimeDAO Seed Factory version 2.1.0\n * @dev Enable PrimeDAO governance to create new Seed contracts.\n */\ncontract SeedFactoryV2 is CloneFactory, Ownable {\n bytes6 public version = \"2.1.0\";\n SeedV2 public masterCopy; // Seed implementation address, which is used in the cloning pattern\n uint256 internal constant MAX_TIP = (45 / 100) * 10**18; // Max tip expressed as a % (e.g. 45 / 100 * 10**18 = 45% fee)\n\n // ----------------------------------------\n // EVENTS\n // ----------------------------------------\n\n event SeedCreated(\n address indexed newSeed,\n address indexed admin,\n address indexed treasury\n );\n\n constructor(SeedV2 _masterCopy) {\n require(address(_masterCopy) != address(0), \"SeedFactory: Error 100\");\n masterCopy = _masterCopy;\n }\n\n // ----------------------------------------\n // ONLY OWNER FUNCTIONS\n // ----------------------------------------\n\n /**\n * @dev Set Seed contract which works as a base for clones.\n * @param _masterCopy The address of the new Seed basis.\n */\n function setMasterCopy(SeedV2 _masterCopy) external onlyOwner {\n require(\n address(_masterCopy) != address(0) &&\n address(_masterCopy) != address(this),\n \"SeedFactory: Error 100\"\n );\n\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Deploys Seed contract.\n * @param _beneficiary The address that recieves fees.\n * @param _projectAddresses Array containing two params:\n - The address of the admin of this contract. Funds contract\n and has permissions to allowlist users, pause and close contract.\n - The treasury address which is the receiver of the funding tokens\n raised, as well as the reciever of the retrievable seed tokens.\n * @param _tokens Array containing two params:\n - The address of the seed token being distributed.\n * - The address of the funding token being exchanged for seed token.\n * @param _softAndHardCap Array containing two params:\n - the minimum funding token collection threshold in wei denomination.\n - the highest possible funding token amount to be raised in wei denomination.\n * @param _price price of a SeedToken, expressed in fundingTokens, with precision of 10**18\n * @param _startTimeAndEndTime Array containing two params:\n - Distribution start time in unix timecode.\n - Distribution end time in unix timecode.\n * @param _defaultClassParameters Array containing three params:\n\t\t\t\t\t\t\t\t\t\t\t\t- Individual buying cap for de default class, expressed in precision 10*18\n\t\t\t\t\t\t\t\t\t\t\t\t- Cliff duration, denominated in seconds.\n - Vesting period duration, denominated in seconds.\n * @param _permissionedSeed Set to true if only allowlisted adresses are allowed to participate.\n * @param _allowlistAddresses Array of addresses to be allowlisted for the default class, at creation time\n * @param _tip Array of containing three parameters:\n\t\t\t\t\t\t\t\t\t\t\t\t- Total amount of tip percentage, calculated from the total amount of Seed tokens added to the contract, expressed as a % (e.g. 10**18 = 100% fee, 10**16 = 1%)\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip cliff duration denominated in seconds.\t\n\t\t\t\t\t\t\t\t\t\t\t\t- Tip vesting period duration denominated in seconds.\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n * @param _metadata Seed contract metadata, that is IPFS URI\n */\n function deploySeed(\n address _beneficiary,\n address[] memory _projectAddresses,\n address[] memory _tokens,\n uint256[] memory _softAndHardCap,\n uint256 _price,\n uint256[] memory _startTimeAndEndTime,\n uint256[] memory _defaultClassParameters,\n bool _permissionedSeed,\n address[] memory _allowlistAddresses,\n uint256[] memory _tip,\n bytes memory _metadata\n ) external onlyOwner returns (address) {\n {\n require(\n _tip.length == 3 &&\n _tokens.length == 2 &&\n _softAndHardCap.length == 2 &&\n _startTimeAndEndTime.length == 2 &&\n _defaultClassParameters.length == 3 &&\n _projectAddresses.length == 2,\n \"SeedFactory: Error 102\"\n );\n require(\n _beneficiary != address(0) &&\n _projectAddresses[0] != address(0) &&\n _projectAddresses[1] != address(0) &&\n _tokens[0] != address(0) &&\n _tokens[1] != address(0),\n \"SeedFactory: Error 100\"\n );\n require(\n _tokens[0] != _tokens[1] &&\n _beneficiary != _projectAddresses[0] &&\n _beneficiary != _projectAddresses[1],\n \"SeedFactory: Error 104\"\n );\n require(\n _softAndHardCap[1] >= _softAndHardCap[0],\n \"SeedFactory: Error 300\"\n );\n require(\n _startTimeAndEndTime[1] > _startTimeAndEndTime[0] &&\n block.timestamp < _startTimeAndEndTime[0],\n \"SeedFactory: Error 106\"\n );\n require(_tip[0] <= MAX_TIP, \"SeedFactory: Error 301\");\n }\n\n // deploy clone\n address _newSeed = createClone(address(masterCopy));\n\n SeedV2(_newSeed).updateMetadata(_metadata);\n\n // initialize\n SeedV2(_newSeed).initialize(\n _beneficiary,\n _projectAddresses,\n _tokens,\n _softAndHardCap,\n _price,\n _startTimeAndEndTime,\n _defaultClassParameters,\n _permissionedSeed,\n _allowlistAddresses,\n _tip\n );\n\n emit SeedCreated(\n address(_newSeed),\n _projectAddresses[0],\n _projectAddresses[1]\n );\n\n return _newSeed;\n }\n}\n" + }, + "contracts/lbp/LBPManagerFactory.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// LBPManager Factory contract. Governance to create new LBPManager contracts.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"../utils/CloneFactory.sol\";\nimport \"@openzeppelin/contracts/access/Ownable.sol\";\nimport \"./LBPManager.sol\";\n\n/**\n * @title LBPManager Factory\n * @dev Governance to create new LBPManager contracts.\n */\ncontract LBPManagerFactory is CloneFactory, Ownable {\n address public masterCopy;\n address public lbpFactory;\n\n event LBPManagerDeployed(\n address indexed lbpManager,\n address indexed admin,\n bytes metadata\n );\n\n event LBPFactoryChanged(\n address indexed oldLBPFactory,\n address indexed newLBPFactory\n );\n\n event MastercopyChanged(\n address indexed oldMasterCopy,\n address indexed newMasterCopy\n );\n\n /**\n * @dev Constructor.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n constructor(address _lbpFactory) {\n require(_lbpFactory != address(0), \"LBPMFactory: LBPFactory is zero\");\n lbpFactory = _lbpFactory;\n }\n\n modifier validAddress(address addressToCheck) {\n require(addressToCheck != address(0), \"LBPMFactory: address is zero\");\n // solhint-disable-next-line reason-string\n require(\n addressToCheck != address(this),\n \"LBPMFactory: address same as LBPManagerFactory\"\n );\n _;\n }\n\n /**\n * @dev Set LBPManager contract which works as a base for clones.\n * @param _masterCopy The address of the new LBPManager basis.\n */\n function setMasterCopy(address _masterCopy)\n external\n onlyOwner\n validAddress(_masterCopy)\n {\n emit MastercopyChanged(masterCopy, _masterCopy);\n masterCopy = _masterCopy;\n }\n\n /**\n * @dev Set Balancers LBP Factory contract as basis for deploying LBPs.\n * @param _lbpFactory The address of Balancers LBP factory.\n */\n function setLBPFactory(address _lbpFactory)\n external\n onlyOwner\n validAddress(_lbpFactory)\n {\n emit LBPFactoryChanged(lbpFactory, _lbpFactory);\n lbpFactory = _lbpFactory;\n }\n\n /**\n * @dev Deploy and initialize LBPManager.\n * @param _admin The address of the admin of the LBPManager.\n * @param _beneficiary The address that receives the _fees.\n * @param _name Name of the LBP.\n * @param _symbol Symbol of the LBP.\n * @param _tokenList Numerically sorted array (ascending) containing two addresses:\n - The address of the project token being distributed.\n - The address of the funding token being exchanged for the project token.\n * @param _amounts Sorted array to match the _tokenList, containing two parameters:\n - The amounts of project token to be added as liquidity to the LBP.\n - The amounts of funding token to be added as liquidity to the LBP.\n * @param _startWeights Sorted array to match the _tokenList, containing two parametes:\n - The start weight for the project token in the LBP.\n - The start weight for the funding token in the LBP.\n * @param _startTimeEndtime Array containing two parameters:\n - Start time for the LBP.\n - End time for the LBP.\n * @param _endWeights Sorted array to match the _tokenList, containing two parametes:\n - The end weight for the project token in the LBP.\n - The end weight for the funding token in the LBP.\n * @param _fees Array containing two parameters:\n - Percentage of fee paid for every swap in the LBP.\n - Percentage of fee paid to the _beneficiary for providing the service of the LBP Manager.\n * @param _metadata IPFS Hash of the LBP creation wizard information.\n */\n function deployLBPManager(\n address _admin,\n address _beneficiary,\n string memory _name,\n string memory _symbol,\n IERC20[] memory _tokenList,\n uint256[] memory _amounts,\n uint256[] memory _startWeights,\n uint256[] memory _startTimeEndtime,\n uint256[] memory _endWeights,\n uint256[] memory _fees,\n bytes memory _metadata\n ) external onlyOwner {\n // solhint-disable-next-line reason-string\n require(\n masterCopy != address(0),\n \"LBPMFactory: LBPManager mastercopy not set\"\n );\n\n address lbpManager = createClone(masterCopy);\n\n LBPManager(lbpManager).initializeLBPManager(\n lbpFactory,\n _beneficiary,\n _name,\n _symbol,\n _tokenList,\n _amounts,\n _startWeights,\n _startTimeEndtime,\n _endWeights,\n _fees,\n _metadata\n );\n\n LBPManager(lbpManager).transferAdminRights(_admin);\n\n emit LBPManagerDeployed(lbpManager, _admin, _metadata);\n }\n}\n" + }, + "contracts/test/ERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\n\ncontract ERC20Mock is ERC20 {\n uint256 public constant initialSupply = 20000000000000000000000;\n\n constructor(string memory _name, string memory _symbol)\n ERC20(_name, _symbol)\n {\n _mint(msg.sender, initialSupply);\n }\n}\n" + }, + "contracts/test/CustomERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\nimport \"hardhat/console.sol\";\n\ncontract CustomERC20Mock is ERC20 {\n mapping(address => uint256) private _balances;\n\n mapping(address => mapping(address => uint256)) private _allowances;\n\n constructor(string memory _name, string memory _symbol)\n ERC20(_name, _symbol)\n {\n _balances[msg.sender] += 20000000000000000000000;\n }\n\n function transfer(address recipient, uint256 amount)\n public\n virtual\n override\n returns (bool)\n {\n bool success = _customTransfer(_msgSender(), recipient, amount);\n return success;\n }\n\n function transferFrom(\n address sender,\n address recipient,\n uint256 amount\n ) public virtual override returns (bool) {\n uint256 currentAllowance = _allowances[sender][_msgSender()];\n if (currentAllowance < amount) {\n return false;\n }\n\n bool success = _customTransfer(sender, recipient, amount);\n if (success) {\n /* solium-disable */\n unchecked {\n _approve(sender, _msgSender(), currentAllowance - amount);\n }\n /* solium-enable */\n }\n return true;\n }\n\n function approve(address spender, uint256 amount)\n public\n virtual\n override\n returns (bool)\n {\n _approve(_msgSender(), spender, amount);\n return true;\n }\n\n function balanceOf(address account)\n public\n view\n virtual\n override\n returns (uint256)\n {\n return _balances[account];\n }\n\n function burn(address account) public {\n _balances[account] = 0;\n }\n\n function mint(address account, uint256 amount) public {\n _balances[account] += amount;\n }\n\n function _customTransfer(\n address sender,\n address recipient,\n uint256 amount\n ) internal virtual returns (bool) {\n uint256 senderBalance = _balances[sender];\n if (\n sender == address(0) ||\n recipient == address(0) ||\n senderBalance < amount\n ) {\n return false;\n }\n unchecked {\n _balances[sender] = senderBalance - amount;\n }\n _balances[recipient] += amount;\n emit Transfer(sender, recipient, amount);\n return true;\n }\n\n function _approve(\n address owner,\n address spender,\n uint256 amount\n ) internal virtual override {\n require(owner != address(0), \"ERC20: approve from the zero address\");\n require(spender != address(0), \"ERC20: approve to the zero address\");\n\n _allowances[owner][spender] = amount;\n emit Approval(owner, spender, amount);\n }\n}\n" + }, + "hardhat/console.sol": { + "content": "// SPDX-License-Identifier: MIT\npragma solidity >= 0.4.22 <0.9.0;\n\nlibrary console {\n\taddress constant CONSOLE_ADDRESS = address(0x000000000000000000636F6e736F6c652e6c6f67);\n\n\tfunction _sendLogPayload(bytes memory payload) private view {\n\t\tuint256 payloadLength = payload.length;\n\t\taddress consoleAddress = CONSOLE_ADDRESS;\n\t\tassembly {\n\t\t\tlet payloadStart := add(payload, 32)\n\t\t\tlet r := staticcall(gas(), consoleAddress, payloadStart, payloadLength, 0, 0)\n\t\t}\n\t}\n\n\tfunction log() internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log()\"));\n\t}\n\n\tfunction logInt(int256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(int256)\", p0));\n\t}\n\n\tfunction logUint(uint256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256)\", p0));\n\t}\n\n\tfunction logString(string memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string)\", p0));\n\t}\n\n\tfunction logBool(bool p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool)\", p0));\n\t}\n\n\tfunction logAddress(address p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address)\", p0));\n\t}\n\n\tfunction logBytes(bytes memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes)\", p0));\n\t}\n\n\tfunction logBytes1(bytes1 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes1)\", p0));\n\t}\n\n\tfunction logBytes2(bytes2 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes2)\", p0));\n\t}\n\n\tfunction logBytes3(bytes3 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes3)\", p0));\n\t}\n\n\tfunction logBytes4(bytes4 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes4)\", p0));\n\t}\n\n\tfunction logBytes5(bytes5 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes5)\", p0));\n\t}\n\n\tfunction logBytes6(bytes6 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes6)\", p0));\n\t}\n\n\tfunction logBytes7(bytes7 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes7)\", p0));\n\t}\n\n\tfunction logBytes8(bytes8 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes8)\", p0));\n\t}\n\n\tfunction logBytes9(bytes9 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes9)\", p0));\n\t}\n\n\tfunction logBytes10(bytes10 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes10)\", p0));\n\t}\n\n\tfunction logBytes11(bytes11 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes11)\", p0));\n\t}\n\n\tfunction logBytes12(bytes12 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes12)\", p0));\n\t}\n\n\tfunction logBytes13(bytes13 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes13)\", p0));\n\t}\n\n\tfunction logBytes14(bytes14 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes14)\", p0));\n\t}\n\n\tfunction logBytes15(bytes15 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes15)\", p0));\n\t}\n\n\tfunction logBytes16(bytes16 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes16)\", p0));\n\t}\n\n\tfunction logBytes17(bytes17 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes17)\", p0));\n\t}\n\n\tfunction logBytes18(bytes18 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes18)\", p0));\n\t}\n\n\tfunction logBytes19(bytes19 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes19)\", p0));\n\t}\n\n\tfunction logBytes20(bytes20 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes20)\", p0));\n\t}\n\n\tfunction logBytes21(bytes21 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes21)\", p0));\n\t}\n\n\tfunction logBytes22(bytes22 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes22)\", p0));\n\t}\n\n\tfunction logBytes23(bytes23 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes23)\", p0));\n\t}\n\n\tfunction logBytes24(bytes24 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes24)\", p0));\n\t}\n\n\tfunction logBytes25(bytes25 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes25)\", p0));\n\t}\n\n\tfunction logBytes26(bytes26 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes26)\", p0));\n\t}\n\n\tfunction logBytes27(bytes27 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes27)\", p0));\n\t}\n\n\tfunction logBytes28(bytes28 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes28)\", p0));\n\t}\n\n\tfunction logBytes29(bytes29 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes29)\", p0));\n\t}\n\n\tfunction logBytes30(bytes30 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes30)\", p0));\n\t}\n\n\tfunction logBytes31(bytes31 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes31)\", p0));\n\t}\n\n\tfunction logBytes32(bytes32 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bytes32)\", p0));\n\t}\n\n\tfunction log(uint256 p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256)\", p0));\n\t}\n\n\tfunction log(string memory p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string)\", p0));\n\t}\n\n\tfunction log(bool p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool)\", p0));\n\t}\n\n\tfunction log(address p0) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address)\", p0));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool)\", p0, p1));\n\t}\n\n\tfunction log(string memory p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool)\", p0, p1));\n\t}\n\n\tfunction log(bool p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address)\", p0, p1));\n\t}\n\n\tfunction log(address p0, uint256 p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256)\", p0, p1));\n\t}\n\n\tfunction log(address p0, string memory p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string)\", p0, p1));\n\t}\n\n\tfunction log(address p0, bool p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool)\", p0, p1));\n\t}\n\n\tfunction log(address p0, address p1) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address)\", p0, p1));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(bool p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, bool p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, bool p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool)\", p0, p1, p2));\n\t}\n\n\tfunction log(address p0, address p1, address p2) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address)\", p0, p1, p2));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(uint256 p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(uint256,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(string memory p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(string,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(bool p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(bool,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, uint256 p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,uint256,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, string memory p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,string,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, bool p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,bool,address,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, uint256 p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,uint256,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, string memory p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,string,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, bool p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,bool,address)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, uint256 p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,uint256)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, string memory p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,string)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, bool p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,bool)\", p0, p1, p2, p3));\n\t}\n\n\tfunction log(address p0, address p1, address p2, address p3) internal view {\n\t\t_sendLogPayload(abi.encodeWithSignature(\"log(address,address,address,address)\", p0, p1, p2, p3));\n\t}\n\n}\n" + }, + "contracts/test/CustomDecimalERC20Mock.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@openzeppelin/contracts/token/ERC20/ERC20.sol\";\n\ncontract CustomDecimalERC20Mock is ERC20 {\n uint8 private immutable _decimals;\n\n constructor(\n string memory _name,\n string memory _symbol,\n uint8 decimals_\n ) ERC20(_name, _symbol) {\n _mint(msg.sender, 200000000000000000000000000);\n _decimals = decimals_;\n }\n\n function decimals() public view virtual override returns (uint8) {\n return _decimals;\n }\n}\n" + }, + "contracts/test/Imports.sol": { + "content": "// SPDX-License-Identifier: GPL-3.0-or-later\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"@gnosis.pm/safe-contracts/contracts/GnosisSafe.sol\";\nimport \"@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxyFactory.sol\";\n" + }, + "@gnosis.pm/safe-contracts/contracts/GnosisSafe.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"./base/ModuleManager.sol\";\nimport \"./base/OwnerManager.sol\";\nimport \"./base/FallbackManager.sol\";\nimport \"./base/GuardManager.sol\";\nimport \"./common/EtherPaymentFallback.sol\";\nimport \"./common/Singleton.sol\";\nimport \"./common/SignatureDecoder.sol\";\nimport \"./common/SecuredTokenTransfer.sol\";\nimport \"./common/StorageAccessible.sol\";\nimport \"./interfaces/ISignatureValidator.sol\";\nimport \"./external/GnosisSafeMath.sol\";\n\n/// @title Gnosis Safe - A multisignature wallet with support for confirmations using signed messages based on ERC191.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract GnosisSafe is\n EtherPaymentFallback,\n Singleton,\n ModuleManager,\n OwnerManager,\n SignatureDecoder,\n SecuredTokenTransfer,\n ISignatureValidatorConstants,\n FallbackManager,\n StorageAccessible,\n GuardManager\n{\n using GnosisSafeMath for uint256;\n\n string public constant VERSION = \"1.3.0\";\n\n // keccak256(\n // \"EIP712Domain(uint256 chainId,address verifyingContract)\"\n // );\n bytes32 private constant DOMAIN_SEPARATOR_TYPEHASH = 0x47e79534a245952e8b16893a336b85a3d9ea9fa8c573f3d803afb92a79469218;\n\n // keccak256(\n // \"SafeTx(address to,uint256 value,bytes data,uint8 operation,uint256 safeTxGas,uint256 baseGas,uint256 gasPrice,address gasToken,address refundReceiver,uint256 nonce)\"\n // );\n bytes32 private constant SAFE_TX_TYPEHASH = 0xbb8310d486368db6bd6f849402fdd73ad53d316b5a4b2644ad6efe0f941286d8;\n\n event SafeSetup(address indexed initiator, address[] owners, uint256 threshold, address initializer, address fallbackHandler);\n event ApproveHash(bytes32 indexed approvedHash, address indexed owner);\n event SignMsg(bytes32 indexed msgHash);\n event ExecutionFailure(bytes32 txHash, uint256 payment);\n event ExecutionSuccess(bytes32 txHash, uint256 payment);\n\n uint256 public nonce;\n bytes32 private _deprecatedDomainSeparator;\n // Mapping to keep track of all message hashes that have been approve by ALL REQUIRED owners\n mapping(bytes32 => uint256) public signedMessages;\n // Mapping to keep track of all hashes (message or transaction) that have been approve by ANY owners\n mapping(address => mapping(bytes32 => uint256)) public approvedHashes;\n\n // This constructor ensures that this contract can only be used as a master copy for Proxy contracts\n constructor() {\n // By setting the threshold it is not possible to call setup anymore,\n // so we create a Safe with 0 owners and threshold 1.\n // This is an unusable Safe, perfect for the singleton\n threshold = 1;\n }\n\n /// @dev Setup function sets initial storage of contract.\n /// @param _owners List of Safe owners.\n /// @param _threshold Number of required confirmations for a Safe transaction.\n /// @param to Contract address for optional delegate call.\n /// @param data Data payload for optional delegate call.\n /// @param fallbackHandler Handler for fallback calls to this contract\n /// @param paymentToken Token that should be used for the payment (0 is ETH)\n /// @param payment Value that should be paid\n /// @param paymentReceiver Adddress that should receive the payment (or 0 if tx.origin)\n function setup(\n address[] calldata _owners,\n uint256 _threshold,\n address to,\n bytes calldata data,\n address fallbackHandler,\n address paymentToken,\n uint256 payment,\n address payable paymentReceiver\n ) external {\n // setupOwners checks if the Threshold is already set, therefore preventing that this method is called twice\n setupOwners(_owners, _threshold);\n if (fallbackHandler != address(0)) internalSetFallbackHandler(fallbackHandler);\n // As setupOwners can only be called if the contract has not been initialized we don't need a check for setupModules\n setupModules(to, data);\n\n if (payment > 0) {\n // To avoid running into issues with EIP-170 we reuse the handlePayment function (to avoid adjusting code of that has been verified we do not adjust the method itself)\n // baseGas = 0, gasPrice = 1 and gas = payment => amount = (payment + 0) * 1 = payment\n handlePayment(payment, 0, 1, paymentToken, paymentReceiver);\n }\n emit SafeSetup(msg.sender, _owners, _threshold, to, fallbackHandler);\n }\n\n /// @dev Allows to execute a Safe transaction confirmed by required number of owners and then pays the account that submitted the transaction.\n /// Note: The fees are always transferred, even if the user transaction fails.\n /// @param to Destination address of Safe transaction.\n /// @param value Ether value of Safe transaction.\n /// @param data Data payload of Safe transaction.\n /// @param operation Operation type of Safe transaction.\n /// @param safeTxGas Gas that should be used for the Safe transaction.\n /// @param baseGas Gas costs that are independent of the transaction execution(e.g. base transaction fee, signature check, payment of the refund)\n /// @param gasPrice Gas price that should be used for the payment calculation.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param signatures Packed signature data ({bytes32 r}{bytes32 s}{uint8 v})\n function execTransaction(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver,\n bytes memory signatures\n ) public payable virtual returns (bool success) {\n bytes32 txHash;\n // Use scope here to limit variable lifetime and prevent `stack too deep` errors\n {\n bytes memory txHashData =\n encodeTransactionData(\n // Transaction info\n to,\n value,\n data,\n operation,\n safeTxGas,\n // Payment info\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n // Signature info\n nonce\n );\n // Increase nonce and execute transaction.\n nonce++;\n txHash = keccak256(txHashData);\n checkSignatures(txHash, txHashData, signatures);\n }\n address guard = getGuard();\n {\n if (guard != address(0)) {\n Guard(guard).checkTransaction(\n // Transaction info\n to,\n value,\n data,\n operation,\n safeTxGas,\n // Payment info\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n // Signature info\n signatures,\n msg.sender\n );\n }\n }\n // We require some gas to emit the events (at least 2500) after the execution and some to perform code until the execution (500)\n // We also include the 1/64 in the check that is not send along with a call to counteract potential shortings because of EIP-150\n require(gasleft() >= ((safeTxGas * 64) / 63).max(safeTxGas + 2500) + 500, \"GS010\");\n // Use scope here to limit variable lifetime and prevent `stack too deep` errors\n {\n uint256 gasUsed = gasleft();\n // If the gasPrice is 0 we assume that nearly all available gas can be used (it is always more than safeTxGas)\n // We only substract 2500 (compared to the 3000 before) to ensure that the amount passed is still higher than safeTxGas\n success = execute(to, value, data, operation, gasPrice == 0 ? (gasleft() - 2500) : safeTxGas);\n gasUsed = gasUsed.sub(gasleft());\n // If no safeTxGas and no gasPrice was set (e.g. both are 0), then the internal tx is required to be successful\n // This makes it possible to use `estimateGas` without issues, as it searches for the minimum gas where the tx doesn't revert\n require(success || safeTxGas != 0 || gasPrice != 0, \"GS013\");\n // We transfer the calculated tx costs to the tx.origin to avoid sending it to intermediate contracts that have made calls\n uint256 payment = 0;\n if (gasPrice > 0) {\n payment = handlePayment(gasUsed, baseGas, gasPrice, gasToken, refundReceiver);\n }\n if (success) emit ExecutionSuccess(txHash, payment);\n else emit ExecutionFailure(txHash, payment);\n }\n {\n if (guard != address(0)) {\n Guard(guard).checkAfterExecution(txHash, success);\n }\n }\n }\n\n function handlePayment(\n uint256 gasUsed,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver\n ) private returns (uint256 payment) {\n // solhint-disable-next-line avoid-tx-origin\n address payable receiver = refundReceiver == address(0) ? payable(tx.origin) : refundReceiver;\n if (gasToken == address(0)) {\n // For ETH we will only adjust the gas price to not be higher than the actual used gas price\n payment = gasUsed.add(baseGas).mul(gasPrice < tx.gasprice ? gasPrice : tx.gasprice);\n require(receiver.send(payment), \"GS011\");\n } else {\n payment = gasUsed.add(baseGas).mul(gasPrice);\n require(transferToken(gasToken, receiver, payment), \"GS012\");\n }\n }\n\n /**\n * @dev Checks whether the signature provided is valid for the provided data, hash. Will revert otherwise.\n * @param dataHash Hash of the data (could be either a message hash or transaction hash)\n * @param data That should be signed (this is passed to an external validator contract)\n * @param signatures Signature data that should be verified. Can be ECDSA signature, contract signature (EIP-1271) or approved hash.\n */\n function checkSignatures(\n bytes32 dataHash,\n bytes memory data,\n bytes memory signatures\n ) public view {\n // Load threshold to avoid multiple storage loads\n uint256 _threshold = threshold;\n // Check that a threshold is set\n require(_threshold > 0, \"GS001\");\n checkNSignatures(dataHash, data, signatures, _threshold);\n }\n\n /**\n * @dev Checks whether the signature provided is valid for the provided data, hash. Will revert otherwise.\n * @param dataHash Hash of the data (could be either a message hash or transaction hash)\n * @param data That should be signed (this is passed to an external validator contract)\n * @param signatures Signature data that should be verified. Can be ECDSA signature, contract signature (EIP-1271) or approved hash.\n * @param requiredSignatures Amount of required valid signatures.\n */\n function checkNSignatures(\n bytes32 dataHash,\n bytes memory data,\n bytes memory signatures,\n uint256 requiredSignatures\n ) public view {\n // Check that the provided signature data is not too short\n require(signatures.length >= requiredSignatures.mul(65), \"GS020\");\n // There cannot be an owner with address 0.\n address lastOwner = address(0);\n address currentOwner;\n uint8 v;\n bytes32 r;\n bytes32 s;\n uint256 i;\n for (i = 0; i < requiredSignatures; i++) {\n (v, r, s) = signatureSplit(signatures, i);\n if (v == 0) {\n // If v is 0 then it is a contract signature\n // When handling contract signatures the address of the contract is encoded into r\n currentOwner = address(uint160(uint256(r)));\n\n // Check that signature data pointer (s) is not pointing inside the static part of the signatures bytes\n // This check is not completely accurate, since it is possible that more signatures than the threshold are send.\n // Here we only check that the pointer is not pointing inside the part that is being processed\n require(uint256(s) >= requiredSignatures.mul(65), \"GS021\");\n\n // Check that signature data pointer (s) is in bounds (points to the length of data -> 32 bytes)\n require(uint256(s).add(32) <= signatures.length, \"GS022\");\n\n // Check if the contract signature is in bounds: start of data is s + 32 and end is start + signature length\n uint256 contractSignatureLen;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n contractSignatureLen := mload(add(add(signatures, s), 0x20))\n }\n require(uint256(s).add(32).add(contractSignatureLen) <= signatures.length, \"GS023\");\n\n // Check signature\n bytes memory contractSignature;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // The signature data for contract signatures is appended to the concatenated signatures and the offset is stored in s\n contractSignature := add(add(signatures, s), 0x20)\n }\n require(ISignatureValidator(currentOwner).isValidSignature(data, contractSignature) == EIP1271_MAGIC_VALUE, \"GS024\");\n } else if (v == 1) {\n // If v is 1 then it is an approved hash\n // When handling approved hashes the address of the approver is encoded into r\n currentOwner = address(uint160(uint256(r)));\n // Hashes are automatically approved by the sender of the message or when they have been pre-approved via a separate transaction\n require(msg.sender == currentOwner || approvedHashes[currentOwner][dataHash] != 0, \"GS025\");\n } else if (v > 30) {\n // If v > 30 then default va (27,28) has been adjusted for eth_sign flow\n // To support eth_sign and similar we adjust v and hash the messageHash with the Ethereum message prefix before applying ecrecover\n currentOwner = ecrecover(keccak256(abi.encodePacked(\"\\x19Ethereum Signed Message:\\n32\", dataHash)), v - 4, r, s);\n } else {\n // Default is the ecrecover flow with the provided data hash\n // Use ecrecover with the messageHash for EOA signatures\n currentOwner = ecrecover(dataHash, v, r, s);\n }\n require(currentOwner > lastOwner && owners[currentOwner] != address(0) && currentOwner != SENTINEL_OWNERS, \"GS026\");\n lastOwner = currentOwner;\n }\n }\n\n /// @dev Allows to estimate a Safe transaction.\n /// This method is only meant for estimation purpose, therefore the call will always revert and encode the result in the revert data.\n /// Since the `estimateGas` function includes refunds, call this method to get an estimated of the costs that are deducted from the safe with `execTransaction`\n /// @param to Destination address of Safe transaction.\n /// @param value Ether value of Safe transaction.\n /// @param data Data payload of Safe transaction.\n /// @param operation Operation type of Safe transaction.\n /// @return Estimate without refunds and overhead fees (base transaction and payload data gas costs).\n /// @notice Deprecated in favor of common/StorageAccessible.sol and will be removed in next version.\n function requiredTxGas(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation\n ) external returns (uint256) {\n uint256 startGas = gasleft();\n // We don't provide an error message here, as we use it to return the estimate\n require(execute(to, value, data, operation, gasleft()));\n uint256 requiredGas = startGas - gasleft();\n // Convert response to string and return via error message\n revert(string(abi.encodePacked(requiredGas)));\n }\n\n /**\n * @dev Marks a hash as approved. This can be used to validate a hash that is used by a signature.\n * @param hashToApprove The hash that should be marked as approved for signatures that are verified by this contract.\n */\n function approveHash(bytes32 hashToApprove) external {\n require(owners[msg.sender] != address(0), \"GS030\");\n approvedHashes[msg.sender][hashToApprove] = 1;\n emit ApproveHash(hashToApprove, msg.sender);\n }\n\n /// @dev Returns the chain id used by this contract.\n function getChainId() public view returns (uint256) {\n uint256 id;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n id := chainid()\n }\n return id;\n }\n\n function domainSeparator() public view returns (bytes32) {\n return keccak256(abi.encode(DOMAIN_SEPARATOR_TYPEHASH, getChainId(), this));\n }\n\n /// @dev Returns the bytes that are hashed to be signed by owners.\n /// @param to Destination address.\n /// @param value Ether value.\n /// @param data Data payload.\n /// @param operation Operation type.\n /// @param safeTxGas Gas that should be used for the safe transaction.\n /// @param baseGas Gas costs for that are independent of the transaction execution(e.g. base transaction fee, signature check, payment of the refund)\n /// @param gasPrice Maximum gas price that should be used for this transaction.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param _nonce Transaction nonce.\n /// @return Transaction hash bytes.\n function encodeTransactionData(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) public view returns (bytes memory) {\n bytes32 safeTxHash =\n keccak256(\n abi.encode(\n SAFE_TX_TYPEHASH,\n to,\n value,\n keccak256(data),\n operation,\n safeTxGas,\n baseGas,\n gasPrice,\n gasToken,\n refundReceiver,\n _nonce\n )\n );\n return abi.encodePacked(bytes1(0x19), bytes1(0x01), domainSeparator(), safeTxHash);\n }\n\n /// @dev Returns hash to be signed by owners.\n /// @param to Destination address.\n /// @param value Ether value.\n /// @param data Data payload.\n /// @param operation Operation type.\n /// @param safeTxGas Fas that should be used for the safe transaction.\n /// @param baseGas Gas costs for data used to trigger the safe transaction.\n /// @param gasPrice Maximum gas price that should be used for this transaction.\n /// @param gasToken Token address (or 0 if ETH) that is used for the payment.\n /// @param refundReceiver Address of receiver of gas payment (or 0 if tx.origin).\n /// @param _nonce Transaction nonce.\n /// @return Transaction hash.\n function getTransactionHash(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) public view returns (bytes32) {\n return keccak256(encodeTransactionData(to, value, data, operation, safeTxGas, baseGas, gasPrice, gasToken, refundReceiver, _nonce));\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxyFactory.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"./GnosisSafeProxy.sol\";\nimport \"./IProxyCreationCallback.sol\";\n\n/// @title Proxy Factory - Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n/// @author Stefan George - \ncontract GnosisSafeProxyFactory {\n event ProxyCreation(GnosisSafeProxy proxy, address singleton);\n\n /// @dev Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n /// @param singleton Address of singleton contract.\n /// @param data Payload for message call sent to new proxy contract.\n function createProxy(address singleton, bytes memory data) public returns (GnosisSafeProxy proxy) {\n proxy = new GnosisSafeProxy(singleton);\n if (data.length > 0)\n // solhint-disable-next-line no-inline-assembly\n assembly {\n if eq(call(gas(), proxy, 0, add(data, 0x20), mload(data), 0, 0), 0) {\n revert(0, 0)\n }\n }\n emit ProxyCreation(proxy, singleton);\n }\n\n /// @dev Allows to retrieve the runtime code of a deployed Proxy. This can be used to check that the expected Proxy was deployed.\n function proxyRuntimeCode() public pure returns (bytes memory) {\n return type(GnosisSafeProxy).runtimeCode;\n }\n\n /// @dev Allows to retrieve the creation code used for the Proxy deployment. With this it is easily possible to calculate predicted address.\n function proxyCreationCode() public pure returns (bytes memory) {\n return type(GnosisSafeProxy).creationCode;\n }\n\n /// @dev Allows to create new proxy contact using CREATE2 but it doesn't run the initializer.\n /// This method is only meant as an utility to be called from other methods\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function deployProxyWithNonce(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce\n ) internal returns (GnosisSafeProxy proxy) {\n // If the initializer changes the proxy address should change too. Hashing the initializer data is cheaper than just concatinating it\n bytes32 salt = keccak256(abi.encodePacked(keccak256(initializer), saltNonce));\n bytes memory deploymentData = abi.encodePacked(type(GnosisSafeProxy).creationCode, uint256(uint160(_singleton)));\n // solhint-disable-next-line no-inline-assembly\n assembly {\n proxy := create2(0x0, add(0x20, deploymentData), mload(deploymentData), salt)\n }\n require(address(proxy) != address(0), \"Create2 call failed\");\n }\n\n /// @dev Allows to create new proxy contact and execute a message call to the new proxy within one transaction.\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function createProxyWithNonce(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce\n ) public returns (GnosisSafeProxy proxy) {\n proxy = deployProxyWithNonce(_singleton, initializer, saltNonce);\n if (initializer.length > 0)\n // solhint-disable-next-line no-inline-assembly\n assembly {\n if eq(call(gas(), proxy, 0, add(initializer, 0x20), mload(initializer), 0, 0), 0) {\n revert(0, 0)\n }\n }\n emit ProxyCreation(proxy, _singleton);\n }\n\n /// @dev Allows to create new proxy contact, execute a message call to the new proxy and call a specified callback within one transaction\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n /// @param callback Callback that will be invoced after the new proxy contract has been successfully deployed and initialized.\n function createProxyWithCallback(\n address _singleton,\n bytes memory initializer,\n uint256 saltNonce,\n IProxyCreationCallback callback\n ) public returns (GnosisSafeProxy proxy) {\n uint256 saltNonceWithCallback = uint256(keccak256(abi.encodePacked(saltNonce, callback)));\n proxy = createProxyWithNonce(_singleton, initializer, saltNonceWithCallback);\n if (address(callback) != address(0)) callback.proxyCreated(proxy, _singleton, initializer, saltNonce);\n }\n\n /// @dev Allows to get the address for a new proxy contact created via `createProxyWithNonce`\n /// This method is only meant for address calculation purpose when you use an initializer that would revert,\n /// therefore the response is returned with a revert. When calling this method set `from` to the address of the proxy factory.\n /// @param _singleton Address of singleton contract.\n /// @param initializer Payload for message call sent to new proxy contract.\n /// @param saltNonce Nonce that will be used to generate the salt to calculate the address of the new proxy contract.\n function calculateCreateProxyWithNonceAddress(\n address _singleton,\n bytes calldata initializer,\n uint256 saltNonce\n ) external returns (GnosisSafeProxy proxy) {\n proxy = deployProxyWithNonce(_singleton, initializer, saltNonce);\n revert(string(abi.encodePacked(proxy)));\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/GuardManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"../common/Enum.sol\";\nimport \"../common/SelfAuthorized.sol\";\n\ninterface Guard {\n function checkTransaction(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address payable refundReceiver,\n bytes memory signatures,\n address msgSender\n ) external;\n\n function checkAfterExecution(bytes32 txHash, bool success) external;\n}\n\n/// @title Fallback Manager - A contract that manages fallback calls made to this contract\n/// @author Richard Meissner - \ncontract GuardManager is SelfAuthorized {\n event ChangedGuard(address guard);\n // keccak256(\"guard_manager.guard.address\")\n bytes32 internal constant GUARD_STORAGE_SLOT = 0x4a204f620c8c5ccdca3fd54d003badd85ba500436a431f0cbda4f558c93c34c8;\n\n /// @dev Set a guard that checks transactions before execution\n /// @param guard The address of the guard to be used or the 0 address to disable the guard\n function setGuard(address guard) external authorized {\n bytes32 slot = GUARD_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n sstore(slot, guard)\n }\n emit ChangedGuard(guard);\n }\n\n function getGuard() internal view returns (address guard) {\n bytes32 slot = GUARD_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n guard := sload(slot)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/FallbackManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\nimport \"../common/SelfAuthorized.sol\";\n\n/// @title Fallback Manager - A contract that manages fallback calls made to this contract\n/// @author Richard Meissner - \ncontract FallbackManager is SelfAuthorized {\n event ChangedFallbackHandler(address handler);\n\n // keccak256(\"fallback_manager.handler.address\")\n bytes32 internal constant FALLBACK_HANDLER_STORAGE_SLOT = 0x6c9a6c4a39284e37ed1cf53d337577d14212a4870fb976a4366c693b939918d5;\n\n function internalSetFallbackHandler(address handler) internal {\n bytes32 slot = FALLBACK_HANDLER_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n sstore(slot, handler)\n }\n }\n\n /// @dev Allows to add a contract to handle fallback calls.\n /// Only fallback calls without value and with data will be forwarded.\n /// This can only be done via a Safe transaction.\n /// @param handler contract to handle fallbacks calls.\n function setFallbackHandler(address handler) public authorized {\n internalSetFallbackHandler(handler);\n emit ChangedFallbackHandler(handler);\n }\n\n // solhint-disable-next-line payable-fallback,no-complex-fallback\n fallback() external {\n bytes32 slot = FALLBACK_HANDLER_STORAGE_SLOT;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let handler := sload(slot)\n if iszero(handler) {\n return(0, 0)\n }\n calldatacopy(0, 0, calldatasize())\n // The msg.sender address is shifted to the left by 12 bytes to remove the padding\n // Then the address without padding is stored right after the calldata\n mstore(calldatasize(), shl(96, caller()))\n // Add 20 bytes for the address appended add the end\n let success := call(gas(), handler, 0, 0, add(calldatasize(), 20), 0, 0)\n returndatacopy(0, 0, returndatasize())\n if iszero(success) {\n revert(0, returndatasize())\n }\n return(0, returndatasize())\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/ModuleManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/Enum.sol\";\nimport \"../common/SelfAuthorized.sol\";\nimport \"./Executor.sol\";\n\n/// @title Module Manager - A contract that manages modules that can execute transactions via this contract\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract ModuleManager is SelfAuthorized, Executor {\n event EnabledModule(address module);\n event DisabledModule(address module);\n event ExecutionFromModuleSuccess(address indexed module);\n event ExecutionFromModuleFailure(address indexed module);\n\n address internal constant SENTINEL_MODULES = address(0x1);\n\n mapping(address => address) internal modules;\n\n function setupModules(address to, bytes memory data) internal {\n require(modules[SENTINEL_MODULES] == address(0), \"GS100\");\n modules[SENTINEL_MODULES] = SENTINEL_MODULES;\n if (to != address(0))\n // Setup has to complete successfully or transaction fails.\n require(execute(to, 0, data, Enum.Operation.DelegateCall, gasleft()), \"GS000\");\n }\n\n /// @dev Allows to add a module to the whitelist.\n /// This can only be done via a Safe transaction.\n /// @notice Enables the module `module` for the Safe.\n /// @param module Module to be whitelisted.\n function enableModule(address module) public authorized {\n // Module address cannot be null or sentinel.\n require(module != address(0) && module != SENTINEL_MODULES, \"GS101\");\n // Module cannot be added twice.\n require(modules[module] == address(0), \"GS102\");\n modules[module] = modules[SENTINEL_MODULES];\n modules[SENTINEL_MODULES] = module;\n emit EnabledModule(module);\n }\n\n /// @dev Allows to remove a module from the whitelist.\n /// This can only be done via a Safe transaction.\n /// @notice Disables the module `module` for the Safe.\n /// @param prevModule Module that pointed to the module to be removed in the linked list\n /// @param module Module to be removed.\n function disableModule(address prevModule, address module) public authorized {\n // Validate module address and check that it corresponds to module index.\n require(module != address(0) && module != SENTINEL_MODULES, \"GS101\");\n require(modules[prevModule] == module, \"GS103\");\n modules[prevModule] = modules[module];\n modules[module] = address(0);\n emit DisabledModule(module);\n }\n\n /// @dev Allows a Module to execute a Safe transaction without any further confirmations.\n /// @param to Destination address of module transaction.\n /// @param value Ether value of module transaction.\n /// @param data Data payload of module transaction.\n /// @param operation Operation type of module transaction.\n function execTransactionFromModule(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation\n ) public virtual returns (bool success) {\n // Only whitelisted modules are allowed.\n require(msg.sender != SENTINEL_MODULES && modules[msg.sender] != address(0), \"GS104\");\n // Execute transaction without further confirmations.\n success = execute(to, value, data, operation, gasleft());\n if (success) emit ExecutionFromModuleSuccess(msg.sender);\n else emit ExecutionFromModuleFailure(msg.sender);\n }\n\n /// @dev Allows a Module to execute a Safe transaction without any further confirmations and return data\n /// @param to Destination address of module transaction.\n /// @param value Ether value of module transaction.\n /// @param data Data payload of module transaction.\n /// @param operation Operation type of module transaction.\n function execTransactionFromModuleReturnData(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation\n ) public returns (bool success, bytes memory returnData) {\n success = execTransactionFromModule(to, value, data, operation);\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // Load free memory location\n let ptr := mload(0x40)\n // We allocate memory for the return data by setting the free memory location to\n // current free memory location + data size + 32 bytes for data size value\n mstore(0x40, add(ptr, add(returndatasize(), 0x20)))\n // Store the size\n mstore(ptr, returndatasize())\n // Store the data\n returndatacopy(add(ptr, 0x20), 0, returndatasize())\n // Point the return data to the correct memory location\n returnData := ptr\n }\n }\n\n /// @dev Returns if an module is enabled\n /// @return True if the module is enabled\n function isModuleEnabled(address module) public view returns (bool) {\n return SENTINEL_MODULES != module && modules[module] != address(0);\n }\n\n /// @dev Returns array of modules.\n /// @param start Start of the page.\n /// @param pageSize Maximum number of modules that should be returned.\n /// @return array Array of modules.\n /// @return next Start of the next page.\n function getModulesPaginated(address start, uint256 pageSize) external view returns (address[] memory array, address next) {\n // Init array with max page size\n array = new address[](pageSize);\n\n // Populate return array\n uint256 moduleCount = 0;\n address currentModule = modules[start];\n while (currentModule != address(0x0) && currentModule != SENTINEL_MODULES && moduleCount < pageSize) {\n array[moduleCount] = currentModule;\n currentModule = modules[currentModule];\n moduleCount++;\n }\n next = currentModule;\n // Set correct size of returned array\n // solhint-disable-next-line no-inline-assembly\n assembly {\n mstore(array, moduleCount)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/OwnerManager.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/SelfAuthorized.sol\";\n\n/// @title OwnerManager - Manages a set of owners and a threshold to perform actions.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract OwnerManager is SelfAuthorized {\n event AddedOwner(address owner);\n event RemovedOwner(address owner);\n event ChangedThreshold(uint256 threshold);\n\n address internal constant SENTINEL_OWNERS = address(0x1);\n\n mapping(address => address) internal owners;\n uint256 internal ownerCount;\n uint256 internal threshold;\n\n /// @dev Setup function sets initial storage of contract.\n /// @param _owners List of Safe owners.\n /// @param _threshold Number of required confirmations for a Safe transaction.\n function setupOwners(address[] memory _owners, uint256 _threshold) internal {\n // Threshold can only be 0 at initialization.\n // Check ensures that setup function can only be called once.\n require(threshold == 0, \"GS200\");\n // Validate that threshold is smaller than number of added owners.\n require(_threshold <= _owners.length, \"GS201\");\n // There has to be at least one Safe owner.\n require(_threshold >= 1, \"GS202\");\n // Initializing Safe owners.\n address currentOwner = SENTINEL_OWNERS;\n for (uint256 i = 0; i < _owners.length; i++) {\n // Owner address cannot be null.\n address owner = _owners[i];\n require(owner != address(0) && owner != SENTINEL_OWNERS && owner != address(this) && currentOwner != owner, \"GS203\");\n // No duplicate owners allowed.\n require(owners[owner] == address(0), \"GS204\");\n owners[currentOwner] = owner;\n currentOwner = owner;\n }\n owners[currentOwner] = SENTINEL_OWNERS;\n ownerCount = _owners.length;\n threshold = _threshold;\n }\n\n /// @dev Allows to add a new owner to the Safe and update the threshold at the same time.\n /// This can only be done via a Safe transaction.\n /// @notice Adds the owner `owner` to the Safe and updates the threshold to `_threshold`.\n /// @param owner New owner address.\n /// @param _threshold New threshold.\n function addOwnerWithThreshold(address owner, uint256 _threshold) public authorized {\n // Owner address cannot be null, the sentinel or the Safe itself.\n require(owner != address(0) && owner != SENTINEL_OWNERS && owner != address(this), \"GS203\");\n // No duplicate owners allowed.\n require(owners[owner] == address(0), \"GS204\");\n owners[owner] = owners[SENTINEL_OWNERS];\n owners[SENTINEL_OWNERS] = owner;\n ownerCount++;\n emit AddedOwner(owner);\n // Change threshold if threshold was changed.\n if (threshold != _threshold) changeThreshold(_threshold);\n }\n\n /// @dev Allows to remove an owner from the Safe and update the threshold at the same time.\n /// This can only be done via a Safe transaction.\n /// @notice Removes the owner `owner` from the Safe and updates the threshold to `_threshold`.\n /// @param prevOwner Owner that pointed to the owner to be removed in the linked list\n /// @param owner Owner address to be removed.\n /// @param _threshold New threshold.\n function removeOwner(\n address prevOwner,\n address owner,\n uint256 _threshold\n ) public authorized {\n // Only allow to remove an owner, if threshold can still be reached.\n require(ownerCount - 1 >= _threshold, \"GS201\");\n // Validate owner address and check that it corresponds to owner index.\n require(owner != address(0) && owner != SENTINEL_OWNERS, \"GS203\");\n require(owners[prevOwner] == owner, \"GS205\");\n owners[prevOwner] = owners[owner];\n owners[owner] = address(0);\n ownerCount--;\n emit RemovedOwner(owner);\n // Change threshold if threshold was changed.\n if (threshold != _threshold) changeThreshold(_threshold);\n }\n\n /// @dev Allows to swap/replace an owner from the Safe with another address.\n /// This can only be done via a Safe transaction.\n /// @notice Replaces the owner `oldOwner` in the Safe with `newOwner`.\n /// @param prevOwner Owner that pointed to the owner to be replaced in the linked list\n /// @param oldOwner Owner address to be replaced.\n /// @param newOwner New owner address.\n function swapOwner(\n address prevOwner,\n address oldOwner,\n address newOwner\n ) public authorized {\n // Owner address cannot be null, the sentinel or the Safe itself.\n require(newOwner != address(0) && newOwner != SENTINEL_OWNERS && newOwner != address(this), \"GS203\");\n // No duplicate owners allowed.\n require(owners[newOwner] == address(0), \"GS204\");\n // Validate oldOwner address and check that it corresponds to owner index.\n require(oldOwner != address(0) && oldOwner != SENTINEL_OWNERS, \"GS203\");\n require(owners[prevOwner] == oldOwner, \"GS205\");\n owners[newOwner] = owners[oldOwner];\n owners[prevOwner] = newOwner;\n owners[oldOwner] = address(0);\n emit RemovedOwner(oldOwner);\n emit AddedOwner(newOwner);\n }\n\n /// @dev Allows to update the number of required confirmations by Safe owners.\n /// This can only be done via a Safe transaction.\n /// @notice Changes the threshold of the Safe to `_threshold`.\n /// @param _threshold New threshold.\n function changeThreshold(uint256 _threshold) public authorized {\n // Validate that threshold is smaller than number of owners.\n require(_threshold <= ownerCount, \"GS201\");\n // There has to be at least one Safe owner.\n require(_threshold >= 1, \"GS202\");\n threshold = _threshold;\n emit ChangedThreshold(threshold);\n }\n\n function getThreshold() public view returns (uint256) {\n return threshold;\n }\n\n function isOwner(address owner) public view returns (bool) {\n return owner != SENTINEL_OWNERS && owners[owner] != address(0);\n }\n\n /// @dev Returns array of owners.\n /// @return Array of Safe owners.\n function getOwners() public view returns (address[] memory) {\n address[] memory array = new address[](ownerCount);\n\n // populate return array\n uint256 index = 0;\n address currentOwner = owners[SENTINEL_OWNERS];\n while (currentOwner != SENTINEL_OWNERS) {\n array[index] = currentOwner;\n currentOwner = owners[currentOwner];\n index++;\n }\n return array;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/Singleton.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title Singleton - Base for singleton contracts (should always be first super contract)\n/// This contract is tightly coupled to our proxy contract (see `proxies/GnosisSafeProxy.sol`)\n/// @author Richard Meissner - \ncontract Singleton {\n // singleton always needs to be first declared variable, to ensure that it is at the same location as in the Proxy contract.\n // It should also always be ensured that the address is stored alone (uses a full word)\n address private singleton;\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SignatureDecoder.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SignatureDecoder - Decodes signatures that a encoded as bytes\n/// @author Richard Meissner - \ncontract SignatureDecoder {\n /// @dev divides bytes signature into `uint8 v, bytes32 r, bytes32 s`.\n /// @notice Make sure to peform a bounds check for @param pos, to avoid out of bounds access on @param signatures\n /// @param pos which signature to read. A prior bounds check of this parameter should be performed, to avoid out of bounds access\n /// @param signatures concatenated rsv signatures\n function signatureSplit(bytes memory signatures, uint256 pos)\n internal\n pure\n returns (\n uint8 v,\n bytes32 r,\n bytes32 s\n )\n {\n // The signature format is a compact form of:\n // {bytes32 r}{bytes32 s}{uint8 v}\n // Compact means, uint8 is not padded to 32 bytes.\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let signaturePos := mul(0x41, pos)\n r := mload(add(signatures, add(signaturePos, 0x20)))\n s := mload(add(signatures, add(signaturePos, 0x40)))\n // Here we are loading the last 32 bytes, including 31 bytes\n // of 's'. There is no 'mload8' to do this.\n //\n // 'byte' is not working due to the Solidity parser, so lets\n // use the second best option, 'and'\n v := and(mload(add(signatures, add(signaturePos, 0x41))), 0xff)\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/EtherPaymentFallback.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title EtherPaymentFallback - A contract that has a fallback to accept ether payments\n/// @author Richard Meissner - \ncontract EtherPaymentFallback {\n event SafeReceived(address indexed sender, uint256 value);\n\n /// @dev Fallback function accepts Ether transactions.\n receive() external payable {\n emit SafeReceived(msg.sender, msg.value);\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/interfaces/ISignatureValidator.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\ncontract ISignatureValidatorConstants {\n // bytes4(keccak256(\"isValidSignature(bytes,bytes)\")\n bytes4 internal constant EIP1271_MAGIC_VALUE = 0x20c13b0b;\n}\n\nabstract contract ISignatureValidator is ISignatureValidatorConstants {\n /**\n * @dev Should return whether the signature provided is valid for the provided data\n * @param _data Arbitrary length data signed on the behalf of address(this)\n * @param _signature Signature byte array associated with _data\n *\n * MUST return the bytes4 magic value 0x20c13b0b when function passes.\n * MUST NOT modify state (using STATICCALL for solc < 0.5, view modifier for solc > 0.5)\n * MUST allow external calls\n */\n function isValidSignature(bytes memory _data, bytes memory _signature) public view virtual returns (bytes4);\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SecuredTokenTransfer.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SecuredTokenTransfer - Secure token transfer\n/// @author Richard Meissner - \ncontract SecuredTokenTransfer {\n /// @dev Transfers a token and returns if it was a success\n /// @param token Token that should be transferred\n /// @param receiver Receiver to whom the token should be transferred\n /// @param amount The amount of tokens that should be transferred\n function transferToken(\n address token,\n address receiver,\n uint256 amount\n ) internal returns (bool transferred) {\n // 0xa9059cbb - keccack(\"transfer(address,uint256)\")\n bytes memory data = abi.encodeWithSelector(0xa9059cbb, receiver, amount);\n // solhint-disable-next-line no-inline-assembly\n assembly {\n // We write the return value to scratch space.\n // See https://docs.soliditylang.org/en/v0.7.6/internals/layout_in_memory.html#layout-in-memory\n let success := call(sub(gas(), 10000), token, 0, add(data, 0x20), mload(data), 0, 0x20)\n switch returndatasize()\n case 0 {\n transferred := success\n }\n case 0x20 {\n transferred := iszero(or(iszero(success), iszero(mload(0))))\n }\n default {\n transferred := 0\n }\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/StorageAccessible.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title StorageAccessible - generic base contract that allows callers to access all internal storage.\n/// @notice See https://github.com/gnosis/util-contracts/blob/bb5fe5fb5df6d8400998094fb1b32a178a47c3a1/contracts/StorageAccessible.sol\ncontract StorageAccessible {\n /**\n * @dev Reads `length` bytes of storage in the currents contract\n * @param offset - the offset in the current contract's storage in words to start reading from\n * @param length - the number of words (32 bytes) of data to read\n * @return the bytes that were read.\n */\n function getStorageAt(uint256 offset, uint256 length) public view returns (bytes memory) {\n bytes memory result = new bytes(length * 32);\n for (uint256 index = 0; index < length; index++) {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let word := sload(add(offset, index))\n mstore(add(add(result, 0x20), mul(index, 0x20)), word)\n }\n }\n return result;\n }\n\n /**\n * @dev Performs a delegetecall on a targetContract in the context of self.\n * Internally reverts execution to avoid side effects (making it static).\n *\n * This method reverts with data equal to `abi.encode(bool(success), bytes(response))`.\n * Specifically, the `returndata` after a call to this method will be:\n * `success:bool || response.length:uint256 || response:bytes`.\n *\n * @param targetContract Address of the contract containing the code to execute.\n * @param calldataPayload Calldata that should be sent to the target contract (encoded method name and arguments).\n */\n function simulateAndRevert(address targetContract, bytes memory calldataPayload) external {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let success := delegatecall(gas(), targetContract, add(calldataPayload, 0x20), mload(calldataPayload), 0, 0)\n\n mstore(0x00, success)\n mstore(0x20, returndatasize())\n returndatacopy(0x40, 0, returndatasize())\n revert(0, add(returndatasize(), 0x40))\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/external/GnosisSafeMath.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/**\n * @title GnosisSafeMath\n * @dev Math operations with safety checks that revert on error\n * Renamed from SafeMath to GnosisSafeMath to avoid conflicts\n * TODO: remove once open zeppelin update to solc 0.5.0\n */\nlibrary GnosisSafeMath {\n /**\n * @dev Multiplies two numbers, reverts on overflow.\n */\n function mul(uint256 a, uint256 b) internal pure returns (uint256) {\n // Gas optimization: this is cheaper than requiring 'a' not being zero, but the\n // benefit is lost if 'b' is also tested.\n // See: https://github.com/OpenZeppelin/openzeppelin-solidity/pull/522\n if (a == 0) {\n return 0;\n }\n\n uint256 c = a * b;\n require(c / a == b);\n\n return c;\n }\n\n /**\n * @dev Subtracts two numbers, reverts on overflow (i.e. if subtrahend is greater than minuend).\n */\n function sub(uint256 a, uint256 b) internal pure returns (uint256) {\n require(b <= a);\n uint256 c = a - b;\n\n return c;\n }\n\n /**\n * @dev Adds two numbers, reverts on overflow.\n */\n function add(uint256 a, uint256 b) internal pure returns (uint256) {\n uint256 c = a + b;\n require(c >= a);\n\n return c;\n }\n\n /**\n * @dev Returns the largest of two numbers.\n */\n function max(uint256 a, uint256 b) internal pure returns (uint256) {\n return a >= b ? a : b;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/SelfAuthorized.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title SelfAuthorized - authorizes current contract to perform actions\n/// @author Richard Meissner - \ncontract SelfAuthorized {\n function requireSelfCall() private view {\n require(msg.sender == address(this), \"GS031\");\n }\n\n modifier authorized() {\n // This is a function call as it minimized the bytecode size\n requireSelfCall();\n _;\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/common/Enum.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title Enum - Collection of enums\n/// @author Richard Meissner - \ncontract Enum {\n enum Operation {Call, DelegateCall}\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/base/Executor.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"../common/Enum.sol\";\n\n/// @title Executor - A contract that can execute transactions\n/// @author Richard Meissner - \ncontract Executor {\n function execute(\n address to,\n uint256 value,\n bytes memory data,\n Enum.Operation operation,\n uint256 txGas\n ) internal returns (bool success) {\n if (operation == Enum.Operation.DelegateCall) {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n success := delegatecall(txGas, to, add(data, 0x20), mload(data), 0, 0)\n }\n } else {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n success := call(txGas, to, value, add(data, 0x20), mload(data), 0, 0)\n }\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/GnosisSafeProxy.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\n\n/// @title IProxy - Helper interface to access masterCopy of the Proxy on-chain\n/// @author Richard Meissner - \ninterface IProxy {\n function masterCopy() external view returns (address);\n}\n\n/// @title GnosisSafeProxy - Generic proxy contract allows to execute all transactions applying the code of a master contract.\n/// @author Stefan George - \n/// @author Richard Meissner - \ncontract GnosisSafeProxy {\n // singleton always needs to be first declared variable, to ensure that it is at the same location in the contracts to which calls are delegated.\n // To reduce deployment costs this variable is internal and needs to be retrieved via `getStorageAt`\n address internal singleton;\n\n /// @dev Constructor function sets address of singleton contract.\n /// @param _singleton Singleton address.\n constructor(address _singleton) {\n require(_singleton != address(0), \"Invalid singleton address provided\");\n singleton = _singleton;\n }\n\n /// @dev Fallback function forwards all transactions and returns all received return data.\n fallback() external payable {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n let _singleton := and(sload(0), 0xffffffffffffffffffffffffffffffffffffffff)\n // 0xa619486e == keccak(\"masterCopy()\"). The value is right padded to 32-bytes with 0s\n if eq(calldataload(0), 0xa619486e00000000000000000000000000000000000000000000000000000000) {\n mstore(0, _singleton)\n return(0, 0x20)\n }\n calldatacopy(0, 0, calldatasize())\n let success := delegatecall(gas(), _singleton, 0, calldatasize(), 0, 0)\n returndatacopy(0, 0, returndatasize())\n if eq(success, 0) {\n revert(0, returndatasize())\n }\n return(0, returndatasize())\n }\n }\n}\n" + }, + "@gnosis.pm/safe-contracts/contracts/proxies/IProxyCreationCallback.sol": { + "content": "// SPDX-License-Identifier: LGPL-3.0-only\npragma solidity >=0.7.0 <0.9.0;\nimport \"./GnosisSafeProxy.sol\";\n\ninterface IProxyCreationCallback {\n function proxyCreated(\n GnosisSafeProxy proxy,\n address _singleton,\n bytes calldata initializer,\n uint256 saltNonce\n ) external;\n}\n" + }, + "contracts/utils/SignerV2.sol": { + "content": "/*\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n// Signer contract. Enables signing transaction before sending it to Gnosis Safe.\n// Copyright (C) 2021 PrimeDao\n\n// solium-disable linebreak-style\npragma solidity 0.8.17;\n\nimport \"./interface/ISafe.sol\";\nimport \"@gnosis.pm/safe-contracts/contracts/interfaces/ISignatureValidator.sol\";\n\n/**\n * @title PrimeDAO Signer Contract\n * @dev Enables signing approved function signature transaction before sending it to Gnosis Safe.\n */\ncontract SignerV2 is ISignatureValidator {\n bytes32 private constant DOMAIN_SEPARATOR_TYPEHASH =\n 0x7a9f5b2bf4dbb53eb85e012c6094a3d71d76e5bfe821f44ab63ed59311264e35;\n bytes32 private constant MSG_TYPEHASH =\n 0xa1a7ad659422d5fc08fdc481fd7d8af8daf7993bc4e833452b0268ceaab66e5d; // mapping for msg typehash\n\n mapping(bytes32 => bytes32) public approvedSignatures;\n\n /* solium-disable */\n address public safe;\n mapping(address => mapping(bytes4 => bool)) public allowedTransactions;\n /* solium-enable */\n\n event SignatureCreated(bytes signature, bytes32 indexed hash);\n\n modifier onlySafe() {\n require(msg.sender == safe, \"Signer: only safe functionality\");\n _;\n }\n\n /**\n * @dev Signer Constructor\n * @param _safe Gnosis Safe address.\n * @param _contracts array of contract addresses\n * @param _functionSignatures array of function signatures\n */\n constructor(\n address _safe,\n address[] memory _contracts,\n bytes4[] memory _functionSignatures\n ) {\n require(_safe != address(0), \"Signer: Safe address zero\");\n safe = _safe;\n for (uint256 i; i < _contracts.length; i++) {\n require(\n _contracts[i] != address(0),\n \"Signer: contract address zero\"\n );\n require(\n _functionSignatures[i] != bytes4(0),\n \"Signer: function signature zero\"\n );\n allowedTransactions[_contracts[i]][_functionSignatures[i]] = true;\n }\n }\n\n /**\n * @dev Signature generator\n * @param _to receiver address.\n * @param _value value in wei.\n * @param _data encoded transaction data.\n * @param _operation type of operation call.\n * @param _safeTxGas safe transaction gas for gnosis safe.\n * @param _baseGas base gas for gnosis safe.\n * @param _gasPrice gas price for gnosis safe transaction.\n * @param _gasToken token which gas needs to paid for gnosis safe transaction.\n * @param _refundReceiver address account to receive refund for remaining gas.\n * @param _nonce gnosis safe contract nonce.\n */\n function generateSignature(\n address _to,\n uint256 _value,\n bytes calldata _data,\n Enum.Operation _operation,\n uint256 _safeTxGas,\n uint256 _baseGas,\n uint256 _gasPrice,\n address _gasToken,\n address _refundReceiver,\n uint256 _nonce\n ) external returns (bytes memory signature, bytes32 hash) {\n // check if transaction parameters are correct\n require(\n allowedTransactions[_to][_getFunctionHashFromData(_data)],\n \"Signer: invalid function\"\n );\n require(\n _value == 0 &&\n _refundReceiver == address(0) &&\n _operation == Enum.Operation.Call,\n \"Signer: invalid arguments\"\n );\n\n // get contractTransactionHash from gnosis safe\n hash = ISafe(safe).getTransactionHash(\n _to,\n 0,\n _data,\n _operation,\n _safeTxGas,\n _baseGas,\n _gasPrice,\n _gasToken,\n _refundReceiver,\n _nonce\n );\n\n bytes memory paddedAddress = bytes.concat(\n bytes12(0),\n bytes20(address(this))\n );\n bytes memory messageHash = _encodeMessageHash(hash);\n // check if transaction is not signed before\n // solhint-disable-next-line reason-string\n require(\n approvedSignatures[hash] != keccak256(messageHash),\n \"Signer: transaction already signed\"\n );\n\n // generate signature and add it to approvedSignatures mapping\n signature = bytes.concat(\n paddedAddress,\n bytes32(uint256(65)),\n bytes1(0),\n bytes32(uint256(messageHash.length)),\n messageHash\n );\n approvedSignatures[hash] = keccak256(messageHash);\n emit SignatureCreated(signature, hash);\n }\n\n /**\n * @dev Validate signature using EIP1271\n * @param _data Encoded transaction hash supplied to verify signature.\n * @param _signature Signature that needs to be verified.\n */\n function isValidSignature(bytes memory _data, bytes memory _signature)\n public\n view\n override\n returns (bytes4)\n {\n if (_data.length == 32) {\n bytes32 hash;\n // solhint-disable-next-line no-inline-assembly\n assembly {\n hash := mload(add(_data, 32))\n }\n if (approvedSignatures[hash] == keccak256(_signature)) {\n return EIP1271_MAGIC_VALUE;\n }\n } else {\n if (approvedSignatures[keccak256(_data)] == keccak256(_signature)) {\n return EIP1271_MAGIC_VALUE;\n }\n }\n return \"0x\";\n }\n\n /**\n * @dev Get the byte hash of function call i.e. first four bytes of data\n * @param data encoded transaction data.\n */\n function _getFunctionHashFromData(bytes memory data)\n private\n pure\n returns (bytes4 functionHash)\n {\n // solhint-disable-next-line no-inline-assembly\n assembly {\n functionHash := mload(add(data, 32))\n }\n }\n\n /**\n * @dev encode message with contants\n * @param message the message that needs to be encoded\n */\n function _encodeMessageHash(bytes32 message)\n private\n pure\n returns (bytes memory)\n {\n bytes32 safeMessageHash = keccak256(abi.encode(MSG_TYPEHASH, message));\n return\n abi.encodePacked(\n bytes1(0x19),\n bytes1(0x23),\n keccak256(\n abi.encode(DOMAIN_SEPARATOR_TYPEHASH, safeMessageHash)\n )\n );\n }\n\n /**\n * @dev set new safe\n * @param _safe safe address\n */\n function setSafe(address _safe) public onlySafe {\n require(_safe != address(0), \"Signer: Safe zero address\");\n safe = _safe;\n }\n\n /**\n * @dev add new contracts and functions\n * @param _contract contract address\n * @param _functionSignature function signature for the contract\n */\n function approveNewTransaction(address _contract, bytes4 _functionSignature)\n external\n onlySafe\n {\n require(_contract != address(0), \"Signer: contract address zero\");\n require(\n _functionSignature != bytes4(0),\n \"Signer: function signature zero\"\n );\n allowedTransactions[_contract][_functionSignature] = true;\n }\n\n /**\n * @dev add new contracts and functions\n * @param _contract contract address\n * @param _functionSignature function signature for the contract\n */\n function removeAllowedTransaction(\n address _contract,\n bytes4 _functionSignature\n ) external onlySafe {\n // solhint-disable-next-line reason-string\n require(\n allowedTransactions[_contract][_functionSignature] == true,\n \"Signer: only approved transactions can be removed\"\n );\n allowedTransactions[_contract][_functionSignature] = false;\n }\n}\n" + }, + "contracts/utils/interface/ISafe.sol": { + "content": "/*\n\n██████╗░██████╗░██╗███╗░░░███╗███████╗██████╗░░█████╗░░█████╗░\n██╔══██╗██╔══██╗██║████╗░████║██╔════╝██╔══██╗██╔══██╗██╔══██╗\n██████╔╝██████╔╝██║██╔████╔██║█████╗░░██║░░██║███████║██║░░██║\n██╔═══╝░██╔══██╗██║██║╚██╔╝██║██╔══╝░░██║░░██║██╔══██║██║░░██║\n██║░░░░░██║░░██║██║██║░╚═╝░██║███████╗██████╔╝██║░░██║╚█████╔╝\n╚═╝░░░░░╚═╝░░╚═╝╚═╝╚═╝░░░░░╚═╝╚══════╝╚═════╝░╚═╝░░╚═╝░╚════╝░\n\n*/\n\n// SPDX-License-Identifier: GPL-3.0-or-later\n\n/* solium-disable */\npragma solidity 0.8.17;\n\ncontract Enum {\n enum Operation {\n Call,\n DelegateCall\n }\n}\n\ninterface ISafe {\n function getTransactionHash(\n address to,\n uint256 value,\n bytes calldata data,\n Enum.Operation operation,\n uint256 safeTxGas,\n uint256 baseGas,\n uint256 gasPrice,\n address gasToken,\n address refundReceiver,\n uint256 _nonce\n ) external view returns (bytes32);\n}\n" + } + }, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": { + "*": { + "*": [ + "abi", + "evm.bytecode", + "evm.deployedBytecode", + "evm.methodIdentifiers", + "metadata", + "devdoc", + "userdoc", + "storageLayout", + "evm.gasEstimates" + ], + "": [ + "ast" + ] + } + }, + "metadata": { + "useLiteralContent": true + } + } +} \ No newline at end of file diff --git a/exports/celo.json b/exports/celo.json index 8ebda13..b6c47f9 100644 --- a/exports/celo.json +++ b/exports/celo.json @@ -2,6 +2,1522 @@ "name": "celo", "chainId": "42220", "contracts": { + "LBPManager": { + "address": "0xd1BFa64799Eae67b6FeC1741889503daD8FEd768", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, + "LBPManagerFactory": { + "address": "0x8717635e4337E4381A2Aed75aFCbc3a6D0998948", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, + "LBPManagerFactoryV1NoAccessControl": { + "address": "0x8afa40718d5e23Ca7E84b2Cd9F55E11491322a42", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + } + ] + }, + "LBPManagerV1": { + "address": "0x49ED64a98FA5E298384000A92CD4A0B0fECeA9b9", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, "Seed": { "address": "0x36C94d5e38c377dD5CAEf83032df12fB5560c63D", "abi": [ diff --git a/exports/goerli.json b/exports/goerli.json index f98169f..41cf55d 100644 --- a/exports/goerli.json +++ b/exports/goerli.json @@ -6,6 +6,1522 @@ "address": "0x2EDbfAeFcaC083A1a199C6835D12782A0868E50B", "abi": "ERC20" }, + "LBPManager": { + "address": "0xDC624C9f99B1FD33743d162b137838E6032b0486", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, + "LBPManagerFactory": { + "address": "0x69Eb008641dDcd0092C26C9A143B164F0CCc17DE", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, + "LBPManagerFactoryV1NoAccessControl": { + "address": "0x5b4C1b1976B0b2D2d1fF26b10913F910D0E18140", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldLBPFactory", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newLBPFactory", + "type": "address" + } + ], + "name": "LBPFactoryChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpManager", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "LBPManagerDeployed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldMasterCopy", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newMasterCopy", + "type": "address" + } + ], + "name": "MastercopyChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "previousOwner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "OwnershipTransferred", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_admin", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndtime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "deployLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "masterCopy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "owner", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "renounceOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + } + ], + "name": "setLBPFactory", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_masterCopy", + "type": "address" + } + ], + "name": "setMasterCopy", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "newOwner", + "type": "address" + } + ], + "name": "transferOwnership", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + } + ] + }, + "LBPManagerV1": { + "address": "0xe5864D50764DB0Fa8266912FC6576100e75b35eB", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "beneficiary", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "tokenAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "FeeTransferred", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "LBPManagerAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes", + "name": "metadata", + "type": "bytes" + } + ], + "name": "MetadataUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "lbpAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "PoolTokensWithdrawn", + "type": "event" + }, + { + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "amounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "beneficiary", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "endWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "feePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getSwapEnabled", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "initializeLBP", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_lbpFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_beneficiary", + "type": "address" + }, + { + "internalType": "string", + "name": "_name", + "type": "string" + }, + { + "internalType": "string", + "name": "_symbol", + "type": "string" + }, + { + "internalType": "contract IERC20[]", + "name": "_tokenList", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "_amounts", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_startTimeEndTime", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_endWeights", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "_fees", + "type": "uint256[]" + }, + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "initializeLBPManager", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "initialized", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbp", + "outputs": [ + { + "internalType": "contract ILBP", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "lbpFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "metadata", + "outputs": [ + { + "internalType": "bytes", + "name": "", + "type": "bytes" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "poolFunded", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokenIndex", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "projectTokensRequired", + "outputs": [ + { + "internalType": "uint256", + "name": "projectTokenAmounts", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "removeLiquidity", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_swapEnabled", + "type": "bool" + } + ], + "name": "setSwapEnabled", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startTimeEndTime", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "startWeights", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "swapFeePercentage", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "tokenList", + "outputs": [ + { + "internalType": "contract IERC20", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newAdmin", + "type": "address" + } + ], + "name": "transferAdminRights", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_metadata", + "type": "bytes" + } + ], + "name": "updateMetadata", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "version", + "outputs": [ + { + "internalType": "bytes6", + "name": "", + "type": "bytes6" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_receiver", + "type": "address" + } + ], + "name": "withdrawPoolTokens", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ] + }, "Safe": { "address": "0xDb19E145b8Acb878B6410704b05BA4f91231E1F0", "abi": [ diff --git a/package-lock.json b/package-lock.json index a77bfdf..83479de 100644 --- a/package-lock.json +++ b/package-lock.json @@ -36,6 +36,11 @@ "regenerator-runtime": "^0.13.4" } }, + "@balancer-labs/v2-deployments": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@balancer-labs/v2-deployments/-/v2-deployments-2.3.0.tgz", + "integrity": "sha512-ShVgce/X8lhb6y9GvLmIXbYM1gONmh3rOM1BW9nfa0qW4hN1SThAbJlNWrEUUkE0VK8UT/fqGwEoyRB5In9QYA==" + }, "@ensdomains/address-encoder": { "version": "0.1.9", "resolved": "https://registry.npmjs.org/@ensdomains/address-encoder/-/address-encoder-0.1.9.tgz", diff --git a/package.json b/package.json index 8086c52..0238034 100644 --- a/package.json +++ b/package.json @@ -43,6 +43,7 @@ "husky": "^8.0.0" }, "dependencies": { + "@balancer-labs/v2-deployments": "^2.3.0", "@nomiclabs/hardhat-web3": "^2.0.0", "axios": "^0.27.2", "dotenv": "^16.0.3",