Cryo Explorer Ethereum Mainnet

Address Contract Verified

Address 0xF4dA885744b6f3107CE13d2d30383dCe2eeA6C85
Balance 1.0497 ETH
Nonce 1
Code Size 14781 bytes
Indexed Transactions 0
External Etherscan · Sourcify

Contract Bytecode

14781 bytes
0x6080604052600436106101e75760003560e01c80636f1e853311610102578063a694fc3a11610095578063e268e4d311610064578063e268e4d314610703578063f2fde38b1461072c578063f93f3b6314610755578063fd5e6dd114610794576101ee565b8063a694fc3a1461065b578063b8e8f0e414610684578063c03d5b47146106af578063ce5494bb146106da576101ee565b806385141a77116100d157806385141a771461059f5780638da5cb5b146105ca5780639e2c8a5b146105f5578063a44bca8e1461061e576101ee565b80636f1e8533146104f5578063715018a61461053257806372f702f314610549578063817b1cd214610574576101ee565b80634a4a7b061161017a578063584b62a111610149578063584b62a1146104235780635a68c154146104625780635c975abb1461048d578063615171b9146104b8576101ee565b80634a4a7b06146103695780634e781513146103a65780635795f341146103cf57806357c26ba4146103fa576101ee565b8063303e6ece116101b6578063303e6ece146102ad578063372500ab146102ea5780633c364c7114610301578063453c23101461033e576101ee565b80630e15561a146101f357806316c38b3c1461021e5780631852e8d9146102475780631e9b12ef14610284576101ee565b366101ee57005b600080fd5b3480156101ff57600080fd5b506102086107d1565b6040516102159190612b2c565b60405180910390f35b34801561022a57600080fd5b5061024560048036038101906102409190612b84565b6107d7565b005b34801561025357600080fd5b5061026e60048036038101906102699190612c3b565b61084b565b60405161027b9190612b2c565b60405180910390f35b34801561029057600080fd5b506102ab60048036038101906102a69190612c7b565b61094a565b005b3480156102b957600080fd5b506102d460048036038101906102cf9190612c7b565b610a05565b6040516102e19190612da8565b60405180910390f35b3480156102f657600080fd5b506102ff610ac1565b005b34801561030d57600080fd5b5061032860048036038101906103239190612c7b565b610c9b565b6040516103359190612b2c565b60405180910390f35b34801561034a57600080fd5b50610353610d76565b6040516103609190612b2c565b60405180910390f35b34801561037557600080fd5b50610390600480360381019061038b9190612c7b565b610d7c565b60405161039d9190612b2c565b60405180910390f35b3480156103b257600080fd5b506103cd60048036038101906103c89190612dca565b610dfa565b005b3480156103db57600080fd5b506103e461136e565b6040516103f19190612b2c565b60405180910390f35b34801561040657600080fd5b50610421600480360381019061041c9190612e0a565b611374565b005b34801561042f57600080fd5b5061044a60048036038101906104459190612c3b565b611386565b60405161045993929190612e37565b60405180910390f35b34801561046e57600080fd5b506104776113cd565b6040516104849190612b2c565b60405180910390f35b34801561049957600080fd5b506104a26113d3565b6040516104af9190612e7d565b60405180910390f35b3480156104c457600080fd5b506104df60048036038101906104da9190612c7b565b6113ea565b6040516104ec9190612b2c565b60405180910390f35b34801561050157600080fd5b5061051c60048036038101906105179190612c7b565b6114c5565b6040516105299190612e7d565b60405180910390f35b34801561053e57600080fd5b506105476114e5565b005b34801561055557600080fd5b5061055e6114f9565b60405161056b9190612ef7565b60405180910390f35b34801561058057600080fd5b5061058961151f565b6040516105969190612b2c565b60405180910390f35b3480156105ab57600080fd5b506105b4611525565b6040516105c19190612f21565b60405180910390f35b3480156105d657600080fd5b506105df61152b565b6040516105ec9190612f21565b60405180910390f35b34801561060157600080fd5b5061061c60048036038101906106179190612dca565b611555565b005b34801561062a57600080fd5b5061064560048036038101906106409190612c7b565b611981565b6040516106529190612b2c565b60405180910390f35b34801561066757600080fd5b50610682600480360381019061067d9190612e0a565b611999565b005b34801561069057600080fd5b50610699611df6565b6040516106a69190612b2c565b60405180910390f35b3480156106bb57600080fd5b506106c4611e72565b6040516106d19190612b2c565b60405180910390f35b3480156106e657600080fd5b5061070160048036038101906106fc9190612c7b565b611e79565b005b34801561070f57600080fd5b5061072a60048036038101906107259190612e0a565b612176565b005b34801561073857600080fd5b50610753600480360381019061074e9190612c7b565b612188565b005b34801561076157600080fd5b5061077c60048036038101906107779190612c7b565b61220e565b60405161078b93929190612feb565b60405180910390f35b3480156107a057600080fd5b506107bb60048036038101906107b69190612e0a565b61241e565b6040516107c89190612f21565b60405180910390f35b60075481565b6107df61245d565b6107e76113d3565b15158115150361082c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161082390613086565b60405180910390fd5b801561083f5761083a6124e4565b610848565b610847612546565b5b50565b600080600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020838154811061089f5761089e6130a6565b5b9060005260206000209060030201905060008160010154426108c19190613104565b905062278d008111156108d55762278d0090505b600062278d00828460000154476108ec9190613138565b6108f69190613138565b61090091906131a9565b905060006008548261091291906131a9565b9050808460020154111561092d576000945050505050610944565b83600201548161093d9190613104565b9450505050505b92915050565b61095261245d565b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16036109c1576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016109b890613226565b60405180910390fd5b80600260006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6060600360008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805480602002602001604051908101604052809291908181526020016000905b82821015610ab65783829060005260206000209060030201604051806060016040529081600082015481526020016001820154815260200160028201548152505081526020019060010190610a66565b505050509050919050565b610ac96125a9565b6000600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002080549050905060008111610b53576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610b4a90613292565b60405180910390fd5b6000805b82811015610b8357610b6933826125ef565b82610b7491906132b2565b91508080600101915050610b57565b5060008111610b93575050610c91565b60003373ffffffffffffffffffffffffffffffffffffffff1682604051610bb990613317565b60006040518083038185875af1925050503d8060008114610bf6576040519150601f19603f3d011682016040523d82523d6000602084013e610bfb565b606091505b5050905080610c3f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610c3690613378565b60405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff167fe2403640ba68fed3a2f88b7557551d1993f84b99bb10ff833f0cf8db0c5e048683604051610c859190612b2c565b60405180910390a25050505b610c99612785565b565b6000806000905060005b600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002080549050811015610d6c57600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208181548110610d4057610d3f6130a6565b5b90600052602060002090600302016000015482610d5d91906132b2565b91508080600101915050610ca5565b5080915050919050565b600b5481565b6000805b600360008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002080549050811015610df4576000610dd6848361084b565b90508083610de491906132b2565b9250508080600101915050610d80565b50919050565b610e026125a9565b600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805490508210610e86576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610e7d906133e4565b60405180910390fd5b6000600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208381548110610ed957610ed86130a6565b5b906000526020600020906003020190508181600001541015610f30576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610f2790613450565b60405180910390fd5b6000816001015442610f429190613104565b905062278d008110610f89576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610f80906134e2565b60405180910390fd5b6000610f9533866125ef565b9050600081111561109c5760003373ffffffffffffffffffffffffffffffffffffffff1682604051610fc690613317565b60006040518083038185875af1925050503d8060008114611003576040519150601f19603f3d011682016040523d82523d6000602084013e611008565b606091505b505090508061104c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161104390613378565b60405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff167fe2403640ba68fed3a2f88b7557551d1993f84b99bb10ff833f0cf8db0c5e0486836040516110929190612b2c565b60405180910390a2505b600062278d00600954846110b09190613138565b6110ba91906131a9565b6009546110c79190613104565b90506000606482876110d99190613138565b6110e391906131a9565b9050600081876110f39190613104565b9050868660000160008282546111099190613104565b9250508190555086600860008282546111229190613104565b925050819055506000600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663a9059cbb61dead856040518363ffffffff1660e01b815260040161118a929190613502565b6020604051808303816000875af11580156111a9573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906111cd9190613540565b90508061120f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611206906135b9565b60405180910390fd5b6000600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663a9059cbb33856040518363ffffffff1660e01b815260040161126e929190613502565b6020604051808303816000875af115801561128d573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906112b19190613540565b9050806112f3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016112ea90613625565b60405180910390fd5b600088600001540361130a57611309338b61278f565b5b3373ffffffffffffffffffffffffffffffffffffffff167f7fc4727e062e336010f2c282598ef5f14facb3de68cf8195c2f23e1454b2b74e848c604051611352929190613645565b60405180910390a2505050505050505061136a612785565b5050565b60095481565b61137c61245d565b80600a8190555050565b600360205281600052604060002081815481106113a257600080fd5b9060005260206000209060030201600091509150508060000154908060010154908060020154905083565b600a5481565b6000600160149054906101000a900460ff16905090565b6000806000905060005b600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805490508110156114bb57600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020818154811061148f5761148e6130a6565b5b906000526020600020906003020160020154826114ac91906132b2565b915080806001019150506113f4565b5080915050919050565b60066020528060005260406000206000915054906101000a900460ff1681565b6114ed61245d565b6114f760006129c4565b565b600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b60085481565b61dead81565b6000600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b61155d6125a9565b600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208054905082106115e1576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016115d8906133e4565b60405180910390fd5b6000600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208381548110611634576116336130a6565b5b9060005260206000209060030201905062278d00816001015461165791906132b2565b421015611699576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611690906136ba565b60405180910390fd5b81816000015410156116e0576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016116d790613450565b60405180910390fd5b60006116ec33856125ef565b905060008111156117f35760003373ffffffffffffffffffffffffffffffffffffffff168260405161171d90613317565b60006040518083038185875af1925050503d806000811461175a576040519150601f19603f3d011682016040523d82523d6000602084013e61175f565b606091505b50509050806117a3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161179a90613378565b60405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff167fe2403640ba68fed3a2f88b7557551d1993f84b99bb10ff833f0cf8db0c5e0486836040516117e99190612b2c565b60405180910390a2505b828260000160008282546118079190613104565b9250508190555082600860008282546118209190613104565b92505081905550600082600001540361183e5761183d338561278f565b5b6000600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663a9059cbb33866040518363ffffffff1660e01b815260040161189d929190613502565b6020604051808303816000875af11580156118bc573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906118e09190613540565b905080611922576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161191990613625565b60405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff167f7fc4727e062e336010f2c282598ef5f14facb3de68cf8195c2f23e1454b2b74e858760405161196a929190613645565b60405180910390a250505061197d612785565b5050565b60046020528060005260406000206000915090505481565b6119a16125a9565b6119a9612a8a565b600081116119ec576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016119e390613726565b60405180910390fd5b600a54816008546119fd91906132b2565b1115611a3e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611a3590613792565b60405180910390fd5b6000611a4933610c9b565b9050600b548282611a5a91906132b2565b1115611a9b576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611a9290613792565b60405180910390fd5b600660003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16611ba8576005339080600181540180825580915050600190039060005260206000200160009091909190916101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506001600660003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055505b6000600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff166323b872dd3330866040518463ffffffff1660e01b8152600401611c09939291906137b2565b6020604051808303816000875af1158015611c28573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c4c9190613540565b905080611c8e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611c8590613625565b60405180910390fd5b600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060405180606001604052808581526020014281526020016000815250908060018154018082558091505060019003906000526020600020906003020160009091909190915060008201518160000155602082015181600101556040820151816002015550508260086000828254611d4491906132b2565b925050819055503373ffffffffffffffffffffffffffffffffffffffff167f1449c6dd7851abc30abf37f57715f492010519147cc2652fbc38202c18a6ee90846001600360003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002080549050611dd39190613104565b604051611de1929190613645565b60405180910390a25050611df3612785565b50565b6000805b600580549050811015611e6e57600060058281548110611e1d57611e1c6130a6565b5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff169050611e5381610d7c565b83611e5e91906132b2565b9250508080600101915050611dfa565b5090565b62278d0081565b611e8161245d565b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1603611ef0576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611ee790613226565b60405180910390fd5b6000600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff166370a08231306040518263ffffffff1660e01b8152600401611f4d9190612f21565b602060405180830381865afa158015611f6a573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611f8e91906137fe565b9050600260009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663a9059cbb83836040518363ffffffff1660e01b8152600401611fed929190613502565b6020604051808303816000875af115801561200c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906120309190613540565b61206f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016120669061389d565b60405180910390fd5b600047905060008373ffffffffffffffffffffffffffffffffffffffff168260405161209a90613317565b60006040518083038185875af1925050503d80600081146120d7576040519150601f19603f3d011682016040523d82523d6000602084013e6120dc565b606091505b5050905080612120576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161211790613909565b60405180910390fd5b8373ffffffffffffffffffffffffffffffffffffffff167fd083678824038160bef3975359ab29f19c3f0e9bcf9d7ead540a492d4d678b638484604051612168929190613645565b60405180910390a250505050565b61217e61245d565b80600b8190555050565b61219061245d565b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16036122025760006040517f1e4fbdf70000000000000000000000000000000000000000000000000000000081526004016121f99190612f21565b60405180910390fd5b61220b816129c4565b50565b60008060606000925060009150600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208054905067ffffffffffffffff81111561227757612276613929565b5b6040519080825280602002602001820160405280156122a55781602001602082028036833780820191505090505b50905060005b600360008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208054905081101561241657600360008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208181548110612346576123456130a6565b5b9060005260206000209060030201600001548461236391906132b2565b935061236f858261084b565b8361237a91906132b2565b9250600360008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081815481106123cd576123cc6130a6565b5b906000526020600020906003020160010154426123ea9190613104565b8282815181106123fd576123fc6130a6565b5b60200260200101818152505080806001019150506122ab565b509193909250565b6005818154811061242e57600080fd5b906000526020600020016000915054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b612465612acb565b73ffffffffffffffffffffffffffffffffffffffff1661248361152b565b73ffffffffffffffffffffffffffffffffffffffff16146124e2576124a6612acb565b6040517f118cdaa70000000000000000000000000000000000000000000000000000000081526004016124d99190612f21565b60405180910390fd5b565b6124ec612a8a565b60018060146101000a81548160ff0219169083151502179055507f62e78cea01bee320cd4e420270b5ea74000d11b0c9f74754ebdbfc544b05a25861252f612acb565b60405161253c9190612f21565b60405180910390a1565b61254e612ad3565b6000600160146101000a81548160ff0219169083151502179055507f5db9ee0a495bf2e6ff9c91a7834c1ba4fdd244a5e8aa4e537bd38aeae4b073aa612592612acb565b60405161259f9190612f21565b60405180910390a1565b6002600054036125e5576040517f3ee5aeb500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6002600081905550565b6000600360008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805490508210612675576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161266c906133e4565b60405180910390fd5b6000600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002083815481106126c8576126c76130a6565b5b9060005260206000209060030201905060006126e4858561084b565b9050600081111561277a578082600201600082825461270391906132b2565b9250508190555080600460008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825461275991906132b2565b92505081905550806007600082825461277291906132b2565b925050819055505b809250505092915050565b6001600081905550565b600360008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805490508110612813576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161280a906133e4565b60405180910390fd5b600360008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206001600360008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020805490506128a19190613104565b815481106128b2576128b16130a6565b5b9060005260206000209060030201600360008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208281548110612911576129106130a6565b5b9060005260206000209060030201600082015481600001556001820154816001015560028201548160020155905050600360008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002080548061298f5761298e613958565b5b600190038181906000526020600020906003020160008082016000905560018201600090556002820160009055505090555050565b6000600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905081600160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a35050565b612a926113d3565b15612ac9576040517fd93c066500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b565b600033905090565b612adb6113d3565b612b11576040517f8dfc202b00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b565b6000819050919050565b612b2681612b13565b82525050565b6000602082019050612b416000830184612b1d565b92915050565b600080fd5b60008115159050919050565b612b6181612b4c565b8114612b6c57600080fd5b50565b600081359050612b7e81612b58565b92915050565b600060208284031215612b9a57612b99612b47565b5b6000612ba884828501612b6f565b91505092915050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000612bdc82612bb1565b9050919050565b612bec81612bd1565b8114612bf757600080fd5b50565b600081359050612c0981612be3565b92915050565b612c1881612b13565b8114612c2357600080fd5b50565b600081359050612c3581612c0f565b92915050565b60008060408385031215612c5257612c51612b47565b5b6000612c6085828601612bfa565b9250506020612c7185828601612c26565b9150509250929050565b600060208284031215612c9157612c90612b47565b5b6000612c9f84828501612bfa565b91505092915050565b600081519050919050565b600082825260208201905092915050565b6000819050602082019050919050565b612cdd81612b13565b82525050565b606082016000820151612cf96000850182612cd4565b506020820151612d0c6020850182612cd4565b506040820151612d1f6040850182612cd4565b50505050565b6000612d318383612ce3565b60608301905092915050565b6000602082019050919050565b6000612d5582612ca8565b612d5f8185612cb3565b9350612d6a83612cc4565b8060005b83811015612d9b578151612d828882612d25565b9750612d8d83612d3d565b925050600181019050612d6e565b5085935050505092915050565b60006020820190508181036000830152612dc28184612d4a565b905092915050565b60008060408385031215612de157612de0612b47565b5b6000612def85828601612c26565b9250506020612e0085828601612c26565b9150509250929050565b600060208284031215612e2057612e1f612b47565b5b6000612e2e84828501612c26565b91505092915050565b6000606082019050612e4c6000830186612b1d565b612e596020830185612b1d565b612e666040830184612b1d565b949350505050565b612e7781612b4c565b82525050565b6000602082019050612e926000830184612e6e565b92915050565b6000819050919050565b6000612ebd612eb8612eb384612bb1565b612e98565b612bb1565b9050919050565b6000612ecf82612ea2565b9050919050565b6000612ee182612ec4565b9050919050565b612ef181612ed6565b82525050565b6000602082019050612f0c6000830184612ee8565b92915050565b612f1b81612bd1565b82525050565b6000602082019050612f366000830184612f12565b92915050565b600081519050919050565b600082825260208201905092915050565b6000819050602082019050919050565b6000612f748383612cd4565b60208301905092915050565b6000602082019050919050565b6000612f9882612f3c565b612fa28185612f47565b9350612fad83612f58565b8060005b83811015612fde578151612fc58882612f68565b9750612fd083612f80565b925050600181019050612fb1565b5085935050505092915050565b60006060820190506130006000830186612b1d565b61300d6020830185612b1d565b818103604083015261301f8184612f8d565b9050949350505050565b600082825260208201905092915050565b7f416c726561647920696e20746865207265717565737465642073746174650000600082015250565b6000613070601e83613029565b915061307b8261303a565b602082019050919050565b6000602082019050818103600083015261309f81613063565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b600061310f82612b13565b915061311a83612b13565b9250828203905081811115613132576131316130d5565b5b92915050565b600061314382612b13565b915061314e83612b13565b925082820261315c81612b13565b91508282048414831517613173576131726130d5565b5b5092915050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b60006131b482612b13565b91506131bf83612b13565b9250826131cf576131ce61317a565b5b828204905092915050565b7f496e76616c696420616464726573730000000000000000000000000000000000600082015250565b6000613210600f83613029565b915061321b826131da565b602082019050919050565b6000602082019050818103600083015261323f81613203565b9050919050565b7f4e6f207374616b657320617661696c61626c6500000000000000000000000000600082015250565b600061327c601383613029565b915061328782613246565b602082019050919050565b600060208201905081810360008301526132ab8161326f565b9050919050565b60006132bd82612b13565b91506132c883612b13565b92508282019050808211156132e0576132df6130d5565b5b92915050565b600081905092915050565b50565b60006133016000836132e6565b915061330c826132f1565b600082019050919050565b6000613322826132f4565b9150819050919050565b7f4661696c656420746f2073656e64204574686572000000000000000000000000600082015250565b6000613362601483613029565b915061336d8261332c565b602082019050919050565b6000602082019050818103600083015261339181613355565b9050919050565b7f496e76616c6964207374616b6520696e64657800000000000000000000000000600082015250565b60006133ce601383613029565b91506133d982613398565b602082019050919050565b600060208201905081810360008301526133fd816133c1565b9050919050565b7f496e73756666696369656e74207374616b656420616d6f756e74000000000000600082015250565b600061343a601a83613029565b915061344582613404565b602082019050919050565b600060208201905081810360008301526134698161342d565b9050919050565b7f5374616b65206973206e6f7420696e206561726c7920756e7374616b6520706560008201527f72696f6400000000000000000000000000000000000000000000000000000000602082015250565b60006134cc602483613029565b91506134d782613470565b604082019050919050565b600060208201905081810360008301526134fb816134bf565b9050919050565b60006040820190506135176000830185612f12565b6135246020830184612b1d565b9392505050565b60008151905061353a81612b58565b92915050565b60006020828403121561355657613555612b47565b5b60006135648482850161352b565b91505092915050565b7f4661696c656420746f206275726e20746f6b656e730000000000000000000000600082015250565b60006135a3601583613029565b91506135ae8261356d565b602082019050919050565b600060208201905081810360008301526135d281613596565b9050919050565b7f4661696c656420746f207472616e7366657220746f6b656e7300000000000000600082015250565b600061360f601983613029565b915061361a826135d9565b602082019050919050565b6000602082019050818103600083015261363e81613602565b9050919050565b600060408201905061365a6000830185612b1d565b6136676020830184612b1d565b9392505050565b7f5374616b65206973207374696c6c206c6f636b65640000000000000000000000600082015250565b60006136a4601583613029565b91506136af8261366e565b602082019050919050565b600060208201905081810360008301526136d381613697565b9050919050565b7f416d6f756e74206d7573742062652067726561746572207468616e2030000000600082015250565b6000613710601d83613029565b915061371b826136da565b602082019050919050565b6000602082019050818103600083015261373f81613703565b9050919050565b7f5374616b696e67206c696d697420657863656564656400000000000000000000600082015250565b600061377c601683613029565b915061378782613746565b602082019050919050565b600060208201905081810360008301526137ab8161376f565b9050919050565b60006060820190506137c76000830186612f12565b6137d46020830185612f12565b6137e16040830184612b1d565b949350505050565b6000815190506137f881612c0f565b92915050565b60006020828403121561381457613813612b47565b5b6000613822848285016137e9565b91505092915050565b7f4661696c656420746f207472616e7366657220746f6b656e7320746f206f776e60008201527f6572000000000000000000000000000000000000000000000000000000000000602082015250565b6000613887602283613029565b91506138928261382b565b604082019050919050565b600060208201905081810360008301526138b68161387a565b9050919050565b7f4661696c656420746f207472616e736665722045544800000000000000000000600082015250565b60006138f3601683613029565b91506138fe826138bd565b602082019050919050565b60006020820190508181036000830152613922816138e6565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fdfea2646970667358221220d714163ac25a3d4d2b952271a8d55fbf570309db0419013cd5542bdd91f42e7b64736f6c63430008180033

