Cryo Explorer Ethereum Mainnet

Address Contract Partially Verified

Address 0x752eBeb79963cf0732E9c0fec72a49FD1DEfAEAC
Balance 143.4703 ETH
Nonce 1
Code Size 23892 bytes
Indexed Transactions 0
External Etherscan · Sourcify

Contract Bytecode

23892 bytes
0x600436101561000d576126f0565b60046000601c37600051635b41b9088118610032576000610e005233610e2052610080565b63394747c58118610056576084358060011c615caf57610e005233610e2052610080565b63ce7d650381186100f5576084358060011c615caf57610e005260a4358060a01c615caf57610e20525b600054615caf576001600055336109a052346109c052608060046109e037610e0051610a6052610e2051610a80526000610aa0526004610e40526000610e6052610e40805160200180610ac0828460045afa905050506100e1610e80614aa0565b610e8051610ea0526020610ea06000600055f35b6365b2489b811861010a5733610e0052610125565b63e2ad025a8118610198576084358060a01c615caf57610e00525b600054615caf576001600055336109a052346109c052608060046109e0376001610a6052610e0051610a80526000610aa0526004610e20526000610e4052610e20805160200180610ac0828460045afa90505050610184610e60614aa0565b610e6051610e80526020610e806000600055f35b631d0dadb78118610275576084358060011c615caf57610e005260a4358060a01c615caf57610e205260c4358060a01c615caf57610e405260e4356004016004813511615caf578080356020018082610e6037505050600054615caf5760016000556004610ee0526000610f0052610ee060200151610e805114615caf57610e20516109a052346109c052608060046109e037610e0051610a6052610e4051610a805233610aa052610e60805160200180610ac0828460045afa90505050610261610ea0614aa0565b610ea051610ec0526020610ec06000600055f35b630b4c7e4d81186102905760006109a052336109c0526102de565b63ee22be2381186102b4576064358060011c615caf576109a052336109c0526102de565b637328333b8118610c19576064358060011c615caf576109a0526084358060a01c615caf576109c0525b600054615caf576001600055602054615caf5760006004351161030657600060243511610309565b60015b15615caf57610319610a20613ac4565b610a2080516109e0528060200151610a00525060803803602081608039608051610a2052602081602001608039608051610a405250601754610a6052601854610a805260e036610aa037610a6051610b8052610a8051610ba052610bc060006002818352015b610a60610bc0516002811015615caf5760200201516020610bc05102600401358181830110615caf5780820190509050610be052610be051610a60610bc0516002811015615caf576020020152610be0516001610bc0516002811015615caf570260170155815160010180835281141561037f575050610a6051610ae052610a8051610b0052600154602060403803602001608039608051808202821582848304141715615caf5790509050610bc052610a6051602060403803608039608051808202821582848304141715615caf5790509050610a6052610a8051610bc051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610a8052610b8051602060403803608039608051808202821582848304141715615caf5790509050610b8052610ba051610bc051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610ba0526109a0516104ed5734615caf575b610be060006002818352015b6109a05161050857600061050e565b610be051155b15610525576020610be05102600401353418615caf575b60006020610be0510260040135111561065c57610a20610be0516002811015615caf576020020151610c00526109a05115610567576000610be051141561056a565b60015b1561060e576323b872dd610c205233610c405230610c60526020610be0510260040135610c80526020610c206064610c3c6000610c00515af16105b2573d600060003e3d6000fd5b601f3d1115615caf57610c205115615caf57610be05161060e57632e1a7d4d610c20526020610be0510260040135610c4052610c00513b15615caf57600060006024610c3c6000610c00515af161060e573d600060003e3d6000fd5b610a60610be0516002811015615caf576020020151610b80610be0516002811015615caf576020020151808210615caf5780820390509050610aa0610be0516002811015615caf5760200201525b81516001018083528114156104f9575050600854610be0526000610be0511161068b57601954610b60526106ce565b6109e05161020052610a005161022052610b805161024052610ba051610260526106b6610c006128bd565b610c0051610b6052610be05142106106ce5760016008555b6109e05161020052610a005161022052610a605161024052610a8051610260526106f9610c206128bd565b610c2051610c00526318160ddd610c40526020610c406004610c5c602060a038036080396080515afa610731573d600060003e3d6000fd5b601f3d1115615caf57610c4051610c20526000610b60511161076d57610c005161020052610760610c40613d82565b610c4051610b20526107b1565b610c2051610c0051808202821582848304141715615caf5790509050610b6051808015615caf57820490509050610c2051808210615caf5780820390509050610b20525b6000610b20511115615caf576000610b60511161083b57610c0051601955670de0b6b3a7640000601e55670de0b6b3a7640000601c556340c10f19610c40526109c051610c6052610b2051610c80526020610c406044610c5c6000602060a038036080396080515af1610829573d600060003e3d6000fd5b601f3d1115615caf57610c4050610b38565b610aa05161016052610ac05161018052610a60516101a052610a80516101c052610866610c406154f4565b610c4051610b2051808202821582848304141715615caf57905090506402540be4008082049050905060018181830110615caf5780820190509050610b4052610b208051610b4051808210615caf5780820390509050815250610c208051610b20518181830110615caf57808201905090508152506340c10f19610c40526109c051610c6052610b2051610c80526020610c406044610c5c6000602060a038036080396080515af161091d573d600060003e3d6000fd5b601f3d1115615caf57610c40506000610c4052620186a0610b20511115610b00576004351561094f5760243515610952565b60015b15610b0057606036610c6037600435156109a657610b0051602060403803602001608039608051808202821582848304141715615caf5790509050610c6052602060403803608039608051610c80526109e8565b610ae051602060403803608039608051808202821582848304141715615caf5790509050610c6052602060403803602001608039608051610c80526001610ca0525b610c6051610b2051808202821582848304141715615caf5790509050610c2051808015615caf57820490509050610c6052610c6051670de0b6b3a7640000808202821582848304141715615caf57905090506020610ca0510260040135610c8051808202821582848304141715615caf5790509050610b2051610ae0610ca0516002811015615caf576020020151808202821582848304141715615caf5790509050610c8051808202821582848304141715615caf5790509050610c2051808015615caf57820490509050808210615caf5780820390509050808015615caf57820490509050610c4052610ca051610b00576ec097ce7bc90715b34b9f1000000000610c4051808015615caf57820490509050610c40525b6109e0516106a052610a00516106c052610a60516106e052610a805161070052610c405161072052610c005161074052610b38614292565b604435610b20511015610bbc576008610c40527f536c697070616765000000000000000000000000000000000000000000000000610c6052610c4050610c405180610c6001818260206001820306601f82010390500336823750506308c379a0610c00526020610c2052610c405160206001820306601f8201039050604401610c1cfd5b6109c0517f540ab385f9b5d450a27404172caade516b3ba3f4be88239ac56a2ad1de2a1f5a600435610c4052602435610c6052610b4051610c8052610c2051610ca0526080610c40a2610b2051610c40526020610c406000600055f35b63fc0c546a8118610c3e5734615caf57602060a0380360803960805160e052602060e0f35b63c66106578118610c8d5734615caf576080380360208160803960805160e052602081602001608039608051610100525060e06004356002811015615caf576020020151610120526020610120f35b63f446c1d08118610cb75734615caf57610ca86101c0613ac4565b6101c051610200526020610200f35b63b13739298118610ce45734615caf57610cd26101c0613ac4565b6101c060200151610200526020610200f35b63ddca3f438118610d3b5734615caf57610cff610160613a4a565b61016080516101c05280602001516101e052506101c05160e0526101e05161010052610d2c6101a0613c37565b6101a051610200526020610200f35b63bb7b8b808118610dd35734615caf57670de0b6b3a764000060195461020052610d66610280613d82565b61028051808202821582848304141715615caf57905090506318160ddd6102a05260206102a060046102bc602060a038036080396080515afa610dae573d600060003e3d6000fd5b601f3d1115615caf576102a051808015615caf578204905090506102e05260206102e0f35b6386fc88d38118610dfd5734615caf57610dee61030061418c565b61030051610320526020610320f35b63556d6e9f81186110dd5734615caf5760243560043514615caf5760026004351015615caf5760026024351015615caf57600154602060403803602001608039608051808202821582848304141715615caf57905090506104a0526017546104c0526018546104e052610e71610540613ac4565b610540805161050052806020015161052052506019546105405260006008541115610ef857610500516105c052610520516105e052610eb1610560613a4a565b610560805161060052806020015161062052506105c051610200526105e0516102205261060051610240526106205161026052610eef6105a06128bd565b6105a051610540525b6104c06004356002811015615caf576020020180516044358181830110615caf57808201905090508152506104c051602060403803608039608051808202821582848304141715615caf57905090506104c0526104e0516104a051808202821582848304141715615caf5790509050670de0b6b3a7640000808204905090506104e0526105005160e05261052051610100526104c051610120526104e05161014052610540516101605260243561018052610fb461058061304c565b61058051610560526104c06024356002811015615caf57602002015161056051808210615caf57808203905090506001808210615caf578082039050905061058052610560516104c06024356002811015615caf57602002015260006024351161103e576105808051602060403803608039608051808015615caf57820490509050815250611075565b61058051670de0b6b3a7640000808202821582848304141715615caf57905090506104a051808015615caf57820490509050610580525b61058080516104c05160e0526104e051610100526110946105a0613c37565b6105a05161058051808202821582848304141715615caf57905090506402540be40080820490509050808210615caf5780820390509050815250610580516105a05260206105a0f35b635b36389c81186110f757600060e0523361010052611143565b63269b5581811861111a576064358060011c615caf5760e0523361010052611143565b631808e84a81186114af576064358060011c615caf5760e0526084358060a01c615caf57610100525b34615caf57600054615caf576001600055608038036020816080396080516101205260208160200160803960805161014052506318160ddd610180526020610180600461019c602060a038036080396080515afa6111a6573d600060003e3d6000fd5b601f3d1115615caf5761018051610160526379cc679061018052336101a0526004356101c0526020610180604461019c6000602060a038036080396080515af16111f5573d600060003e3d6000fd5b601f3d1115615caf5761018050601754610180526018546101a0526004356001808210615caf57808203905090506101c0526101e060006002818352015b6101806101e0516002811015615caf5760200201516101c051808202821582848304141715615caf579050905061016051808015615caf578204905090506102005260206101e05102602401356102005110615caf576101806101e0516002811015615caf57602002015161020051808210615caf578082039050905060016101e0516002811015615caf570260170155610200516101806101e0516002811015615caf57602002015260e0516112eb5760006112f1565b6101e051155b6113cf576101206101e0516002811015615caf576020020151610220526101e05161136d5763d0e30db0610240526101206101e0516002811015615caf5760200201513b15615caf5760006000600461025c610200516101206101e0516002811015615caf5760200201515af161136d573d600060003e3d6000fd5b63a9059cbb61024052610100516102605261020051610280526020610240604461025c60006101206101e0516002811015615caf5760200201515af16113b8573d600060003e3d6000fd5b601f3d1115615caf576102405115615caf576113fd565b60006102205261022050600060006102205161024061020051610100515af16113fd573d600060003e3d6000fd5b81516001018083528114156112335750506019546101e0526101e0516101e0516101c051808202821582848304141715615caf579050905061016051808015615caf57820490509050808210615caf5780820390509050601955337fdd3c0336a16f1b64f172b7bb0dad5b2b3c7c76f91e8c4aafd6aae60dce80015361018051610200526101a0516102205261016051600435808210615caf5780820390509050610240526060610200a26000600055005b638d8ea727811861173b5734615caf576318160ddd6104c05260206104c060046104dc602060a038036080396080515afa6114ef573d600060003e3d6000fd5b601f3d1115615caf576104c0516104a052600154602060403803602001608039608051808202821582848304141715615caf57905090506104c052611535610520613ac4565b61052080516104e05280602001516105005250611553610560613a4a565b61056080516105205280602001516105405250600435602060403803608039608051808202821582848304141715615caf5790509050610560526024356104c051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610580526019546105a05260006008541115611602576104e051610200526105005161022052610520516102405261054051610260526115f96105c06128bd565b6105c0516105a0525b6105208051610560518181830110615caf57808201905090508152506105408051610580518181830110615caf57808201905090508152506104e051610200526105005161022052610520516102405261054051610260526116656105e06128bd565b6105e0516105c0526104a0516105c051808202821582848304141715615caf57905090506105a051808015615caf578204905090506104a051808210615caf57808203905090506105e0526105e0805161056051610160526105805161018052610520516101a052610540516101c0526116e06106006154f4565b610600516105e051808202821582848304141715615caf57905090506402540be4008082049050905060018181830110615caf5780820190509050808210615caf57808203905090508152506105e051610600526020610600f35b634fb08c5e81186117c75734615caf57611756610740613ac4565b61074080516108205280602001516108405250604060046108603760016108a05260006108c052610820516104a052610840516104c052610860516104e05261088051610500526108a051610520526108c051610540526117b861078061567d565b610780516108e05260206108e0f35b63f1dc3cc981186117e25760006109a052336109c052611830565b638f15b6b58118611806576064358060011c615caf576109a052336109c052611830565b6307329bcd8118611b71576064358060011c615caf576109a0526084358060a01c615caf576109c0525b34615caf57600054615caf576001600055602054615caf57611853610a20613ac4565b610a2080516109e0528060200151610a00525060a036610a2037600854610ac0526109e0516104a052610a00516104c052604060046104e0376000610ac05111610520526001610540526118a8610ae061567d565b610ae08051610a20526020810151610a60526040810151610a4052606081018051610a80528060200151610aa0525050604435610a2051101561195c576008610ae0527f536c697070616765000000000000000000000000000000000000000000000000610b0052610ae050610ae05180610b0001818260206001820306601f82010390500336823750506308c379a0610aa0526020610ac052610ae05160206001820306601f8201039050604401610abcfd5b610ac051421061196c5760016008555b60016024356002811015615caf57026017018054610a2051808210615caf57808203905090508155506379cc6790610ae05233610b0052600435610b20526020610ae06044610afc6000602060a038036080396080515af16119d3573d600060003e3d6000fd5b601f3d1115615caf57610ae05060803803602081608039608051610ae052602081602001608039608051610b0052506109a051611a11576000611a16565b602435155b611abf57610ae06024356002811015615caf576020020151610b2052602435611a6e5763d0e30db0610b4052610b20513b15615caf57600060006004610b5c610a2051610b20515af1611a6e573d600060003e3d6000fd5b63a9059cbb610b40526109c051610b6052610a2051610b80526020610b406044610b5c6000610b20515af1611aa8573d600060003e3d6000fd5b601f3d1115615caf57610b405115615caf57611aed565b6000610b2052610b205060006000610b2051610b40610a20516109c0515af1611aed573d600060003e3d6000fd5b6109e0516106a052610a00516106c052610a80516106e052610aa05161070052610a605161072052610a405161074052611b25614292565b337f5ad056f2e28a8cec232015406b843668c1e36cda598127ec3b8c59b8c72773a060406004610b2037610a2051610b60526060610b20a2610a2051610b20526020610b206000600055f35b63c93f49e88118611b9c5734615caf57600054615caf576001600055611b95613e07565b6000600055005b635e2480728118611d985734615caf57601a543318615caf576007546201517f8181830110615caf5780820190509050421115615caf57426201517f8181830110615caf57808201905090506044351115615caf57611bfc610200613ac4565b61020080516101c05280602001516101e052506101c05160801b610200526101e051610200511761020052610f9f6004351115615caf5763ee6b28016004351015615caf576402540be3ff6024351115615caf5766470de4df8200016024351015615caf57670de0b6b3a7640000600435808202821582848304141715615caf57905090506101c051808015615caf5782049050905061022052678ac7230489e80001610220511015615caf5767016345785d89ffff610220511115615caf57670de0b6b3a7640000602435808202821582848304141715615caf57905090506101e051808015615caf5782049050905061022052678ac7230489e80001610220511015615caf5767016345785d89ffff610220511115615caf57610200516005554260075560043560801b61024052602435610240511761024052604435600855610240516006557fe35f0559b0642164e286b30df2077ec3a05426617a25db7578fd20ba39a6cd056101c05161026052600435610280526101e0516102a0526024356102c052426102e0526044356103005260c0610260a1005b63244c7c2e8118611e3b5734615caf57601a543318615caf57611dbc610200613ac4565b61020080516101c05280602001516101e052506101c05160801b610200526101e051610200511761020052610200516005556102005160065542600755426008557f5f0e7fba3d100c9e19446e1c92fe436f0a9a22fe99669360e4fdd6d3de2fc2846101c051610220526101e0516102405242610260526060610220a1005b63a43c335181186120015734615caf57601a543318615caf57602354615caf5760e0600460e0376402540be4016101005110611e7d5760125461010052611e8c565b6207a11f610100511115615caf575b6402540be40060e0511115611ea25760115460e0525b6101005160e05111615caf576402540be400610120511115611ec657601354610120525b670de0b6b3a76400006101405110611ee457600b5461014052611ef1565b6000610140511115615caf575b670de0b6b3a7640000610160511115611f0c57600954610160525b670de0b6b3a7640000610180511115611f2757600d54610180525b62093a806101a05110611f4057600f546101a052611f4d565b60006101a0511115615caf575b426203f4808181830110615caf57808201905090506101c0526101c0516023556101205160165560e0516014556101005160155561014051600c5561016051600a5561018051600e556101a0516010556101c0517f913fde9a37e1f8ab67876a4d0ce80790d764fcfc5692f4529526df9c6bdde553610120516101e05260e0516102005261010051610220526101405161024052610160516102605261018051610280526101a0516102a05260e06101e0a2005b632a7dd7cd811861211b5734615caf57600054615caf576001600055601a543318615caf576023544210615caf57600060235414615caf5760006023556016546106a0526106a0516013541461206157612059613e07565b6106a0516013555b6014546106c0526106c0516011556015546106e0526106e051601255600c546107005261070051600b55600a546107205261072051600955600e546107405261074051600d556010546107605261076051600f557f1c65bbdc939f346e5d6f0bde1f072819947438d4fc7b182cc59c2f6dc55040876106a051610780526106c0516107a0526106e0516107c052610700516107e05261072051610800526107405161082052610760516108405260e0610780a16000600055005b63226840fb811861213b5734615caf57601a543318615caf576000602355005b636b441a4081186121bf576004358060a01c615caf5760e05234615caf57601a543318615caf57602254615caf57426203f4808181830110615caf5780820190509050610100526101005160225560e051601b5560e051610100517f181aa3aa17d4cbf99265dd4443eba009433d3cde79d60164fde1d1a192beb9356000610120a3005b636a1c05ae81186122285734615caf57601a543318615caf576022544210615caf57600060225414615caf576000602255601b5460e05260e051601a5560e0517f71614071b88dee5e0b2ae578a9dd7b2ebbe9ae832ba419dc0242cd065a290b6c6000610100a2005b6386fbf19381186122485734615caf57601a543318615caf576000602255005b63e369885381186122725734615caf57601a543318615caf57426021541115615caf576001602055005b633046f97281186122925734615caf57601a543318615caf576000602055005b637242e52481186122c1576004358060a01c615caf5760e05234615caf57601a543318615caf5760e051602455005b6354f0f7d581186123425734615caf576002601e54808202821582848304141715615caf57905090506122f561030061418c565b61030051610340526103405160e05261230f610320615b62565b61032051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610360526020610360f35b63b9e8c9fd811861235e5734615caf5760015460e052602060e0f35b63c146bf94811861237a5734615caf5760035460e052602060e0f35b636112c74781186123965734615caf5760045460e052602060e0f35b63204fe3d581186123b25734615caf5760055460e052602060e0f35b63f30cfad581186123ce5734615caf5760065460e052602060e0f35b63e89876ff81186123ea5734615caf5760075460e052602060e0f35b63f9ed959781186124065734615caf5760085460e052602060e0f35b6349fe9e7781186124225734615caf5760095460e052602060e0f35b63727ced57811861243e5734615caf57600a5460e052602060e0f35b6372d4f0e2811861245a5734615caf57600b5460e052602060e0f35b63d7c3dcbe81186124765734615caf57600c5460e052602060e0f35b63083812e581186124925734615caf57600d5460e052602060e0f35b634ea12c7d81186124ae5734615caf57600e5460e052602060e0f35b63662b627481186124ca5734615caf57600f5460e052602060e0f35b630c5e23d481186124e65734615caf5760105460e052602060e0f35b6392526c0c81186125025734615caf5760115460e052602060e0f35b63ee8de675811861251e5734615caf5760125460e052602060e0f35b63fee3f7f9811861253a5734615caf5760135460e052602060e0f35b637cf9aedc81186125565734615caf5760145460e052602060e0f35b637d1b060c81186125725734615caf5760155460e052602060e0f35b63e3824462811861258e5734615caf5760165460e052602060e0f35b634903b0d181186125ba5734615caf5760016004356002811015615caf57026017015460e052602060e0f35b630f529ba281186125d65734615caf5760195460e052602060e0f35b638da5cb5b81186125f25734615caf57601a5460e052602060e0f35b631ec0cdc1811861260e5734615caf57601b5460e052602060e0f35b637ba1a74d811861262a5734615caf57601c5460e052602060e0f35b630b7b594b81186126465734615caf57601d5460e052602060e0f35b630c46b72a81186126625734615caf57601e5460e052602060e0f35b639c868ac0811861267e5734615caf5760205460e052602060e0f35b632a426896811861269a5734615caf5760215460e052602060e0f35b63e0a0b58681186126b65734615caf5760225460e052602060e0f35b63405e28f881186126d25734615caf5760235460e052602060e0f35b636e42e4d281186126ee5734615caf5760245460e052602060e0f35b505b005b60e0516101405261010051610160526101205161271057600061271a565b6101605161014051105b1561272f57610100516101405260e051610160525b610140516101805260006101a0526101c0600060ff818352015b610180516101e052610180516101405161016051808202821582848304141715615caf579050905061018051808015615caf578204905090508181830110615caf5780820190509050600280820490509050610180526101e05161018051116127cb576101e05161018051808210615caf57808203905090506101a0526127e6565b610180516101e051808210615caf57808203905090506101a0525b60016101a051111561281d57610180516101a051670de0b6b3a7640000808202821582848304141715615caf579050905010612820565b60015b15612833575050610180518152506128bb565b815160010180835281141561274957505060106101c0527f446964206e6f7420636f6e7665726765000000000000000000000000000000006101e0526101c0506101c051806101e001818260206001820306601f82010390500336823750506308c379a06101805260206101a0526101c05160206001820306601f820103905060440161019cfd5b565b610f9f61020051116128d05760006128db565b63ee6b280161020051105b15615caf576402540be3ff61022051116128f6576000612904565b66470de4df82000161022051105b15615caf576102405161028052610260516102a0526102a051610280511015612938576102605161028052610240516102a0525b633b9ac9ff610280511161294d576000612962565b6d314dc6448d9338c15b0a0000000161028051105b15615caf57655af3107a3fff6102a051670de0b6b3a7640000808202821582848304141715615caf579050905061028051808015615caf578204905090501115615caf5760026102805160e0526102a051610100526000610120526129c86102e06126f2565b6102e051808202821582848304141715615caf57905090506102c052610280516102a0518181830110615caf57808201905090506102e052610300600060ff818352015b6102c05161032052673782dace9d90000061028051808202821582848304141715615caf57905090506102c051808015615caf578204905090506102a051808202821582848304141715615caf57905090506102c051808015615caf578204905090506103405261022051670de0b6b3a76400008181830110615caf578082019050905061036052610340516103605111612ad2576103405161036051808210615caf578082039050905060018181830110615caf578082019050905061036052612aff565b6103605161034051808210615caf578082039050905060018181830110615caf5780820190509050610360525b670de0b6b3a76400006102c051808202821582848304141715615caf579050905061022051808015615caf5782049050905061036051808202821582848304141715615caf579050905061022051808015615caf5782049050905061036051808202821582848304141715615caf5790509050612710808202821582848304141715615caf579050905061020051808015615caf5782049050905061038052673782dace9d90000061034051808202821582848304141715615caf579050905061036051808015615caf578204905090506103a0526102e0516102e0516103a051808202821582848304141715615caf5790509050670de0b6b3a7640000808204905090508181830110615caf5780820190509050610380516002808202821582848304141715615caf579050905061034051808015615caf578204905090508181830110615caf57808201905090506103a0516102c051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050808210615caf57808203905090506103c0526102c0516103c0516102e0518181830110615caf5780820190509050808202821582848304141715615caf57905090506103c051808015615caf578204905090506103e0526102c0516102c051808202821582848304141715615caf57905090506103c051808015615caf578204905090506104005261034051670de0b6b3a764000011612dad5761040080516102c051610380516103c051808015615caf57820490509050808202821582848304141715615caf5790509050670de0b6b3a76400008082049050905061034051670de0b6b3a7640000808210615caf5780820390509050808202821582848304141715615caf579050905061034051808015615caf57820490509050808210615caf5780820390509050815250612e43565b61040080516102c051610380516103c051808015615caf57820490509050808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050670de0b6b3a764000061034051808210615caf5780820390509050808202821582848304141715615caf579050905061034051808015615caf578204905090508181830110615caf57808201905090508152505b610400516103e05111612e7857610400516103e051808210615caf57808203905090506002808204905090506102c052612e93565b6103e05161040051808210615caf57808203905090506102c0525b600061042052610320516102c05111612ec557610320516102c051808210615caf578082039050905061042052612ee0565b6102c05161032051808210615caf5780820390509050610420525b662386f26fc100006102c051808210612ef95781612efb565b805b9050905061042051655af3107a4000808202821582848304141715615caf57905090501015612fc25761046060006002818352015b6020610460510261028001516104405261044051670de0b6b3a7640000808202821582848304141715615caf57905090506102c051808015615caf5782049050905061048052662386f26fc0ffff6104805111612f8e576000612f9e565b68056bc75e2d6310000161048051105b15615caf578151600101808352811415612f3057505050506102c05181525061304a565b8151600101808352811415612a0c5750506010610300527f446964206e6f7420636f6e7665726765000000000000000000000000000000006103205261030050610300518061032001818260206001820306601f82010390500336823750506308c379a06102c05260206102e0526103005160206001820306601f82010390506044016102dcfd5b565b610f9f60e0511161305e576000613068565b63ee6b280160e051105b15615caf576402540be3ff6101005111613083576000613091565b66470de4df82000161010051105b15615caf5767016345785d89ffff61016051116130af5760006130c4565b6d314dc6448d9338c15b0a0000000161016051105b15615caf57610120600161018051808210615caf57808203905090506002811015615caf5760200201516101a052700100000000000000000000000000000000610160511015615caf576002610160510a6101a0516004808202821582848304141715615caf5790509050808015615caf578204905090506101c052671bc16d674ec800006101a051808202821582848304141715615caf579050905061016051808015615caf578204905090506101e05266470de4df81ffff6101e0511161318e57600061319e565b680ad78ebc5ac62000016101e051105b15615caf576101a051655af3107a40008082049050905061016051655af3107a4000808204905090508082106131d457816131d6565b805b9050905060648082106131e957816131eb565b805b9050905061020052610220600060ff818352015b6101c051610240526101e0516101c051808202821582848304141715615caf57905090506002808202821582848304141715615caf579050905061016051808015615caf57820490509050610260526101a0516101c0518181830110615caf57808201905090506102805261010051670de0b6b3a76400008181830110615caf57808201905090506102a052610260516102a051116132c957610260516102a051808210615caf578082039050905060018181830110615caf57808201905090506102a0526132f6565b6102a05161026051808210615caf578082039050905060018181830110615caf57808201905090506102a0525b670de0b6b3a764000061016051808202821582848304141715615caf579050905061010051808015615caf578204905090506102a051808202821582848304141715615caf579050905061010051808015615caf578204905090506102a051808202821582848304141715615caf5790509050612710808202821582848304141715615caf579050905060e051808015615caf578204905090506102c052670de0b6b3a7640000671bc16d674ec8000061026051808202821582848304141715615caf57905090506102a051808015615caf578204905090508181830110615caf57808201905090506102e052670de0b6b3a76400006101c051808202821582848304141715615caf5790509050610280516102e051808202821582848304141715615caf57905090508181830110615caf57808201905090506102c0518181830110615caf578082019050905061030052610160516102e051808202821582848304141715615caf57905090506103205261032051610300511061349457610300805161032051808210615caf57808203905090508152506134aa565b610240516002808204905090506101c0526136e1565b610300516101c051808015615caf57820490509050610340526102c05161034051808015615caf578204905090506103605261030051670de0b6b3a764000061016051808202821582848304141715615caf57905090508181830110615caf578082019050905061034051808015615caf5782049050905061036051670de0b6b3a7640000808202821582848304141715615caf579050905061026051808015615caf578204905090508181830110615caf5780820190509050610380526103608051670de0b6b3a764000061028051808202821582848304141715615caf579050905061034051808015615caf578204905090508181830110615caf57808201905090508152506103605161038051106135de576103805161036051808210615caf57808203905090506101c0526135f0565b610240516002808204905090506101c0525b60006103a052610240516101c0511161362257610240516101c051808210615caf57808203905090506103a05261363d565b6101c05161024051808210615caf57808203905090506103a0525b610200516101c051655af3107a4000808204905090508082106136605781613662565b805b905090506103a05110156136e1576101c051670de0b6b3a7640000808202821582848304141715615caf579050905061016051808015615caf578204905090506103c052662386f26fc0ffff6103c051116136be5760006136ce565b68056bc75e2d631000016103c051105b15615caf5750506101c051815250613769565b81516001018083528114156131ff5750506010610220527f446964206e6f7420636f6e7665726765000000000000000000000000000000006102405261022050610220518061024001818260206001820306601f82010390500336823750506308c379a06101e0526020610200526102205160206001820306601f82010390506044016101fcfd5b565b60e051670de0b6b3a7640000808204905090506101005260e05161010051670de0b6b3a7640000808202821582848304141715615caf5790509050808210615caf578082039050905061012052603b6101005111156137ce576000815250613a48565b670de0b6b3a7640000610100610100511015615caf576101005160020a808015615caf5782049050905061014052610120516138105761014051815250613a48565b670de0b6b3a7640000610160526706f05b59d3b2000061018052670de0b6b3a76400006101a05260006101c0526101e0600160ff818352015b6101e051670de0b6b3a7640000808202821582848304141715615caf57905090506102005261020051670de0b6b3a7640000808210615caf5780820390509050610220526102205161012051116138b957610220805161012051808210615caf57808203905090508152506138dd565b6101205161022051808210615caf5780820390509050610220526101c051156101c0525b610160516102205161018051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050808202821582848304141715615caf579050905061020051808015615caf57820490509050610160526101c05161395f576101a08051610160518181830110615caf578082019050905081525061397a565b6101a0805161016051808210615caf57808203905090508152505b6402540be4006101605110156139c0575050610140516101a051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050815250613a48565b815160010180835281141561384957505060106101e0527f446964206e6f7420636f6e766572676500000000000000000000000000000000610200526101e0506101e0518061020001818260206001820306601f82010390500336823750506308c379a06101a05260206101c0526101e05160206001820306601f82010390506044016101bcfd5b565b601754602060403803608039608051808202821582848304141715615caf57905090508152601854602060403803602001608039608051808202821582848304141715615caf5790509050600154808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050816020015250565b60085460e052600654610100526fffffffffffffffffffffffffffffffff6101005116610120526101005160801c6101405260e051421015613c2557600554610160526007546101805260e0805161018051808210615caf57808203905090508152504261018051808210615caf57808203905090506101805260e05161018051808210615caf57808203905090506101a0526101605160801c6101a051808202821582848304141715615caf57905090506101405161018051808202821582848304141715615caf57905090508181830110615caf578082019050905060e051808015615caf57820490509050610140526fffffffffffffffffffffffffffffffff61016051166101a051808202821582848304141715615caf57905090506101205161018051808202821582848304141715615caf57905090508181830110615caf578082019050905060e051808015615caf57820490509050610120525b61014051815261012051816020015250565b600b546101205260e051610100518181830110615caf57808201905090506101405261012051670de0b6b3a7640000808202821582848304141715615caf579050905061012051670de0b6b3a76400008181830110615caf5780820190509050673782dace9d90000060e051808202821582848304141715615caf579050905061014051808015615caf5782049050905061010051808202821582848304141715615caf579050905061014051808015615caf57820490509050808210615caf5780820390509050808015615caf578204905090506101405260115461014051808202821582848304141715615caf5790509050601254670de0b6b3a764000061014051808210615caf5780820390509050808202821582848304141715615caf57905090508181830110615caf5780820190509050670de0b6b3a764000080820490509050815250565b610200516002808204905090506102205261020051670de0b6b3a7640000808202821582848304141715615caf57905090506001546002808202821582848304141715615caf5790509050808015615caf57820490509050610240526102205160e0526102405161010052600161012052613dfe6102606126f2565b61026051815250565b613e126104e0613ac4565b6104e080516104a05280602001516104c05250601c546104e052601d54610500526080380360208160803960805161052052602081602001608039608051610540525061056060006002818352015b6105605115613ece576370a0823161058052306105a0526020610580602461059c610520610560516002811015615caf5760200201515afa613ea8573d600060003e3d6000fd5b601f3d1115615caf57610580516001610560516002811015615caf570260170155613ee4565b476001610560516002811015615caf5702601701555b8151600101808352811415613e61575050601e5461056052610500516104e0511115614083576104e05161050051808210615caf5780820390509050601354808202821582848304141715615caf57905090506404a817c80080820490509050610580526000610580511115614083576024546105a05260006105a051146140835761056051670de0b6b3a7640000808202821582848304141715615caf57905090506105605161058051808210615caf5780820390509050808015615caf57820490509050670de0b6b3a7640000808210615caf57808203905090506105c052636962f845610600526105a051610620526105c051610640526020610600604461061c6000602060a038036080396080515af1614007573d600060003e3d6000fd5b601f3d1115615caf57610600516105e0526104e08051610580516002808202821582848304141715615caf5790509050808210615caf57808203905090508152506104e051601c556105a0517f6059a38198b1dc42b3791087d1ff0fbd72b3179553c25f678cd246f52ffaaf596105e051610600526020610600a25b6318160ddd6105a05260206105a060046105bc602060a038036080396080515afa6140b3573d600060003e3d6000fd5b601f3d1115615caf576105a051610580526104a051610620526104c051610640526140df6105c0613a4a565b6105c080516106605280602001516106805250610620516102005261064051610220526106605161024052610680516102605261411d6106006128bd565b610600516105a0526105a051601955670de0b6b3a76400006105a051610200526141486105c0613d82565b6105c051808202821582848304141715615caf579050905061058051808015615caf57820490509050601e55610500516104e051111561418a576104e051601d555b565b60025461024052600454610260524261026051106141b4576102405181525061429056614290565b600f54610280526003546102a0524261026051808210615caf5780820390509050670de0b6b3a7640000808202821582848304141715615caf579050905061028051808015615caf5782049050905060e0526142116102e061376b565b6102e0516102c0526102a051670de0b6b3a76400006102c051808210615caf5780820390509050808202821582848304141715615caf5790509050610240516102c051808202821582848304141715615caf57905090508181830110615caf5780820190509050670de0b6b3a764000080820490509050815250614290565b565b60025461076052600354610780526001546107a0526004546107c05260006107e052426107c051101561439c57600f5461080052426107c051808210615caf5780820390509050670de0b6b3a7640000808202821582848304141715615caf579050905061080051808015615caf5782049050905060e05261431561084061376b565b610840516108205261078051670de0b6b3a764000061082051808210615caf5780820390509050808202821582848304141715615caf57905090506107605161082051808202821582848304141715615caf57905090508181830110615caf5780820190509050670de0b6b3a7640000808204905090506107605261076051600255426004555b6107405161080052610740516143e0576106a051610200526106c051610220526106e0516102405261070051610260526143d76108206128bd565b61082051610800525b600061072051116144aa576106e05161082052610700516108405261082051620f424080820490509050610860526108208051610860518181830110615caf57808201905090508152506107a05161086051808202821582848304141715615caf5790509050610700516106a05160e0526106c0516101005261082051610120526108405161014052610800516101605260016101805261448261088061304c565b61088051808210615caf5780820390509050808015615caf57820490509050610780526144b3565b61072051610780525b610780516003556318160ddd610840526020610840600461085c602060a038036080396080515afa6144ea573d600060003e3d6000fd5b601f3d1115615caf576108405161082052601c5461084052601e5461086052610800516002808204905090506108805261080051670de0b6b3a7640000808202821582848304141715615caf579050905060026107a051808202821582848304141715615caf5790509050808015615caf578204905090506108a052670de0b6b3a76400006108c052670de0b6b3a76400006108e05260006108605111156146c9576108805160e0526108a051610100526001610120526145ac6109206126f2565b6109205161090052670de0b6b3a764000061090051808202821582848304141715615caf579050905061082051808015615caf578204905090506108e052610840516108e051808202821582848304141715615caf579050905061086051808015615caf578204905090506108c05260085461092052610860516108e0511061463657600061463c565b61092051155b156146b8576004610940527f4c6f7373000000000000000000000000000000000000000000000000000000006109605261094050610940518061096001818260206001820306601f82010390500336823750506308c379a0610900526020610920526109405160206001820306601f820103905060440161091cfd5b600161092051186146c95760006008555b6108c051601c5561076051670de0b6b3a7640000808202821582848304141715615caf57905090506107a051808015615caf5782049050905061090052670de0b6b3a7640000610900511161473c57670de0b6b3a764000061090051808210615caf57808203905090506109005261475c565b6109008051670de0b6b3a7640000808210615caf57808203905090508152505b600d5461090051600a80820490509050808210614779578161477b565b805b9050905061092052601f5461094052610940511561479a576000614820565b6108c0516002600954808202821582848304141715615caf57905090508181830110615caf57808201905090506108e0516002808202821582848304141715615caf5790509050670de0b6b3a7640000808210615caf578082039050905011614804576000614820565b610920516109005111614818576000614820565b600061086051115b15614831576001610940526001601f555b6109405115614a7a5761092051610900511161484e576000614856565b600061086051115b15614a7a576107a0516109005161092051808210615caf5780820390509050808202821582848304141715615caf57905090506109205161076051808202821582848304141715615caf57905090508181830110615caf578082019050905061090051808015615caf578204905090506107e0526106e05161088052610700516107e051808202821582848304141715615caf57905090506107a051808015615caf578204905090506108a0526106a051610200526106c0516102205261088051610240526108a0516102605261492e6109806128bd565b6109805161096052610960516002808204905090506108805261096051670de0b6b3a7640000808202821582848304141715615caf579050905060026107e051808202821582848304141715615caf5790509050808015615caf578204905090506108a052670de0b6b3a76400006108805160e0526108a051610100526001610120526149bc6109806126f2565b61098051808202821582848304141715615caf579050905061082051808015615caf5782049050905061086052670de0b6b3a76400006108605111614a02576000614a39565b6108c051600261086051808202821582848304141715615caf5790509050670de0b6b3a7640000808210615caf5780820390509050115b614a60576000601f55610800516019556108e051601e55614a9e613e0756614a9e56614a7a565b6107e0516001556109605160195561086051601e55614a9e565b610800516019556108e051601e556109405115614a9e576000601f55614a9e613e07565b565b602054615caf57610a00516109e05114615caf5760026109e0511015615caf576002610a00511015615caf576000610a20511115615caf57614ae3610b40613ac4565b610b408051610b00528060200151610b205250601754610b4052601854610b6052604036610b803760803803602081608039608051610bc052602081602001608039608051610be05250610b40610a00516002811015615caf576020020151610c0052610b406109e0516002811015615caf576020020151610c2052610c2051610a20518181830110615caf5780820190509050610b406109e0516002811015615caf576020020152610b406109e0516002811015615caf57602002015160016109e0516002811015615caf570260170155600154610c4052610b4051602060403803608039608051808202821582848304141715615caf5790509050610b4052610b6051610c4051808202821582848304141715615caf5790509050602060403803602001608039608051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610b6052602060403803608039608051610c6052602060403803602001608039608051610c805260016109e05118614c8957602060403803602001608039608051610c6052602060403803608039608051610c80525b600854610ca0526000610ca0511115614d8657610c208051610c6051808202821582848304141715615caf579050905081525060006109e0511115614cf957610c2051610c4051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610c20525b610b406109e0516002811015615caf576020020151610cc052610c2051610b406109e0516002811015615caf576020020152610b005161020052610b205161022052610b405161024052610b605161026052614d56610ce06128bd565b610ce051601955610cc051610b406109e0516002811015615caf576020020152610ca0514210614d865760016008555b610b40610a00516002811015615caf576020020151610b005160e052610b205161010052610b405161012052610b60516101405260195461016052610a005161018052614dd4610cc061304c565b610cc051808210615caf5780820390509050610ba052610b40610a00516002811015615caf57602002018051610ba051808210615caf5780820390509050815250610ba080516001808210615caf57808203905090508152506000610a00511115614e7057610ba051670de0b6b3a7640000808202821582848304141715615caf5790509050610c4051808015615caf57820490509050610ba0525b610ba08051610c8051808015615caf57820490509050815250610ba08051610b405160e052610b605161010052614ea8610cc0613c37565b610cc051610ba051808202821582848304141715615caf57905090506402540be40080820490509050808210615caf5780820390509050815250610a4051610ba0511015614f67576008610cc0527f536c697070616765000000000000000000000000000000000000000000000000610ce052610cc050610cc05180610ce001818260206001820306601f82010390500336823750506308c379a0610c80526020610ca052610cc05160206001820306601f8201039050604401610c9cfd5b610c008051610ba051808210615caf5780820390509050815250610c00516001610a00516002811015615caf570260170155610a6051614fa8576000614fae565b6109e051155b615200576109c051615caf576004610d00526000610d2052610d0060200151610ae0511861503d576323b872dd610d40526109a051610d605230610d8052610a2051610da0526020610d406064610d5c6000610bc06109e0516002811015615caf5760200201515af1615026573d600060003e3d6000fd5b601f3d1115615caf57610d405115615caf57615197565b610bc06109e0516002811015615caf576020020151610cc0526370a08231610d005230610d20526020610d006024610d1c610cc0515afa615083573d600060003e3d6000fd5b601f3d1115615caf57610d0051610ce0526000610ac0600480602084610d000101826020850160045afa5050805182019150506109a051602082610d00010152602081019050610a8051602082610d00010152602081019050610cc051602082610d00010152602081019050610a2051602082610d00010152602081019050610ba051602082610d0001015260208101905080610d0052610d00505060006000610d0051610d206000610aa0515af1615141573d600060003e3d6000fd5b610a20516370a08231610d005230610d20526020610d006024610d1c610cc0515afa615172573d600060003e3d6000fd5b601f3d1115615caf57610d0051610ce051808210615caf578082039050905018615caf575b6109e05161520e57632e1a7d4d610cc052610a2051610ce052610bc06109e0516002811015615caf5760200201513b15615caf57600060006024610cdc6000610bc06109e0516002811015615caf5760200201515af161520e573d600060003e3d6000fd61520e565b610a20516109c05118615caf575b610a605161521d576000615223565b610a0051155b6152e857610a00516152865763d0e30db0610cc052610bc0610a00516002811015615caf5760200201513b15615caf57600060006004610cdc610ba051610bc0610a00516002811015615caf5760200201515af1615286573d600060003e3d6000fd5b63a9059cbb610cc052610a8051610ce052610ba051610d00526020610cc06044610cdc6000610bc0610a00516002811015615caf5760200201515af16152d1573d600060003e3d6000fd5b601f3d1115615caf57610cc05115615caf57615316565b6000610cc052610cc05060006000610cc051610ce0610ba051610a80515af1615316573d600060003e3d6000fd5b610c008051610c8051808202821582848304141715615caf57905090508152506000610a0051111561537357610c0051610c4051808202821582848304141715615caf5790509050670de0b6b3a764000080820490509050610c00525b610c0051610b40610a00516002811015615caf576020020152620186a0610a2051116153a05760006153aa565b620186a0610ba051115b1561546a57610a2051610c6051808202821582848304141715615caf5790509050610cc052610ba051610c8051808202821582848304141715615caf5790509050610ce0526109e0511561543357610ce051670de0b6b3a7640000808202821582848304141715615caf5790509050610cc051808015615caf57820490509050610b805261546a565b610cc051670de0b6b3a7640000808202821582848304141715615caf5790509050610ce051808015615caf57820490509050610b80525b610b00516106a052610b20516106c052610b40516106e052610b605161070052610b8051610720526000610740526154a0614292565b6109a0517fb2e76ae99761dc136e598d4a629bb347eccb9532a5f8bbd72e18467c3c34cc986109e051610cc052610a2051610ce052610a0051610d0052610ba051610d20526080610cc0a2610ba051815250565b6101a05160e0526101c0516101005261550e610200613c37565b610200516002808202821582848304141715615caf57905090506004808204905090506101e05260006102005261024060006002818352015b602061024051026101600151610220526102008051610220518181830110615caf57808201905090508152508151600101808352811415615547575050610200516002808204905090506102205260006102405261028060006002818352015b602061028051026101600151610260526102205161026051116155f75761024080516102205161026051808210615caf57808203905090508181830110615caf5780820190509050815250615626565b61024080516102605161022051808210615caf57808203905090508181830110615caf57808201905090508152505b81516001018083528114156155a75750506101e05161024051808202821582848304141715615caf579050905061020051808015615caf57820490509050620186a08181830110615caf5780820190509050815250565b6318160ddd610580526020610580600461059c602060a038036080396080515afa6156ad573d600060003e3d6000fd5b601f3d1115615caf576105805161056052610560516104e05111615caf576002610500511015615caf57601754610580526018546105a05260006105c052600154602060403803602001608039608051808202821582848304141715615caf57905090506105e05261058051602060403803608039608051808202821582848304141715615caf5790509050610600526105a0516105e051808202821582848304141715615caf5790509050670de0b6b3a76400008082049050905061062052610500516157a357670de0b6b3a7640000602060403803608039608051808202821582848304141715615caf57905090506105e0525b610520516157b7576019546105c0526157eb565b6104a051610200526104c05161022052610600516102405261062051610260526157e26106406128bd565b610640516105c0525b6105c051610640526106005160e052610620516101005261580d610680613c37565b61068051610660526104e05161064051808202821582848304141715615caf579050905061056051808015615caf57820490509050610680526106408051610680516106605161068051808202821582848304141715615caf57905090506404a817c8008082049050905060018181830110615caf5780820190509050808210615caf5780820390509050808210615caf57808203905090508152506104a05160e0526104c0516101005261060051610120526106205161014052610640516101605261050051610180526158e36106c061304c565b6106c0516106a052610600610500516002811015615caf5760200201516106a051808210615caf5780820390509050670de0b6b3a7640000808202821582848304141715615caf57905090506105e051808015615caf578204905090506106c0526106a051610600610500516002811015615caf57602002015260006106e05261054051615972576000615990565b620186a06106c05111615986576000615990565b620186a06104e051115b15615b335760006107005260206040380360803960805161072052600161050051186159f65761058051602060403803608039608051808202821582848304141715615caf57905090506107005260206040380360200160803960805161072052615a22565b6105a051602060403803602001608039608051808202821582848304141715615caf5790509050610700525b6107005161068051808202821582848304141715615caf57905090506105c051808015615caf578204905090506107005261070051670de0b6b3a7640000808202821582848304141715615caf57905090506106c05161072051808202821582848304141715615caf579050905061068051610580610500516002811015615caf576020020151808202821582848304141715615caf579050905061072051808202821582848304141715615caf57905090506105c051808015615caf57820490509050808210615caf5780820390509050808015615caf578204905090506106e05261050051615b33576ec097ce7bc90715b34b9f10000000006106e051808015615caf578204905090506106e0525b6106c05181526106e0516020820152610640516040820152606081016106005181526106205181602001525050565b60e051615b73576000815250615cad565b60e051670de0b6b3a76400008181830110615caf57808201905090506002808204905090506101005260e051610120526101406000610100818352015b610120516101005118615bcb57505061012051815250615cad565b610100516101205260e051670de0b6b3a7640000808202821582848304141715615caf579050905061010051808015615caf57820490509050610100518181830110615caf5780820190509050600280820490509050610100528151600101808352811415615bb05750506010610140527f446964206e6f7420636f6e7665726765000000000000000000000000000000006101605261014050610140518061016001818260206001820306601f82010390500336823750506308c379a0610100526020610120526101405160206001820306601f820103905060440161011cfd5b565b600080fd000000000000000000000000cb08717451aae9ef950a2524e33b6dcaba60147b000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000cdf7028ceab81fa0c6971208e83fa7872994bee500000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001

