Address Contract Verified
Address
0x46950Ba8946D7be4594399bcf203fB53E1fd7D37
Balance
0 ETH
Nonce
12395
Code Size
11619 bytes
Creator
0x225124dB...c71C at tx 0x937867fc...177e0d
Indexed Transactions
0
Contract Bytecode
11619 bytes
0x60806040526004361061021c5760003560e01c806301e88208146102285780630c8d1a961461026857806311c919141461028a578063197ebb86146102bd5780631d85570a146102d3578063229c86d4146102f35780632659ac0f146103135780632f54bf6e1461033357806331b33f4314610353578063328bc10d1461038057806338715158146103a05780633df53c57146103e65780633f4ba83a1461041a57806342942cb91461042f57806343565ca61461044f578063493bf970146104835780634a6f2397146104b35780634ada739a146104f45780635e0b862b146105145780635e867c711461054857806363e85d2d1461056857806364751e411461058857806364a197f3146105a85780636b1cc751146105c85780636ec2f8f6146105e85780638456cb59146105fd5780638da5cb5b146106125780638f975a64146106325780639388d2b0146106525780639830ff6a146106725780639990c944146106925780639da947d8146106c6578063a659eb8e146106e6578063aba58e771461071a578063b187bd261461073a578063b23563041461074f578063b61d27f61461076f578063c04450d31461078f578063c2b95680146107af578063c2d0d1d0146107cf578063d255b4a4146107ef578063d572c88c14610823578063d8050ed214610857578063e6d119991461088b578063ebc1a309146108ab578063f1411c33146108df578063f2fde38b1461091357600080fd5b3661022357005b600080fd5b34801561023457600080fd5b50610255610243366004612459565b60026020526000908152604090205481565b6040519081526020015b60405180910390f35b34801561027457600080fd5b506102886102833660046124c8565b610933565b005b34801561029657600080fd5b506102ad6102a536600461251c565b600154101590565b604051901515815260200161025f565b3480156102c957600080fd5b5061025560015481565b3480156102df57600080fd5b506102886102ee36600461254b565b610a11565b3480156102ff57600080fd5b5061028861030e3660046124c8565b610a56565b34801561031f57600080fd5b5061028861032e366004612580565b610a9d565b34801561033f57600080fd5b506102ad61034e366004612459565b610bd8565b34801561035f57600080fd5b5061037361036e366004612643565b610c04565b60405161025f91906126eb565b34801561038c57600080fd5b5061028861039b3660046126fe565b610cea565b3480156103ac57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000581565b60405160ff909116815260200161025f565b3480156103f257600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000b81565b34801561042657600080fd5b50610288610da3565b34801561043b57600080fd5b5061028861044a366004612720565b610e21565b34801561045b57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000281565b34801561048f57600080fd5b506102ad61049e366004612761565b60036020526000908152604090205460ff1681565b3480156104bf57600080fd5b506104e77f000000000000000000000000bfac0f451e63d2d639b05bbea3e72318ac5abc0981565b60405161025f919061277c565b34801561050057600080fd5b5061028861050f36600461254b565b610f0b565b34801561052057600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000681565b34801561055457600080fd5b50610288610563366004612790565b610f4c565b34801561057457600080fd5b506102ad61058336600461254b565b6110f6565b34801561059457600080fd5b506102886105a336600461283c565b611123565b3480156105b457600080fd5b506102886105c336600461287d565b6111ef565b3480156105d457600080fd5b506102886105e33660046128a9565b611302565b3480156105f457600080fd5b506102886113d3565b34801561060957600080fd5b50610288611434565b34801561061e57600080fd5b506000546104e7906001600160a01b031681565b34801561063e57600080fd5b5061028861064d366004612720565b6114dc565b34801561065e57600080fd5b5061028861066d3660046128f1565b611587565b34801561067e57600080fd5b5061028861068d36600461251c565b611687565b34801561069e57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000a81565b3480156106d257600080fd5b506102886106e1366004612459565b611727565b3480156106f257600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000381565b34801561072657600080fd5b5061028861073536600461251c565b61176a565b34801561074657600080fd5b506102ad6117aa565b34801561075b57600080fd5b506104e761076a36600461251c565b6117cb565b34801561077b57600080fd5b5061037361078a366004612937565b611844565b34801561079b57600080fd5b506102886107aa366004612992565b61196a565b3480156107bb57600080fd5b506102886107ca36600461283c565b611b39565b3480156107db57600080fd5b506102886107ea366004612790565b611bfa565b3480156107fb57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000181565b34801561082f57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000881565b34801561086357600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000481565b34801561089757600080fd5b506102886108a636600461287d565b611d93565b3480156108b757600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000981565b3480156108eb57600080fd5b506103d47f000000000000000000000000000000000000000000000000000000000000000781565b34801561091f57600080fd5b5061028861092e366004612459565b611e34565b600260045460ff16600281111561094c5761094c6129f1565b0361096a5760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000161099533826110f6565b1580156109a857506109a633610bd8565b155b156109d3573381604051630d000ed760e31b81526004016109ca929190612a07565b60405180910390fd5b8160005b81811015610a0957610a01868686848181106109f5576109f5612a23565b90506020020135611f31565b6001016109d7565b505050505050565b610a1a33610bd8565b610a4857600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b610a528282612014565b5050565b610a5f33610bd8565b610a8d57600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b610a98838383612077565b505050565b600260045460ff166002811115610ab657610ab66129f1565b03610ad45760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000002610aff33826110f6565b158015610b125750610b1033610bd8565b155b15610b34573381604051630d000ed760e31b81526004016109ca929190612a07565b83828114610b5f5760405163094b3f4960e21b815260048101829052602481018490526044016109ca565b60005b81811015610bce57610bc6878783818110610b7f57610b7f612a23565b9050602002016020810190610b949190612459565b868684818110610ba657610ba6612a23565b905060200201358a6001600160a01b03166120ba9092919063ffffffff16565b600101610b62565b5050505050505050565b600080546001600160a01b038381169116148015610bfe57506001600160a01b03821615155b92915050565b6060600260045460ff166002811115610c1f57610c1f6129f1565b03610c3d5760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000006610c6833826110f6565b158015610c7b5750610c7933610bd8565b155b15610c9d573381604051630d000ed760e31b81526004016109ca929190612a07565b610cdf87878787878080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506121a092505050565b979650505050505050565b600260045460ff166002811115610d0357610d036129f1565b03610d215760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000008610d4c33826110f6565b158015610d5f5750610d5d33610bd8565b155b15610d81573381604051630d000ed760e31b81526004016109ca929190612a07565b825b82811015610d9d57610d94816121bf565b50600101610d83565b50505050565b610dac33610bd8565b610dda57600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b6004805460ff191660011790556040517f5db9ee0a495bf2e6ff9c91a7834c1ba4fdd244a5e8aa4e537bd38aeae4b073aa90610e1790339061277c565b60405180910390a1565b600260045460ff166002811115610e3a57610e3a6129f1565b03610e585760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000b610e8333826110f6565b158015610e965750610e9433610bd8565b155b15610eb8573381604051630d000ed760e31b81526004016109ca929190612a07565b81610ec581600154101590565b610ef057600154604051636174885160e01b81526109ca918391600401918252602082015260400190565b610f046001600160a01b03861685856120ba565b5050505050565b610f1433610bd8565b610f4257600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b610a5282826121d3565b600260045460ff166002811115610f6557610f656129f1565b03610f835760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000003610fae33826110f6565b158015610fc15750610fbf33610bd8565b155b15610fe3573381604051630d000ed760e31b81526004016109ca929190612a07565b858481141580610ff35750808314155b156110175760405163c8ef4fcb60e01b81526109ca90829087908690600401612a53565b60005b818110156110ea5760006110458a8a8481811061103957611039612a23565b905060200201356121bf565b90506110e0818c60006323b872dd60e01b838d8d8981811061106957611069612a23565b905060200201602081019061107e9190612459565b8c8c8a81811061109057611090612a23565b905060200201356040516024016110a993929190612a69565b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915261222d565b505060010161101a565b50505050505050505050565b6000600160ff83161b6001600160a01b038416600090815260026020526040902054161515905092915050565b600260045460ff16600281111561113c5761113c6129f1565b0361115a5760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000461118533826110f6565b158015611198575061119633610bd8565b155b156111ba573381604051630d000ed760e31b81526004016109ca929190612a07565b8160005b81811015610f04576111e78585838181106111db576111db612a23565b905060200201356122df565b6001016111be565b600260045460ff166002811115611208576112086129f1565b036112265760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000561125133826110f6565b158015611264575061126233610bd8565b155b15611286573381604051630d000ed760e31b81526004016109ca929190612a07565b600080846001600160a01b03168460405160006040518083038185875af1925050503d80600081146112d4576040519150601f19603f3d011682016040523d82523d6000602084013e6112d9565b606091505b509150915081610f04578484826040516363ccad4b60e01b81526004016109ca93929190612a8d565b600260045460ff16600281111561131b5761131b6129f1565b036113395760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000361136433826110f6565b158015611377575061137533610bd8565b155b15611399573381604051630d000ed760e31b81526004016109ca929190612a07565b60006113a4856121bf565b90506113ca818760006323b872dd60e01b8589896040516024016110a993929190612a69565b50505050505050565b6113dc33610bd8565b61140a57600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b600080546001600160a01b03191681556040513390600080516020612d0e833981519152908390a3565b7f000000000000000000000000000000000000000000000000000000000000000a61145f33826110f6565b158015611472575061147033610bd8565b155b15611494573381604051630d000ed760e31b81526004016109ca929190612a07565b6004805460ff191660021790556040517f62e78cea01bee320cd4e420270b5ea74000d11b0c9f74754ebdbfc544b05a258906114d190339061277c565b60405180910390a150565b600260045460ff1660028111156114f5576114f56129f1565b036115135760405163ab35696f60e01b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000261153e33826110f6565b158015611551575061154f33610bd8565b155b15611573573381604051630d000ed760e31b81526004016109ca929190612a07565b610d9d6001600160a01b03851684846120ba565b600260045460ff1660028111156115a0576115a06129f1565b036115be5760405163ab35696f60e01b815260040160405180910390fd5b7f00000000000000000000000000000000000000000000000000000000000000096115e933826110f6565b1580156115fc57506115fa33610bd8565b155b1561161e573381604051630d000ed760e31b81526004016109ca929190612a07565b6040516336bf91df60e21b81526001600160a01b0385169063dafe477c9061164e90889087908790600401612ab4565b600060405180830381600087803b15801561166857600080fd5b505af115801561167c573d6000803e3d6000fd5b505050505050505050565b600260045460ff1660028111156116a0576116a06129f1565b036116be5760405163ab35696f60e01b815260040160405180910390fd5b7f00000000000000000000000000000000000000000000000000000000000000046116e933826110f6565b1580156116fc57506116fa33610bd8565b155b1561171e573381604051630d000ed760e31b81526004016109ca929190612a07565b610a52826122df565b61173033610bd8565b61175e57600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b61176781612323565b50565b61177333610bd8565b6117a157600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b61176781612367565b6000600260045460ff1660028111156117c5576117c56129f1565b14905090565b604080516001600160f81b03196020808301919091523060601b6001600160601b0319166021830152603582018490527f000b19e3acc789bcb990a47f4d5f7d66193da17469fecc8940cc6c1281542a3d6055808401919091528351808403909101815260759092019092528051910120600090610bfe565b6060600260045460ff16600281111561185f5761185f6129f1565b0361187d5760405163ab35696f60e01b815260040160405180910390fd5b7f00000000000000000000000000000000000000000000000000000000000000076118a833826110f6565b1580156118bb57506118b933610bd8565b155b156118dd573381604051630d000ed760e31b81526004016109ca929190612a07565b600080876001600160a01b03168787876040516118fb929190612ad5565b60006040518083038185875af1925050503d8060008114611938576040519150601f19603f3d011682016040523d82523d6000602084013e61193d565b606091505b509150915081610cdf57878787878460405163f5faddbb60e01b81526004016109ca959493929190612ae5565b600260045460ff166002811115611983576119836129f1565b036119a15760405163ab35696f60e01b815260040160405180910390fd5b7f00000000000000000000000000000000000000000000000000000000000000056119cc33826110f6565b1580156119df57506119dd33610bd8565b155b15611a01573381604051630d000ed760e31b81526004016109ca929190612a07565b83828114611a2c57604051632105fa9560e21b815260048101829052602481018490526044016109ca565b60005b818110156113ca57600080888884818110611a4c57611a4c612a23565b9050602002016020810190611a619190612459565b6001600160a01b0316878785818110611a7c57611a7c612a23565b9050602002013560405160006040518083038185875af1925050503d8060008114611ac3576040519150601f19603f3d011682016040523d82523d6000602084013e611ac8565b606091505b509150915081611b2f57888884818110611ae457611ae4612a23565b9050602002016020810190611af99190612459565b878785818110611b0b57611b0b612a23565b90506020020135826040516363ccad4b60e01b81526004016109ca93929190612a8d565b5050600101611a2f565b600260045460ff166002811115611b5257611b526129f1565b03611b705760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000008611b9b33826110f6565b158015611bae5750611bac33610bd8565b155b15611bd0573381604051630d000ed760e31b81526004016109ca929190612a07565b8160005b81811015610f0457611bf185858381811061103957611039612a23565b50600101611bd4565b600260045460ff166002811115611c1357611c136129f1565b03611c315760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000009611c5c33826110f6565b158015611c6f5750611c6d33610bd8565b155b15611c91573381604051630d000ed760e31b81526004016109ca929190612a07565b858481141580611ca15750808314155b15611cc5576040516312c28db360e21b81526109ca90829087908690600401612a53565b60005b818110156110ea57888882818110611ce257611ce2612a23565b9050602002016020810190611cf79190612459565b6001600160a01b031663dafe477c8b898985818110611d1857611d18612a23565b90506020020135888886818110611d3157611d31612a23565b905060200201356040518463ffffffff1660e01b8152600401611d5693929190612ab4565b600060405180830381600087803b158015611d7057600080fd5b505af1158015611d84573d6000803e3d6000fd5b50505050806001019050611cc8565b600260045460ff166002811115611dac57611dac6129f1565b03611dca5760405163ab35696f60e01b815260040160405180910390fd5b7f0000000000000000000000000000000000000000000000000000000000000001611df533826110f6565b158015611e085750611e0633610bd8565b155b15611e2a573381604051630d000ed760e31b81526004016109ca929190612a07565b610a988383611f31565b611e3d33610bd8565b611e6b57600054604051631194af8760e11b81526109ca9133916001600160a01b0390911690600401612a39565b6001600160a01b038116611e9257604051632a52b3c360e11b815260040160405180910390fd5b600080546001600160a01b0319166001600160a01b038316908117825560405190913391600080516020612d0e8339815191529190a350565b604051733d602d80600a3d3981f3363d3d373d3d3d363d7360601b6020820152606082811b6001600160601b03191660348301526e5af43d82803e903d91602b57fd5bf360881b6048830152906057016040516020818303038152906040529050919050565b6000611f3c826117cb565b90506000836001600160a01b03166370a08231836040518263ffffffff1660e01b8152600401611f6c919061277c565b602060405180830381865afa158015611f89573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611fad9190612b46565b90508015610d9d57611fbf828461239c565b506000611fe48386600063a9059cbb60e01b30876040516024016110a9929190612b5f565b9050611fef816123c0565b610f04578483838360405163d0acb72d60e01b81526004016109ca9493929190612b78565b6001600160a01b0382166000818152600260209081526040918290208054600160ff871690811b1990911690915591519182527f31712f88cf0ac4bb1f2a194ba7f7eedf070f0e687bb81f6c7dd562e2a4a975bf91015b60405180910390a25050565b60005b81811015610d9d576120b28484848481811061209857612098612a23565b90506020020160208101906120ad9190612761565b6121d3565b60010161207a565b600080846001600160a01b031663a9059cbb60e01b85856040516024016120e2929190612b5f565b60408051601f198184030181529181526020820180516001600160e01b03166001600160e01b03199094169390931790925290516121209190612bab565b6000604051808303816000865af19150503d806000811461215d576040519150601f19603f3d011682016040523d82523d6000602084013e612162565b606091505b509150915081158061217a5750612178816123c0565b155b15610f04578484848360405163194f44ab60e11b81526004016109ca9493929190612b78565b60606121b66121ae866121bf565b85858561222d565b95945050505050565b6000610bfe6121cd836117cb565b8361239c565b6001600160a01b0382166000818152600260209081526040918290208054600160ff871690811b90911790915591519182527f87dd0a07ce69ed29fb6177354fd667fd36f490b40e519f46d19343eee4e6082d910161206b565b6060600080866001600160a01b031663b61d27f68787876040518463ffffffff1660e01b815260040161226293929190612a8d565b6000604051808303816000875af1158015612281573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f191682016040526122a99190810190612bed565b91509150816122d55786868686846040516353df14d960e01b81526004016109ca959493929190612cad565b9695505050505050565b60006122ea826117cb565b90506001600160a01b038116318015610a9857612307828461239c565b50610d9d8230836040518060200160405280600081525061222d565b6001600160a01b038116600081815260026020526040808220829055517ff3ae8a9ec7a74524888eda748db87556dc0137c576e33d9e443ff7c7045d8af79190a250565b60018190556040518181527fc789f3c6e11c26e01497dbada79eb3e880962e86835be4139cce578f55341e03906020016114d1565b6000823b80156123af5783915050610bfe565b6123b8836123e1565b949350505050565b6000815160001480610bfe575081806020019051810190610bfe9190612cf2565b6000610bfe826124107f000000000000000000000000bfac0f451e63d2d639b05bbea3e72318ac5abc09611ecb565b60008282516020840134f590506001600160a01b038116610bfe5760405163219c53f560e21b815260040160405180910390fd5b6001600160a01b038116811461176757600080fd5b60006020828403121561246b57600080fd5b813561247681612444565b9392505050565b60008083601f84011261248f57600080fd5b5081356001600160401b038111156124a657600080fd5b6020830191508360208260051b85010111156124c157600080fd5b9250929050565b6000806000604084860312156124dd57600080fd5b83356124e881612444565b925060208401356001600160401b0381111561250357600080fd5b61250f8682870161247d565b9497909650939450505050565b60006020828403121561252e57600080fd5b5035919050565b803560ff8116811461254657600080fd5b919050565b6000806040838503121561255e57600080fd5b823561256981612444565b915061257760208401612535565b90509250929050565b60008060008060006060868803121561259857600080fd5b85356125a381612444565b945060208601356001600160401b03808211156125bf57600080fd5b6125cb89838a0161247d565b909650945060408801359150808211156125e457600080fd5b506125f18882890161247d565b969995985093965092949392505050565b60008083601f84011261261457600080fd5b5081356001600160401b0381111561262b57600080fd5b6020830191508360208285010111156124c157600080fd5b60008060008060006080868803121561265b57600080fd5b85359450602086013561266d81612444565b93506040860135925060608601356001600160401b0381111561268f57600080fd5b6125f188828901612602565b60005b838110156126b657818101518382015260200161269e565b50506000910152565b600081518084526126d781602086016020860161269b565b601f01601f19169290920160200192915050565b60208152600061247660208301846126bf565b6000806040838503121561271157600080fd5b50508035926020909101359150565b60008060006060848603121561273557600080fd5b833561274081612444565b9250602084013561275081612444565b929592945050506040919091013590565b60006020828403121561277357600080fd5b61247682612535565b6001600160a01b0391909116815260200190565b60008060008060008060006080888a0312156127ab57600080fd5b87356127b681612444565b965060208801356001600160401b03808211156127d257600080fd5b6127de8b838c0161247d565b909850965060408a01359150808211156127f757600080fd5b6128038b838c0161247d565b909650945060608a013591508082111561281c57600080fd5b506128298a828b0161247d565b989b979a50959850939692959293505050565b6000806020838503121561284f57600080fd5b82356001600160401b0381111561286557600080fd5b6128718582860161247d565b90969095509350505050565b6000806040838503121561289057600080fd5b823561289b81612444565b946020939093013593505050565b600080600080608085870312156128bf57600080fd5b84356128ca81612444565b93506020850135925060408501356128e181612444565b9396929550929360600135925050565b6000806000806080858703121561290757600080fd5b843561291281612444565b9350602085013561292281612444565b93969395505050506040820135916060013590565b6000806000806060858703121561294d57600080fd5b843561295881612444565b93506020850135925060408501356001600160401b0381111561297a57600080fd5b61298687828801612602565b95989497509550505050565b600080600080604085870312156129a857600080fd5b84356001600160401b03808211156129bf57600080fd5b6129cb8883890161247d565b909650945060208701359150808211156129e457600080fd5b506129868782880161247d565b634e487b7160e01b600052602160045260246000fd5b6001600160a01b0392909216825260ff16602082015260400190565b634e487b7160e01b600052603260045260246000fd5b6001600160a01b0392831681529116602082015260400190565b9283526020830191909152604082015260600190565b6001600160a01b039384168152919092166020820152604081019190915260600190565b60018060a01b03841681528260208201526060604082015260006121b660608301846126bf565b6001600160a01b039390931683526020830191909152604082015260600190565b8183823760009101908152919050565b6001600160a01b0386168152602081018590526080604082018190528101839052828460a0830137600060a084830101526000601f19601f850116820160a0838203016060840152612b3a60a08201856126bf565b98975050505050505050565b600060208284031215612b5857600080fd5b5051919050565b6001600160a01b03929092168252602082015260400190565b6001600160a01b03858116825284166020820152604081018390526080606082018190526000906122d5908301846126bf565b60008251612bbd81846020870161269b565b9190910192915050565b8051801515811461254657600080fd5b634e487b7160e01b600052604160045260246000fd5b60008060408385031215612c0057600080fd5b612c0983612bc7565b60208401519092506001600160401b0380821115612c2657600080fd5b818501915085601f830112612c3a57600080fd5b815181811115612c4c57612c4c612bd7565b604051601f8201601f19908116603f01168101908382118183101715612c7457612c74612bd7565b81604052828152886020848701011115612c8d57600080fd5b612c9e83602083016020880161269b565b80955050505050509250929050565b6001600160a01b038681168252851660208201526040810184905260a060608201819052600090612ce0908301856126bf565b8281036080840152612b3a81856126bf565b600060208284031215612d0457600080fd5b61247682612bc756fe8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0a2646970667358221220b1370cc75c594ee5aad71fa03331a3c68d87ce592afff2818cdfca8bedce938f64736f6c63430008100033
Verified Source Code Full Match
Compiler: v0.8.16+commit.07a7930e
EVM: london
Optimization: Yes (1 runs)
VaultETH.sol 75 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/receiver/ReceiverHub.sol";
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
abstract contract VaultETH is ReceiverHub, Permissions, Pausable {
error ErrorSendingETH(address _to, uint256 _amount, bytes _result);
error ArrayLengthMismatchETH(uint256 _array1, uint256 _array2);
uint8 public immutable PERMISSION_SWEEP_ETH;
uint8 public immutable PERMISSION_SEND_ETH;
constructor (uint8 _sweepETHPermission, uint8 _sendETHPermission) {
PERMISSION_SWEEP_ETH = _sweepETHPermission;
PERMISSION_SEND_ETH = _sendETHPermission;
_registerPermission(PERMISSION_SWEEP_ETH);
_registerPermission(PERMISSION_SEND_ETH);
}
function sweepETH(
uint256 _id
) external notPaused onlyPermissioned(PERMISSION_SWEEP_ETH) {
_sweepETH(_id);
}
function sweepBatchETH(
uint256[] calldata _ids
) external notPaused onlyPermissioned(PERMISSION_SWEEP_ETH) {
unchecked {
uint256 idsLength = _ids.length;
for (uint256 i = 0; i < idsLength; ++i) {
_sweepETH(_ids[i]);
}
}
}
function _sweepETH(uint256 _id) internal {
Receiver receiver = receiverFor(_id);
uint256 balance = address(receiver).balance;
if (balance != 0) {
createIfNeeded(receiver, _id);
executeOnReceiver(receiver, address(this), balance, bytes(""));
}
}
function sendETH(
address payable _to,
uint256 _amount
) external notPaused onlyPermissioned(PERMISSION_SEND_ETH) {
(bool succeed, bytes memory result) = _to.call{ value: _amount }("");
if (!succeed) { revert ErrorSendingETH(_to, _amount, result); }
}
function sendBatchETH(
address payable[] calldata _tos,
uint256[] calldata _amounts
) external notPaused onlyPermissioned(PERMISSION_SEND_ETH) {
uint256 toLength = _tos.length;
if (toLength != _amounts.length) {
revert ArrayLengthMismatchETH(toLength, _amounts.length);
}
unchecked {
for (uint256 i = 0; i < toLength; ++i) {
(bool succeed, bytes memory result) = _tos[i].call{ value: _amounts[i] }("");
if (!succeed) { revert ErrorSendingETH(_tos[i], _amounts[i], result); }
}
}
}
receive() external payable {}
}
VaultERC20.sol 108 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/interfaces/IERC20.sol";
import "src/commons/receiver/ReceiverHub.sol";
import "src/commons/Limits.sol";
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
import "src/utils/SafeERC20.sol";
abstract contract VaultERC20 is ReceiverHub, Limits, Permissions, Pausable {
using SafeERC20 for IERC20;
error ErrorSweepingERC20(address _token, address _receiver, uint256 _amount, bytes _result);
error ArrayLengthMismatchERC20(uint256 _array1, uint256 _array2);
uint8 public immutable PERMISSION_SWEEP_ERC20;
uint8 public immutable PERMISSION_SEND_ERC20;
uint8 public immutable PERMISSION_SEND_ERC20_LIMIT;
constructor (uint8 _sweepErc20Permission, uint8 _sendErc20Permission, uint8 _sendErc20LimitPermission) {
PERMISSION_SWEEP_ERC20 = _sweepErc20Permission;
PERMISSION_SEND_ERC20 = _sendErc20Permission;
PERMISSION_SEND_ERC20_LIMIT = _sendErc20LimitPermission;
_registerPermission(PERMISSION_SWEEP_ERC20);
_registerPermission(PERMISSION_SEND_ERC20);
_registerPermission(PERMISSION_SEND_ERC20_LIMIT);
}
function sweepERC20(
IERC20 _token,
uint256 _id
) external notPaused onlyPermissioned(PERMISSION_SWEEP_ERC20) {
_sweepERC20(_token, _id);
}
function sweepBatchERC20(
IERC20 _token,
uint256[] calldata _ids
) external notPaused onlyPermissioned(PERMISSION_SWEEP_ERC20) {
unchecked {
uint256 idsLength = _ids.length;
for (uint256 i = 0; i < idsLength; ++i) {
_sweepERC20(_token, _ids[i]);
}
}
}
function _sweepERC20(
IERC20 _token,
uint256 _id
) internal {
Receiver receiver = receiverFor(_id);
uint256 balance = _token.balanceOf(address(receiver));
if (balance != 0) {
createIfNeeded(receiver, _id);
bytes memory res = executeOnReceiver(receiver, address(_token), 0, abi.encodeWithSelector(
IERC20.transfer.selector,
address(this),
balance
));
if (!SafeERC20.optionalReturnsTrue(res)) {
revert ErrorSweepingERC20(address(_token), address(receiver), balance, res);
}
}
}
function sendERC20(
IERC20 _token,
address _to,
uint256 _amount
) external notPaused onlyPermissioned(PERMISSION_SEND_ERC20) {
_token.safeTransfer(_to, _amount);
}
function sendBatchERC20(
IERC20 _token,
address[] calldata _to,
uint256[] calldata _amounts
) external notPaused onlyPermissioned(PERMISSION_SEND_ERC20) {
uint256 toLength = _to.length;
if (toLength != _amounts.length) {
revert ArrayLengthMismatchERC20(toLength, _amounts.length);
}
unchecked {
for (uint256 i = 0; i < toLength; ++i) {
_token.safeTransfer(_to[i], _amounts[i]);
}
}
}
function sendERC20WithLimit(
IERC20 _token,
address _to,
uint256 _amount
) external notPaused onlyPermissioned(PERMISSION_SEND_ERC20_LIMIT) underLimit(_amount) {
_token.safeTransfer(_to, _amount);
}
}
Vault.sol 28 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/VaultERC20.sol";
import "src/VaultERC721.sol";
import "src/VaultETH.sol";
import "src/VaultExecute.sol";
import "src/VaultNewReceivers.sol";
import "src/VaultIssueERC721.sol";
contract Vault is
VaultERC20,
VaultERC721,
VaultETH,
VaultExecute,
VaultNewReceivers,
VaultIssueERC721
{
constructor()
VaultERC20(1, 2, 11)
VaultERC721(3)
VaultETH(4, 5)
VaultExecute(6, 7)
VaultNewReceivers(8)
VaultIssueERC721(9)
Pausable(10)
{}
}
VaultERC721.sol 63 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/interfaces/IERC721.sol";
import "src/commons/receiver/ReceiverHub.sol";
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
abstract contract VaultERC721 is ReceiverHub, Permissions, Pausable {
uint8 public immutable PERMISSION_SEND_ERC721;
error ArrayLengthMismatchERC721(uint256 _array1, uint256 _array2, uint256 _array3);
constructor (uint8 _sendErc721Permission) {
PERMISSION_SEND_ERC721 = _sendErc721Permission;
_registerPermission(PERMISSION_SEND_ERC721);
}
function sendERC721(
IERC721 _token,
uint256 _from,
address _to,
uint256 _id
) external notPaused onlyPermissioned(PERMISSION_SEND_ERC721) {
Receiver receiver = useReceiver(_from);
executeOnReceiver(receiver, address(_token), 0, abi.encodeWithSelector(
_token.transferFrom.selector,
address(receiver),
_to,
_id
)
);
}
function sendBatchERC721(
IERC721 _token,
uint256[] calldata _ids,
address[] calldata _tos,
uint256[] calldata _tokenIds
) external notPaused onlyPermissioned(PERMISSION_SEND_ERC721) {
unchecked {
uint256 idsLength = _ids.length;
if (idsLength != _tos.length || idsLength != _tokenIds.length) {
revert ArrayLengthMismatchERC721(idsLength, _tos.length, _tokenIds.length);
}
for (uint256 i = 0; i < idsLength; ++i) {
Receiver receiver = useReceiver(_ids[i]);
executeOnReceiver(receiver, address(_token), 0, abi.encodeWithSelector(
_token.transferFrom.selector,
address(receiver),
_tos[i],
_tokenIds[i]
)
);
}
}
}
}
Proxy.sol 35 lines
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.16;
/*
The MIT License (MIT)
Copyright (c) 2018 Murray Software, LLC.
Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice shall be included
in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
//solhint-disable max-line-length
//solhint-disable no-inline-assembly
library Proxy {
function creationCode(address _target) internal pure returns (bytes memory result) {
return abi.encodePacked(
hex'3d602d80600a3d3981f3363d3d373d3d3d363d73',
_target,
hex'5af43d82803e903d91602b57fd5bf3'
);
}
}
VaultExecute.sol 43 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/receiver/ReceiverHub.sol";
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
abstract contract VaultExecute is ReceiverHub, Permissions, Pausable {
uint8 public immutable PERMISSION_EXECUTE_ON_RECEIVER;
uint8 public immutable PERMISSION_EXECUTE;
error CallError(address _to, uint256 _value, bytes _data, bytes _result);
constructor(
uint8 _executeOnReceiverPermission,
uint8 _executePermission
) {
PERMISSION_EXECUTE_ON_RECEIVER = _executeOnReceiverPermission;
PERMISSION_EXECUTE = _executePermission;
_registerPermission(PERMISSION_EXECUTE_ON_RECEIVER);
_registerPermission(PERMISSION_EXECUTE);
}
function executeOnReceiver(
uint256 _id,
address payable _to,
uint256 _value,
bytes calldata _data
) external notPaused onlyPermissioned(PERMISSION_EXECUTE_ON_RECEIVER) returns (bytes memory) {
return executeOnReceiver(_id, _to, _value, _data);
}
function execute(
address payable _to,
uint256 _value,
bytes calldata _data
) external notPaused onlyPermissioned(PERMISSION_EXECUTE) returns (bytes memory) {
(bool res, bytes memory result) = _to.call{ value: _value }(_data);
if (!res) revert CallError(_to, _value, _data, result);
return result;
}
}
CREATE2.sol 36 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
library CREATE2 {
error ContractNotCreated();
function addressOf(address _creator, uint256 _salt, bytes32 _creationCodeHash) internal pure returns (address payable) {
return payable(
address(
uint160(
uint256(
keccak256(
abi.encodePacked(
bytes1(0xff),
_creator,
_salt,
_creationCodeHash
)
)
)
)
)
);
}
function deploy(uint256 _salt, bytes memory _creationCode) internal returns (address payable _contract) {
assembly {
_contract := create2(callvalue(), add(_creationCode, 32), mload(_creationCode), _salt)
}
if (_contract == address(0)) {
revert ContractNotCreated();
}
}
}
Limits.sol 34 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/Ownable.sol";
contract Limits is Ownable {
error ExceededLimit(uint256 _amount, uint256 _limit);
uint256 public ERC20Limit;
event UpdateERC20Limit(uint256 _limit);
modifier underLimit(uint256 _amount) {
if (!isUnderLimit(_amount)) {
revert ExceededLimit(_amount, ERC20Limit);
}
_;
}
function isUnderLimit(uint256 _amount) public view returns (bool) {
return _amount <= ERC20Limit;
}
function updateERC20Limit(uint256 _limit) external virtual onlyOwner {
_updateERC20Limit(_limit);
}
function _updateERC20Limit(uint256 _limit) internal {
ERC20Limit = _limit;
emit UpdateERC20Limit(_limit);
}
}
Ownable.sol 37 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/interfaces/IERC173.sol";
contract Ownable is IERC173 {
error NotOwner(address _sender, address _owner);
error InvalidNewOwner();
address public owner;
constructor() {
owner = msg.sender;
emit OwnershipTransferred(address(0), msg.sender);
}
modifier onlyOwner() {
if (!isOwner(msg.sender)) revert NotOwner(msg.sender, owner);
_;
}
function isOwner(address _owner) public view returns (bool) {
return _owner == owner && _owner != address(0);
}
function transferOwnership(address _newOwner) external onlyOwner {
if (_newOwner == address(0)) revert InvalidNewOwner();
owner = _newOwner;
emit OwnershipTransferred(msg.sender, _newOwner);
}
function rennounceOwnership() external onlyOwner {
owner = address(0);
emit OwnershipTransferred(msg.sender, address(0));
}
}
SafeERC20.sol 25 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/interfaces/IERC20.sol";
library SafeERC20 {
error ErrorSendingERC20(address _token, address _to, uint256 _amount, bytes _result);
function safeTransfer(IERC20 _token, address _to, uint256 _amount) internal {
(bool success, bytes memory result) = address(_token).call(abi.encodeWithSelector(
IERC20.transfer.selector,
_to,
_amount
));
if (!success || !optionalReturnsTrue(result)) {
revert ErrorSendingERC20(address(_token), _to, _amount, result);
}
}
function optionalReturnsTrue(bytes memory _return) internal pure returns (bool) {
return _return.length == 0 || abi.decode(_return, (bool));
}
}
VaultIssueERC721.sol 47 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
import "src/interfaces/IERC721Deterministic.sol";
abstract contract VaultIssueERC721 is Permissions, Pausable {
uint8 public immutable PERMISSION_ISSUE_ERC721;
error ArrayLengthMismatchIssueERC721(uint256 _array1, uint256 _array2, uint256 _array3);
constructor (uint8 _issueERC721Permission) {
PERMISSION_ISSUE_ERC721 = _issueERC721Permission;
_registerPermission(PERMISSION_ISSUE_ERC721);
}
function issueERC721(
address _beneficiary,
IERC721Deterministic _contract,
uint256 _optionId,
uint256 _issuedId
) external notPaused onlyPermissioned(PERMISSION_ISSUE_ERC721) {
_contract.issueToken(_beneficiary, _optionId, _issuedId);
}
function issueBatchERC721(
address _beneficiary,
IERC721Deterministic[] calldata _contracts,
uint256[] calldata _optionIds,
uint256[] calldata _issuedIds
) external notPaused onlyPermissioned(PERMISSION_ISSUE_ERC721) {
unchecked {
uint256 contractsLength = _contracts.length;
if (contractsLength != _optionIds.length || contractsLength != _issuedIds.length) {
revert ArrayLengthMismatchIssueERC721(contractsLength, _optionIds.length, _issuedIds.length);
}
for (uint256 i = 0; i < contractsLength; ++i) {
_contracts[i].issueToken(_beneficiary, _optionIds[i], _issuedIds[i]);
}
}
}
}
Pausable.sol 43 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/Ownable.sol";
import "src/commons/Permissions.sol";
contract Pausable is Ownable, Permissions {
error ContractPaused();
event Unpaused(address _sender);
event Paused(address _sender);
enum State { Invalid, Unpaused, Paused }
State internal _state = State.Unpaused;
uint8 public immutable PERMISSION_PAUSE;
constructor(uint8 _permissionPause) {
PERMISSION_PAUSE = _permissionPause;
}
modifier notPaused() {
if (_state == State.Paused) {
revert ContractPaused();
}
_;
}
function isPaused() public view returns (bool) {
return _state == State.Paused;
}
function pause() external onlyPermissioned(PERMISSION_PAUSE) {
_state = State.Paused;
emit Paused(msg.sender);
}
function unpause() external onlyOwner {
_state = State.Unpaused;
emit Unpaused(msg.sender);
}
}
VaultNewReceivers.sol 39 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/receiver/ReceiverHub.sol";
import "src/commons/Permissions.sol";
import "src/commons/Pausable.sol";
abstract contract VaultNewReceivers is ReceiverHub, Permissions, Pausable {
uint8 public immutable PERMISSION_DEPLOY_RECEIVER;
constructor (uint8 _deployReceiverPermission) {
PERMISSION_DEPLOY_RECEIVER = _deployReceiverPermission;
_registerPermission(PERMISSION_DEPLOY_RECEIVER);
}
function deployReceivers(
uint256[] calldata _receivers
) external notPaused onlyPermissioned(PERMISSION_DEPLOY_RECEIVER) {
unchecked {
uint256 receiversLength = _receivers.length;
for (uint256 i = 0; i < receiversLength; ++i) {
useReceiver(_receivers[i]);
}
}
}
function deployReceiversRange(
uint256 _from,
uint256 _to
) external notPaused onlyPermissioned(PERMISSION_DEPLOY_RECEIVER) {
unchecked {
for (uint256 i = _from; i < _to; ++i) {
useReceiver(i);
}
}
}
}
IERC20.sol 15 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
interface IERC20 {
event Transfer(address indexed _from, address indexed _to, uint256 _value);
event Approval(address indexed _owner, address indexed _spender, uint256 _value);
function totalSupply() external view returns (uint256);
function balanceOf(address _account) external view returns (uint256);
function transfer(address _to, uint256 _amount) external returns (bool);
function allowance(address _owner, address _spender) external view returns (uint256);
function approve(address _spender, uint256 _amount) external returns (bool);
function transferFrom(address _from, address _to, uint256 _amount) external returns (bool);
}
IERC173.sol 9 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
interface IERC173 {
event OwnershipTransferred(address indexed _previousOwner, address indexed _newOwner);
function owner() view external returns(address);
function transferOwnership(address _newOwner) external;
}
IERC721.sol 20 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
interface IERC721 {
event Transfer(address indexed _from, address indexed _to, uint256 indexed _tokenId);
event Approval(address indexed _owner, address indexed _approved, uint256 indexed _tokenId);
event ApprovalForAll(address indexed _owner, address indexed _operator, bool _approved);
function balanceOf(address _owner) external view returns (uint256);
function ownerOf(uint256 _tokenId) external view returns (address);
function safeTransferFrom(address _from, address _to, uint256 _tokenId, bytes calldata data) external payable;
function safeTransferFrom(address _from, address _to, uint256 _tokenId) external payable;
function transferFrom(address _from, address _to, uint256 _tokenId) external payable;
function approve(address _approved, uint256 _tokenId) external payable;
function setApprovalForAll(address _operator, bool _approved) external;
function getApproved(uint256 _tokenId) external view returns (address);
function isApprovedForAll(address _owner, address _operator) external view returns (bool);
}
Permissions.sol 80 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/commons/Ownable.sol";
contract Permissions is Ownable {
error PermissionDenied(address _sender, uint8 _permission);
error DuplicatedPermission(uint8 _permission);
mapping (address => bytes32) public permissions;
mapping (uint8 => bool) public permissionExists;
event AddPermission(address indexed _addr, uint8 _permission);
event DelPermission(address indexed _addr, uint8 _permission);
event ClearPermissions(address indexed _addr);
modifier onlyPermissioned(uint8 _permission) {
if (!hasPermission(msg.sender, _permission) && !isOwner(msg.sender)) {
revert PermissionDenied(msg.sender, _permission);
}
_;
}
function _registerPermission(uint8 _permission) internal {
if (permissionExists[_permission]) {
revert DuplicatedPermission(_permission);
}
permissionExists[_permission] = true;
}
function hasPermission(address _addr, uint8 _permission) public view returns (bool) {
return (permissions[_addr] & _maskForPermission(_permission)) != 0;
}
function addPermission(address _addr, uint8 _permission) external virtual onlyOwner {
_addPermission(_addr, _permission);
}
function addPermissions(address _addr, uint8[] calldata _permissions) external virtual onlyOwner {
_addPermissions(_addr, _permissions);
}
function delPermission(address _addr, uint8 _permission) external virtual onlyOwner {
_delPermission(_addr, _permission);
}
function clearPermissions(address _addr) external virtual onlyOwner {
_clearPermissions(_addr);
}
function _maskForPermission(uint8 _permission) internal pure returns (bytes32) {
return bytes32(1 << _permission);
}
function _addPermission(address _addr, uint8 _permission) internal {
permissions[_addr] |= _maskForPermission(_permission);
emit AddPermission(_addr, _permission);
}
function _addPermissions(address _addr, uint8[] calldata _permissions) internal {
unchecked {
for (uint256 i = 0; i < _permissions.length; ++i) {
_addPermission(_addr, _permissions[i]);
}
}
}
function _delPermission(address _addr, uint8 _permission) internal {
permissions[_addr] &= ~_maskForPermission(_permission);
emit DelPermission(_addr, _permission);
}
function _clearPermissions(address _addr) internal {
delete permissions[_addr];
emit ClearPermissions(_addr);
}
}
Receiver.sol 28 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/interfaces/IERC721Receiver.sol";
contract Receiver is IERC721Receiver {
error NotAuthorized(address _sender);
address immutable private owner;
constructor () {
owner = msg.sender;
}
function execute(address payable _to, uint256 _value, bytes calldata _data) external returns (bool, bytes memory) {
if (msg.sender != owner) revert NotAuthorized(msg.sender);
return _to.call{ value: _value }(_data);
}
function onERC721Received(address, address, uint256, bytes calldata) external pure returns (bytes4) {
// return bytes4(keccak256("onERC721Received(address,address,uint256,bytes)"))
return 0x150b7a02;
}
receive() external payable { }
fallback() external payable { }
}
IERC721Receiver.sol 7 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
interface IERC721Receiver {
function onERC721Received(address _operator, address _from, uint256 _tokenId, bytes calldata _data) external returns(bytes4);
}
ReceiverHub.sol 51 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
import "src/libs/CREATE2.sol";
import "src/utils/Proxy.sol";
import "src/commons/receiver/Receiver.sol";
contract ReceiverHub {
error ReceiverCallError(address _receiver, address _to, uint256 _value, bytes _data, bytes _result);
address immutable public receiverTemplate;
bytes32 immutable private receiverTemplateCreationCodeHash;
constructor () {
receiverTemplate = address(new Receiver());
receiverTemplateCreationCodeHash = keccak256(Proxy.creationCode(address(receiverTemplate)));
}
function receiverFor(uint256 _id) public view returns (Receiver) {
return Receiver(CREATE2.addressOf(address(this), _id, receiverTemplateCreationCodeHash));
}
function createReceiver(uint256 _id) internal returns (Receiver) {
return Receiver(CREATE2.deploy(_id, Proxy.creationCode(receiverTemplate)));
}
function createIfNeeded(Receiver receiver, uint256 _id) internal returns (Receiver) {
uint256 receiverCodeSize; assembly { receiverCodeSize := extcodesize(receiver) }
if (receiverCodeSize != 0) {
return receiver;
}
return createReceiver(_id);
}
function useReceiver(uint256 _id) internal returns (Receiver) {
return createIfNeeded(receiverFor(_id), _id);
}
function executeOnReceiver(uint256 _id, address _to, uint256 _value, bytes memory _data) internal returns (bytes memory) {
return executeOnReceiver(useReceiver(_id), _to, _value, _data);
}
function executeOnReceiver(Receiver _receiver, address _to, uint256 _value, bytes memory _data) internal returns (bytes memory) {
(bool succeed, bytes memory result) = _receiver.execute(payable(_to), _value, _data);
if (!succeed) revert ReceiverCallError(address(_receiver), _to, _value, _data, result);
return result;
}
}
IERC721Deterministic.sol 7 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.16;
interface IERC721Deterministic {
function issueToken(address _beneficiary, uint256 _optionId, uint256 _issuedId) external;
}
Read Contract
ERC20Limit 0x197ebb86 → uint256
PERMISSION_DEPLOY_RECEIVER 0xd572c88c → uint8
PERMISSION_EXECUTE 0xf1411c33 → uint8
PERMISSION_EXECUTE_ON_RECEIVER 0x5e0b862b → uint8
PERMISSION_ISSUE_ERC721 0xebc1a309 → uint8
PERMISSION_PAUSE 0x9990c944 → uint8
PERMISSION_SEND_ERC20 0x43565ca6 → uint8
PERMISSION_SEND_ERC20_LIMIT 0x3df53c57 → uint8
PERMISSION_SEND_ERC721 0xa659eb8e → uint8
PERMISSION_SEND_ETH 0x38715158 → uint8
PERMISSION_SWEEP_ERC20 0xd255b4a4 → uint8
PERMISSION_SWEEP_ETH 0xd8050ed2 → uint8
hasPermission 0x63e85d2d → bool
isOwner 0x2f54bf6e → bool
isPaused 0xb187bd26 → bool
isUnderLimit 0x11c91914 → bool
owner 0x8da5cb5b → address
permissionExists 0x493bf970 → bool
permissions 0x01e88208 → bytes32
receiverFor 0xb2356304 → address
receiverTemplate 0x4a6f2397 → address
Write Contract 26 functions
These functions modify contract state and require a wallet transaction to execute.
addPermission 0x4ada739a
address _addr
uint8 _permission
addPermissions 0x229c86d4
address _addr
uint8[] _permissions
clearPermissions 0x9da947d8
address _addr
delPermission 0x1d85570a
address _addr
uint8 _permission
deployReceivers 0xc2b95680
uint256[] _receivers
deployReceiversRange 0x328bc10d
uint256 _from
uint256 _to
execute 0xb61d27f6
address _to
uint256 _value
bytes _data
returns: bytes
executeOnReceiver 0x31b33f43
uint256 _id
address _to
uint256 _value
bytes _data
returns: bytes
issueBatchERC721 0xc2d0d1d0
address _beneficiary
address[] _contracts
uint256[] _optionIds
uint256[] _issuedIds
issueERC721 0x9388d2b0
address _beneficiary
address _contract
uint256 _optionId
uint256 _issuedId
pause 0x8456cb59
No parameters
rennounceOwnership 0x6ec2f8f6
No parameters
sendBatchERC20 0x2659ac0f
address _token
address[] _to
uint256[] _amounts
sendBatchERC721 0x5e867c71
address _token
uint256[] _ids
address[] _tos
uint256[] _tokenIds
sendBatchETH 0xc04450d3
address[] _tos
uint256[] _amounts
sendERC20 0x8f975a64
address _token
address _to
uint256 _amount
sendERC20WithLimit 0x42942cb9
address _token
address _to
uint256 _amount
sendERC721 0x6b1cc751
address _token
uint256 _from
address _to
uint256 _id
sendETH 0x64a197f3
address _to
uint256 _amount
sweepBatchERC20 0x0c8d1a96
address _token
uint256[] _ids
sweepBatchETH 0x64751e41
uint256[] _ids
sweepERC20 0xe6d11999
address _token
uint256 _id
sweepETH 0x9830ff6a
uint256 _id
transferOwnership 0xf2fde38b
address _newOwner
unpause 0x3f4ba83a
No parameters
updateERC20Limit 0xaba58e77
uint256 _limit
Recent Transactions
No transactions found for this address