Verified Source Code Full Match

Compiler: v0.8.24+commit.e11b9ed9 EVM: paris Optimization: No
NodeStaking.sol 347 lines
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.24;

import '@openzeppelin/contracts/utils/ReentrancyGuard.sol';
import '@openzeppelin/contracts/access/Ownable.sol';
import '@openzeppelin/contracts/utils/Pausable.sol';

interface IERC20 {
  function transfer(address recipient, uint256 amount) external returns (bool);

  function transferFrom(
    address sender,
    address recipient,
    uint256 amount
  ) external returns (bool);

  function balanceOf(address account) external view returns (uint256);

  function approve(address spender, uint256 value) external returns (bool);
}

contract NodeStaking is ReentrancyGuard, Ownable, Pausable {
  IERC20 public stakingToken;

  struct Stake {
    uint256 amount;
    uint256 startTime;
    uint256 rewardPaid;
  }

  mapping(address => Stake[]) public stakes;
  mapping(address => uint256) public totalUserRewards;

  address[] public stakers;
  mapping(address => bool) public isStaker;

  uint256 public totalRewards = 0;

  uint256 public totalStaked;

  uint256 public earlyUnstakePenality = 30;

  uint256 public maxTotalStaked = 10_000_000 * (10 ** 18); // Example: 10 million tokens
  uint256 public maxPerWallet = 1_000 * (10 ** 18); // Example: 1,000 tokens per wallet

  uint256 public constant stakingPeriod = 30 days;
  address public constant deadWallet =
    0x000000000000000000000000000000000000dEaD;

  event Staked(address indexed user, uint256 amount, uint256 index);
  event Unstaked(address indexed user, uint256 amount, uint256 index);
  event RewardPaid(address indexed user, uint256 reward);
  event Migrated(
    address indexed newStakingContract,
    uint256 tokenAmount,
    uint256 ethAmount
  );

  /* Initializes the constructure with the staking token set and owner */
  constructor(address _stakingToken) Ownable(_msgSender()) {
    stakingToken = IERC20(_stakingToken);
  }

  /* Sets the staking token */
  function setStakingToken(address _stakingToken) external onlyOwner {
    require(_stakingToken != address(0), 'Invalid address');

    stakingToken = IERC20(_stakingToken);
  }

  /* Sets the maximum total staked amount */
  function setMaxTotalStaked(uint256 _maxTotalStaked) external onlyOwner {
    maxTotalStaked = _maxTotalStaked;
  }

  /* Sets the maximum staked amount per wallet */
  function setMaxPerWallet(uint256 _maxPerWallet) external onlyOwner {
    maxPerWallet = _maxPerWallet;
  }

  /* Sets the pause state of the contract */
  function setPaused(bool _paused) external onlyOwner {
    require(_paused != paused(), 'Already in the requested state');

    if (_paused) {
      _pause();
    } else {
      _unpause();
    }
  }

  /* Migrates the staking contract to a new contract */
  function migrate(address _newStakingContract) external onlyOwner {
    require(_newStakingContract != address(0), 'Invalid address');

    uint256 contractTokenBalance = stakingToken.balanceOf(address(this));
    require(
      stakingToken.transfer(_newStakingContract, contractTokenBalance),
      'Failed to transfer tokens to owner'
    );

    uint256 contractETHBalance = address(this).balance;
    (bool sent, ) = _newStakingContract.call{value: contractETHBalance}('');

    require(sent, 'Failed to transfer ETH');

    emit Migrated(
      _newStakingContract,
      contractTokenBalance,
      contractETHBalance
    );
  }

  function stake(uint256 _amount) external nonReentrant whenNotPaused {
    require(_amount > 0, 'Amount must be greater than 0');
    require(totalStaked + _amount <= maxTotalStaked, 'Staking limit exceeded');

    uint256 walletStaked = getWalletStaked(msg.sender);
    require(walletStaked + _amount <= maxPerWallet, 'Staking limit exceeded');

    if(!isStaker[msg.sender]) {
      stakers.push(msg.sender);
      isStaker[msg.sender] = true;
    }

    bool success = stakingToken.transferFrom(msg.sender, address(this), _amount);
    require(success, 'Failed to transfer tokens');
    stakes[msg.sender].push(Stake(_amount, block.timestamp, 0));
    totalStaked += _amount;

    emit Staked(msg.sender, _amount, stakes[msg.sender].length - 1);
  }

  function unstake(uint256 _index, uint256 _amount) external nonReentrant {
    require(_index < stakes[msg.sender].length, 'Invalid stake index');

    Stake storage userStake = stakes[msg.sender][_index];

    require(
      block.timestamp >= userStake.startTime + stakingPeriod,
      'Stake is still locked'
    );

    require(userStake.amount >= _amount, 'Insufficient staked amount');

    uint256 reward = _claimRewards(msg.sender, _index);

    if(reward > 0) {
      (bool sent, ) = payable(msg.sender).call{value: reward}('');
      require(sent, 'Failed to send Ether');

      emit RewardPaid(msg.sender, reward);
    }

    userStake.amount -= _amount;
    totalStaked -= _amount;

    if (userStake.amount == 0) {
      removeStake(msg.sender, _index);
    }

    bool success = stakingToken.transfer(msg.sender, _amount);
    require(success, 'Failed to transfer tokens');
    emit Unstaked(msg.sender, _amount, _index);
  }

  function earlyUnstake(uint256 _index, uint256 _amount) external nonReentrant {
    require(_index < stakes[msg.sender].length, 'Invalid stake index');

    Stake storage userStake = stakes[msg.sender][_index];
    require(userStake.amount >= _amount, 'Insufficient staked amount');

    uint256 timeElapsed = block.timestamp - userStake.startTime;
    require(
      timeElapsed < stakingPeriod,
      'Stake is not in early unstake period'
    );

    uint256 reward = _claimRewards(msg.sender, _index);

    if(reward > 0) {
      (bool sent, ) = payable(msg.sender).call{value: reward}('');
      require(sent, 'Failed to send Ether');

      emit RewardPaid(msg.sender, reward);
    }

    // Calculate the penalty fee, which linearly decreases from 50% to 0% over the lock-up period
    uint256 penaltyPercentage = earlyUnstakePenality -
      ((timeElapsed * earlyUnstakePenality) / stakingPeriod);
    uint256 penaltyAmount = (_amount * penaltyPercentage) / 100;

    // Apply the penalty
    uint256 returnAmount = _amount - penaltyAmount;

    // Update the stake and total staked amount
    userStake.amount -= _amount;
    totalStaked -= _amount;

    // Burn the penalty amount
    bool successBurn = stakingToken.transfer(deadWallet, penaltyAmount);
    require(successBurn, 'Failed to burn tokens');

    // Return the remaining tokens to the user
    bool sucessUnstake = stakingToken.transfer(msg.sender, returnAmount);
    require(sucessUnstake, 'Failed to transfer tokens');

    // Remove the stake if it's fully unstaked
    if (userStake.amount == 0) {
      removeStake(msg.sender, _index);
    }

    emit Unstaked(msg.sender, returnAmount, _index);
  }

  function _claimRewards(
    address user,
    uint256 index
  ) private returns (uint256) {
    require(index < stakes[user].length, 'Invalid stake index');

    Stake storage userStake = stakes[user][index];
    uint256 reward = calculateReward(user, index);

    if (reward > 0) {
      userStake.rewardPaid += reward;
      totalUserRewards[user] += reward;
      totalRewards += reward;
    }

    return reward;
  }

  function claimRewards() external nonReentrant {
    uint256 stakeCount = stakes[msg.sender].length;
    require(stakeCount > 0, 'No stakes available');

    uint256 totalReward = 0;
    for (uint256 i = 0; i < stakeCount; i++) {
      totalReward += _claimRewards(msg.sender, i); // Aggregate rewards
    }

    if(totalReward <= 0) {
      return;
    }

    (bool sent, ) = payable(msg.sender).call{value: totalReward}('');
    require(sent, 'Failed to send Ether');

    emit RewardPaid(msg.sender, totalReward);
  }

  function getWalletStaked(address _user) public view returns (uint256) {
    uint256 walletStaked = 0;

    for (uint256 i = 0; i < stakes[_user].length; i++) {
      walletStaked += stakes[_user][i].amount;
    }

    return walletStaked;
  }

  function getWalletReward(address _user) public view returns (uint256) {
    uint256 walletReward = 0;

    for (uint256 i = 0; i < stakes[_user].length; i++) {
      walletReward += stakes[_user][i].rewardPaid;
    }

    return walletReward;
  }

  function getWalletStakes(address _user) public view returns (Stake[] memory) {
    return stakes[_user];
  }

  function getWalletClaimableRewards(
    address _user
  ) public view returns (uint256 totalClaimable) {
    totalClaimable = 0;
    for (uint256 i = 0; i < stakes[_user].length; i++) {
      uint256 reward = calculateReward(_user, i);
      totalClaimable += reward;
    }
  }

  function calculateAllPendingRewards() public view returns (uint256 totalClaimable) {
    totalClaimable = 0;
    for (uint256 i = 0; i < stakers.length; i++) {
      address staker = stakers[i];
      totalClaimable += getWalletClaimableRewards(staker);
    }
  }

  function calculateReward(
    address _user,
    uint256 _index
  ) public view returns (uint256) {
    Stake storage userStake = stakes[_user][_index];
    uint256 stakeDuration = block.timestamp - userStake.startTime;
    if (stakeDuration > stakingPeriod) {
      stakeDuration = stakingPeriod; // Cap the stake duration to the lock-up period for reward calculation
    }
    // Scale the numerator before dividing
    uint256 scaledReward = (address(this).balance *
      userStake.amount *
      stakeDuration) / stakingPeriod;
    uint256 reward = scaledReward / totalStaked;

    if(userStake.rewardPaid > reward) {
      return 0;
    }

    return reward - userStake.rewardPaid; // Assuming rewardPaid is correctly managed elsewhere
  }

  function getUserStakingDetails(
    address _user
  )
    public
    view
    returns (
      uint256 _totalStaked,
      uint256 totalRewardsInEth,
      uint256[] memory timeElapsedPerStake
    )
  {
    _totalStaked = 0;
    totalRewardsInEth = 0;
    timeElapsedPerStake = new uint256[](stakes[_user].length);

    for (uint256 i = 0; i < stakes[_user].length; i++) {
      _totalStaked += stakes[_user][i].amount;
      totalRewardsInEth += calculateReward(_user, i); // This should return ETH rewards
      timeElapsedPerStake[i] = block.timestamp - stakes[_user][i].startTime;
    }
  }

  function removeStake(address _user, uint256 _index) private {
    require(_index < stakes[_user].length, 'Invalid stake index');

    stakes[_user][_index] = stakes[_user][stakes[_user].length - 1];
    stakes[_user].pop();
  }

  receive() external payable {}
}
Context.sol 28 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.1) (utils/Context.sol)