Verified Source Code Partial Match

Compiler: v0.3.1
Vyper_contract.vy 1412 lines
# @version 0.3.1
# (c) Curve.Fi, 2021
# Pool for two crypto assets

# Expected coins:
# eth/whatever

interface CurveToken:
    def totalSupply() -> uint256: view
    def mint(_to: address, _value: uint256) -> bool: nonpayable
    def mint_relative(_to: address, frac: uint256) -> uint256: nonpayable
    def burnFrom(_to: address, _value: uint256) -> bool: nonpayable

interface ERC20:
    def transfer(_to: address, _value: uint256) -> bool: nonpayable
    def transferFrom(_from: address, _to: address, _value: uint256) -> bool: nonpayable
    def decimals() -> uint256: view
    def balanceOf(_user: address) -> uint256: view

interface WETH:
    def deposit(): payable
    def withdraw(_amount: uint256): nonpayable


# Events
event TokenExchange:
    buyer: indexed(address)
    sold_id: uint256
    tokens_sold: uint256
    bought_id: uint256
    tokens_bought: uint256

event AddLiquidity:
    provider: indexed(address)
    token_amounts: uint256[N_COINS]
    fee: uint256
    token_supply: uint256

event RemoveLiquidity:
    provider: indexed(address)
    token_amounts: uint256[N_COINS]
    token_supply: uint256

