tx · 4MhhyvP8Xj3rktJ7FGKE5SyeYDBjd5zzsPfTN7PC8Z63

3Mx3zmXrMcLFCafMuPtXAzR4ZPVeZYb6qLz:  -0.03500000 Waves

2022.06.27 23:54 [2115345] smart account 3Mx3zmXrMcLFCafMuPtXAzR4ZPVeZYb6qLz > SELF 0.00000000 Waves

{ "type": 13, "id": "4MhhyvP8Xj3rktJ7FGKE5SyeYDBjd5zzsPfTN7PC8Z63", "fee": 3500000, "feeAssetId": null, "timestamp": 1656363263755, "version": 2, "chainId": 84, "sender": "3Mx3zmXrMcLFCafMuPtXAzR4ZPVeZYb6qLz", "senderPublicKey": "D28XoueZWsMfm8Y5pa6C5ZFuYoWgre2Wm8tzJANJgMnq", "proofs": [ "2ocXqipqntNiBU36iRWsvs2MYmpiAuniRpM5YcxaYvqjFYiEBiSFQzrEfoNMo3NmDCdkHBZnEeytYJzdYjUxemWo" ], "script": "base64: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YXRjaDAJAAQdAAAAAgUAAAAHYWRkcmVzcwUAAAADa2V5AwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAAZTdHJpbmcEAAAAAXMFAAAAByRtYXRjaDAJAQAAAAV2YWx1ZQAAAAEJAAGoAAAAAQUAAAABcwMJAAABAAAAAgUAAAAHJG1hdGNoMAIAAAAEVW5pdAUAAAAKZGVmYXVsdFZhbAkAAAIAAAABAgAAAAtNYXRjaCBlcnJvcgEAAAAFdG9YMTgAAAACAAAAB29yaWdWYWwAAAANb3JpZ1NjYWxlTXVsdAkAATwAAAADCQABNgAAAAEFAAAAB29yaWdWYWwFAAAABk1VTFQxOAkAATYAAAABBQAAAA1vcmlnU2NhbGVNdWx0AQAAAAdmcm9tWDE4AAAAAgAAAAN2YWwAAAAPcmVzdWx0U2NhbGVNdWx0CQABoAAAAAEJAAE8AAAAAwUAAAADdmFsCQABNgAAAAEFAAAAD3Jlc3VsdFNjYWxlTXVsdAUAAAAGTVVMVDE4AQAAABFrZXlGYWN0b3J5QWRkcmVzcwAAAAACAAAAHCVzJXNfX2NvbmZpZ19fZmFjdG9yeUFkZHJlc3MAAAAAGElkeEZhY3RvcnlDZmdTdGFraW5nRGFwcAAAAAAAAAAAAQAAAAAZSWR4RmFjdG9yeUNmZ0Jvb3N0aW5nRGFwcAAAAAAAAAAAAgAAAAAUSWR4RmFjdG9yeUNmZ0lkb0RhcHAAAAAAAAAAAAMAAAAAFUlkeEZhY3RvcnlDZmdUZWFtRGFwcAAAAAAAAAAABAAAAAAZSWR4RmFjdG9yeUNmZ0VtaXNzaW9uRGFwcAAAAAAAAAAABQAAAAAVSWR4RmFjdG9yeUNmZ1Jlc3REYXBwAAAAAAAAAAAGAAAAABlJZHhGYWN0b3J5Q2ZnU2xpcHBhZ2VEYXBwAAAAAAAAAAAHAQAAAA1rZXlGYWN0b3J5Q2ZnAAAAAAIAAAARJXNfX2ZhY3RvcnlDb25maWcBAAAAE2tleU1hbmFnZXJQdWJsaWNLZXkAAAAAAgAAABQlc19fbWFuYWdlclB1YmxpY0tleQEAAAAUa2V5TWlncmF0b3JQdWJsaWNLZXkAAAAAAgAAABUlc19fbWlncmF0b3JQdWJsaWNLZXkBAAAAGmtleVBlbmRpbmdNYW5hZ2VyUHVibGljS2V5AAAAAAIAAAAbJXNfX3BlbmRpbmdNYW5hZ2VyUHVibGljS2V5AQAAABZrZXlTdGFibGVQb29sQWRkb25BZGRyAAAAAAIAAAAXJXNfX3N0YWJsZVBvb2xBZGRvbkFkZHIBAAAAGmtleUZhY3RvcnlMcDJBc3NldHNNYXBwaW5nAAAAAQAAAApscEFzc2V0U3RyCQAEuQAAAAIJAARMAAAAAgIAAAAGJXMlcyVzCQAETAAAAAIFAAAACmxwQXNzZXRTdHIJAARMAAAAAgIAAAAebWFwcGluZ3NfX2xwQXNzZXQyUG9vbENvbnRyYWN0BQAAAANuaWwFAAAAA1NFUAEAAAAQa2V5RmFjdG9yeUxwTGlzdAAAAAACAAAAECVzX19scFRva2Vuc0xpc3QBAAAAJmtleUZhY3RvcnlMcEFzc2V0VG9Qb29sQ29udHJhY3RBZGRyZXNzAAAAAQAAAApscEFzc2V0U3RyCQAEuQAAAAIJAARMAAAAAgIAAAAGJXMlcyVzCQAETAAAAAIFAAAACmxwQXNzZXRTdHIJAARMAAAAAgIAAAAebWFwcGluZ3NfX2xwQXNzZXQyUG9vbENvbnRyYWN0BQAAAANuaWwFAAAAA1NFUAEAAAAUa2V5RmFjdG9yeVBvb2xXZWlnaHQAAAABAAAAD2NvbnRyYWN0QWRkcmVzcwkABLkAAAACCQAETAAAAAICAAAABCVzJXMJAARMAAAAAgIAAAAKcG9vbFdlaWdodAkABEwAAAACBQAAAA9jb250cmFjdEFkZHJlc3MFAAAAA25pbAUAAAADU0VQAQAAAApyZWFkTHBMaXN0AAAAAQAAAAdmYWN0b3J5CQAEtQAAAAIJAQAAAAt2YWx1ZU9yRWxzZQAAAAIJAAQdAAAAAgUAAAAHZmFjdG9yeQkBAAAAEGtleUZhY3RvcnlMcExpc3QAAAAAAgAAAAAFAAAAA1NFUAEAAAAUcmVhZEZhY3RvcnlDZmdPckZhaWwAAAABAAAAB2ZhY3RvcnkJAAS1AAAAAgkBAAAAGGdldFN0cmluZ0J5QWRkcmVzc09yRmFpbAAAAAIFAAAAB2ZhY3RvcnkJAQAAAA1rZXlGYWN0b3J5Q2ZnAAAAAAUAAAADU0VQAQAAABhnZXRCb29zdGluZ0FkZHJlc3NPckZhaWwAAAABAAAACmZhY3RvcnlDZmcJAQAAABFAZXh0ck5hdGl2ZSgxMDYyKQAAAAEJAAGRAAAAAgUAAAAKZmFjdG9yeUNmZwUAAAAZSWR4RmFjdG9yeUNmZ0Jvb3N0aW5nRGFwcAEAAAAYZ2V0RW1pc3Npb25BZGRyZXNzT3JGYWlsAAAAAQAAAApmYWN0b3J5Q2ZnCQEAAAARQGV4dHJOYXRpdmUoMTA2MikAAAABCQABkQAAAAIFAAAACmZhY3RvcnlDZmcFAAAAGUlkeEZhY3RvcnlDZmdFbWlzc2lvbkRhcHABAAAAF2dldFN0YWtpbmdBZGRyZXNzT3JGYWlsAAAAAQAAAApmYWN0b3J5Q2ZnCQEAAAARQGV4dHJOYXRpdmUoMTA2MikAAAABCQABkQAAAAIFAAAACmZhY3RvcnlDZmcFAAAAGElkeEZhY3RvcnlDZmdTdGFraW5nRGFwcAEAAAAea2V5RW1pc3Npb25SYXRlUGVyQmxvY2tDdXJyZW50AAAAAAIAAAAbJXMlc19fcmF0ZVBlckJsb2NrX19jdXJyZW50AQAAACFrZXlFbWlzc2lvblJhdGVQZXJCbG9ja01heEN1cnJlbnQAAAAAAgAAAB4lcyVzX19yYXRlUGVyQmxvY2tNYXhfX2N1cnJlbnQBAAAAFWtleUVtaXNzaW9uU3RhcnRCbG9jawAAAAACAAAAGiVzJXNfX2VtaXNzaW9uX19zdGFydEJsb2NrAQAAABtrZXlFbWlzc2lvbkR1cmF0aW9uSW5CbG9ja3MAAAAAAgAAABglcyVzX19lbWlzc2lvbl9fZHVyYXRpb24BAAAAE2tleUVtaXNzaW9uRW5kQmxvY2sAAAAAAgAAABglcyVzX19lbWlzc2lvbl9fZW5kQmxvY2sBAAAAD2tleVN0YWtlZEJ5VXNlcgAAAAIAAAAOdXNlckFkZHJlc3NTdHIAAAAMbHBBc3NldElkU3RyCQAEuQAAAAIJAARMAAAAAgIAAAAOJXMlcyVzX19zdGFrZWQJAARMAAAAAgUAAAAOdXNlckFkZHJlc3NTdHIJAARMAAAAAgUAAAAMbHBBc3NldElkU3RyBQAAAANuaWwFAAAAA1NFUAEAAAAOa2V5U3Rha2VkVG90YWwAAAABAAAADGxwQXNzZXRJZFN0cgkAASwAAAACAgAAABclcyVzJXNfX3N0YWtlZF9fdG90YWxfXwUAAAAMbHBB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dGl2ZSgxMDYyKQAAAAEFAAAADmZhY3RvcnlBZGRyZXNzAAAAAApmYWN0b3J5Q2ZnCQEAAAAUcmVhZEZhY3RvcnlDZmdPckZhaWwAAAABBQAAAA9mYWN0b3J5Q29udHJhY3QAAAAAEGVtaXNzaW9uQ29udHJhY3QJAQAAABhnZXRFbWlzc2lvbkFkZHJlc3NPckZhaWwAAAABBQAAAApmYWN0b3J5Q2ZnAAAAABBib29zdGluZ0NvbnRyYWN0CQEAAAAYZ2V0Qm9vc3RpbmdBZGRyZXNzT3JGYWlsAAAAAQUAAAAKZmFjdG9yeUNmZwEAAAAbY2FsY1d4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0AAAABAAAAAxzdGFrZWRCeVVzZXIAAAAmd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHRPclplcm8AAAASd3hQZXJMcEludGVncmFsTmV3AAAAGnd4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0S0VZAwMJAAAAAAAAAgUAAAAmd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHRPclplcm8FAAAACnplcm9CaWdJbnQJAAE/AAAAAgUAAAAMc3Rha2VkQnlVc2VyBQAAAAp6ZXJvQmlnSW50BwUAAAAKemVyb0JpZ0ludAMJAAAAAAAAAgUAAAAMc3Rha2VkQnlVc2VyBQAAAAp6ZXJvQmlnSW50BQAAABJ3eFBlckxwSW50ZWdyYWxOZXcDAwkAAT8AAAACBQAAACZ3eFBlckxwSW50ZWdyYWxVc2VyTGFzdFVwZEhlaWdodE9yWmVybwUAAAAKemVyb0JpZ0ludAkAAT8AAAACBQAAAAxzdGFrZWRCeVVzZXIFAAAACnplcm9CaWdJbnQHCQEAAAAFdmFsdWUAAAABCQABqAAAAAEJAQAAAA9nZXRTdHJpbmdPckZhaWwAAAACBQAAAAR0aGlzBQAAABp3eFBlckxwSW50ZWdyYWxVc2VyTGFzdEtFWQkAAAIAAAABAgAAAC1jYWxjV3hQZXJMcEludGVncmFsVXNlckxhc3Q6IHVuZXhwZWN0ZWQgc3RhdGUBAAAAFHJlZnJlc2hQb29sSU5URUdSQUxTAAAAAwAAAAxscEFzc2V0SWRTdHIAAAAOcG9vbEFkZHJlc3NTdHIAAAANbHBEZWx0YUFtb3VudAQAAAAOc3Rha2VkVG90YWxLRVkJAQAAAA5rZXlTdGFrZWRUb3RhbAAAAAEFAAAADGxwQXNzZXRJZFN0cgQAAAALc3Rha2VkVG90YWwJAAE2AAAAAQkBAAAACnJlYWRTdGFrZWQAAAABBQAAAA5zdGFrZWRUb3RhbEtFWQQAAAASbm9uWmVyb1N0YWtlZFRvdGFsAwkAAAAAAAACBQAAAAtzdGFrZWRUb3RhbAUAAAAKemVyb0JpZ0ludAUAAAAJb25lQmlnSW50BQAAAAtzdGFrZWRUb3RhbAQAAAAKcG9vbFdlaWdodAkBAAAAEUBleHRyTmF0aXZlKDEwNTApAAAAAgUAAAAPZmFjdG9yeUNvbnRyYWN0CQEAAAAUa2V5RmFjdG9yeVBvb2xXZWlnaHQAAAABBQAAAA5wb29sQWRkcmVzc1N0cgQAAAASZW1pc3Npb25TdGFydEJsb2NrCQEAAAAMZ2V0SW50T3JGYWlsAAAAAgUAAAAQZW1pc3Npb25Db250cmFjdAkBAAAAFWtleUVtaXNzaW9uU3RhcnRCbG9jawAAAAAEAAAABU1VTFQzAAAAAAAAAAPoBAAAABR3eEVtaXNzaW9uUGVyQmxvY2tYMwkAAGgAAAACCQEAAAAMZ2V0SW50T3JGYWlsAAAAAgUAAAAQZW1pc3Npb25Db250cmFjdAkBAAAAHmtleUVtaXNzaW9uUmF0ZVBlckJsb2NrQ3VycmVudAAAAAAFAAAABU1VTFQzBAAAABhwb29sV3hFbWlzc2lvblBlckJsb2NrWDMJAABrAAAAAwUAAAAUd3hFbWlzc2lvblBlckJsb2NrWDMFAAAACnBvb2xXZWlnaHQJAABoAAAAAgUAAAAOUE9PTFdFSUdIVE1VTFQAAAAAAAAAAAMEAAAAEnd4UGVyTHBJbnRlZ3JhbEtFWQkBAAAAEmtleVd4UGVyTHBJbnRlZ3JhbAAAAAEFAAAADGxwQXNzZXRJZFN0cgQAAAAfd3hQZXJMcEludGVncmFsTGFzdFVwZEhlaWdodEtFWQkBAAAAH2tleVd4UGVyTHBJbnRlZ3JhbExhc3RVcGRIZWlnaHQAAAABBQAAAAxscEFzc2V0SWRTdHIEAAAACnd4UGVyTHBLRVkJAQAAAAprZXlXeFBlckxwAAAAAQUAAAAMbHBBc3NldElkU3RyBAAAABx3eFBlckxwSW50ZWdyYWxMYXN0VXBkSGVpZ2h0CQEAAAAPZ2V0SW50T3JEZWZhdWx0AAAAAwUAAAAEdGhpcwUAAAAfd3hQZXJMcEludGVncmFsTGFzdFVwZEhlaWdodEtFWQUAAAASZW1pc3Npb25TdGFydEJsb2NrBAAAAA93eFBlckxwSW50ZWdyYWwJAQAAABlnZXRCaWdJbnRGcm9tU3RyaW5nT3JaZXJvAAAAAgUAAAAEdGhpcwUAAAASd3hQZXJMcEludGVncmFsS0VZBAAAAA93eFBlckxwT3JaZXJvWDMAAAAAAAAAAAAEAAAAAmRoCQABlgAAAAEJAARMAAAAAgkAAGUAAAACBQAAAAZoZWlnaHQFAAAAHHd4UGVyTHBJbnRlZ3JhbExhc3RVcGRIZWlnaHQJAARMAAAAAgAAAAAAAAAAAAUAAAADbmlsBAAAAAl3eFBlckxwWDMDCQEAAAACIT0AAAACBQAAAA93eFBlckxwT3JaZXJvWDMAAAAAAAAAAAAJAAE2AAAAAQUAAAAPd3hQZXJMcE9yWmVyb1gzCQABPAAAAAMJAAE2AAAAAQUAAAAYcG9vbFd4RW1pc3Npb25QZXJCbG9ja1gzCQABNgAAAAEFAAAABU1VTFQ4BQAAABJub25aZXJvU3Rha2VkVG90YWwEAAAADnN0YWtlZFRvdGFsTmV3CQABNwAAAAIFAAAAC3N0YWtlZFRvdGFsCQABNgAAAAEFAAAADWxwRGVsdGFBbW91bnQEAAAAFW5vblplcm9TdGFrZWRUb3RhbE5ldwMJAAAAAAAAAgUAAAAOc3Rha2VkVG90YWxOZXcFAAAACnplcm9CaWdJbnQFAAAACW9uZUJpZ0ludAUAAAAOc3Rha2VkVG90YWxOZXcEAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwkAATcAAAACBQAAAA93eFBlckxwSW50ZWdyYWwJAAE5AAAAAgUAAAAJd3hQZXJMcFgzCQABNgAAAAEFAAAAAmRoBAAAAAx3eFBlckxwWDNOZXcJAAE6AAAAAgkAATYAAAABBQAAABhwb29sV3hFbWlzc2lvblBlckJsb2NrWDMFAAAAFW5vblplcm9TdGFrZWRUb3RhbE5ldwQAAAAfd3hQZXJMcEludGVncmFsTGFzdFVwZEhlaWdodE5ldwUAAAAGaGVpZ2h0BAAAAAVkZWJ1ZwkABLkAAAACCQAETAAAAAIJAAGmAAAAAQUAAAASd3hQZXJMcEludGVncmFsTmV3CQAETAAAAAIJAAGkAAAAAQUAAAACZGgJAARMAAAAAgkAAaYAAAABBQAAAAl3eFBlckxwWDMJAARMAAAAAgkAAaYAAAABBQAAAAtzdGFrZWRUb3RhbAkABEwAAAACCQABpAAAAAEFAAAAGHBvb2xXeEVtaXNzaW9uUGVyQmxvY2tYMwkABEwAAAACCQABpAAAAAEFAAAAFHd4RW1pc3Npb25QZXJCbG9ja1gzCQAETAAAAAIJAAGkAAAAAQUAAAAKcG9vbFdlaWdodAUAAAADbmlsAgAAAAI6OgkABRUAAAADBQAAABJ3eFBlckxwSW50ZWdyYWxOZXcJAARMAAAAAgkBAAAAC1N0cmluZ0VudHJ5AAAAAgUAAAASd3hQZXJMcEludGVncmFsS0VZCQABpgAAAAEFAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgUAAAAfd3hQZXJMcEludGVncmFsTGFzdFVwZEhlaWdodEtFWQUAAAAfd3hQZXJMcEludGVncmFsTGFzdFVwZEhlaWdodE5ldwkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAAAp3eFBlckxwS0VZCQABpgAAAAEFAAAADHd4UGVyTHBYM05ldwUAAAADbmlsBQAAAAVkZWJ1ZwEAAAAQcmVmcmVzaElOVEVHUkFMUwAAAAQAAAAMbHBBc3NldElkU3RyAAAADnVzZXJBZGRyZXNzU3RyAAAADnBvb2xBZGRyZXNzU3RyAAAADWxwRGVsdGFBbW91bnQEAAAADSR0MDExODc1MTE5OTcJAQAAABRyZWZyZXNoUG9vbElOVEVHUkFMUwAAAAMFAAAADGxwQXNzZXRJZFN0cgUAAAAOcG9vbEFkZHJlc3NTdHIFAAAADWxwRGVsdGFBbW91bnQEAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwgFAAAADSR0MDExODc1MTE5OTcAAAACXzEEAAAAEXBvb2xJbnRlZ3JhbFNUQVRFCAUAAAANJHQwMTE4NzUxMTk5NwAAAAJfMgQAAAAJcG9vbERFQlVHCAUAAAANJHQwMTE4NzUxMTk5NwAAAAJfMwQAAAAFTVVMVDMAAAAAAAAAA+gEAAAAD3N0YWtlZEJ5VXNlcktFWQkBAAAAD2tleVN0YWtlZEJ5VXNlcgAAAAIFAAAADnVzZXJBZGRyZXNzU3RyBQAAAAxscEFzc2V0SWRTdHIEAAAADHN0YWtlZEJ5VXNlcgkBAAAACnJlYWRTdGFrZWQAAAABBQAAAA9zdGFrZWRCeVVzZXJLRVkEAAAAEHd4VG9DbGFpbVVzZXJLRVkJAQAAABBrZXlXeFRvQ2xhaW1Vc2VyAAAAAgUAAAAMbHBBc3NldElkU3RyBQAAAA51c2VyQWRkcmVzc1N0cgQAAAAjd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHRLRVkJAQAAACNrZXlXeFBlckxwSW50ZWdyYWxVc2VyTGFzdFVwZEhlaWdodAAAAAIFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIEAAAAGnd4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0S0VZCQEAAAAaa2V5V3hQZXJMcEludGVncmFsVXNlckxhc3QAAAACBQAAAAxscEFzc2V0SWRTdHIFAAAADnVzZXJBZGRyZXNzU3RyBAAAAA13eFRvQ2xhaW1Vc2VyCQEAAAAZZ2V0QmlnSW50RnJvbVN0cmluZ09yWmVybwAAAAIFAAAABHRoaXMFAAAAEHd4VG9DbGFpbVVzZXJLRVkEAAAAJnd4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0VXBkSGVpZ2h0T3JaZXJvCQEAAAAMZ2V0SW50T3JaZXJvAAAAAgUAAAAEdGhpcwUAAAAjd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHRLRVkEAAAAF3d4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0CQEAAAAbY2FsY1d4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0AAAABAkAATYAAAABBQAAAAxzdGFrZWRCeVVzZXIJAAE2AAAAAQUAAAAmd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHRPclplcm8FAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwUAAAAad3hQZXJMcEludGVncmFsVXNlckxhc3RLRVkEAAAABk1VTFQxMQkAAGgAAAACBQAAAAVNVUxUOAUAAAAFTVVMVDMEAAAAEHd4VG9DbGFpbVVzZXJOZXcJAAE3AAAAAgUAAAANd3hUb0NsYWltVXNlcgkAATwAAAADCQABOAAAAAIFAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwUAAAAXd3hQZXJMcEludGVncmFsVXNlckxhc3QJAAE2AAAAAQUAAAAMc3Rha2VkQnlVc2VyCQABNgAAAAEFAAAABk1VTFQxMQQAAAAad3hQZXJMcEludGVncmFsVXNlckxhc3ROZXcFAAAAEnd4UGVyTHBJbnRlZ3JhbE5ldwQAAAAjd3hQZXJMcEludGVncmFsVXNlckxhc3RVcGRIZWlnaHROZXcFAAAABmhlaWdodAQAAAAFZGVidWcJAAS5AAAAAgkABEwAAAACCQABpgAAAAEFAAAAEHd4VG9DbGFpbVVzZXJOZXcJAARMAAAAAgkAAaYAAAABBQAAABd3eFBlckxwSW50ZWdyYWxVc2VyTGFzdAkABEwAAAACCQABpAAAAAEFAAAADHN0YWtlZEJ5VXNlcgkABEwAAAACBQAAAAlwb29sREVCVUcJAARMAAAAAgkAAaQAAAABBQAAAAZoZWlnaHQFAAAAA25pbAIAAAACOjoJAAUVAAAAAwUAAAAQd3hUb0NsYWltVXNlck5ldwkABE4AAAACBQAAABFwb29sSW50ZWdyYWxTVEFURQkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAABB3eFRvQ2xhaW1Vc2VyS0VZCQABpgAAAAEFAAAAEHd4VG9DbGFpbVVzZXJOZXcJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIFAAAAI3d4UGVyTHBJbnRlZ3JhbFVzZXJMYXN0VXBkSGVpZ2h0S0VZBQAAACN3eFBlckxwSW50ZWdyYWxVc2VyTGFzdFVwZEhlaWdodE5ldwkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAABp3eFBlckxwSW50ZWdyYWxVc2VyTGFzdEtFWQkAAaYAAAABBQAAABp3eFBlckxwSW50ZWdyYWxVc2VyTGFzdE5ldwUAAAADbmlsBQAAAAVkZWJ1ZwEAAAAWbWFuYWdlclB1YmxpY0tleU9yVW5pdAAAAAAEAAAAByRtYXRjaDAJAAQiAAAAAQkBAAAAE2tleU1hbmFnZXJQdWJsaWNLZXkAAAAAAwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAAZTdHJpbmcEAAAAAXMFAAAAByRtYXRjaDAJAAJZAAAAAQUAAAABcwMJAAABAAAAAgUAAAAHJG1hdGNoMAIAAAAEVW5pdAUAAAAEdW5pdAkAAAIAAAABAgAAAAtNYXRjaCBlcnJvcgEAAAAXbWlncmF0b3JQdWJsaWNLZXlPclVuaXQAAAAABAAAAAckbWF0Y2gwCQAEIgAAAAEJAQAAABRrZXlNaWdyYXRvclB1YmxpY0tleQAAAAADCQAAAQAAAAIFAAAAByRtYXRjaDACAAAABlN0cmluZwQAAAABcwUAAAAHJG1hdGNoMAkAAlkAAAABBQAAAAFzAwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAARVbml0BQAAAAR1bml0CQAAAgAAAAECAAAAC01hdGNoIGVycm9yAQAAAB1wZW5kaW5nTWFuYWdlclB1YmxpY0tleU9yVW5pdAAAAAAEAAAAByRtYXRjaDAJAAQiAAAAAQkBAAAAGmtleVBlbmRpbmdNYW5hZ2VyUHVibGljS2V5AAAAAAMJAAABAAAAAgUAAAAHJG1hdGNoMAIAAAAGU3RyaW5nBAAAAAFzBQAAAAckbWF0Y2gwCQACWQAAAAEFAAAAAXMDCQAAAQAAAAIFAAAAByRtYXRjaDACAAAABFVuaXQFAAAABHVuaXQJAAACAAAAAQIAAAALTWF0Y2ggZXJyb3IBAAAAC211c3RNYW5hZ2VyAAAAAQAAAAFpBAAAAAJwZAkAAAIAAAABAgAAABFQZXJtaXNzaW9uIGRlbmllZAQAAAAHJG1hdGNoMAkBAAAAFm1hbmFnZXJQdWJsaWNLZXlPclVuaXQAAAAAAwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAApCeXRlVmVjdG9yBAAAAAJwawUAAAAHJG1hdGNoMAMJAAAAAAAAAggFAAAAAWkAAAAPY2FsbGVyUHVibGljS2V5BQAAAAJwawYFAAAAAnBkAwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAARVbml0AwkAAAAAAAACCAUAAAABaQAAAAZjYWxsZXIFAAAABHRoaXMGBQAAAAJwZAkAAAIAAAABAgAAAAtNYXRjaCBlcnJvcgAAAAgAAAABaQEAAAALY29uc3RydWN0b3IAAAABAAAAEWZhY3RvcnlBZGRyZXNzU3RyBAAAAAtjaGVja0NhbGxlcgkBAAAAC211c3RNYW5hZ2VyAAAAAQUAAAABaQMJAAAAAAAAAgUAAAALY2hlY2tDYWxsZXIFAAAAC2NoZWNrQ2FsbGVyCQAETAAAAAIJAQAAAAtTdHJpbmdFbnRyeQAAAAIJAQAAABFrZXlGYWN0b3J5QWRkcmVzcwAAAAAFAAAAEWZhY3RvcnlBZGRyZXNzU3RyBQAAAANuaWwJAAACAAAAAQIAAAAkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAAAAAWkBAAAACnNldE1hbmFnZXIAAAABAAAAF3BlbmRpbmdNYW5hZ2VyUHVibGljS2V5BAAAAAtjaGVja0NhbGxlcgkBAAAAC211c3RNYW5hZ2VyAAAAAQUAAAABaQMJAAAAAAAAAgUAAAALY2hlY2tDYWxsZXIFAAAAC2NoZWNrQ2FsbGVyBAAAABVjaGVja01hbmFnZXJQdWJsaWNLZXkJAAJZAAAAAQUAAAAXcGVuZGluZ01hbmFnZXJQdWJsaWNLZXkDCQAAAAAAAAIFAAAAFWNoZWNrTWFuYWdlclB1YmxpY0tleQUAAAAVY2hlY2tNYW5hZ2VyUHVibGljS2V5CQAETAAAAAIJAQAAAAtTdHJpbmdFbnRyeQAAAAIJAQAAABprZXlQZW5kaW5nTWFuYWdlclB1YmxpY0tleQAAAAAFAAAAF3BlbmRpbmdNYW5hZ2VyUHVibGljS2V5BQAAAANuaWwJAAACAAAAAQIAAAAkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuCQAAAgAAAAECAAAAJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgAAAAFpAQAAAA5jb25maXJtTWFuYWdlcgAAAAAEAAAAAnBtCQEAAAAdcGVuZGluZ01hbmFnZXJQdWJsaWNLZXlPclVuaXQAAAAABAAAAAVoYXNQTQMJAQAAAAlpc0RlZmluZWQAAAABBQAAAAJwbQYJAAACAAAAAQIAAAASTm8gcGVuZGluZyBtYW5hZ2VyAwkAAAAAAAACBQAAAAVoYXNQTQUAAAAFaGFzUE0EAAAAB2NoZWNrUE0DCQAAAAAAAAIIBQAAAAFpAAAAD2NhbGxlclB1YmxpY0tleQkBAAAABXZhbHVlAAAAAQUAAAACcG0GCQAAAgAAAAECAAAAG1lvdSBhcmUgbm90IHBlbmRpbmcgbWFuYWdlcgMJAAAAAAAAAgUAAAAHY2hlY2tQTQUAAAAHY2hlY2tQTQkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACCQEAAAATa2V5TWFuYWdlclB1YmxpY0tleQAAAAAJAAJYAAAAAQkBAAAABXZhbHVlAAAAAQUAAAACcG0JAARMAAAAAgkBAAAAC0RlbGV0ZUVudHJ5AAAAAQkBAAAAGmtleVBlbmRpbmdNYW5hZ2VyUHVibGljS2V5AAAAAAUAAAADbmlsCQAAAgAAAAECAAAAJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgkAAAIAAAABAgAAACRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4AAAABaQEAAAAFc3Rha2UAAAAAAwkBAAAAAiE9AAAAAgkAAZAAAAABCAUAAAABaQAAAAhwYXltZW50cwAAAAAAAAAAAQkAAAIAAAABAgAAADRpbnZhbGlkIHBheW1lbnQgLSBleGFjdCBvbmUgcGF5bWVudCBtdXN0IGJlIGF0dGFjaGVkBAAAAANwbXQJAAGRAAAAAggFAAAAAWkAAAAIcGF5bWVudHMAAAAAAAAAAAAEAAAACWxwQXNzZXRJZAkBAAAABXZhbHVlAAAAAQgFAAAAA3BtdAAAAAdhc3NldElkBAAAAAxscEFzc2V0SWRTdHIJAAJYAAAAAQUAAAAJbHBBc3NldElkBAAAAAZhbW91bnQIBQAAAANwbXQAAAAGYW1vdW50BAAAAA5wb29sQWRkcmVzc1N0cgkBAAAAE3ZhbHVlT3JFcnJvck1lc3NhZ2UAAAACCQAEHQAAAAIFAAAAD2ZhY3RvcnlDb250cmFjdAkBAAAAGmtleUZhY3RvcnlMcDJBc3NldHNNYXBwaW5nAAAAAQUAAAAMbHBBc3NldElkU3RyCQABLAAAAAICAAAAFXVuc3VwcG9ydGVkIGxwIGFzc2V0IAUAAAAMbHBBc3NldElkU3RyBAAAAAljYWxsZXJTdHIJAAQlAAAAAQgFAAAAAWkAAAAGY2FsbGVyBAAAAA51c2VyQWRkcmVzc1N0cgMJAAAAAAAAAgUAAAAJY2FsbGVyU3RyBQAAAA5wb29sQWRkcmVzc1N0cgkABCUAAAABCAUAAAABaQAAAAxvcmlnaW5DYWxsZXIFAAAACWNhbGxlclN0cgQAAAAPc3Rha2VkQnlVc2VyS0VZCQEAAAAPa2V5U3Rha2VkQnlVc2VyAAAAAgUAAAAOdXNlckFkZHJlc3NTdHIFAAAADGxwQXNzZXRJZFN0cgQAAAAOc3Rha2VkVG90YWxLRVkJAQAAAA5rZXlTdGFrZWRUb3RhbAAAAAEFAAAADGxwQXNzZXRJZFN0cgQAAAAMc3Rha2VkQnlVc2VyCQEAAAAKcmVhZFN0YWtlZAAAAAEFAAAAD3N0YWtlZEJ5VXNlcktFWQQAAAALc3Rha2VkVG90YWwJAQAAAApyZWFkU3Rha2VkAAAAAQUAAAAOc3Rha2VkVG90YWxLRVkEAAAADSR0MDE2ODA2MTY5MjMJAQAAABByZWZyZXNoSU5URUdSQUxTAAAABAUAAAAMbHBBc3NldElkU3RyBQAAAA51c2VyQWRkcmVzc1N0cgUAAAAOcG9vbEFkZHJlc3NTdHIFAAAABmFtb3VudAQAAAAQd3hUb0NsYWltVXNlck5ldwgFAAAADSR0MDE2ODA2MTY5MjMAAAACXzEEAAAADWludGVncmFsU1RBVEUIBQAAAA0kdDAxNjgwNjE2OTIzAAAAAl8yBAAAAAVkZWJ1ZwgFAAAADSR0MDE2ODA2MTY5MjMAAAACXzMJAAROAAAAAgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgUAAAAPc3Rha2VkQnlVc2VyS0VZCQAAZAAAAAIFAAAADHN0YWtlZEJ5VXNlcgUAAAAGYW1vdW50CQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACBQAAAA5zdGFrZWRUb3RhbEtFWQkAAGQAAAACBQAAAAtzdGFrZWRUb3RhbAUAAAAGYW1vdW50CQAETAAAAAIJAQAAABVPcGVyYXRpb25IaXN0b3J5RW50cnkAAAAFAgAAAAVzdGFrZQUAAAAOdXNlckFkZHJlc3NTdHIFAAAADGxwQXNzZXRJZFN0cgUAAAAGYW1vdW50CAUAAAABaQAAAA10cmFuc2FjdGlvbklkBQAAAANuaWwFAAAADWludGVncmFsU1RBVEUAAAABaQEAAAAHdW5zdGFrZQAAAAIAAAAMbHBBc3NldElkU3RyAAAABmFtb3VudAQAAAAJbHBBc3NldElkCQACWQAAAAEFAAAADGxwQXNzZXRJZFN0cgQAAAAOcG9vbEFkZHJlc3NTdHIJAQAAABN2YWx1ZU9yRXJyb3JNZXNzYWdlAAAAAgkABB0AAAACBQAAAA9mYWN0b3J5Q29udHJhY3QJAQAAABprZXlGYWN0b3J5THAyQXNzZXRzTWFwcGluZwAAAAEFAAAADGxwQXNzZXRJZFN0cgkAASwAAAACAgAAABV1bnN1cHBvcnRlZCBscCBhc3NldCAFAAAADGxwQXNzZXRJZFN0cgQAAAAJcG9vbEFkZG9uCQEAAAALdmFsdWVPckVsc2UAAAACCQAEHQAAAAIFAAAABHRoaXMJAQAAABZrZXlTdGFibGVQb29sQWRkb25BZGRyAAAAAAUAAAAOcG9vbEFkZHJlc3NTdHIEAAAACWNhbGxlclN0cgkABCUAAAABCAUAAAABaQAAAAZjYWxsZXIEAAAADnVzZXJBZGRyZXNzU3RyAwMJAAAAAAAAAgUAAAAJY2FsbGVyU3RyBQAAAA5wb29sQWRkcmVzc1N0cgYJAAAAAAAAAgUAAAAJY2FsbGVyU3RyBQAAAAlwb29sQWRkb24JAAQlAAAAAQgFAAAAAWkAAAAMb3JpZ2luQ2FsbGVyBQAAAAljYWxsZXJTdHIEAAAAD3N0YWtlZEJ5VXNlcktFWQkBAAAAD2tleVN0YWtlZEJ5VXNlcgAAAAIFAAAADnVzZXJBZGRyZXNzU3RyBQAAAAxscEFzc2V0SWRTdHIEAAAADnN0YWtlZFRvdGFsS0VZCQEAAAAOa2V5U3Rha2VkVG90YWwAAAABBQAAAAxscEFzc2V0SWRTdHIEAAAADHN0YWtlZEJ5VXNlcgkBAAAACnJlYWRTdGFrZWQAAAABBQAAAA9zdGFrZWRCeVVzZXJLRVkEAAAAC3N0YWtlZFRvdGFsCQEAAAAKcmVhZFN0YWtlZAAAAAEFAAAADnN0YWtlZFRvdGFsS0VZBAAAAA0kdDAxODA2MDE4MTc4CQEAAAAQcmVmcmVzaElOVEVHUkFMUwAAAAQFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIFAAAADnBvb2xBZGRyZXNzU3RyCQEAAAABLQAAAAEFAAAABmFtb3VudAQAAAAQd3hUb0NsYWltVXNlck5ldwgFAAAADSR0MDE4MDYwMTgxNzgAAAACXzEEAAAADWludGVncmFsU1RBVEUIBQAAAA0kdDAxODA2MDE4MTc4AAAAAl8yBAAAAAVkZWJ1ZwgFAAAADSR0MDE4MDYwMTgxNzgAAAACXzMDCQAAZgAAAAIFAAAABmFtb3VudAUAAAAMc3Rha2VkQnlVc2VyCQAAAgAAAAECAAAAJHBhc3NlZCBhbW91bnQgaXMgbGVzcyB0aGVuIGF2YWlsYWJsZQkABE4AAAACCQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACBQAAAA9zdGFrZWRCeVVzZXJLRVkJAABlAAAAAgUAAAAMc3Rha2VkQnlVc2VyBQAAAAZhbW91bnQJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIFAAAADnN0YWtlZFRvdGFsS0VZCQAAZQAAAAIFAAAAC3N0YWtlZFRvdGFsBQAAAAZhbW91bnQJAARMAAAAAgkBAAAADlNjcmlwdFRyYW5zZmVyAAAAAwgFAAAAAWkAAAAGY2FsbGVyBQAAAAZhbW91bnQFAAAACWxwQXNzZXRJZAkABEwAAAACCQEAAAAVT3BlcmF0aW9uSGlzdG9yeUVudHJ5AAAABQIAAAAHdW5zdGFrZQUAAAAOdXNlckFkZHJlc3NTdHIFAAAADGxwQXNzZXRJZFN0cgUAAAAGYW1vdW50CAUAAAABaQAAAA10cmFuc2FjdGlvbklkBQAAAANuaWwFAAAADWludGVncmFsU1RBVEUAAAABaQEAAAAHY2xhaW1XeAAAAAEAAAAMbHBBc3NldElkU3RyBAAAAAt1c2VyQWRkcmVzcwgFAAAAAWkAAAAGY2FsbGVyBAAAAA51c2VyQWRkcmVzc1N0cgkABCUAAAABCAUAAAABaQAAAAZjYWxsZXIEAAAADnBvb2xBZGRyZXNzU3RyCQEAAAAYZ2V0U3RyaW5nQnlBZGRyZXNzT3JGYWlsAAAAAgUAAAAPZmFjdG9yeUNvbnRyYWN0CQEAAAAma2V5RmFjdG9yeUxwQXNzZXRUb1Bvb2xDb250cmFjdEFkZHJlc3MAAAABBQAAAAxscEFzc2V0SWRTdHIEAAAAEGNsYWltZWRCeVVzZXJLRVkJAQAAABBrZXlDbGFpbWVkQnlVc2VyAAAAAgUAAAAMbHBBc3NldElkU3RyBQAAAA51c2VyQWRkcmVzc1N0cgQAAAAPY2xhaW1lZFRvdGFsS0VZCQEAAAAPa2V5Q2xhaW1lZFRvdGFsAAAAAQUAAAAMbHBBc3NldElkU3RyBAAAABljbGFpbWVkQnlVc2VyTWluUmV3YXJkS0VZCQEAAAAZa2V5Q2xhaW1lZEJ5VXNlck1pblJld2FyZAAAAAIFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIEAAAAG2NsYWltZWRCeVVzZXJCb29zdFJld2FyZEtFWQkBAAAAG2tleUNsYWltZWRCeVVzZXJCb29zdFJld2FyZAAAAAIFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIEAAAADWNsYWltZWRCeVVzZXIJAAE2AAAAAQkBAAAADGdldEludE9yWmVybwAAAAIFAAAABHRoaXMFAAAAEGNsYWltZWRCeVVzZXJLRVkEAAAAFmNsYWltZWRCeVVzZXJNaW5SZXdhcmQJAAE2AAAAAQkBAAAADGdldEludE9yWmVybwAAAAIFAAAABHRoaXMFAAAAGWNsYWltZWRCeVVzZXJNaW5SZXdhcmRLRVkEAAAAGGNsYWltZWRCeVVzZXJCb29zdFJld2FyZAkAATYAAAABCQEAAAAMZ2V0SW50T3JaZXJvAAAAAgUAAAAEdGhpcwUAAAAbY2xhaW1lZEJ5VXNlckJvb3N0UmV3YXJkS0VZBAAAAAxjbGFpbWVkVG90YWwJAQAAABlnZXRCaWdJbnRGcm9tU3RyaW5nT3JaZXJvAAAAAgUAAAAEdGhpcwUAAAAPY2xhaW1lZFRvdGFsS0VZBAAAAA0kdDAxOTQxNjE5NTI4CQEAAAAQcmVmcmVzaElOVEVHUkFMUwAAAAQFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIFAAAADnBvb2xBZGRyZXNzU3RyAAAAAAAAAAAABAAAABB3eFRvQ2xhaW1Vc2VyTmV3CAUAAAANJHQwMTk0MTYxOTUyOAAAAAJfMQQAAAANaW50ZWdyYWxTVEFURQgFAAAADSR0MDE5NDE2MTk1MjgAAAACXzIEAAAABWRlYnVnCAUAAAANJHQwMTk0MTYxOTUyOAAAAAJfMwQAAAAQYXZhaWxhYmxlVG9DbGFpbQkAATgAAAACBQAAABB3eFRvQ2xhaW1Vc2VyTmV3BQAAAA1jbGFpbWVkQnlVc2VyAwkAAUAAAAACBQAAAAp6ZXJvQmlnSW50BQAAABBhdmFpbGFibGVUb0NsYWltCQAAAgAAAAECAAAAEG5vdGhpbmcgdG8gY2xhaW0EAAAAEnd4QW1vdW50Qm9vc3RUb3RhbAkBAAAABWFzSW50AAAAAQkAAZEAAAACCQEAAAAJYXNBbnlMaXN0AAAAAQkAA/wAAAAEBQAAABBib29zdGluZ0NvbnRyYWN0AgAAAAxjbGFpbVd4Qm9vc3QJAARMAAAAAgUAAAAMbHBBc3NldElkU3RyCQAETAAAAAIFAAAADnVzZXJBZGRyZXNzU3RyBQAAAANuaWwFAAAAA25pbAAAAAAAAAAAAAQAAAANbWluUmV3YXJkUGFydAUAAAAQYXZhaWxhYmxlVG9DbGFpbQQAAAAPYm9vc3RSZXdhcmRQYXJ0CQABmQAAAAEJAARMAAAAAgkAATkAAAACBQAAAA1taW5SZXdhcmRQYXJ0CQABNgAAAAEAAAAAAAAAAAIJAARMAAAAAgkAATYAAAABBQAAABJ3eEFtb3VudEJvb3N0VG90YWwFAAAAA25pbAQAAAAJd3hBc3NldElkCQEAAAAMYXNCeXRlVmVjdG9yAAAAAQkAAZEAAAACCQEAAAAJYXNBbnlMaXN0AAAAAQkAA/wAAAAEBQAAABBlbWlzc2lvbkNvbnRyYWN0AgAAAARlbWl0CQAETAAAAAIJAAGgAAAAAQUAAAANbWluUmV3YXJkUGFydAUAAAADbmlsBQAAAANuaWwAAAAAAAAAAAAEAAAACWVtaXRCb29zdAkBAAAACWFzQW55TGlzdAAAAAEJAAP8AAAABAUAAAAQZW1pc3Npb25Db250cmFjdAIAAAAEZW1pdAkABEwAAAACCQABoAAAAAEFAAAAD2Jvb3N0UmV3YXJkUGFydAUAAAADbmlsBQAAAANuaWwDCQAAAAAAAAIFAAAACWVtaXRCb29zdAUAAAAJZW1pdEJvb3N0BAAAABJjbGFpbWVkQnlVc2VyVmFsdWUJAAE3AAAAAgUAAAANY2xhaW1lZEJ5VXNlcgUAAAAQYXZhaWxhYmxlVG9DbGFpbQQAAAAeY2xhaW1lZEJ5VXNlck1pblJld2FyZFBsdXNQYXJ0CQABNwAAAAIFAAAAFmNsYWltZWRCeVVzZXJNaW5SZXdhcmQFAAAADW1pblJld2FyZFBhcnQEAAAAK2NsYWltZWRCeVVzZXJCb29zdFJld2FyZFBsdXNCb29zdFJld2FyZFBhcnQJAAE3AAAAAgUAAAAWY2xhaW1lZEJ5VXNlck1pblJld2FyZAUAAAANbWluUmV3YXJkUGFydAQAAAAgY2xhaW1lZFRvdGFsUGx1c0F2YWlsYWJsZVRvQ2xhaW0JAAE3AAAAAgUAAAAWY2xhaW1lZEJ5VXNlck1pblJld2FyZAUAAAANbWluUmV3YXJkUGFydAkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAABBjbGFpbWVkQnlVc2VyS0VZCQABpgAAAAEFAAAAEmNsYWltZWRCeVVzZXJWYWx1ZQkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAABljbGFpbWVkQnlVc2VyTWluUmV3YXJkS0VZCQABpgAAAAEFAAAAHmNsYWltZWRCeVVzZXJNaW5SZXdhcmRQbHVzUGFydAkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAABtjbGFpbWVkQnlVc2VyQm9vc3RSZXdhcmRLRVkJAAGmAAAAAQUAAAArY2xhaW1lZEJ5VXNlckJvb3N0UmV3YXJkUGx1c0Jvb3N0UmV3YXJkUGFydAkABEwAAAACCQEAAAALU3RyaW5nRW50cnkAAAACBQAAAA9jbGFpbWVkVG90YWxLRVkJAAGmAAAAAQUAAAAgY2xhaW1lZFRvdGFsUGx1c0F2YWlsYWJsZVRvQ2xhaW0JAARMAAAAAgkBAAAADlNjcmlwdFRyYW5zZmVyAAAAAwUAAAALdXNlckFkZHJlc3MJAAGgAAAAAQUAAAANbWluUmV3YXJkUGFydAUAAAAJd3hBc3NldElkCQAETAAAAAIJAQAAAA5TY3JpcHRUcmFuc2ZlcgAAAAMFAAAAC3VzZXJBZGRyZXNzCQABoAAAAAEFAAAAD2Jvb3N0UmV3YXJkUGFydAUAAAAJd3hBc3NldElkCQAETAAAAAIJAQAAABVPcGVyYXRpb25IaXN0b3J5RW50cnkAAAAFAgAAAAVjbGFpbQUAAAAOdXNlckFkZHJlc3NTdHIFAAAADGxwQXNzZXRJZFN0cgkAAaAAAAABBQAAABBhdmFpbGFibGVUb0NsYWltCAUAAAABaQAAAA10cmFuc2FjdGlvbklkBQAAAANuaWwJAAACAAAAAQIAAAAkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAAAAAWkBAAAAD2NsYWltV3hSRUFET05MWQAAAAIAAAAMbHBBc3NldElkU3RyAAAADnVzZXJBZGRyZXNzU3RyBAAAAA9zdGFrZWRCeVVzZXJLRVkJAQAAAA9rZXlTdGFrZWRCeVVzZXIAAAACBQAAAA51c2VyQWRkcmVzc1N0cgUAAAAMbHBBc3NldElkU3RyBAAAAA5zdGFrZWRUb3RhbEtFWQkBAAAADmtleVN0YWtlZFRvdGFsAAAAAQUAAAAMbHBBc3NldElkU3RyBAAAABBjbGFpbWVkQnlVc2VyS0VZCQEAAAAQa2V5Q2xhaW1lZEJ5VXNlcgAAAAIFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIEAAAADHN0YWtlZEJ5VXNlcgkBAAAACnJlYWRTdGFrZWQAAAABBQAAAA9zdGFrZWRCeVVzZXJLRVkEAAAAC3N0YWtlZFRvdGFsCQEAAAAKcmVhZFN0YWtlZAAAAAEFAAAADnN0YWtlZFRvdGFsS0VZBAAAAA1jbGFpbWVkQnlVc2VyCQEAAAAMZ2V0SW50T3JaZXJvAAAAAgUAAAAEdGhpcwUAAAAQY2xhaW1lZEJ5VXNlcktFWQQAAAAOcG9vbEFkZHJlc3NTdHIJAQAAABhnZXRTdHJpbmdCeUFkZHJlc3NPckZhaWwAAAACBQAAAA9mYWN0b3J5Q29udHJhY3QJAQAAACZrZXlGYWN0b3J5THBBc3NldFRvUG9vbENvbnRyYWN0QWRkcmVzcwAAAAEFAAAADGxwQXNzZXRJZFN0cgQAAAAKcG9vbFdlaWdodAkBAAAAEUBleHRyTmF0aXZlKDEwNTApAAAAAgUAAAAPZmFjdG9yeUNvbnRyYWN0CQEAAAAUa2V5RmFjdG9yeVBvb2xXZWlnaHQAAAABBQAAAA5wb29sQWRkcmVzc1N0cgQAAAASd3hFbWlzc2lvblBlckJsb2NrCQEAAAAMZ2V0SW50T3JGYWlsAAAAAgUAAAAQZW1pc3Npb25Db250cmFjdAkBAAAAHmtleUVtaXNzaW9uUmF0ZVBlckJsb2NrQ3VycmVudAAAAAAEAAAAEmVtaXNzaW9uU3RhcnRCbG9jawkBAAAADGdldEludE9yRmFpbAAAAAIFAAAAEGVtaXNzaW9uQ29udHJhY3QJAQAAABVrZXlFbWlzc2lvblN0YXJ0QmxvY2sAAAAABAAAAAxwYXNzZWRCbG9ja3MDCQAAZgAAAAIFAAAAEmVtaXNzaW9uU3RhcnRCbG9jawUAAAAGaGVpZ2h0AAAAAAAAAAAACQAAZQAAAAIFAAAABmhlaWdodAUAAAASZW1pc3Npb25TdGFydEJsb2NrBAAAAA5wb29sV3hFbWlzc2lvbgkAAGsAAAADCQAAaAAAAAIFAAAAEnd4RW1pc3Npb25QZXJCbG9jawUAAAAMcGFzc2VkQmxvY2tzBQAAAApwb29sV2VpZ2h0BQAAAA5QT09MV0VJR0hUTVVMVAQAAAAMdXNlcld4UmV3YXJkCQAAawAAAAMFAAAADnBvb2xXeEVtaXNzaW9uBQAAAAxzdGFrZWRCeVVzZXIFAAAAC3N0YWtlZFRvdGFsBAAAAA0kdDAyMjEyODIyMjQwCQEAAAAQcmVmcmVzaElOVEVHUkFMUwAAAAQFAAAADGxwQXNzZXRJZFN0cgUAAAAOdXNlckFkZHJlc3NTdHIFAAAADnBvb2xBZGRyZXNzU3RyAAAAAAAAAAAABAAAABB3eFRvQ2xhaW1Vc2VyTmV3CAUAAAANJHQwMjIxMjgyMjI0MAAAAAJfMQQAAAANaW50ZWdyYWxTVEFURQgFAAAADSR0MDIyMTI4MjIyNDAAAAACXzIEAAAABWRlYnVnCAUAAAANJHQwMjIxMjgyMjI0MAAAAAJfMwQAAAAQYXZhaWxhYmxlVG9DbGFpbQkAATgAAAACBQAAABB3eFRvQ2xhaW1Vc2VyTmV3CQABNgAAAAEFAAAADWNsYWltZWRCeVVzZXIEAAAADmJvb3N0SW52UmVzdWx0CQEAAAAJYXNBbnlMaXN0AAAAAQkAA/wAAAAEBQAAABBib29zdGluZ0NvbnRyYWN0AgAAABRjbGFpbVd4Qm9vc3RSRUFET05MWQkABEwAAAACBQAAAAxs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", "height": 2115345, "applicationStatus": "succeeded", "spentComplexity": 0 } View: original | compacted Prev: 9ao1vdAZstA8KzEzPqtUt8UT7QDQBJR4pNoZbhWEYfi6 Next: 8t1ALZNyyWyrykM8CxzxZMquZ6msueaHd3a1mfbG2ewe Diff:
OldNewDifferences
1212 let SEP = "__"
1313
1414 let POOLWEIGHTMULT = MULT8
15+
16+let zeroBigInt = toBigInt(0)
17+
18+let oneBigInt = toBigInt(1)
1519
1620 func asAnyList (val) = match val {
1721 case valAnyLyst: List[Any] =>
4549 }
4650
4751
48-func getStringOrFail (key) = valueOrErrorMessage(getString(key), (("mandatory this." + key) + " is not defined"))
52+func getStringOrFail (address,key) = valueOrErrorMessage(getString(address, key), (("mandatory this." + key) + " is not defined"))
4953
5054
5155 func getStringByAddressOrFail (address,key) = valueOrErrorMessage(getString(address, key), (((("mandatory " + toString(address)) + ".") + key) + " is not defined"))
5862
5963
6064 func getIntOrFail (address,key) = valueOrErrorMessage(getInteger(address, key), (("mandatory this." + key) + " is not defined"))
65+
66+
67+func getBigIntFromStringOrZero (address,key) = value(parseBigInt(valueOrElse(getString(address, key), "0")))
68+
69+
70+func getBigIntFromStringOrDefault (address,key,defaultVal) = match getString(address, key) {
71+ case s: String =>
72+ value(parseBigInt(s))
73+ case _: Unit =>
74+ defaultVal
75+ case _ =>
76+ throw("Match error")
77+}
6178
6279
6380 func toX18 (origVal,origScaleMult) = fraction(toBigInt(origVal), MULT18, toBigInt(origScaleMult))
155172 func keyClaimedByUserBoostReward (lpAssetIdStr,userAddressStr) = makeString(["%s%s%s__claimedBoostReward", userAddressStr, lpAssetIdStr], SEP)
156173
157174
158-func keyClaimedTotal (lpAssetIdStr) = makeString(["%s%s%s__claimed", "total", lpAssetIdStr], SEP)
175+func keyClaimedTotal (lpAssetIdStr) = makeString(["%s%s%s__claimed__total", lpAssetIdStr], SEP)
159176
160177
161178 func readStaked (key) = valueOrElse(getInteger(this, key), 0)
209226 func OperationHistoryEntry (type,userAddress,lpAssetId,amount,txId) = StringEntry(keyOperationHistoryRecord(type, userAddress, toBase58String(txId)), formatHistoryRecord(userAddress, lpAssetId, type, amount))
210227
211228
212-let factoryAddress = getStringOrFail(keyFactoryAddress())
229+let factoryAddress = getStringOrFail(this, keyFactoryAddress())
213230
214231 let factoryContract = addressFromStringValue(factoryAddress)
215232
219236
220237 let boostingContract = getBoostingAddressOrFail(factoryCfg)
221238
222-func calcWxPerLpIntegralUserLast (stakedByUser,wxPerLpIntegralUserLastUpdHeightOrZero,wxPerLpIntegralNew,wxPerLpIntegralUserLastKEY) = if (if ((wxPerLpIntegralUserLastUpdHeightOrZero == 0))
223- then (stakedByUser > 0)
239+func calcWxPerLpIntegralUserLast (stakedByUser,wxPerLpIntegralUserLastUpdHeightOrZero,wxPerLpIntegralNew,wxPerLpIntegralUserLastKEY) = if (if ((wxPerLpIntegralUserLastUpdHeightOrZero == zeroBigInt))
240+ then (stakedByUser > zeroBigInt)
224241 else false)
225- then 0
226- else if ((stakedByUser == 0))
242+ then zeroBigInt
243+ else if ((stakedByUser == zeroBigInt))
227244 then wxPerLpIntegralNew
228- else if (if ((wxPerLpIntegralUserLastUpdHeightOrZero > 0))
229- then (stakedByUser > 0)
245+ else if (if ((wxPerLpIntegralUserLastUpdHeightOrZero > zeroBigInt))
246+ then (stakedByUser > zeroBigInt)
230247 else false)
231- then getIntOrFail(this, wxPerLpIntegralUserLastKEY)
248+ then value(parseBigInt(getStringOrFail(this, wxPerLpIntegralUserLastKEY)))
232249 else throw("calcWxPerLpIntegralUserLast: unexpected state")
233250
234251
235252 func refreshPoolINTEGRALS (lpAssetIdStr,poolAddressStr,lpDeltaAmount) = {
236253 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
237- let stakedTotal = readStaked(stakedTotalKEY)
254+ let stakedTotal = toBigInt(readStaked(stakedTotalKEY))
255+ let nonZeroStakedTotal = if ((stakedTotal == zeroBigInt))
256+ then oneBigInt
257+ else stakedTotal
238258 let poolWeight = getIntegerValue(factoryContract, keyFactoryPoolWeight(poolAddressStr))
239259 let emissionStartBlock = getIntOrFail(emissionContract, keyEmissionStartBlock())
240260 let MULT3 = 1000
244264 let wxPerLpIntegralLastUpdHeightKEY = keyWxPerLpIntegralLastUpdHeight(lpAssetIdStr)
245265 let wxPerLpKEY = keyWxPerLp(lpAssetIdStr)
246266 let wxPerLpIntegralLastUpdHeight = getIntOrDefault(this, wxPerLpIntegralLastUpdHeightKEY, emissionStartBlock)
247- let wxPerLpIntegral = getIntOrZero(this, wxPerLpIntegralKEY)
267+ let wxPerLpIntegral = getBigIntFromStringOrZero(this, wxPerLpIntegralKEY)
248268 let wxPerLpOrZeroX3 = 0
249269 let dh = max([(height - wxPerLpIntegralLastUpdHeight), 0])
250270 let wxPerLpX3 = if ((wxPerLpOrZeroX3 != 0))
251- then wxPerLpOrZeroX3
252- else fraction(poolWxEmissionPerBlockX3, MULT8, stakedTotal)
253- let stakedTotalNew = (stakedTotal + lpDeltaAmount)
254- let wxPerLpIntegralNew = (wxPerLpIntegral + (wxPerLpX3 * dh))
255- let wxPerLpX3New = (poolWxEmissionPerBlockX3 / stakedTotalNew)
271+ then toBigInt(wxPerLpOrZeroX3)
272+ else fraction(toBigInt(poolWxEmissionPerBlockX3), toBigInt(MULT8), nonZeroStakedTotal)
273+ let stakedTotalNew = (stakedTotal + toBigInt(lpDeltaAmount))
274+ let nonZeroStakedTotalNew = if ((stakedTotalNew == zeroBigInt))
275+ then oneBigInt
276+ else stakedTotalNew
277+ let wxPerLpIntegralNew = (wxPerLpIntegral + (wxPerLpX3 * toBigInt(dh)))
278+ let wxPerLpX3New = (toBigInt(poolWxEmissionPerBlockX3) / nonZeroStakedTotalNew)
256279 let wxPerLpIntegralLastUpdHeightNew = height
257280 let debug = makeString([toString(wxPerLpIntegralNew), toString(dh), toString(wxPerLpX3), toString(stakedTotal), toString(poolWxEmissionPerBlockX3), toString(wxEmissionPerBlockX3), toString(poolWeight)], "::")
258- $Tuple3(wxPerLpIntegralNew, [IntegerEntry(wxPerLpIntegralKEY, wxPerLpIntegralNew), IntegerEntry(wxPerLpIntegralLastUpdHeightKEY, wxPerLpIntegralLastUpdHeightNew), IntegerEntry(wxPerLpKEY, wxPerLpX3New)], debug)
281+ $Tuple3(wxPerLpIntegralNew, [StringEntry(wxPerLpIntegralKEY, toString(wxPerLpIntegralNew)), IntegerEntry(wxPerLpIntegralLastUpdHeightKEY, wxPerLpIntegralLastUpdHeightNew), StringEntry(wxPerLpKEY, toString(wxPerLpX3New))], debug)
259282 }
260283
261284
262285 func refreshINTEGRALS (lpAssetIdStr,userAddressStr,poolAddressStr,lpDeltaAmount) = {
263- let $t01057910701 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, lpDeltaAmount)
264- let wxPerLpIntegralNew = $t01057910701._1
265- let poolIntegralSTATE = $t01057910701._2
266- let poolDEBUG = $t01057910701._3
286+ let $t01187511997 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, lpDeltaAmount)
287+ let wxPerLpIntegralNew = $t01187511997._1
288+ let poolIntegralSTATE = $t01187511997._2
289+ let poolDEBUG = $t01187511997._3
267290 let MULT3 = 1000
268291 let stakedByUserKEY = keyStakedByUser(userAddressStr, lpAssetIdStr)
269292 let stakedByUser = readStaked(stakedByUserKEY)
270293 let wxToClaimUserKEY = keyWxToClaimUser(lpAssetIdStr, userAddressStr)
271294 let wxPerLpIntegralUserLastUpdHeightKEY = keyWxPerLpIntegralUserLastUpdHeight(lpAssetIdStr, userAddressStr)
272295 let wxPerLpIntegralUserLastKEY = keyWxPerLpIntegralUserLast(lpAssetIdStr, userAddressStr)
273- let wxToClaimUser = getIntOrZero(this, wxToClaimUserKEY)
296+ let wxToClaimUser = getBigIntFromStringOrZero(this, wxToClaimUserKEY)
274297 let wxPerLpIntegralUserLastUpdHeightOrZero = getIntOrZero(this, wxPerLpIntegralUserLastUpdHeightKEY)
275- let wxPerLpIntegralUserLast = calcWxPerLpIntegralUserLast(stakedByUser, wxPerLpIntegralUserLastUpdHeightOrZero, wxPerLpIntegralNew, wxPerLpIntegralUserLastKEY)
276- let wxToClaimUserNew = (wxToClaimUser + fraction((wxPerLpIntegralNew - wxPerLpIntegralUserLast), stakedByUser, (MULT8 * MULT3)))
298+ let wxPerLpIntegralUserLast = calcWxPerLpIntegralUserLast(toBigInt(stakedByUser), toBigInt(wxPerLpIntegralUserLastUpdHeightOrZero), wxPerLpIntegralNew, wxPerLpIntegralUserLastKEY)
299+ let MULT11 = (MULT8 * MULT3)
300+ let wxToClaimUserNew = (wxToClaimUser + fraction((wxPerLpIntegralNew - wxPerLpIntegralUserLast), toBigInt(stakedByUser), toBigInt(MULT11)))
277301 let wxPerLpIntegralUserLastNew = wxPerLpIntegralNew
278302 let wxPerLpIntegralUserLastUpdHeightNew = height
279303 let debug = makeString([toString(wxToClaimUserNew), toString(wxPerLpIntegralUserLast), toString(stakedByUser), poolDEBUG, toString(height)], "::")
280- $Tuple3(wxToClaimUserNew, (poolIntegralSTATE ++ [IntegerEntry(wxToClaimUserKEY, wxToClaimUserNew), IntegerEntry(wxPerLpIntegralUserLastUpdHeightKEY, wxPerLpIntegralUserLastUpdHeightNew), IntegerEntry(wxPerLpIntegralUserLastKEY, wxPerLpIntegralUserLastNew)]), debug)
304+ $Tuple3(wxToClaimUserNew, (poolIntegralSTATE ++ [StringEntry(wxToClaimUserKEY, toString(wxToClaimUserNew)), IntegerEntry(wxPerLpIntegralUserLastUpdHeightKEY, wxPerLpIntegralUserLastUpdHeightNew), StringEntry(wxPerLpIntegralUserLastKEY, toString(wxPerLpIntegralUserLastNew))]), debug)
281305 }
282306
283307
390414 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
391415 let stakedByUser = readStaked(stakedByUserKEY)
392416 let stakedTotal = readStaked(stakedTotalKEY)
393- let $t01516415281 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, amount)
394- let wxToClaimUserNew = $t01516415281._1
395- let integralSTATE = $t01516415281._2
396- let debug = $t01516415281._3
417+ let $t01680616923 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, amount)
418+ let wxToClaimUserNew = $t01680616923._1
419+ let integralSTATE = $t01680616923._2
420+ let debug = $t01680616923._3
397421 ([IntegerEntry(stakedByUserKEY, (stakedByUser + amount)), IntegerEntry(stakedTotalKEY, (stakedTotal + amount)), OperationHistoryEntry("stake", userAddressStr, lpAssetIdStr, amount, i.transactionId)] ++ integralSTATE)
398422 }
399423
414438 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
415439 let stakedByUser = readStaked(stakedByUserKEY)
416440 let stakedTotal = readStaked(stakedTotalKEY)
417- let $t01641816536 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, -(amount))
418- let wxToClaimUserNew = $t01641816536._1
419- let integralSTATE = $t01641816536._2
420- let debug = $t01641816536._3
441+ let $t01806018178 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, -(amount))
442+ let wxToClaimUserNew = $t01806018178._1
443+ let integralSTATE = $t01806018178._2
444+ let debug = $t01806018178._3
421445 if ((amount > stakedByUser))
422446 then throw("passed amount is less then available")
423447 else ([IntegerEntry(stakedByUserKEY, (stakedByUser - amount)), IntegerEntry(stakedTotalKEY, (stakedTotal - amount)), ScriptTransfer(i.caller, amount, lpAssetId), OperationHistoryEntry("unstake", userAddressStr, lpAssetIdStr, amount, i.transactionId)] ++ integralSTATE)
434458 let claimedTotalKEY = keyClaimedTotal(lpAssetIdStr)
435459 let claimedByUserMinRewardKEY = keyClaimedByUserMinReward(lpAssetIdStr, userAddressStr)
436460 let claimedByUserBoostRewardKEY = keyClaimedByUserBoostReward(lpAssetIdStr, userAddressStr)
437- let claimedByUser = getIntOrZero(this, claimedByUserKEY)
438- let claimedByUserMinReward = getIntOrZero(this, claimedByUserMinRewardKEY)
439- let claimedByUserBoostReward = getIntOrZero(this, claimedByUserBoostRewardKEY)
440- let claimedTotal = getIntOrZero(this, claimedTotalKEY)
441- let $t01772817840 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
442- let wxToClaimUserNew = $t01772817840._1
443- let integralSTATE = $t01772817840._2
444- let debug = $t01772817840._3
461+ let claimedByUser = toBigInt(getIntOrZero(this, claimedByUserKEY))
462+ let claimedByUserMinReward = toBigInt(getIntOrZero(this, claimedByUserMinRewardKEY))
463+ let claimedByUserBoostReward = toBigInt(getIntOrZero(this, claimedByUserBoostRewardKEY))
464+ let claimedTotal = getBigIntFromStringOrZero(this, claimedTotalKEY)
465+ let $t01941619528 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
466+ let wxToClaimUserNew = $t01941619528._1
467+ let integralSTATE = $t01941619528._2
468+ let debug = $t01941619528._3
445469 let availableToClaim = (wxToClaimUserNew - claimedByUser)
446- if ((0 >= availableToClaim))
470+ if ((zeroBigInt >= availableToClaim))
447471 then throw("nothing to claim")
448472 else {
449473 let wxAmountBoostTotal = asInt(asAnyList(invoke(boostingContract, "claimWxBoost", [lpAssetIdStr, userAddressStr], nil))[0])
450474 let minRewardPart = availableToClaim
451- let boostRewardPart = min([(minRewardPart * 2), wxAmountBoostTotal])
452- let wxAssetId = asByteVector(asAnyList(invoke(emissionContract, "emit", [minRewardPart], nil))[0])
453- let emitBoost = asAnyList(invoke(emissionContract, "emit", [boostRewardPart], nil))
475+ let boostRewardPart = min([(minRewardPart * toBigInt(2)), toBigInt(wxAmountBoostTotal)])
476+ let wxAssetId = asByteVector(asAnyList(invoke(emissionContract, "emit", [toInt(minRewardPart)], nil))[0])
477+ let emitBoost = asAnyList(invoke(emissionContract, "emit", [toInt(boostRewardPart)], nil))
454478 if ((emitBoost == emitBoost))
455- then [IntegerEntry(claimedByUserKEY, (claimedByUser + availableToClaim)), IntegerEntry(claimedByUserMinRewardKEY, (claimedByUserMinReward + minRewardPart)), IntegerEntry(claimedByUserBoostRewardKEY, (claimedByUserBoostReward + boostRewardPart)), IntegerEntry(claimedTotalKEY, (claimedTotal + availableToClaim)), ScriptTransfer(userAddress, minRewardPart, wxAssetId), ScriptTransfer(userAddress, boostRewardPart, wxAssetId), OperationHistoryEntry("claim", userAddressStr, lpAssetIdStr, availableToClaim, i.transactionId)]
479+ then {
480+ let claimedByUserValue = (claimedByUser + availableToClaim)
481+ let claimedByUserMinRewardPlusPart = (claimedByUserMinReward + minRewardPart)
482+ let claimedByUserBoostRewardPlusBoostRewardPart = (claimedByUserMinReward + minRewardPart)
483+ let claimedTotalPlusAvailableToClaim = (claimedByUserMinReward + minRewardPart)
484+[StringEntry(claimedByUserKEY, toString(claimedByUserValue)), StringEntry(claimedByUserMinRewardKEY, toString(claimedByUserMinRewardPlusPart)), StringEntry(claimedByUserBoostRewardKEY, toString(claimedByUserBoostRewardPlusBoostRewardPart)), StringEntry(claimedTotalKEY, toString(claimedTotalPlusAvailableToClaim)), ScriptTransfer(userAddress, toInt(minRewardPart), wxAssetId), ScriptTransfer(userAddress, toInt(boostRewardPart), wxAssetId), OperationHistoryEntry("claim", userAddressStr, lpAssetIdStr, toInt(availableToClaim), i.transactionId)]
485+ }
456486 else throw("Strict value is not equal to itself.")
457487 }
458488 }
476506 else (height - emissionStartBlock)
477507 let poolWxEmission = fraction((wxEmissionPerBlock * passedBlocks), poolWeight, POOLWEIGHTMULT)
478508 let userWxReward = fraction(poolWxEmission, stakedByUser, stakedTotal)
479- let $t02004120153 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
480- let wxToClaimUserNew = $t02004120153._1
481- let integralSTATE = $t02004120153._2
482- let debug = $t02004120153._3
483- let availableToClaim = (wxToClaimUserNew - claimedByUser)
509+ let $t02212822240 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
510+ let wxToClaimUserNew = $t02212822240._1
511+ let integralSTATE = $t02212822240._2
512+ let debug = $t02212822240._3
513+ let availableToClaim = (wxToClaimUserNew - toBigInt(claimedByUser))
484514 let boostInvResult = asAnyList(invoke(boostingContract, "claimWxBoostREADONLY", [lpAssetIdStr, userAddressStr], nil))
485515 let wxAmountBoostTotal = asInt(boostInvResult[0])
486516 let boostDebug = asString(boostInvResult[1])
487517 let minRewardPart = availableToClaim
488- let boostRewardPart = min([(minRewardPart * 2), wxAmountBoostTotal])
518+ let boostRewardPart = min([(minRewardPart * toBigInt(2)), toBigInt(wxAmountBoostTotal)])
489519 let totalReward = (minRewardPart + boostRewardPart)
490520 $Tuple2(nil, makeString(["%s%s%d%d%d%d%s", lpAssetIdStr, userAddressStr, toString(totalReward), toString(claimedByUser), toString(minRewardPart), toString(boostRewardPart), ((((debug + "::") + toString(userWxReward)) + "::BOOSTDEBUG::") + boostDebug)], SEP))
491521 }
496526 func onModifyWeight (lpAssetIdStr,poolAddressStr) = if ((i.caller != factoryContract))
497527 then throw("permissions denied")
498528 else {
499- let $t02103321143 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, 0)
500- let wxPerLpIntegralNew = $t02103321143._1
501- let poolIntegralSTATE = $t02103321143._2
502- let poolDEBUG = $t02103321143._3
529+ let $t02315323263 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, 0)
530+ let wxPerLpIntegralNew = $t02315323263._1
531+ let poolIntegralSTATE = $t02315323263._2
532+ let poolDEBUG = $t02315323263._3
503533 poolIntegralSTATE
504534 }
505535
Full:
OldNewDifferences
11 {-# STDLIB_VERSION 5 #-}
22 {-# SCRIPT_TYPE ACCOUNT #-}
33 {-# CONTENT_TYPE DAPP #-}
44 let SCALE8 = 8
55
66 let MULT8 = 100000000
77
88 let SCALE18 = 18
99
1010 let MULT18 = toBigInt(1000000000000000000)
1111
1212 let SEP = "__"
1313
1414 let POOLWEIGHTMULT = MULT8
15+
16+let zeroBigInt = toBigInt(0)
17+
18+let oneBigInt = toBigInt(1)
1519
1620 func asAnyList (val) = match val {
1721 case valAnyLyst: List[Any] =>
1822 valAnyLyst
1923 case _ =>
2024 throw("fail to cast into List[Any]")
2125 }
2226
2327
2428 func asInt (val) = match val {
2529 case valInt: Int =>
2630 valInt
2731 case _ =>
2832 throw("fail to cast into Int")
2933 }
3034
3135
3236 func asString (val) = match val {
3337 case valStr: String =>
3438 valStr
3539 case _ =>
3640 throw("fail to cast into Int")
3741 }
3842
3943
4044 func asByteVector (val) = match val {
4145 case valBin: ByteVector =>
4246 valBin
4347 case _ =>
4448 throw("fail to cast into Int")
4549 }
4650
4751
48-func getStringOrFail (key) = valueOrErrorMessage(getString(key), (("mandatory this." + key) + " is not defined"))
52+func getStringOrFail (address,key) = valueOrErrorMessage(getString(address, key), (("mandatory this." + key) + " is not defined"))
4953
5054
5155 func getStringByAddressOrFail (address,key) = valueOrErrorMessage(getString(address, key), (((("mandatory " + toString(address)) + ".") + key) + " is not defined"))
5256
5357
5458 func getIntOrZero (address,key) = valueOrElse(getInteger(address, key), 0)
5559
5660
5761 func getIntOrDefault (address,key,defaultVal) = valueOrElse(getInteger(address, key), defaultVal)
5862
5963
6064 func getIntOrFail (address,key) = valueOrErrorMessage(getInteger(address, key), (("mandatory this." + key) + " is not defined"))
65+
66+
67+func getBigIntFromStringOrZero (address,key) = value(parseBigInt(valueOrElse(getString(address, key), "0")))
68+
69+
70+func getBigIntFromStringOrDefault (address,key,defaultVal) = match getString(address, key) {
71+ case s: String =>
72+ value(parseBigInt(s))
73+ case _: Unit =>
74+ defaultVal
75+ case _ =>
76+ throw("Match error")
77+}
6178
6279
6380 func toX18 (origVal,origScaleMult) = fraction(toBigInt(origVal), MULT18, toBigInt(origScaleMult))
6481
6582
6683 func fromX18 (val,resultScaleMult) = toInt(fraction(val, toBigInt(resultScaleMult), MULT18))
6784
6885
6986 func keyFactoryAddress () = "%s%s__config__factoryAddress"
7087
7188
7289 let IdxFactoryCfgStakingDapp = 1
7390
7491 let IdxFactoryCfgBoostingDapp = 2
7592
7693 let IdxFactoryCfgIdoDapp = 3
7794
7895 let IdxFactoryCfgTeamDapp = 4
7996
8097 let IdxFactoryCfgEmissionDapp = 5
8198
8299 let IdxFactoryCfgRestDapp = 6
83100
84101 let IdxFactoryCfgSlippageDapp = 7
85102
86103 func keyFactoryCfg () = "%s__factoryConfig"
87104
88105
89106 func keyManagerPublicKey () = "%s__managerPublicKey"
90107
91108
92109 func keyMigratorPublicKey () = "%s__migratorPublicKey"
93110
94111
95112 func keyPendingManagerPublicKey () = "%s__pendingManagerPublicKey"
96113
97114
98115 func keyStablePoolAddonAddr () = "%s__stablePoolAddonAddr"
99116
100117
101118 func keyFactoryLp2AssetsMapping (lpAssetStr) = makeString(["%s%s%s", lpAssetStr, "mappings__lpAsset2PoolContract"], SEP)
102119
103120
104121 func keyFactoryLpList () = "%s__lpTokensList"
105122
106123
107124 func keyFactoryLpAssetToPoolContractAddress (lpAssetStr) = makeString(["%s%s%s", lpAssetStr, "mappings__lpAsset2PoolContract"], SEP)
108125
109126
110127 func keyFactoryPoolWeight (contractAddress) = makeString(["%s%s", "poolWeight", contractAddress], SEP)
111128
112129
113130 func readLpList (factory) = split(valueOrElse(getString(factory, keyFactoryLpList()), ""), SEP)
114131
115132
116133 func readFactoryCfgOrFail (factory) = split(getStringByAddressOrFail(factory, keyFactoryCfg()), SEP)
117134
118135
119136 func getBoostingAddressOrFail (factoryCfg) = addressFromStringValue(factoryCfg[IdxFactoryCfgBoostingDapp])
120137
121138
122139 func getEmissionAddressOrFail (factoryCfg) = addressFromStringValue(factoryCfg[IdxFactoryCfgEmissionDapp])
123140
124141
125142 func getStakingAddressOrFail (factoryCfg) = addressFromStringValue(factoryCfg[IdxFactoryCfgStakingDapp])
126143
127144
128145 func keyEmissionRatePerBlockCurrent () = "%s%s__ratePerBlock__current"
129146
130147
131148 func keyEmissionRatePerBlockMaxCurrent () = "%s%s__ratePerBlockMax__current"
132149
133150
134151 func keyEmissionStartBlock () = "%s%s__emission__startBlock"
135152
136153
137154 func keyEmissionDurationInBlocks () = "%s%s__emission__duration"
138155
139156
140157 func keyEmissionEndBlock () = "%s%s__emission__endBlock"
141158
142159
143160 func keyStakedByUser (userAddressStr,lpAssetIdStr) = makeString(["%s%s%s__staked", userAddressStr, lpAssetIdStr], SEP)
144161
145162
146163 func keyStakedTotal (lpAssetIdStr) = ("%s%s%s__staked__total__" + lpAssetIdStr)
147164
148165
149166 func keyClaimedByUser (lpAssetIdStr,userAddressStr) = makeString(["%s%s%s__claimed", userAddressStr, lpAssetIdStr], SEP)
150167
151168
152169 func keyClaimedByUserMinReward (lpAssetIdStr,userAddressStr) = makeString(["%s%s%s__claimedMinReward", userAddressStr, lpAssetIdStr], SEP)
153170
154171
155172 func keyClaimedByUserBoostReward (lpAssetIdStr,userAddressStr) = makeString(["%s%s%s__claimedBoostReward", userAddressStr, lpAssetIdStr], SEP)
156173
157174
158-func keyClaimedTotal (lpAssetIdStr) = makeString(["%s%s%s__claimed", "total", lpAssetIdStr], SEP)
175+func keyClaimedTotal (lpAssetIdStr) = makeString(["%s%s%s__claimed__total", lpAssetIdStr], SEP)
159176
160177
161178 func readStaked (key) = valueOrElse(getInteger(this, key), 0)
162179
163180
164181 func keyLastTotalLpBalance (lpAssetId) = makeString(["%s%s%s", lpAssetId, "total", "bal"], SEP)
165182
166183
167184 func keyLastUserLpBalance (lpAssetId,userAddress) = makeString(["%s%s%s", lpAssetId, userAddress, "bal"], SEP)
168185
169186
170187 func keyTotalLpBalanceIntegral (lpAssetId) = makeString(["%s%s%s", lpAssetId, "total", "balINT"], SEP)
171188
172189
173190 func keyUserLpBalanceIntegral (lpAssetId,userAddress) = makeString(["%s%s%s", lpAssetId, userAddress, "balINT"], SEP)
174191
175192
176193 func keyTotalLpBalanceIntegralLastUpdHeight (lpAssetId) = makeString(["%s%s%s", lpAssetId, "total", "lastUpd"], SEP)
177194
178195
179196 func keyUserLpBalanceIntegralLastUpdHeight (lpAssetId,userAddress) = makeString(["%s%s%s", lpAssetId, userAddress, "lastUpd"], SEP)
180197
181198
182199 func keyWxPerLpIntegral (lpAssetId) = makeString(["%s%s%s%s", lpAssetId, "common", "lpInt"], SEP)
183200
184201
185202 func keyWxPerLpIntegralLastUpdHeight (lpAssetId) = makeString(["%s%s%s%s", lpAssetId, "common", "lpIntH"], SEP)
186203
187204
188205 func keyWxToClaimUser (lpAssetId,userAddress) = makeString(["%s%s%s%s", lpAssetId, userAddress, "lpInt"], SEP)
189206
190207
191208 func keyWxPerLpIntegralUserLastUpdHeight (lpAssetId,userAddress) = makeString(["%s%s%s%s", lpAssetId, userAddress, "lpIntH"], SEP)
192209
193210
194211 func keyWxPerLp (lpAssetId) = makeString(["%s", lpAssetId, "wxPerLp"], SEP)
195212
196213
197214 func keyWxPerLpX18 (lpAssetId) = makeString(["%s", lpAssetId, "wxPerLpX18"], SEP)
198215
199216
200217 func keyWxPerLpIntegralUserLast (lpAssetId,userAddress) = makeString(["%s%s%s%s", lpAssetId, userAddress, "uIntL"], SEP)
201218
202219
203220 func keyOperationHistoryRecord (type,userAddress,txId58) = makeString(["%s%s%s%s__history", type, userAddress, txId58], SEP)
204221
205222
206223 func formatHistoryRecord (userAddress,lpAssetId,type,amount) = makeString(["%s%s%s%d%d%d", userAddress, lpAssetId, type, toString(height), toString(lastBlock.timestamp), toString(amount)], SEP)
207224
208225
209226 func OperationHistoryEntry (type,userAddress,lpAssetId,amount,txId) = StringEntry(keyOperationHistoryRecord(type, userAddress, toBase58String(txId)), formatHistoryRecord(userAddress, lpAssetId, type, amount))
210227
211228
212-let factoryAddress = getStringOrFail(keyFactoryAddress())
229+let factoryAddress = getStringOrFail(this, keyFactoryAddress())
213230
214231 let factoryContract = addressFromStringValue(factoryAddress)
215232
216233 let factoryCfg = readFactoryCfgOrFail(factoryContract)
217234
218235 let emissionContract = getEmissionAddressOrFail(factoryCfg)
219236
220237 let boostingContract = getBoostingAddressOrFail(factoryCfg)
221238
222-func calcWxPerLpIntegralUserLast (stakedByUser,wxPerLpIntegralUserLastUpdHeightOrZero,wxPerLpIntegralNew,wxPerLpIntegralUserLastKEY) = if (if ((wxPerLpIntegralUserLastUpdHeightOrZero == 0))
223- then (stakedByUser > 0)
239+func calcWxPerLpIntegralUserLast (stakedByUser,wxPerLpIntegralUserLastUpdHeightOrZero,wxPerLpIntegralNew,wxPerLpIntegralUserLastKEY) = if (if ((wxPerLpIntegralUserLastUpdHeightOrZero == zeroBigInt))
240+ then (stakedByUser > zeroBigInt)
224241 else false)
225- then 0
226- else if ((stakedByUser == 0))
242+ then zeroBigInt
243+ else if ((stakedByUser == zeroBigInt))
227244 then wxPerLpIntegralNew
228- else if (if ((wxPerLpIntegralUserLastUpdHeightOrZero > 0))
229- then (stakedByUser > 0)
245+ else if (if ((wxPerLpIntegralUserLastUpdHeightOrZero > zeroBigInt))
246+ then (stakedByUser > zeroBigInt)
230247 else false)
231- then getIntOrFail(this, wxPerLpIntegralUserLastKEY)
248+ then value(parseBigInt(getStringOrFail(this, wxPerLpIntegralUserLastKEY)))
232249 else throw("calcWxPerLpIntegralUserLast: unexpected state")
233250
234251
235252 func refreshPoolINTEGRALS (lpAssetIdStr,poolAddressStr,lpDeltaAmount) = {
236253 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
237- let stakedTotal = readStaked(stakedTotalKEY)
254+ let stakedTotal = toBigInt(readStaked(stakedTotalKEY))
255+ let nonZeroStakedTotal = if ((stakedTotal == zeroBigInt))
256+ then oneBigInt
257+ else stakedTotal
238258 let poolWeight = getIntegerValue(factoryContract, keyFactoryPoolWeight(poolAddressStr))
239259 let emissionStartBlock = getIntOrFail(emissionContract, keyEmissionStartBlock())
240260 let MULT3 = 1000
241261 let wxEmissionPerBlockX3 = (getIntOrFail(emissionContract, keyEmissionRatePerBlockCurrent()) * MULT3)
242262 let poolWxEmissionPerBlockX3 = fraction(wxEmissionPerBlockX3, poolWeight, (POOLWEIGHTMULT * 3))
243263 let wxPerLpIntegralKEY = keyWxPerLpIntegral(lpAssetIdStr)
244264 let wxPerLpIntegralLastUpdHeightKEY = keyWxPerLpIntegralLastUpdHeight(lpAssetIdStr)
245265 let wxPerLpKEY = keyWxPerLp(lpAssetIdStr)
246266 let wxPerLpIntegralLastUpdHeight = getIntOrDefault(this, wxPerLpIntegralLastUpdHeightKEY, emissionStartBlock)
247- let wxPerLpIntegral = getIntOrZero(this, wxPerLpIntegralKEY)
267+ let wxPerLpIntegral = getBigIntFromStringOrZero(this, wxPerLpIntegralKEY)
248268 let wxPerLpOrZeroX3 = 0
249269 let dh = max([(height - wxPerLpIntegralLastUpdHeight), 0])
250270 let wxPerLpX3 = if ((wxPerLpOrZeroX3 != 0))
251- then wxPerLpOrZeroX3
252- else fraction(poolWxEmissionPerBlockX3, MULT8, stakedTotal)
253- let stakedTotalNew = (stakedTotal + lpDeltaAmount)
254- let wxPerLpIntegralNew = (wxPerLpIntegral + (wxPerLpX3 * dh))
255- let wxPerLpX3New = (poolWxEmissionPerBlockX3 / stakedTotalNew)
271+ then toBigInt(wxPerLpOrZeroX3)
272+ else fraction(toBigInt(poolWxEmissionPerBlockX3), toBigInt(MULT8), nonZeroStakedTotal)
273+ let stakedTotalNew = (stakedTotal + toBigInt(lpDeltaAmount))
274+ let nonZeroStakedTotalNew = if ((stakedTotalNew == zeroBigInt))
275+ then oneBigInt
276+ else stakedTotalNew
277+ let wxPerLpIntegralNew = (wxPerLpIntegral + (wxPerLpX3 * toBigInt(dh)))
278+ let wxPerLpX3New = (toBigInt(poolWxEmissionPerBlockX3) / nonZeroStakedTotalNew)
256279 let wxPerLpIntegralLastUpdHeightNew = height
257280 let debug = makeString([toString(wxPerLpIntegralNew), toString(dh), toString(wxPerLpX3), toString(stakedTotal), toString(poolWxEmissionPerBlockX3), toString(wxEmissionPerBlockX3), toString(poolWeight)], "::")
258- $Tuple3(wxPerLpIntegralNew, [IntegerEntry(wxPerLpIntegralKEY, wxPerLpIntegralNew), IntegerEntry(wxPerLpIntegralLastUpdHeightKEY, wxPerLpIntegralLastUpdHeightNew), IntegerEntry(wxPerLpKEY, wxPerLpX3New)], debug)
281+ $Tuple3(wxPerLpIntegralNew, [StringEntry(wxPerLpIntegralKEY, toString(wxPerLpIntegralNew)), IntegerEntry(wxPerLpIntegralLastUpdHeightKEY, wxPerLpIntegralLastUpdHeightNew), StringEntry(wxPerLpKEY, toString(wxPerLpX3New))], debug)
259282 }
260283
261284
262285 func refreshINTEGRALS (lpAssetIdStr,userAddressStr,poolAddressStr,lpDeltaAmount) = {
263- let $t01057910701 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, lpDeltaAmount)
264- let wxPerLpIntegralNew = $t01057910701._1
265- let poolIntegralSTATE = $t01057910701._2
266- let poolDEBUG = $t01057910701._3
286+ let $t01187511997 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, lpDeltaAmount)
287+ let wxPerLpIntegralNew = $t01187511997._1
288+ let poolIntegralSTATE = $t01187511997._2
289+ let poolDEBUG = $t01187511997._3
267290 let MULT3 = 1000
268291 let stakedByUserKEY = keyStakedByUser(userAddressStr, lpAssetIdStr)
269292 let stakedByUser = readStaked(stakedByUserKEY)
270293 let wxToClaimUserKEY = keyWxToClaimUser(lpAssetIdStr, userAddressStr)
271294 let wxPerLpIntegralUserLastUpdHeightKEY = keyWxPerLpIntegralUserLastUpdHeight(lpAssetIdStr, userAddressStr)
272295 let wxPerLpIntegralUserLastKEY = keyWxPerLpIntegralUserLast(lpAssetIdStr, userAddressStr)
273- let wxToClaimUser = getIntOrZero(this, wxToClaimUserKEY)
296+ let wxToClaimUser = getBigIntFromStringOrZero(this, wxToClaimUserKEY)
274297 let wxPerLpIntegralUserLastUpdHeightOrZero = getIntOrZero(this, wxPerLpIntegralUserLastUpdHeightKEY)
275- let wxPerLpIntegralUserLast = calcWxPerLpIntegralUserLast(stakedByUser, wxPerLpIntegralUserLastUpdHeightOrZero, wxPerLpIntegralNew, wxPerLpIntegralUserLastKEY)
276- let wxToClaimUserNew = (wxToClaimUser + fraction((wxPerLpIntegralNew - wxPerLpIntegralUserLast), stakedByUser, (MULT8 * MULT3)))
298+ let wxPerLpIntegralUserLast = calcWxPerLpIntegralUserLast(toBigInt(stakedByUser), toBigInt(wxPerLpIntegralUserLastUpdHeightOrZero), wxPerLpIntegralNew, wxPerLpIntegralUserLastKEY)
299+ let MULT11 = (MULT8 * MULT3)
300+ let wxToClaimUserNew = (wxToClaimUser + fraction((wxPerLpIntegralNew - wxPerLpIntegralUserLast), toBigInt(stakedByUser), toBigInt(MULT11)))
277301 let wxPerLpIntegralUserLastNew = wxPerLpIntegralNew
278302 let wxPerLpIntegralUserLastUpdHeightNew = height
279303 let debug = makeString([toString(wxToClaimUserNew), toString(wxPerLpIntegralUserLast), toString(stakedByUser), poolDEBUG, toString(height)], "::")
280- $Tuple3(wxToClaimUserNew, (poolIntegralSTATE ++ [IntegerEntry(wxToClaimUserKEY, wxToClaimUserNew), IntegerEntry(wxPerLpIntegralUserLastUpdHeightKEY, wxPerLpIntegralUserLastUpdHeightNew), IntegerEntry(wxPerLpIntegralUserLastKEY, wxPerLpIntegralUserLastNew)]), debug)
304+ $Tuple3(wxToClaimUserNew, (poolIntegralSTATE ++ [StringEntry(wxToClaimUserKEY, toString(wxToClaimUserNew)), IntegerEntry(wxPerLpIntegralUserLastUpdHeightKEY, wxPerLpIntegralUserLastUpdHeightNew), StringEntry(wxPerLpIntegralUserLastKEY, toString(wxPerLpIntegralUserLastNew))]), debug)
281305 }
282306
283307
284308 func managerPublicKeyOrUnit () = match getString(keyManagerPublicKey()) {
285309 case s: String =>
286310 fromBase58String(s)
287311 case _: Unit =>
288312 unit
289313 case _ =>
290314 throw("Match error")
291315 }
292316
293317
294318 func migratorPublicKeyOrUnit () = match getString(keyMigratorPublicKey()) {
295319 case s: String =>
296320 fromBase58String(s)
297321 case _: Unit =>
298322 unit
299323 case _ =>
300324 throw("Match error")
301325 }
302326
303327
304328 func pendingManagerPublicKeyOrUnit () = match getString(keyPendingManagerPublicKey()) {
305329 case s: String =>
306330 fromBase58String(s)
307331 case _: Unit =>
308332 unit
309333 case _ =>
310334 throw("Match error")
311335 }
312336
313337
314338 func mustManager (i) = {
315339 let pd = throw("Permission denied")
316340 match managerPublicKeyOrUnit() {
317341 case pk: ByteVector =>
318342 if ((i.callerPublicKey == pk))
319343 then true
320344 else pd
321345 case _: Unit =>
322346 if ((i.caller == this))
323347 then true
324348 else pd
325349 case _ =>
326350 throw("Match error")
327351 }
328352 }
329353
330354
331355 @Callable(i)
332356 func constructor (factoryAddressStr) = {
333357 let checkCaller = mustManager(i)
334358 if ((checkCaller == checkCaller))
335359 then [StringEntry(keyFactoryAddress(), factoryAddressStr)]
336360 else throw("Strict value is not equal to itself.")
337361 }
338362
339363
340364
341365 @Callable(i)
342366 func setManager (pendingManagerPublicKey) = {
343367 let checkCaller = mustManager(i)
344368 if ((checkCaller == checkCaller))
345369 then {
346370 let checkManagerPublicKey = fromBase58String(pendingManagerPublicKey)
347371 if ((checkManagerPublicKey == checkManagerPublicKey))
348372 then [StringEntry(keyPendingManagerPublicKey(), pendingManagerPublicKey)]
349373 else throw("Strict value is not equal to itself.")
350374 }
351375 else throw("Strict value is not equal to itself.")
352376 }
353377
354378
355379
356380 @Callable(i)
357381 func confirmManager () = {
358382 let pm = pendingManagerPublicKeyOrUnit()
359383 let hasPM = if (isDefined(pm))
360384 then true
361385 else throw("No pending manager")
362386 if ((hasPM == hasPM))
363387 then {
364388 let checkPM = if ((i.callerPublicKey == value(pm)))
365389 then true
366390 else throw("You are not pending manager")
367391 if ((checkPM == checkPM))
368392 then [StringEntry(keyManagerPublicKey(), toBase58String(value(pm))), DeleteEntry(keyPendingManagerPublicKey())]
369393 else throw("Strict value is not equal to itself.")
370394 }
371395 else throw("Strict value is not equal to itself.")
372396 }
373397
374398
375399
376400 @Callable(i)
377401 func stake () = if ((size(i.payments) != 1))
378402 then throw("invalid payment - exact one payment must be attached")
379403 else {
380404 let pmt = i.payments[0]
381405 let lpAssetId = value(pmt.assetId)
382406 let lpAssetIdStr = toBase58String(lpAssetId)
383407 let amount = pmt.amount
384408 let poolAddressStr = valueOrErrorMessage(getString(factoryContract, keyFactoryLp2AssetsMapping(lpAssetIdStr)), ("unsupported lp asset " + lpAssetIdStr))
385409 let callerStr = toString(i.caller)
386410 let userAddressStr = if ((callerStr == poolAddressStr))
387411 then toString(i.originCaller)
388412 else callerStr
389413 let stakedByUserKEY = keyStakedByUser(userAddressStr, lpAssetIdStr)
390414 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
391415 let stakedByUser = readStaked(stakedByUserKEY)
392416 let stakedTotal = readStaked(stakedTotalKEY)
393- let $t01516415281 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, amount)
394- let wxToClaimUserNew = $t01516415281._1
395- let integralSTATE = $t01516415281._2
396- let debug = $t01516415281._3
417+ let $t01680616923 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, amount)
418+ let wxToClaimUserNew = $t01680616923._1
419+ let integralSTATE = $t01680616923._2
420+ let debug = $t01680616923._3
397421 ([IntegerEntry(stakedByUserKEY, (stakedByUser + amount)), IntegerEntry(stakedTotalKEY, (stakedTotal + amount)), OperationHistoryEntry("stake", userAddressStr, lpAssetIdStr, amount, i.transactionId)] ++ integralSTATE)
398422 }
399423
400424
401425
402426 @Callable(i)
403427 func unstake (lpAssetIdStr,amount) = {
404428 let lpAssetId = fromBase58String(lpAssetIdStr)
405429 let poolAddressStr = valueOrErrorMessage(getString(factoryContract, keyFactoryLp2AssetsMapping(lpAssetIdStr)), ("unsupported lp asset " + lpAssetIdStr))
406430 let poolAddon = valueOrElse(getString(this, keyStablePoolAddonAddr()), poolAddressStr)
407431 let callerStr = toString(i.caller)
408432 let userAddressStr = if (if ((callerStr == poolAddressStr))
409433 then true
410434 else (callerStr == poolAddon))
411435 then toString(i.originCaller)
412436 else callerStr
413437 let stakedByUserKEY = keyStakedByUser(userAddressStr, lpAssetIdStr)
414438 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
415439 let stakedByUser = readStaked(stakedByUserKEY)
416440 let stakedTotal = readStaked(stakedTotalKEY)
417- let $t01641816536 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, -(amount))
418- let wxToClaimUserNew = $t01641816536._1
419- let integralSTATE = $t01641816536._2
420- let debug = $t01641816536._3
441+ let $t01806018178 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, -(amount))
442+ let wxToClaimUserNew = $t01806018178._1
443+ let integralSTATE = $t01806018178._2
444+ let debug = $t01806018178._3
421445 if ((amount > stakedByUser))
422446 then throw("passed amount is less then available")
423447 else ([IntegerEntry(stakedByUserKEY, (stakedByUser - amount)), IntegerEntry(stakedTotalKEY, (stakedTotal - amount)), ScriptTransfer(i.caller, amount, lpAssetId), OperationHistoryEntry("unstake", userAddressStr, lpAssetIdStr, amount, i.transactionId)] ++ integralSTATE)
424448 }
425449
426450
427451
428452 @Callable(i)
429453 func claimWx (lpAssetIdStr) = {
430454 let userAddress = i.caller
431455 let userAddressStr = toString(i.caller)
432456 let poolAddressStr = getStringByAddressOrFail(factoryContract, keyFactoryLpAssetToPoolContractAddress(lpAssetIdStr))
433457 let claimedByUserKEY = keyClaimedByUser(lpAssetIdStr, userAddressStr)
434458 let claimedTotalKEY = keyClaimedTotal(lpAssetIdStr)
435459 let claimedByUserMinRewardKEY = keyClaimedByUserMinReward(lpAssetIdStr, userAddressStr)
436460 let claimedByUserBoostRewardKEY = keyClaimedByUserBoostReward(lpAssetIdStr, userAddressStr)
437- let claimedByUser = getIntOrZero(this, claimedByUserKEY)
438- let claimedByUserMinReward = getIntOrZero(this, claimedByUserMinRewardKEY)
439- let claimedByUserBoostReward = getIntOrZero(this, claimedByUserBoostRewardKEY)
440- let claimedTotal = getIntOrZero(this, claimedTotalKEY)
441- let $t01772817840 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
442- let wxToClaimUserNew = $t01772817840._1
443- let integralSTATE = $t01772817840._2
444- let debug = $t01772817840._3
461+ let claimedByUser = toBigInt(getIntOrZero(this, claimedByUserKEY))
462+ let claimedByUserMinReward = toBigInt(getIntOrZero(this, claimedByUserMinRewardKEY))
463+ let claimedByUserBoostReward = toBigInt(getIntOrZero(this, claimedByUserBoostRewardKEY))
464+ let claimedTotal = getBigIntFromStringOrZero(this, claimedTotalKEY)
465+ let $t01941619528 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
466+ let wxToClaimUserNew = $t01941619528._1
467+ let integralSTATE = $t01941619528._2
468+ let debug = $t01941619528._3
445469 let availableToClaim = (wxToClaimUserNew - claimedByUser)
446- if ((0 >= availableToClaim))
470+ if ((zeroBigInt >= availableToClaim))
447471 then throw("nothing to claim")
448472 else {
449473 let wxAmountBoostTotal = asInt(asAnyList(invoke(boostingContract, "claimWxBoost", [lpAssetIdStr, userAddressStr], nil))[0])
450474 let minRewardPart = availableToClaim
451- let boostRewardPart = min([(minRewardPart * 2), wxAmountBoostTotal])
452- let wxAssetId = asByteVector(asAnyList(invoke(emissionContract, "emit", [minRewardPart], nil))[0])
453- let emitBoost = asAnyList(invoke(emissionContract, "emit", [boostRewardPart], nil))
475+ let boostRewardPart = min([(minRewardPart * toBigInt(2)), toBigInt(wxAmountBoostTotal)])
476+ let wxAssetId = asByteVector(asAnyList(invoke(emissionContract, "emit", [toInt(minRewardPart)], nil))[0])
477+ let emitBoost = asAnyList(invoke(emissionContract, "emit", [toInt(boostRewardPart)], nil))
454478 if ((emitBoost == emitBoost))
455- then [IntegerEntry(claimedByUserKEY, (claimedByUser + availableToClaim)), IntegerEntry(claimedByUserMinRewardKEY, (claimedByUserMinReward + minRewardPart)), IntegerEntry(claimedByUserBoostRewardKEY, (claimedByUserBoostReward + boostRewardPart)), IntegerEntry(claimedTotalKEY, (claimedTotal + availableToClaim)), ScriptTransfer(userAddress, minRewardPart, wxAssetId), ScriptTransfer(userAddress, boostRewardPart, wxAssetId), OperationHistoryEntry("claim", userAddressStr, lpAssetIdStr, availableToClaim, i.transactionId)]
479+ then {
480+ let claimedByUserValue = (claimedByUser + availableToClaim)
481+ let claimedByUserMinRewardPlusPart = (claimedByUserMinReward + minRewardPart)
482+ let claimedByUserBoostRewardPlusBoostRewardPart = (claimedByUserMinReward + minRewardPart)
483+ let claimedTotalPlusAvailableToClaim = (claimedByUserMinReward + minRewardPart)
484+[StringEntry(claimedByUserKEY, toString(claimedByUserValue)), StringEntry(claimedByUserMinRewardKEY, toString(claimedByUserMinRewardPlusPart)), StringEntry(claimedByUserBoostRewardKEY, toString(claimedByUserBoostRewardPlusBoostRewardPart)), StringEntry(claimedTotalKEY, toString(claimedTotalPlusAvailableToClaim)), ScriptTransfer(userAddress, toInt(minRewardPart), wxAssetId), ScriptTransfer(userAddress, toInt(boostRewardPart), wxAssetId), OperationHistoryEntry("claim", userAddressStr, lpAssetIdStr, toInt(availableToClaim), i.transactionId)]
485+ }
456486 else throw("Strict value is not equal to itself.")
457487 }
458488 }
459489
460490
461491
462492 @Callable(i)
463493 func claimWxREADONLY (lpAssetIdStr,userAddressStr) = {
464494 let stakedByUserKEY = keyStakedByUser(userAddressStr, lpAssetIdStr)
465495 let stakedTotalKEY = keyStakedTotal(lpAssetIdStr)
466496 let claimedByUserKEY = keyClaimedByUser(lpAssetIdStr, userAddressStr)
467497 let stakedByUser = readStaked(stakedByUserKEY)
468498 let stakedTotal = readStaked(stakedTotalKEY)
469499 let claimedByUser = getIntOrZero(this, claimedByUserKEY)
470500 let poolAddressStr = getStringByAddressOrFail(factoryContract, keyFactoryLpAssetToPoolContractAddress(lpAssetIdStr))
471501 let poolWeight = getIntegerValue(factoryContract, keyFactoryPoolWeight(poolAddressStr))
472502 let wxEmissionPerBlock = getIntOrFail(emissionContract, keyEmissionRatePerBlockCurrent())
473503 let emissionStartBlock = getIntOrFail(emissionContract, keyEmissionStartBlock())
474504 let passedBlocks = if ((emissionStartBlock > height))
475505 then 0
476506 else (height - emissionStartBlock)
477507 let poolWxEmission = fraction((wxEmissionPerBlock * passedBlocks), poolWeight, POOLWEIGHTMULT)
478508 let userWxReward = fraction(poolWxEmission, stakedByUser, stakedTotal)
479- let $t02004120153 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
480- let wxToClaimUserNew = $t02004120153._1
481- let integralSTATE = $t02004120153._2
482- let debug = $t02004120153._3
483- let availableToClaim = (wxToClaimUserNew - claimedByUser)
509+ let $t02212822240 = refreshINTEGRALS(lpAssetIdStr, userAddressStr, poolAddressStr, 0)
510+ let wxToClaimUserNew = $t02212822240._1
511+ let integralSTATE = $t02212822240._2
512+ let debug = $t02212822240._3
513+ let availableToClaim = (wxToClaimUserNew - toBigInt(claimedByUser))
484514 let boostInvResult = asAnyList(invoke(boostingContract, "claimWxBoostREADONLY", [lpAssetIdStr, userAddressStr], nil))
485515 let wxAmountBoostTotal = asInt(boostInvResult[0])
486516 let boostDebug = asString(boostInvResult[1])
487517 let minRewardPart = availableToClaim
488- let boostRewardPart = min([(minRewardPart * 2), wxAmountBoostTotal])
518+ let boostRewardPart = min([(minRewardPart * toBigInt(2)), toBigInt(wxAmountBoostTotal)])
489519 let totalReward = (minRewardPart + boostRewardPart)
490520 $Tuple2(nil, makeString(["%s%s%d%d%d%d%s", lpAssetIdStr, userAddressStr, toString(totalReward), toString(claimedByUser), toString(minRewardPart), toString(boostRewardPart), ((((debug + "::") + toString(userWxReward)) + "::BOOSTDEBUG::") + boostDebug)], SEP))
491521 }
492522
493523
494524
495525 @Callable(i)
496526 func onModifyWeight (lpAssetIdStr,poolAddressStr) = if ((i.caller != factoryContract))
497527 then throw("permissions denied")
498528 else {
499- let $t02103321143 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, 0)
500- let wxPerLpIntegralNew = $t02103321143._1
501- let poolIntegralSTATE = $t02103321143._2
502- let poolDEBUG = $t02103321143._3
529+ let $t02315323263 = refreshPoolINTEGRALS(lpAssetIdStr, poolAddressStr, 0)
530+ let wxPerLpIntegralNew = $t02315323263._1
531+ let poolIntegralSTATE = $t02315323263._2
532+ let poolDEBUG = $t02315323263._3
503533 poolIntegralSTATE
504534 }
505535
506536
507537 @Verifier(tx)
508538 func verify () = {
509539 let targetPublicKey = match managerPublicKeyOrUnit() {
510540 case pk: ByteVector =>
511541 pk
512542 case _: Unit =>
513543 tx.senderPublicKey
514544 case _ =>
515545 throw("Match error")
516546 }
517547 let migratorPublicKey = match migratorPublicKeyOrUnit() {
518548 case pk: ByteVector =>
519549 pk
520550 case _: Unit =>
521551 tx.senderPublicKey
522552 case _ =>
523553 throw("Match error")
524554 }
525555 if (sigVerify(tx.bodyBytes, tx.proofs[0], targetPublicKey))
526556 then true
527557 else sigVerify(tx.bodyBytes, tx.proofs[0], migratorPublicKey)
528558 }
529559

github/deemru/w8io/6500d08 
158.81 ms