pragma solidity ^0.8.20;

/**
 * @dev Provides information about the current execution context, including the
 * sender of the transaction and its data. While these are generally available
 * via msg.sender and msg.data, they should not be accessed in such a direct
 * manner, since when dealing with meta-transactions the account sending and
 * paying for execution may not be the actual sender (as far as an application
 * is concerned).
 *
 * This contract is only required for intermediate, library-like contracts.
 */
abstract contract Context {
    function _msgSender() internal view virtual returns (address) {
        return msg.sender;
    }

    function _msgData() internal view virtual returns (bytes calldata) {
        return msg.data;
    }

    function _contextSuffixLength() internal view virtual returns (uint256) {
        return 0;
    }
}
Ownable.sol 100 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (access/Ownable.sol)

pragma solidity ^0.8.20;

import {Context} from "../utils/Context.sol";

/**
 * @dev Contract module which provides a basic access control mechanism, where
 * there is an account (an owner) that can be granted exclusive access to
 * specific functions.
 *
 * The initial owner is set to the address provided by the deployer. This can
 * later be changed with {transferOwnership}.
 *
 * This module is used through inheritance. It will make available the modifier
 * `onlyOwner`, which can be applied to your functions to restrict their use to
 * the owner.
 */
abstract contract Ownable is Context {
    address private _owner;

    /**
     * @dev The caller account is not authorized to perform an operation.
     */
    error OwnableUnauthorizedAccount(address account);

    /**
     * @dev The owner is not a valid owner account. (eg. `address(0)`)
     */
    error OwnableInvalidOwner(address owner);

    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);

    /**
     * @dev Initializes the contract setting the address provided by the deployer as the initial owner.
     */
    constructor(address initialOwner) {
        if (initialOwner == address(0)) {
            revert OwnableInvalidOwner(address(0));
        }
        _transferOwnership(initialOwner);
    }

    /**
     * @dev Throws if called by any account other than the owner.
     */
    modifier onlyOwner() {
        _checkOwner();
        _;
    }

    /**
     * @dev Returns the address of the current owner.
     */
    function owner() public view virtual returns (address) {
        return _owner;
    }

    /**
     * @dev Throws if the sender is not the owner.
     */
    function _checkOwner() internal view virtual {
        if (owner() != _msgSender()) {
            revert OwnableUnauthorizedAccount(_msgSender());
        }
    }

    /**
     * @dev Leaves the contract without owner. It will not be possible to call
     * `onlyOwner` functions. Can only be called by the current owner.
     *
     * NOTE: Renouncing ownership will leave the contract without an owner,
     * thereby disabling any functionality that is only available to the owner.
     */
    function renounceOwnership() public virtual onlyOwner {
        _transferOwnership(address(0));
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`).
     * Can only be called by the current owner.
     */
    function transferOwnership(address newOwner) public virtual onlyOwner {
        if (newOwner == address(0)) {
            revert OwnableInvalidOwner(address(0));
        }
        _transferOwnership(newOwner);
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`).
     * Internal function without access restriction.
     */
    function _transferOwnership(address newOwner) internal virtual {
        address oldOwner = _owner;
        _owner = newOwner;
        emit OwnershipTransferred(oldOwner, newOwner);
    }
}
Pausable.sol 119 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/Pausable.sol)