event RemoveLiquidityOne:
    provider: indexed(address)
    token_amount: uint256
    coin_index: uint256
    coin_amount: uint256

event CommitNewAdmin:
    deadline: indexed(uint256)
    admin: indexed(address)

event NewAdmin:
    admin: indexed(address)

event CommitNewParameters:
    deadline: indexed(uint256)
    admin_fee: uint256
    mid_fee: uint256
    out_fee: uint256
    fee_gamma: uint256
    allowed_extra_profit: uint256
    adjustment_step: uint256
    ma_half_time: uint256

event NewParameters:
    admin_fee: uint256
    mid_fee: uint256
    out_fee: uint256
    fee_gamma: uint256
    allowed_extra_profit: uint256
    adjustment_step: uint256
    ma_half_time: uint256

event RampAgamma:
    initial_A: uint256
    future_A: uint256
    initial_gamma: uint256
    future_gamma: uint256
    initial_time: uint256
    future_time: uint256

event StopRampA:
    current_A: uint256
    current_gamma: uint256
    time: uint256

event ClaimAdminFee:
    admin: indexed(address)
    tokens: uint256


N_COINS: constant(int128) = 2
PRECISION: constant(uint256) = 10 ** 18  # The precision to convert to
A_MULTIPLIER: constant(uint256) = 10000

token: immutable(address)
coins: immutable(address[N_COINS])

price_scale: public(uint256)   # Internal price scale
_price_oracle: uint256  # Price target given by MA

last_prices: public(uint256)
last_prices_timestamp: public(uint256)

initial_A_gamma: public(uint256)
future_A_gamma: public(uint256)
initial_A_gamma_time: public(uint256)
future_A_gamma_time: public(uint256)

allowed_extra_profit: public(uint256)  # 2 * 10**12 - recommended value
future_allowed_extra_profit: public(uint256)

fee_gamma: public(uint256)
future_fee_gamma: public(uint256)

adjustment_step: public(uint256)
future_adjustment_step: public(uint256)

ma_half_time: public(uint256)
future_ma_half_time: public(uint256)

mid_fee: public(uint256)
out_fee: public(uint256)
admin_fee: public(uint256)
future_mid_fee: public(uint256)
future_out_fee: public(uint256)
future_admin_fee: public(uint256)

balances: public(uint256[N_COINS])
D: public(uint256)

owner: public(address)
future_owner: public(address)

xcp_profit: public(uint256)
xcp_profit_a: public(uint256)  # Full profit at last claim of admin fees
virtual_price: public(uint256)  # Cached (fast to read) virtual price also used internally
not_adjusted: bool