pragma solidity ^0.8.20;

import {Context} from "../utils/Context.sol";

/**
 * @dev Contract module which allows children to implement an emergency stop
 * mechanism that can be triggered by an authorized account.
 *
 * This module is used through inheritance. It will make available the
 * modifiers `whenNotPaused` and `whenPaused`, which can be applied to
 * the functions of your contract. Note that they will not be pausable by
 * simply including this module, only once the modifiers are put in place.
 */
abstract contract Pausable is Context {
    bool private _paused;

    /**
     * @dev Emitted when the pause is triggered by `account`.
     */
    event Paused(address account);

    /**
     * @dev Emitted when the pause is lifted by `account`.
     */
    event Unpaused(address account);

    /**
     * @dev The operation failed because the contract is paused.
     */
    error EnforcedPause();

    /**
     * @dev The operation failed because the contract is not paused.
     */
    error ExpectedPause();

    /**
     * @dev Initializes the contract in unpaused state.
     */
    constructor() {
        _paused = false;
    }

    /**
     * @dev Modifier to make a function callable only when the contract is not paused.
     *
     * Requirements:
     *
     * - The contract must not be paused.
     */
    modifier whenNotPaused() {
        _requireNotPaused();
        _;
    }

    /**
     * @dev Modifier to make a function callable only when the contract is paused.
     *
     * Requirements:
     *
     * - The contract must be paused.
     */
    modifier whenPaused() {
        _requirePaused();
        _;
    }

    /**
     * @dev Returns true if the contract is paused, and false otherwise.
     */
    function paused() public view virtual returns (bool) {
        return _paused;
    }

    /**
     * @dev Throws if the contract is paused.
     */
    function _requireNotPaused() internal view virtual {
        if (paused()) {
            revert EnforcedPause();
        }
    }

    /**
     * @dev Throws if the contract is not paused.
     */
    function _requirePaused() internal view virtual {
        if (!paused()) {
            revert ExpectedPause();
        }
    }

    /**
     * @dev Triggers stopped state.
     *
     * Requirements:
     *
     * - The contract must not be paused.
     */
    function _pause() internal virtual whenNotPaused {
        _paused = true;
        emit Paused(_msgSender());
    }

    /**
     * @dev Returns to normal state.
     *
     * Requirements:
     *
     * - The contract must be paused.
     */
    function _unpause() internal virtual whenPaused {
        _paused = false;
        emit Unpaused(_msgSender());
    }
}
ReentrancyGuard.sol 84 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/ReentrancyGuard.sol)