is_killed: public(bool)
kill_deadline: public(uint256)
transfer_ownership_deadline: public(uint256)
admin_actions_deadline: public(uint256)

admin_fee_receiver: public(address)

KILL_DEADLINE_DT: constant(uint256) = 2 * 30 * 86400
ADMIN_ACTIONS_DELAY: constant(uint256) = 3 * 86400
MIN_RAMP_TIME: constant(uint256) = 86400

MAX_ADMIN_FEE: constant(uint256) = 10 * 10 ** 9
MIN_FEE: constant(uint256) = 5 * 10 ** 5  # 0.5 bps
MAX_FEE: constant(uint256) = 10 * 10 ** 9
MAX_A_CHANGE: constant(uint256) = 10
NOISE_FEE: constant(uint256) = 10**5  # 0.1 bps

MIN_GAMMA: constant(uint256) = 10**10
MAX_GAMMA: constant(uint256) = 2 * 10**16

MIN_A: constant(uint256) = N_COINS**N_COINS * A_MULTIPLIER / 10
MAX_A: constant(uint256) = N_COINS**N_COINS * A_MULTIPLIER * 100000

# This must be changed for different N_COINS
# For example:
# N_COINS = 3 -> 1  (10**18 -> 10**18)
# N_COINS = 4 -> 10**8  (10**18 -> 10**10)
# PRICE_PRECISION_MUL: constant(uint256) = 1
PRECISIONS: immutable(uint256[N_COINS])

EXP_PRECISION: constant(uint256) = 10**10

ETH_INDEX: constant(uint256) = 0  # Can put it to something big to turn the logic off


@external
def __init__(
    owner: address,
    admin_fee_receiver: address,
    A: uint256,
    gamma: uint256,
    mid_fee: uint256,
    out_fee: uint256,
    allowed_extra_profit: uint256,
    fee_gamma: uint256,
    adjustment_step: uint256,
    admin_fee: uint256,
    ma_half_time: uint256,
    initial_price: uint256,
    _token: address,
    _coins: address[N_COINS]
):
    self.owner = owner

    # Pack A and gamma:
    # shifted A + gamma
    A_gamma: uint256 = shift(A, 128)
    A_gamma = bitwise_or(A_gamma, gamma)
    self.initial_A_gamma = A_gamma
    self.future_A_gamma = A_gamma

    self.mid_fee = mid_fee
    self.out_fee = out_fee
    self.allowed_extra_profit = allowed_extra_profit
    self.fee_gamma = fee_gamma
    self.adjustment_step = adjustment_step
    self.admin_fee = admin_fee

    self.price_scale = initial_price
    self._price_oracle = initial_price
    self.last_prices = initial_price
    self.last_prices_timestamp = block.timestamp
    self.ma_half_time = ma_half_time

    self.xcp_profit_a = 10**18

    self.kill_deadline = block.timestamp + KILL_DEADLINE_DT

    self.admin_fee_receiver = admin_fee_receiver

    token = _token
    coins = _coins
    PRECISIONS = [10 ** (18 - ERC20(_coins[0]).decimals()),
                  10 ** (18 - ERC20(_coins[1]).decimals())]


@payable
@external
def __default__():
    pass


### Math functions
@internal
@pure
def geometric_mean(unsorted_x: uint256[N_COINS], sort: bool) -> uint256:
    """
    (x[0] * x[1] * ...) ** (1/N)
    """
    x: uint256[N_COINS] = unsorted_x
    if sort and x[0] < x[1]:
        x = [unsorted_x[1], unsorted_x[0]]
    D: uint256 = x[0]
    diff: uint256 = 0
    for i in range(255):
        D_prev: uint256 = D
        # tmp: uint256 = 10**18
        # for _x in x:
        #     tmp = tmp * _x / D
        # D = D * ((N_COINS - 1) * 10**18 + tmp) / (N_COINS * 10**18)
        # line below makes it for 2 coins
        D = (D + x[0] * x[1] / D) / N_COINS
        if D > D_prev:
            diff = D - D_prev
        else:
            diff = D_prev - D
        if diff <= 1 or diff * 10**18 < D:
            return D
    raise "Did not converge"


@internal
@view
def newton_D(ANN: uint256, gamma: uint256, x_unsorted: uint256[N_COINS]) -> uint256:
    """
    Finding the invariant using Newton method.
    ANN is higher by the factor A_MULTIPLIER
    ANN is already A * N**N

    Currently uses 60k gas
    """
    # Safety checks
    assert ANN > MIN_A - 1 and ANN < MAX_A + 1  # dev: unsafe values A
    assert gamma > MIN_GAMMA - 1 and gamma < MAX_GAMMA + 1  # dev: unsafe values gamma

    # Initial value of invariant D is that for constant-product invariant
    x: uint256[N_COINS] = x_unsorted
    if x[0] < x[1]:
        x = [x_unsorted[1], x_unsorted[0]]

    assert x[0] > 10**9 - 1 and x[0] < 10**15 * 10**18 + 1  # dev: unsafe values x[0]
    assert x[1] * 10**18 / x[0] > 10**14-1  # dev: unsafe values x[i] (input)

    D: uint256 = N_COINS * self.geometric_mean(x, False)
    S: uint256 = x[0] + x[1]

    for i in range(255):
        D_prev: uint256 = D

        # K0: uint256 = 10**18
        # for _x in x:
        #     K0 = K0 * _x * N_COINS / D
        # collapsed for 2 coins
        K0: uint256 = (10**18 * N_COINS**2) * x[0] / D * x[1] / D

        _g1k0: uint256 = gamma + 10**18
        if _g1k0 > K0:
            _g1k0 = _g1k0 - K0 + 1
        else:
            _g1k0 = K0 - _g1k0 + 1

        # D / (A * N**N) * _g1k0**2 / gamma**2
        mul1: uint256 = 10**18 * D / gamma * _g1k0 / gamma * _g1k0 * A_MULTIPLIER / ANN

        # 2*N*K0 / _g1k0
        mul2: uint256 = (2 * 10**18) * N_COINS * K0 / _g1k0

        neg_fprime: uint256 = (S + S * mul2 / 10**18) + mul1 * N_COINS / K0 - mul2 * D / 10**18

        # D -= f / fprime
        D_plus: uint256 = D * (neg_fprime + S) / neg_fprime
        D_minus: uint256 = D*D / neg_fprime
        if 10**18 > K0:
            D_minus += D * (mul1 / neg_fprime) / 10**18 * (10**18 - K0) / K0
        else:
            D_minus -= D * (mul1 / neg_fprime) / 10**18 * (K0 - 10**18) / K0

        if D_plus > D_minus:
            D = D_plus - D_minus
        else:
            D = (D_minus - D_plus) / 2

        diff: uint256 = 0
        if D > D_prev:
            diff = D - D_prev
        else:
            diff = D_prev - D
        if diff * 10**14 < max(10**16, D):  # Could reduce precision for gas efficiency here
            # Test that we are safe with the next newton_y
            for _x in x:
                frac: uint256 = _x * 10**18 / D
                assert (frac > 10**16 - 1) and (frac < 10**20 + 1)  # dev: unsafe values x[i]
            return D

    raise "Did not converge"


@internal
@pure
def newton_y(ANN: uint256, gamma: uint256, x: uint256[N_COINS], D: uint256, i: uint256) -> uint256:
    """
    Calculating x[i] given other balances x[0..N_COINS-1] and invariant D
    ANN = A * N**N
    """
    # Safety checks
    assert ANN > MIN_A - 1 and ANN < MAX_A + 1  # dev: unsafe values A
    assert gamma > MIN_GAMMA - 1 and gamma < MAX_GAMMA + 1  # dev: unsafe values gamma
    assert D > 10**17 - 1 and D < 10**15 * 10**18 + 1 # dev: unsafe values D

    x_j: uint256 = x[1 - i]
    y: uint256 = D**2 / (x_j * N_COINS**2)
    K0_i: uint256 = (10**18 * N_COINS) * x_j / D
    # S_i = x_j

    # frac = x_j * 1e18 / D => frac = K0_i / N_COINS
    assert (K0_i > 10**16*N_COINS - 1) and (K0_i < 10**20*N_COINS + 1)  # dev: unsafe values x[i]

    # x_sorted: uint256[N_COINS] = x
    # x_sorted[i] = 0
    # x_sorted = self.sort(x_sorted)  # From high to low
    # x[not i] instead of x_sorted since x_soted has only 1 element

    convergence_limit: uint256 = max(max(x_j / 10**14, D / 10**14), 100)

    for j in range(255):
        y_prev: uint256 = y

        K0: uint256 = K0_i * y * N_COINS / D
        S: uint256 = x_j + y

        _g1k0: uint256 = gamma + 10**18
        if _g1k0 > K0:
            _g1k0 = _g1k0 - K0 + 1
        else:
            _g1k0 = K0 - _g1k0 + 1

        # D / (A * N**N) * _g1k0**2 / gamma**2
        mul1: uint256 = 10**18 * D / gamma * _g1k0 / gamma * _g1k0 * A_MULTIPLIER / ANN

        # 2*K0 / _g1k0
        mul2: uint256 = 10**18 + (2 * 10**18) * K0 / _g1k0

        yfprime: uint256 = 10**18 * y + S * mul2 + mul1
        _dyfprime: uint256 = D * mul2
        if yfprime < _dyfprime:
            y = y_prev / 2
            continue
        else:
            yfprime -= _dyfprime
        fprime: uint256 = yfprime / y

        # y -= f / f_prime;  y = (y * fprime - f) / fprime
        # y = (yfprime + 10**18 * D - 10**18 * S) // fprime + mul1 // fprime * (10**18 - K0) // K0
        y_minus: uint256 = mul1 / fprime
        y_plus: uint256 = (yfprime + 10**18 * D) / fprime + y_minus * 10**18 / K0
        y_minus += 10**18 * S / fprime

        if y_plus < y_minus:
            y = y_prev / 2
        else:
            y = y_plus - y_minus

        diff: uint256 = 0
        if y > y_prev:
            diff = y - y_prev
        else:
            diff = y_prev - y
        if diff < max(convergence_limit, y / 10**14):
            frac: uint256 = y * 10**18 / D
            assert (frac > 10**16 - 1) and (frac < 10**20 + 1)  # dev: unsafe value for y
            return y

    raise "Did not converge"


@internal
@pure
def halfpow(power: uint256) -> uint256:
    """
    1e18 * 0.5 ** (power/1e18)

    Inspired by: https://github.com/balancer-labs/balancer-core/blob/master/contracts/BNum.sol#L128
    """
    intpow: uint256 = power / 10**18
    otherpow: uint256 = power - intpow * 10**18
    if intpow > 59:
        return 0
    result: uint256 = 10**18 / (2**intpow)
    if otherpow == 0:
        return result

    term: uint256 = 10**18
    x: uint256 = 5 * 10**17
    S: uint256 = 10**18
    neg: bool = False

    for i in range(1, 256):
        K: uint256 = i * 10**18
        c: uint256 = K - 10**18
        if otherpow > c:
            c = otherpow - c
            neg = not neg
        else:
            c -= otherpow
        term = term * (c * x / 10**18) / K
        if neg:
            S -= term
        else:
            S += term
        if term < EXP_PRECISION:
            return result * S / 10**18

    raise "Did not converge"
### end of Math functions


@external
@view
def token() -> address:
    return token


@external
@view
def coins(i: uint256) -> address:
    _coins: address[N_COINS] = coins
    return _coins[i]


@internal
@view
def xp() -> uint256[N_COINS]:
    return [self.balances[0] * PRECISIONS[0],
            self.balances[1] * PRECISIONS[1] * self.price_scale / PRECISION]


@view
@internal
def _A_gamma() -> uint256[2]:
    t1: uint256 = self.future_A_gamma_time

    A_gamma_1: uint256 = self.future_A_gamma
    gamma1: uint256 = bitwise_and(A_gamma_1, 2**128-1)
    A1: uint256 = shift(A_gamma_1, -128)

    if block.timestamp < t1:
        # handle ramping up and down of A
        A_gamma_0: uint256 = self.initial_A_gamma
        t0: uint256 = self.initial_A_gamma_time

        # Less readable but more compact way of writing and converting to uint256
        # gamma0: uint256 = bitwise_and(A_gamma_0, 2**128-1)
        # A0: uint256 = shift(A_gamma_0, -128)
        # A1 = A0 + (A1 - A0) * (block.timestamp - t0) / (t1 - t0)
        # gamma1 = gamma0 + (gamma1 - gamma0) * (block.timestamp - t0) / (t1 - t0)

        t1 -= t0
        t0 = block.timestamp - t0
        t2: uint256 = t1 - t0

        A1 = (shift(A_gamma_0, -128) * t2 + A1 * t0) / t1
        gamma1 = (bitwise_and(A_gamma_0, 2**128-1) * t2 + gamma1 * t0) / t1

    return [A1, gamma1]


@view
@external
def A() -> uint256:
    return self._A_gamma()[0]


@view
@external
def gamma() -> uint256:
    return self._A_gamma()[1]


@internal
@view
def _fee(xp: uint256[N_COINS]) -> uint256:
    """
    f = fee_gamma / (fee_gamma + (1 - K))
    where
    K = prod(x) / (sum(x) / N)**N
    (all normalized to 1e18)
    """
    fee_gamma: uint256 = self.fee_gamma
    f: uint256 = xp[0] + xp[1]  # sum
    f = fee_gamma * 10**18 / (
        fee_gamma + 10**18 - (10**18 * N_COINS**N_COINS) * xp[0] / f * xp[1] / f
    )
    return (self.mid_fee * f + self.out_fee * (10**18 - f)) / 10**18


@external
@view
def fee() -> uint256:
    return self._fee(self.xp())


@internal
@view
def get_xcp(D: uint256) -> uint256:
    x: uint256[N_COINS] = [D / N_COINS, D * PRECISION / (self.price_scale * N_COINS)]
    return self.geometric_mean(x, True)


@external
@view
def get_virtual_price() -> uint256:
    return 10**18 * self.get_xcp(self.D) / CurveToken(token).totalSupply()


@internal
def _claim_admin_fees():
    A_gamma: uint256[2] = self._A_gamma()

    xcp_profit: uint256 = self.xcp_profit
    xcp_profit_a: uint256 = self.xcp_profit_a

    # Gulp here
    _coins: address[N_COINS] = coins
    for i in range(N_COINS):
        if i == ETH_INDEX:
            self.balances[i] = self.balance
        else:
            self.balances[i] = ERC20(_coins[i]).balanceOf(self)

    vprice: uint256 = self.virtual_price

    if xcp_profit > xcp_profit_a:
        fees: uint256 = (xcp_profit - xcp_profit_a) * self.admin_fee / (2 * 10**10)
        if fees > 0:
            receiver: address = self.admin_fee_receiver
            if receiver != ZERO_ADDRESS:
                frac: uint256 = vprice * 10**18 / (vprice - fees) - 10**18
                claimed: uint256 = CurveToken(token).mint_relative(receiver, frac)
                xcp_profit -= fees*2
                self.xcp_profit = xcp_profit
                log ClaimAdminFee(receiver, claimed)

    total_supply: uint256 = CurveToken(token).totalSupply()

    # Recalculate D b/c we gulped
    D: uint256 = self.newton_D(A_gamma[0], A_gamma[1], self.xp())
    self.D = D

    self.virtual_price = 10**18 * self.get_xcp(D) / total_supply

    if xcp_profit > xcp_profit_a:
        self.xcp_profit_a = xcp_profit


@internal
@view
def internal_price_oracle() -> uint256:
    price_oracle: uint256 = self._price_oracle
    last_prices_timestamp: uint256 = self.last_prices_timestamp

    if last_prices_timestamp < block.timestamp:
        ma_half_time: uint256 = self.ma_half_time
        last_prices: uint256 = self.last_prices
        alpha: uint256 = self.halfpow((block.timestamp - last_prices_timestamp) * 10**18 / ma_half_time)
        return (last_prices * (10**18 - alpha) + price_oracle * alpha) / 10**18

    else:
        return price_oracle


@external
@view
def price_oracle() -> uint256:
    return self.internal_price_oracle()


@internal
def tweak_price(A_gamma: uint256[2],_xp: uint256[N_COINS], p_i: uint256, new_D: uint256):
    price_oracle: uint256 = self._price_oracle
    last_prices: uint256 = self.last_prices
    price_scale: uint256 = self.price_scale
    last_prices_timestamp: uint256 = self.last_prices_timestamp
    p_new: uint256 = 0

    if last_prices_timestamp < block.timestamp:
        # MA update required
        ma_half_time: uint256 = self.ma_half_time
        alpha: uint256 = self.halfpow((block.timestamp - last_prices_timestamp) * 10**18 / ma_half_time)
        price_oracle = (last_prices * (10**18 - alpha) + price_oracle * alpha) / 10**18
        self._price_oracle = price_oracle
        self.last_prices_timestamp = block.timestamp

    D_unadjusted: uint256 = new_D  # Withdrawal methods know new D already
    if new_D == 0:
        # We will need this a few times (35k gas)
        D_unadjusted = self.newton_D(A_gamma[0], A_gamma[1], _xp)

    if p_i > 0:
        last_prices = p_i

    else:
        # calculate real prices
        __xp: uint256[N_COINS] = _xp
        dx_price: uint256 = __xp[0] / 10**6
        __xp[0] += dx_price
        last_prices = price_scale * dx_price / (_xp[1] - self.newton_y(A_gamma[0], A_gamma[1], __xp, D_unadjusted, 1))

    self.last_prices = last_prices

    total_supply: uint256 = CurveToken(token).totalSupply()
    old_xcp_profit: uint256 = self.xcp_profit
    old_virtual_price: uint256 = self.virtual_price

    # Update profit numbers without price adjustment first
    xp: uint256[N_COINS] = [D_unadjusted / N_COINS, D_unadjusted * PRECISION / (N_COINS * price_scale)]
    xcp_profit: uint256 = 10**18
    virtual_price: uint256 = 10**18

    if old_virtual_price > 0:
        xcp: uint256 = self.geometric_mean(xp, True)
        virtual_price = 10**18 * xcp / total_supply
        xcp_profit = old_xcp_profit * virtual_price / old_virtual_price

        t: uint256 = self.future_A_gamma_time
        if virtual_price < old_virtual_price and t == 0:
            raise "Loss"
        if t == 1:
            self.future_A_gamma_time = 0

    self.xcp_profit = xcp_profit

    norm: uint256 = price_oracle * 10**18 / price_scale
    if norm > 10**18:
        norm -= 10**18
    else:
        norm = 10**18 - norm
    adjustment_step: uint256 = max(self.adjustment_step, norm / 10)

    needs_adjustment: bool = self.not_adjusted
    # if not needs_adjustment and (virtual_price-10**18 > (xcp_profit-10**18)/2 + self.allowed_extra_profit):
    # (re-arrange for gas efficiency)
    if not needs_adjustment and (virtual_price * 2 - 10**18 > xcp_profit + 2*self.allowed_extra_profit) and (norm > adjustment_step) and (old_virtual_price > 0):
        needs_adjustment = True
        self.not_adjusted = True

    if needs_adjustment:
        if norm > adjustment_step and old_virtual_price > 0:
            p_new = (price_scale * (norm - adjustment_step) + adjustment_step * price_oracle) / norm

            # Calculate balances*prices
            xp = [_xp[0], _xp[1] * p_new / price_scale]

            # Calculate "extended constant product" invariant xCP and virtual price
            D: uint256 = self.newton_D(A_gamma[0], A_gamma[1], xp)
            xp = [D / N_COINS, D * PRECISION / (N_COINS * p_new)]
            # We reuse old_virtual_price here but it's not old anymore
            old_virtual_price = 10**18 * self.geometric_mean(xp, True) / total_supply

            # Proceed if we've got enough profit
            # if (old_virtual_price > 10**18) and (2 * (old_virtual_price - 10**18) > xcp_profit - 10**18):
            if (old_virtual_price > 10**18) and (2 * old_virtual_price - 10**18 > xcp_profit):
                self.price_scale = p_new
                self.D = D
                self.virtual_price = old_virtual_price

                return

            else:
                self.not_adjusted = False

                # Can instead do another flag variable if we want to save bytespace
                self.D = D_unadjusted
                self.virtual_price = virtual_price
                self._claim_admin_fees()

                return

    # If we are here, the price_scale adjustment did not happen
    # Still need to update the profit counter and D
    self.D = D_unadjusted
    self.virtual_price = virtual_price

    # norm appeared < adjustment_step after
    if needs_adjustment:
        self.not_adjusted = False
        self._claim_admin_fees()


@internal
def _exchange(sender: address, mvalue: uint256, i: uint256, j: uint256, dx: uint256, min_dy: uint256,
              use_eth: bool, receiver: address, callbacker: address, callback_sig: Bytes[4]) -> uint256:
    assert not self.is_killed  # dev: the pool is killed
    assert i != j  # dev: coin index out of range
    assert i < N_COINS  # dev: coin index out of range
    assert j < N_COINS  # dev: coin index out of range
    assert dx > 0  # dev: do not exchange 0 coins

    A_gamma: uint256[2] = self._A_gamma()
    xp: uint256[N_COINS] = self.balances
    p: uint256 = 0
    dy: uint256 = 0

    _coins: address[N_COINS] = coins

    y: uint256 = xp[j]
    x0: uint256 = xp[i]
    xp[i] = x0 + dx
    self.balances[i] = xp[i]

    price_scale: uint256 = self.price_scale

    xp = [xp[0] * PRECISIONS[0], xp[1] * price_scale * PRECISIONS[1] / PRECISION]

    prec_i: uint256 = PRECISIONS[0]
    prec_j: uint256 = PRECISIONS[1]
    if i == 1:
        prec_i = PRECISIONS[1]
        prec_j = PRECISIONS[0]

    # In case ramp is happening
    t: uint256 = self.future_A_gamma_time
    if t > 0:
        x0 *= prec_i
        if i > 0:
            x0 = x0 * price_scale / PRECISION
        x1: uint256 = xp[i]  # Back up old value in xp
        xp[i] = x0
        self.D = self.newton_D(A_gamma[0], A_gamma[1], xp)
        xp[i] = x1  # And restore
        if block.timestamp >= t:
            self.future_A_gamma_time = 1

    dy = xp[j] - self.newton_y(A_gamma[0], A_gamma[1], xp, self.D, j)
    # Not defining new "y" here to have less variables / make subsequent calls cheaper
    xp[j] -= dy
    dy -= 1

    if j > 0:
        dy = dy * PRECISION / price_scale
    dy /= prec_j

    dy -= self._fee(xp) * dy / 10**10
    assert dy >= min_dy, "Slippage"
    y -= dy

    self.balances[j] = y

    # Do transfers in and out together
    if use_eth and i == ETH_INDEX:
        assert mvalue == dx  # dev: incorrect eth amount
    else:
        assert mvalue == 0  # dev: nonzero eth amount
        if callback_sig == b"\x00\x00\x00\x00":
            assert ERC20(_coins[i]).transferFrom(sender, self, dx)
        else:
            c: address = _coins[i]
            b: uint256 = ERC20(c).balanceOf(self)
            raw_call(callbacker,
                     concat(
                        callback_sig,
                        convert(sender, bytes32),
                        convert(receiver, bytes32),
                        convert(c, bytes32),
                        convert(dx, bytes32),
                        convert(dy, bytes32)
                     )
            )
            assert ERC20(c).balanceOf(self) - b == dx  # dev: callback didn't give us coins
        if i == ETH_INDEX:
            WETH(_coins[i]).withdraw(dx)

    if use_eth and j == ETH_INDEX:
        raw_call(receiver, b"", value=dy)
    else:
        if j == ETH_INDEX:
            WETH(_coins[j]).deposit(value=dy)
        assert ERC20(_coins[j]).transfer(receiver, dy)

    y *= prec_j
    if j > 0:
        y = y * price_scale / PRECISION
    xp[j] = y

    # Calculate price
    if dx > 10**5 and dy > 10**5:
        _dx: uint256 = dx * prec_i
        _dy: uint256 = dy * prec_j
        if i == 0:
            p = _dx * 10**18 / _dy
        else:  # j == 0
            p = _dy * 10**18 / _dx

    self.tweak_price(A_gamma, xp, p, 0)

    log TokenExchange(sender, i, dx, j, dy)

    return dy


@payable
@external
@nonreentrant('lock')
def exchange(i: uint256, j: uint256, dx: uint256, min_dy: uint256,
             use_eth: bool = False, receiver: address = msg.sender) -> uint256:
    """
    Exchange using WETH by default
    """
    return self._exchange(msg.sender, msg.value, i, j, dx, min_dy, use_eth, receiver, ZERO_ADDRESS, b'\x00\x00\x00\x00')