pragma solidity ^0.8.20;

/**
 * @dev Contract module that helps prevent reentrant calls to a function.
 *
 * Inheriting from `ReentrancyGuard` will make the {nonReentrant} modifier
 * available, which can be applied to functions to make sure there are no nested
 * (reentrant) calls to them.
 *
 * Note that because there is a single `nonReentrant` guard, functions marked as
 * `nonReentrant` may not call one another. This can be worked around by making
 * those functions `private`, and then adding `external` `nonReentrant` entry
 * points to them.
 *
 * TIP: If you would like to learn more about reentrancy and alternative ways
 * to protect against it, check out our blog post
 * https://blog.openzeppelin.com/reentrancy-after-istanbul/[Reentrancy After Istanbul].
 */
abstract contract ReentrancyGuard {
    // Booleans are more expensive than uint256 or any type that takes up a full
    // word because each write operation emits an extra SLOAD to first read the
    // slot's contents, replace the bits taken up by the boolean, and then write
    // back. This is the compiler's defense against contract upgrades and
    // pointer aliasing, and it cannot be disabled.

    // The values being non-zero value makes deployment a bit more expensive,
    // but in exchange the refund on every call to nonReentrant will be lower in
    // amount. Since refunds are capped to a percentage of the total
    // transaction's gas, it is best to keep them low in cases like this one, to
    // increase the likelihood of the full refund coming into effect.
    uint256 private constant NOT_ENTERED = 1;
    uint256 private constant ENTERED = 2;

    uint256 private _status;

    /**
     * @dev Unauthorized reentrant call.
     */
    error ReentrancyGuardReentrantCall();

    constructor() {
        _status = NOT_ENTERED;
    }

    /**
     * @dev Prevents a contract from calling itself, directly or indirectly.
     * Calling a `nonReentrant` function from another `nonReentrant`
     * function is not supported. It is possible to prevent this from happening
     * by making the `nonReentrant` function external, and making it call a
     * `private` function that does the actual work.
     */
    modifier nonReentrant() {
        _nonReentrantBefore();
        _;
        _nonReentrantAfter();
    }

    function _nonReentrantBefore() private {
        // On the first call to nonReentrant, _status will be NOT_ENTERED
        if (_status == ENTERED) {
            revert ReentrancyGuardReentrantCall();
        }

        // Any calls to nonReentrant after this point will fail
        _status = ENTERED;
    }

    function _nonReentrantAfter() private {
        // By storing the original value once again, a refund is triggered (see
        // https://eips.ethereum.org/EIPS/eip-2200)
        _status = NOT_ENTERED;
    }

    /**
     * @dev Returns true if the reentrancy guard is currently set to "entered", which indicates there is a
     * `nonReentrant` function in the call stack.
     */
    function _reentrancyGuardEntered() internal view returns (bool) {
        return _status == ENTERED;
    }
}

Read Contract

calculateAllPendingRewards 0xb8e8f0e4 → uint256
calculateReward 0x1852e8d9 → uint256
deadWallet 0x85141a77 → address
earlyUnstakePenality 0x5795f341 → uint256
getUserStakingDetails 0xf93f3b63 → uint256, uint256, uint256[]
getWalletClaimableRewards 0x4a4a7b06 → uint256
getWalletReward 0x615171b9 → uint256
getWalletStaked 0x3c364c71 → uint256
getWalletStakes 0x303e6ece → tuple[]
isStaker 0x6f1e8533 → bool
maxPerWallet 0x453c2310 → uint256
maxTotalStaked 0x5a68c154 → uint256
owner 0x8da5cb5b → address
paused 0x5c975abb → bool
stakers 0xfd5e6dd1 → address
stakes 0x584b62a1 → uint256, uint256, uint256
stakingPeriod 0xc03d5b47 → uint256
stakingToken 0x72f702f3 → address
totalRewards 0x0e15561a → uint256
totalStaked 0x817b1cd2 → uint256
totalUserRewards 0xa44bca8e → uint256

Write Contract 11 functions

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

claimRewards 0x372500ab
No parameters
earlyUnstake 0x4e781513
uint256 _index
uint256 _amount
migrate 0xce5494bb
address _newStakingContract
renounceOwnership 0x715018a6
No parameters
setMaxPerWallet 0xe268e4d3
uint256 _maxPerWallet
setMaxTotalStaked 0x57c26ba4
uint256 _maxTotalStaked
setPaused 0x16c38b3c
bool _paused
setStakingToken 0x1e9b12ef
address _stakingToken
stake 0xa694fc3a
uint256 _amount
transferOwnership 0xf2fde38b
address newOwner
unstake 0x9e2c8a5b
uint256 _index
uint256 _amount

Token Balances (1)

View Transfers →
WETH 0

Recent Transactions

No transactions found for this address