@payable
@external
@nonreentrant('lock')
def exchange_underlying(i: uint256, j: uint256, dx: uint256, min_dy: uint256,
                        receiver: address = msg.sender) -> uint256:
    """
    Exchange using ETH
    """
    return self._exchange(msg.sender, msg.value, i, j, dx, min_dy, True, receiver, ZERO_ADDRESS, b'\x00\x00\x00\x00')


@payable
@external
@nonreentrant('lock')
def exchange_extended(i: uint256, j: uint256, dx: uint256, min_dy: uint256,
                      use_eth: bool, sender: address, receiver: address, cb: Bytes[4]) -> uint256:
    assert cb != b'\x00\x00\x00\x00'  # dev: No callback specified
    return self._exchange(sender, msg.value, i, j, dx, min_dy, use_eth, receiver, msg.sender, cb)


@external
@view
def get_dy(i: uint256, j: uint256, dx: uint256) -> uint256:
    assert i != j  # dev: same input and output coin
    assert i < N_COINS  # dev: coin index out of range
    assert j < N_COINS  # dev: coin index out of range

    price_scale: uint256 = self.price_scale * PRECISIONS[1]
    xp: uint256[N_COINS] = self.balances

    A_gamma: uint256[2] = self._A_gamma()
    D: uint256 = self.D
    if self.future_A_gamma_time > 0:
        D = self.newton_D(A_gamma[0], A_gamma[1], self.xp())

    xp[i] += dx
    xp = [xp[0] * PRECISIONS[0], xp[1] * price_scale / PRECISION]

    y: uint256 = self.newton_y(A_gamma[0], A_gamma[1], xp, D, j)
    dy: uint256 = xp[j] - y - 1
    xp[j] = y
    if j > 0:
        dy = dy * PRECISION / price_scale
    else:
        dy /= PRECISIONS[0]
    dy -= self._fee(xp) * dy / 10**10

    return dy


@view
@internal
def _calc_token_fee(amounts: uint256[N_COINS], xp: uint256[N_COINS]) -> uint256:
    # fee = sum(amounts_i - avg(amounts)) * fee' / sum(amounts)
    fee: uint256 = self._fee(xp) * N_COINS / (4 * (N_COINS-1))
    S: uint256 = 0
    for _x in amounts:
        S += _x
    avg: uint256 = S / N_COINS
    Sdiff: uint256 = 0
    for _x in amounts:
        if _x > avg:
            Sdiff += _x - avg
        else:
            Sdiff += avg - _x
    return fee * Sdiff / S + NOISE_FEE


@payable
@external
@nonreentrant('lock')
def add_liquidity(amounts: uint256[N_COINS], min_mint_amount: uint256,
                  use_eth: bool = False, receiver: address = msg.sender) -> uint256:
    assert not self.is_killed  # dev: the pool is killed
    assert amounts[0] > 0 or amounts[1] > 0  # dev: no coins to add

    A_gamma: uint256[2] = self._A_gamma()

    _coins: address[N_COINS] = coins

    xp: uint256[N_COINS] = self.balances
    amountsp: uint256[N_COINS] = empty(uint256[N_COINS])
    xx: uint256[N_COINS] = empty(uint256[N_COINS])
    d_token: uint256 = 0
    d_token_fee: uint256 = 0
    old_D: uint256 = 0

    xp_old: uint256[N_COINS] = xp

    for i in range(N_COINS):
        bal: uint256 = xp[i] + amounts[i]
        xp[i] = bal
        self.balances[i] = bal
    xx = xp

    price_scale: uint256 = self.price_scale * PRECISIONS[1]
    xp = [xp[0] * PRECISIONS[0], xp[1] * price_scale / PRECISION]
    xp_old = [xp_old[0] * PRECISIONS[0], xp_old[1] * price_scale / PRECISION]

    if not use_eth:
        assert msg.value == 0  # dev: nonzero eth amount

    for i in range(N_COINS):
        if use_eth and i == ETH_INDEX:
            assert msg.value == amounts[i]  # dev: incorrect eth amount
        if amounts[i] > 0:
            coin: address = _coins[i]
            if (not use_eth) or (i != ETH_INDEX):
                assert ERC20(coin).transferFrom(msg.sender, self, amounts[i])
                if i == ETH_INDEX:
                    WETH(coin).withdraw(amounts[i])
            amountsp[i] = xp[i] - xp_old[i]

    t: uint256 = self.future_A_gamma_time
    if t > 0:
        old_D = self.newton_D(A_gamma[0], A_gamma[1], xp_old)
        if block.timestamp >= t:
            self.future_A_gamma_time = 1
    else:
        old_D = self.D

    D: uint256 = self.newton_D(A_gamma[0], A_gamma[1], xp)

    token_supply: uint256 = CurveToken(token).totalSupply()
    if old_D > 0:
        d_token = token_supply * D / old_D - token_supply
    else:
        d_token = self.get_xcp(D)  # making initial virtual price equal to 1
    assert d_token > 0  # dev: nothing minted

    if old_D > 0:
        d_token_fee = self._calc_token_fee(amountsp, xp) * d_token / 10**10 + 1
        d_token -= d_token_fee
        token_supply += d_token
        CurveToken(token).mint(receiver, d_token)

        # Calculate price
        # p_i * (dx_i - dtoken / token_supply * xx_i) = sum{k!=i}(p_k * (dtoken / token_supply * xx_k - dx_k))
        # Simplified for 2 coins
        p: uint256 = 0
        if d_token > 10**5:
            if amounts[0] == 0 or amounts[1] == 0:
                S: uint256 = 0
                precision: uint256 = 0
                ix: uint256 = 0
                if amounts[0] == 0:
                    S = xx[0] * PRECISIONS[0]
                    precision = PRECISIONS[1]
                    ix = 1
                else:
                    S = xx[1] * PRECISIONS[1]
                    precision = PRECISIONS[0]
                S = S * d_token / token_supply
                p = S * PRECISION / (amounts[ix] * precision - d_token * xx[ix] * precision / token_supply)
                if ix == 0:
                    p = (10**18)**2 / p

        self.tweak_price(A_gamma, xp, p, D)

    else:
        self.D = D
        self.virtual_price = 10**18
        self.xcp_profit = 10**18
        CurveToken(token).mint(receiver, d_token)

    assert d_token >= min_mint_amount, "Slippage"

    log AddLiquidity(receiver, amounts, d_token_fee, token_supply)

    return d_token


@external
@nonreentrant('lock')
def remove_liquidity(_amount: uint256, min_amounts: uint256[N_COINS],
                     use_eth: bool = False, receiver: address = msg.sender):
    """
    This withdrawal method is very safe, does no complex math
    """
    _coins: address[N_COINS] = coins
    total_supply: uint256 = CurveToken(token).totalSupply()
    CurveToken(token).burnFrom(msg.sender, _amount)
    balances: uint256[N_COINS] = self.balances
    amount: uint256 = _amount - 1  # Make rounding errors favoring other LPs a tiny bit

    for i in range(N_COINS):
        d_balance: uint256 = balances[i] * amount / total_supply
        assert d_balance >= min_amounts[i]
        self.balances[i] = balances[i] - d_balance
        balances[i] = d_balance  # now it's the amounts going out
        if use_eth and i == ETH_INDEX:
            raw_call(receiver, b"", value=d_balance)
        else:
            coin: address = _coins[i]
            if i == ETH_INDEX:
                WETH(_coins[i]).deposit(value=d_balance)
            assert ERC20(_coins[i]).transfer(receiver, d_balance)

    D: uint256 = self.D
    self.D = D - D * amount / total_supply

    log RemoveLiquidity(msg.sender, balances, total_supply - _amount)


@view
@external
def calc_token_amount(amounts: uint256[N_COINS]) -> uint256:
    token_supply: uint256 = CurveToken(token).totalSupply()
    price_scale: uint256 = self.price_scale * PRECISIONS[1]
    A_gamma: uint256[2] = self._A_gamma()
    xp: uint256[N_COINS] = self.xp()
    amountsp: uint256[N_COINS] = [
        amounts[0] * PRECISIONS[0],
        amounts[1] * price_scale / PRECISION]
    D0: uint256 = self.D
    if self.future_A_gamma_time > 0:
        D0 = self.newton_D(A_gamma[0], A_gamma[1], xp)
    xp[0] += amountsp[0]
    xp[1] += amountsp[1]
    D: uint256 = self.newton_D(A_gamma[0], A_gamma[1], xp)
    d_token: uint256 = token_supply * D / D0 - token_supply
    d_token -= self._calc_token_fee(amountsp, xp) * d_token / 10**10 + 1
    return d_token


@internal
@view
def _calc_withdraw_one_coin(A_gamma: uint256[2], token_amount: uint256, i: uint256, update_D: bool,
                            calc_price: bool) -> (uint256, uint256, uint256, uint256[N_COINS]):
    token_supply: uint256 = CurveToken(token).totalSupply()
    assert token_amount <= token_supply  # dev: token amount more than supply
    assert i < N_COINS  # dev: coin out of range

    xx: uint256[N_COINS] = self.balances
    D0: uint256 = 0

    price_scale_i: uint256 = self.price_scale * PRECISIONS[1]
    xp: uint256[N_COINS] = [xx[0] * PRECISIONS[0], xx[1] * price_scale_i / PRECISION]
    if i == 0:
        price_scale_i = PRECISION * PRECISIONS[0]

    if update_D:
        D0 = self.newton_D(A_gamma[0], A_gamma[1], xp)
    else:
        D0 = self.D

    D: uint256 = D0

    # Charge the fee on D, not on y, e.g. reducing invariant LESS than charging the user
    fee: uint256 = self._fee(xp)
    dD: uint256 = token_amount * D / token_supply
    D -= (dD - (fee * dD / (2 * 10**10) + 1))
    y: uint256 = self.newton_y(A_gamma[0], A_gamma[1], xp, D, i)
    dy: uint256 = (xp[i] - y) * PRECISION / price_scale_i
    xp[i] = y

    # Price calc
    p: uint256 = 0
    if calc_price and dy > 10**5 and token_amount > 10**5:
        # p_i = dD / D0 * sum'(p_k * x_k) / (dy - dD / D0 * y0)
        S: uint256 = 0
        precision: uint256 = PRECISIONS[0]
        if i == 1:
            S = xx[0] * PRECISIONS[0]
            precision = PRECISIONS[1]
        else:
            S = xx[1] * PRECISIONS[1]
        S = S * dD / D0
        p = S * PRECISION / (dy * precision - dD * xx[i] * precision / D0)
        if i == 0:
            p = (10**18)**2 / p

    return dy, p, D, xp


@view
@external
def calc_withdraw_one_coin(token_amount: uint256, i: uint256) -> uint256:
    return self._calc_withdraw_one_coin(self._A_gamma(), token_amount, i, True, False)[0]


@external
@nonreentrant('lock')
def remove_liquidity_one_coin(token_amount: uint256, i: uint256, min_amount: uint256,
                              use_eth: bool = False, receiver: address = msg.sender) -> uint256:
    assert not self.is_killed  # dev: the pool is killed

    A_gamma: uint256[2] = self._A_gamma()

    dy: uint256 = 0
    D: uint256 = 0
    p: uint256 = 0
    xp: uint256[N_COINS] = empty(uint256[N_COINS])
    future_A_gamma_time: uint256 = self.future_A_gamma_time
    dy, p, D, xp = self._calc_withdraw_one_coin(A_gamma, token_amount, i, (future_A_gamma_time > 0), True)
    assert dy >= min_amount, "Slippage"

    if block.timestamp >= future_A_gamma_time:
        self.future_A_gamma_time = 1

    self.balances[i] -= dy
    CurveToken(token).burnFrom(msg.sender, token_amount)

    _coins: address[N_COINS] = coins
    if use_eth and i == ETH_INDEX:
        raw_call(receiver, b"", value=dy)
    else:
        coin: address = _coins[i]
        if i == ETH_INDEX:
            WETH(coin).deposit(value=dy)
        assert ERC20(coin).transfer(receiver, dy)

    self.tweak_price(A_gamma, xp, p, D)

    log RemoveLiquidityOne(msg.sender, token_amount, i, dy)

    return dy


@external
@nonreentrant('lock')
def claim_admin_fees():
    self._claim_admin_fees()


# Admin parameters
@external
def ramp_A_gamma(future_A: uint256, future_gamma: uint256, future_time: uint256):
    assert msg.sender == self.owner  # dev: only owner
    assert block.timestamp > self.initial_A_gamma_time + (MIN_RAMP_TIME-1)
    assert future_time > block.timestamp + (MIN_RAMP_TIME-1)  # dev: insufficient time

    A_gamma: uint256[2] = self._A_gamma()
    initial_A_gamma: uint256 = shift(A_gamma[0], 128)
    initial_A_gamma = bitwise_or(initial_A_gamma, A_gamma[1])

    assert future_A > MIN_A-1
    assert future_A < MAX_A+1
    assert future_gamma > MIN_GAMMA-1
    assert future_gamma < MAX_GAMMA+1

    ratio: uint256 = 10**18 * future_A / A_gamma[0]
    assert ratio < 10**18 * MAX_A_CHANGE + 1
    assert ratio > 10**18 / MAX_A_CHANGE - 1

    ratio = 10**18 * future_gamma / A_gamma[1]
    assert ratio < 10**18 * MAX_A_CHANGE + 1
    assert ratio > 10**18 / MAX_A_CHANGE - 1

    self.initial_A_gamma = initial_A_gamma
    self.initial_A_gamma_time = block.timestamp

    future_A_gamma: uint256 = shift(future_A, 128)
    future_A_gamma = bitwise_or(future_A_gamma, future_gamma)
    self.future_A_gamma_time = future_time
    self.future_A_gamma = future_A_gamma

    log RampAgamma(A_gamma[0], future_A, A_gamma[1], future_gamma, block.timestamp, future_time)


@external
def stop_ramp_A_gamma():
    assert msg.sender == self.owner  # dev: only owner

    A_gamma: uint256[2] = self._A_gamma()
    current_A_gamma: uint256 = shift(A_gamma[0], 128)
    current_A_gamma = bitwise_or(current_A_gamma, A_gamma[1])
    self.initial_A_gamma = current_A_gamma
    self.future_A_gamma = current_A_gamma
    self.initial_A_gamma_time = block.timestamp
    self.future_A_gamma_time = block.timestamp
    # now (block.timestamp < t1) is always False, so we return saved A

    log StopRampA(A_gamma[0], A_gamma[1], block.timestamp)


@external
def commit_new_parameters(
    _new_mid_fee: uint256,
    _new_out_fee: uint256,
    _new_admin_fee: uint256,
    _new_fee_gamma: uint256,
    _new_allowed_extra_profit: uint256,
    _new_adjustment_step: uint256,
    _new_ma_half_time: uint256,
    ):
    assert msg.sender == self.owner  # dev: only owner
    assert self.admin_actions_deadline == 0  # dev: active action

    new_mid_fee: uint256 = _new_mid_fee
    new_out_fee: uint256 = _new_out_fee
    new_admin_fee: uint256 = _new_admin_fee
    new_fee_gamma: uint256 = _new_fee_gamma
    new_allowed_extra_profit: uint256 = _new_allowed_extra_profit
    new_adjustment_step: uint256 = _new_adjustment_step
    new_ma_half_time: uint256 = _new_ma_half_time

    # Fees
    if new_out_fee < MAX_FEE+1:
        assert new_out_fee > MIN_FEE-1  # dev: fee is out of range
    else:
        new_out_fee = self.out_fee
    if new_mid_fee > MAX_FEE:
        new_mid_fee = self.mid_fee
    assert new_mid_fee <= new_out_fee  # dev: mid-fee is too high
    if new_admin_fee > MAX_ADMIN_FEE:
        new_admin_fee = self.admin_fee

    # AMM parameters
    if new_fee_gamma < 10**18:
        assert new_fee_gamma > 0  # dev: fee_gamma out of range [1 .. 10**18]
    else:
        new_fee_gamma = self.fee_gamma
    if new_allowed_extra_profit > 10**18:
        new_allowed_extra_profit = self.allowed_extra_profit
    if new_adjustment_step > 10**18:
        new_adjustment_step = self.adjustment_step

    # MA
    if new_ma_half_time < 7*86400:
        assert new_ma_half_time > 0  # dev: MA time should be longer than 1 second
    else:
        new_ma_half_time = self.ma_half_time

    _deadline: uint256 = block.timestamp + ADMIN_ACTIONS_DELAY
    self.admin_actions_deadline = _deadline

    self.future_admin_fee = new_admin_fee
    self.future_mid_fee = new_mid_fee
    self.future_out_fee = new_out_fee
    self.future_fee_gamma = new_fee_gamma
    self.future_allowed_extra_profit = new_allowed_extra_profit
    self.future_adjustment_step = new_adjustment_step
    self.future_ma_half_time = new_ma_half_time

    log CommitNewParameters(_deadline, new_admin_fee, new_mid_fee, new_out_fee,
                            new_fee_gamma,
                            new_allowed_extra_profit, new_adjustment_step,
                            new_ma_half_time)


@external
@nonreentrant('lock')
def apply_new_parameters():
    assert msg.sender == self.owner  # dev: only owner
    assert block.timestamp >= self.admin_actions_deadline  # dev: insufficient time
    assert self.admin_actions_deadline != 0  # dev: no active action

    self.admin_actions_deadline = 0

    admin_fee: uint256 = self.future_admin_fee
    if self.admin_fee != admin_fee:
        self._claim_admin_fees()
        self.admin_fee = admin_fee

    mid_fee: uint256 = self.future_mid_fee
    self.mid_fee = mid_fee
    out_fee: uint256 = self.future_out_fee
    self.out_fee = out_fee
    fee_gamma: uint256 = self.future_fee_gamma
    self.fee_gamma = fee_gamma
    allowed_extra_profit: uint256 = self.future_allowed_extra_profit
    self.allowed_extra_profit = allowed_extra_profit
    adjustment_step: uint256 = self.future_adjustment_step
    self.adjustment_step = adjustment_step
    ma_half_time: uint256 = self.future_ma_half_time
    self.ma_half_time = ma_half_time

    log NewParameters(admin_fee, mid_fee, out_fee,
                      fee_gamma,
                      allowed_extra_profit, adjustment_step,
                      ma_half_time)


@external
def revert_new_parameters():
    assert msg.sender == self.owner  # dev: only owner

    self.admin_actions_deadline = 0


@external
def commit_transfer_ownership(_owner: address):
    assert msg.sender == self.owner  # dev: only owner
    assert self.transfer_ownership_deadline == 0  # dev: active transfer

    _deadline: uint256 = block.timestamp + ADMIN_ACTIONS_DELAY
    self.transfer_ownership_deadline = _deadline
    self.future_owner = _owner

    log CommitNewAdmin(_deadline, _owner)


@external
def apply_transfer_ownership():
    assert msg.sender == self.owner  # dev: only owner
    assert block.timestamp >= self.transfer_ownership_deadline  # dev: insufficient time
    assert self.transfer_ownership_deadline != 0  # dev: no active transfer

    self.transfer_ownership_deadline = 0
    _owner: address = self.future_owner
    self.owner = _owner

    log NewAdmin(_owner)


@external
def revert_transfer_ownership():
    assert msg.sender == self.owner  # dev: only owner

    self.transfer_ownership_deadline = 0


@external
def kill_me():
    assert msg.sender == self.owner  # dev: only owner
    assert self.kill_deadline > block.timestamp  # dev: deadline has passed
    self.is_killed = True


@external
def unkill_me():
    assert msg.sender == self.owner  # dev: only owner
    self.is_killed = False


@external
def set_admin_fee_receiver(_admin_fee_receiver: address):
    assert msg.sender == self.owner  # dev: only owner
    self.admin_fee_receiver = _admin_fee_receiver


@internal
@pure
def sqrt_int(x: uint256) -> uint256:
    """
    Originating from: https://github.com/vyperlang/vyper/issues/1266
    """

    if x == 0:
        return 0

    z: uint256 = (x + 10**18) / 2
    y: uint256 = x

    for i in range(256):
        if z == y:
            return y
        y = z
        z = (x * 10**18 / z + z) / 2

    raise "Did not converge"


@external
@view
def lp_price() -> uint256:
    """
    Approximate LP token price
    """
    return 2 * self.virtual_price * self.sqrt_int(self.internal_price_oracle()) / 10**18

Read Contract

A 0xf446c1d0 → uint256
D 0x0f529ba2 → uint256
adjustment_step 0x083812e5 → uint256
admin_actions_deadline 0x405e28f8 → uint256
admin_fee 0xfee3f7f9 → uint256
admin_fee_receiver 0x6e42e4d2 → address
allowed_extra_profit 0x49fe9e77 → uint256
balances 0x4903b0d1 → uint256
calc_token_amount 0x8d8ea727 → uint256
calc_withdraw_one_coin 0x4fb08c5e → uint256
coins 0xc6610657 → address
fee 0xddca3f43 → uint256
fee_gamma 0x72d4f0e2 → uint256
future_A_gamma 0xf30cfad5 → uint256
future_A_gamma_time 0xf9ed9597 → uint256
future_adjustment_step 0x4ea12c7d → uint256
future_admin_fee 0xe3824462 → uint256
future_allowed_extra_profit 0x727ced57 → uint256
future_fee_gamma 0xd7c3dcbe → uint256
future_ma_half_time 0x0c5e23d4 → uint256
future_mid_fee 0x7cf9aedc → uint256
future_out_fee 0x7d1b060c → uint256
future_owner 0x1ec0cdc1 → address
gamma 0xb1373929 → uint256
get_dy 0x556d6e9f → uint256
get_virtual_price 0xbb7b8b80 → uint256
initial_A_gamma 0x204fe3d5 → uint256
initial_A_gamma_time 0xe89876ff → uint256
is_killed 0x9c868ac0 → bool
kill_deadline 0x2a426896 → uint256
last_prices 0xc146bf94 → uint256
last_prices_timestamp 0x6112c747 → uint256
lp_price 0x54f0f7d5 → uint256
ma_half_time 0x662b6274 → uint256
mid_fee 0x92526c0c → uint256
out_fee 0xee8de675 → uint256
owner 0x8da5cb5b → address
price_oracle 0x86fc88d3 → uint256
price_scale 0xb9e8c9fd → uint256
token 0xfc0c546a → address
transfer_ownership_deadline 0xe0a0b586 → uint256
virtual_price 0x0c46b72a → uint256
xcp_profit 0x7ba1a74d → uint256
xcp_profit_a 0x0b7b594b → uint256

Write Contract 27 functions

These functions modify contract state and require a wallet transaction to execute.

add_liquidity 0x0b4c7e4d
uint256[2] amounts
uint256 min_mint_amount
returns: uint256
add_liquidity 0xee22be23
uint256[2] amounts
uint256 min_mint_amount
bool use_eth
returns: uint256
add_liquidity 0x7328333b
uint256[2] amounts
uint256 min_mint_amount
bool use_eth
address receiver
returns: uint256
apply_new_parameters 0x2a7dd7cd
No parameters
apply_transfer_ownership 0x6a1c05ae
No parameters
claim_admin_fees 0xc93f49e8
No parameters
commit_new_parameters 0xa43c3351
uint256 _new_mid_fee
uint256 _new_out_fee
uint256 _new_admin_fee
uint256 _new_fee_gamma
uint256 _new_allowed_extra_profit
uint256 _new_adjustment_step
uint256 _new_ma_half_time
commit_transfer_ownership 0x6b441a40
address _owner
exchange 0x5b41b908
uint256 i
uint256 j
uint256 dx
uint256 min_dy
returns: uint256
exchange 0x394747c5
uint256 i
uint256 j
uint256 dx
uint256 min_dy
bool use_eth
returns: uint256
exchange 0xce7d6503
uint256 i
uint256 j
uint256 dx
uint256 min_dy
bool use_eth
address receiver
returns: uint256
exchange_extended 0x1d0dadb7
uint256 i
uint256 j
uint256 dx
uint256 min_dy
bool use_eth
address sender
address receiver
bytes cb
returns: uint256
exchange_underlying 0x65b2489b
uint256 i
uint256 j
uint256 dx
uint256 min_dy
returns: uint256
exchange_underlying 0xe2ad025a
uint256 i
uint256 j
uint256 dx
uint256 min_dy
address receiver
returns: uint256
kill_me 0xe3698853
No parameters
ramp_A_gamma 0x5e248072
uint256 future_A
uint256 future_gamma
uint256 future_time
remove_liquidity 0x5b36389c
uint256 _amount
uint256[2] min_amounts
remove_liquidity 0x269b5581
uint256 _amount
uint256[2] min_amounts
bool use_eth
remove_liquidity 0x1808e84a
uint256 _amount
uint256[2] min_amounts
bool use_eth
address receiver
remove_liquidity_one_coin 0xf1dc3cc9
uint256 token_amount
uint256 i
uint256 min_amount
returns: uint256
remove_liquidity_one_coin 0x8f15b6b5
uint256 token_amount
uint256 i
uint256 min_amount
bool use_eth
returns: uint256
remove_liquidity_one_coin 0x07329bcd
uint256 token_amount
uint256 i
uint256 min_amount
bool use_eth
address receiver
returns: uint256
revert_new_parameters 0x226840fb
No parameters
revert_transfer_ownership 0x86fbf193
No parameters
set_admin_fee_receiver 0x7242e524
address _admin_fee_receiver
stop_ramp_A_gamma 0x244c7c2e
No parameters
unkill_me 0x3046f972
No parameters

Token Balances (1)

View Transfers →
WETH 0

Recent Transactions

No transactions found for this address