2023.10.11 20:39 [3860132] smart account 3P8w8NXZUtYdCA13tHbDY5sW4mC27ZFJgG3 > SELF 0.00000000 Waves

{ "type": 13, "id": "AfpEi7zLmx7g617RrcUR1NgDLi9RSoDWJirTh9jAtTYe", "fee": 3100000, "feeAssetId": null, "timestamp": 1697050097579, "version": 2, "chainId": 87, "sender": "3P8w8NXZUtYdCA13tHbDY5sW4mC27ZFJgG3", "senderPublicKey": "6uKJV5r5qjqG9uVK4Q24W7zG5KZtGtKXz3NWRMwfZbB7", "proofs": [ "4YA6yePsWUk6rQLxYiifFZwhnFG7vkn6KfQ38bdJwoS7RbLVhhwusTxRQTfquggCbFckHiapnHwoygzQDNdHeU6G", "4guv8hyBJFFs3TvUb9yJPmcVEWDgCmPxF7EYCvZhSj9fpt7wPfEy2SmDptNnkmqGrXH1Yg1njHsk2yVPV2NWF3BQ", "", "5swRzrDiGPie8PWYn336VtRNc5KAqWuLom39VFMr5FwTNgk2DameKuGN5RqYWsNvdmELJosvYudB3t5xYUpVM3bA" ], "script": "base64:BgIzCAISBwoFCAgBAQgSBAoCAQESABIDCgEBEgASABIAEgASABIDCgEIEgQKAggBEgQKAggBYAALcmV2aXNpb25OdW0CAAAJc2VwYXJhdG9yAgJfXwADU0VQAgJfXwAFTVVMVDYAwIQ9AAVNVUxUOACAwtcvAAZNVUxUWDYJALYCAQUFTVVMVDYABk1VTFRYOAkAtgIBBQVNVUxUOAAHTVVMVFgxOAkAtgIBAICAkLu61q3wDQAKV0FWRVNJRFNUUgIFV0FWRVMAB1dBVkVTSUQJANkEAQUKV0FWRVNJRFNUUgAJREFZTUlMTElTAIC4mSkACU1BWEJBU0tFVAAJABlJZHhDb250cm9sQ2ZnTmV1dHJpbm9EYXBwAAEAGElkeENvbnRyb2xDZmdBdWN0aW9uRGFwcAACABRJZHhDb250cm9sQ2ZnUnBkRGFwcAADABVJZHhDb250cm9sQ2ZnTWF0aERhcHAABAAcSWR4Q29udHJvbENmZ0xpcXVpZGF0aW9uRGFwcAAFABVJZHhDb250cm9sQ2ZnUmVzdERhcHAABgAdSWR4Q29udHJvbENmZ05vZGVSZWdpc3RyeURhcHAABwAcSWR4Q29udHJvbENmZ05zYnRTdGFraW5nRGFwcAAIABlJZHhDb250cm9sQ2ZnTWVkaWF0b3JEYXBwAAkAG0lkeENvbnRyb2xDZmdHb3Zlcm5hbmNlRGFwcAANAQ9nZXRTdHJpbmdPckZhaWwCB2FkZHJlc3MDa2V5CQETdmFsdWVPckVycm9yTWVzc2FnZQIJAJ0IAgUHYWRkcmVzcwUDa2V5CQCsAgIJAKwCAgkArAICCQCsAgICCm1hbmRhdG9yeSAJAKUIAQUHYWRkcmVzcwIBLgUDa2V5Ag8gaXMgbm90IGRlZmluZWQBHWtleUNmZ1gyR25zYnRPZmZlckhlaWdodFN0YXJ0AAIlJXMlc19fY29uZmlnX194Mkduc2J0T2ZmZXJIZWlnaHRTdGFydAEba2V5Q2ZnWDJHbnNidE9mZmVySGVpZ2h0RW5kAAIjJXMlc19fY29uZmlnX194Mkduc2J0T2ZmZXJIZWlnaHRFbmQBEWtleUNvbnRyb2xBZGRyZXNzAAIcJXMlc19fY29uZmlnX19jb250cm9sQWRkcmVzcwENa2V5Q29udHJvbENmZwACESVzX19jb250cm9sQ29uZmlnARRyZWFkQ29udHJvbENmZ09yRmFpbAEHY29udHJvbAkAvAkCCQEPZ2V0U3RyaW5nT3JGYWlsAgUHY29udHJvbAkBDWtleUNvbnRyb2xDZmcABQNTRVABGGdldENvbnRyYWN0QWRkcmVzc09yRmFpbAIKY29udHJvbENmZwNpZHgJARN2YWx1ZU9yRXJyb3JNZXNzYWdlAgkApggBCQCRAwIFCmNvbnRyb2xDZmcFA2lkeAkArAICAi1Db250cm9sIGNmZyBkb2Vzbid0IGNvbnRhaW4gYWRkcmVzcyBhdCBpbmRleCAJAKQDAQUDaWR4AA9jb250cm9sQ29udHJhY3QJARFAZXh0ck5hdGl2ZSgxMDYyKQEJAQt2YWx1ZU9yRWxzZQIJAJ0IAgUEdGhpcwkBEWtleUNvbnRyb2xBZGRyZXNzAAIjM1A1QmZkNThQUGZOdkJNMkh5OFFmYmNEcU1lTnR6ZzdLZlAACmNvbnRyb2xDZmcJARRyZWFkQ29udHJvbENmZ09yRmFpbAEFD2NvbnRyb2xDb250cmFjdAAMbWF0aENvbnRyYWN0CQEYZ2V0Q29udHJhY3RBZGRyZXNzT3JGYWlsAgUKY29udHJvbENmZwUVSWR4Q29udHJvbENmZ01hdGhEYXBwABBuZXV0cmlub0NvbnRyYWN0CQEYZ2V0Q29udHJhY3RBZGRyZXNzT3JGYWlsAgUKY29udHJvbENmZwUZSWR4Q29udHJvbENmZ05ldXRyaW5vRGFwcAAPYXVjdGlvbkNvbnRyYWN0CQEYZ2V0Q29udHJhY3RBZGRyZXNzT3JGYWlsAgUKY29udHJvbENmZwUYSWR4Q29udHJvbENmZ0F1Y3Rpb25EYXBwAAtnb3ZDb250cmFjdAkBGGdldENvbnRyYWN0QWRkcmVzc09yRmFpbAIFCmNvbnRyb2xDZmcFG0lkeENvbnRyb2xDZmdHb3Zlcm5hbmNlRGFwcAATbmV1dHJpbm9EYW9Db250cmFjdAkBEUBleHRyTmF0aXZlKDEwNjIpAQIjM1BFaWlKUmtWNjZUMU5XN01vWTNER2dDYXhvRFJDZXo4ZkwAElJFTkVXX1NUQVJUX0hFSUdIVAkBC3ZhbHVlT3JFbHNlAgkAmggCBQR0aGlzCQEda2V5Q2ZnWDJHbnNidE9mZmVySGVpZ2h0U3RhcnQAAAAAEFJFTkVXX0VORF9IRUlHSFQJAQt2YWx1ZU9yRWxzZQIJAJoIAgUEdGhpcwkBG2tleUNmZ1gyR25zYnRPZmZlckhlaWdodEVuZAAAAAEMa2V5Qm9uZEFzc2V0AAINYm9uZF9hc3NldF9pZAEXa2V5VXNlckduc2J0UmVsZWFzZVRpbWUBCHVzZXJBZGRyCQCsAgICGyVzJXNfdXNlckduc2J0UmVsZWFzZVRpbWVfXwUIdXNlckFkZHIBGmtleU5ldXRyaW5vQ29udHJhY3RBZGRyZXNzAAIbJXNfX25ldXRyaW5vQ29udHJhY3RBZGRyZXNzARZrZXlNYXRoQ29udHJhY3RBZGRyZXNzAAIQJXNfX21hdGhDb250cmFjdAEQa2V5TWluTG9ja0Ftb3VudAACESVzX19taW5Mb2NrQW1vdW50AQtrZXlIYWxmTGlmZQACDCVzX19oYWxmTGlmZQEWa2V5TG9ja1BhcmFtVXNlckFtb3VudAELdXNlckFkZHJlc3MJALkJAgkAzAgCAgYlcyVzJXMJAMwIAgILcGFyYW1CeVVzZXIJAMwIAgkApQgBBQt1c2VyQWRkcmVzcwkAzAgCAgZhbW91bnQFA25pbAUJc2VwYXJhdG9yARZrZXlMb2NrUGFyYW1TdGFydEJsb2NrAQt1c2VyQWRkcmVzcwkAuQkCCQDMCAICBiVzJXMlcwkAzAgCAgtwYXJhbUJ5VXNlcgkAzAgCCQClCAEFC3VzZXJBZGRyZXNzCQDMCAICBXN0YXJ0BQNuaWwFCXNlcGFyYXRvcgEVa2V5TG9ja1BhcmFtVXNlckduc2J0AQt1c2VyQWRkcmVzcwkAuQkCCQDMCAICBiVzJXMlcwkAzAgCAgtwYXJhbUJ5VXNlcgkAzAgCCQClCAEFC3VzZXJBZGRyZXNzCQDMCAICBWdOc2J0BQNuaWwFCXNlcGFyYXRvcgEZa2V5VXNlckNvbnNlbnRlZFRvWDJHbnNidAELdXNlckFkZHJlc3MJALkJAgkAzAgCAgYlcyVzJXMJAMwIAgILcGFyYW1CeVVzZXIJAMwIAgkApQgBBQt1c2VyQWRkcmVzcwkAzAgCAhJjb25zZW50ZWRUb1gyR25zYnQFA25pbAUJc2VwYXJhdG9yARBrZXlIaXN0b3J5UmVjb3JkAwR0eXBlC3VzZXJBZGRyZXNzBHR4SWQJALkJAgkAzAgCAgglcyVzJXMlcwkAzAgCAgdoaXN0b3J5CQDMCAIFBHR5cGUJAMwIAgkApQgBBQt1c2VyQWRkcmVzcwkAzAgCCQDYBAEFBHR4SWQFA25pbAUJc2VwYXJhdG9yARdrZXlMb2NrUGFyYW1Ub3RhbEFtb3VudAAJALkJAgkAzAgCAgQlcyVzCQDMCAICBXN0YXRzCQDMCAICEWFjdGl2ZVRvdGFsTG9ja2VkBQNuaWwFCXNlcGFyYXRvcgEWa2V5TG9ja1BhcmFtVG90YWxHbnNidAAJALkJAgkAzAgCAgQlcyVzCQDMCAICBXN0YXRzCQDMCAICEGFjdGl2ZVRvdGFsR25zYnQFA25pbAUJc2VwYXJhdG9yARJrZXlTdGF0c0xvY2tzQ291bnQACQC5CQIJAMwIAgIEJXMlcwkAzAgCAgVzdGF0cwkAzAgCAgpsb2Nrc0NvdW50BQNuaWwFCXNlcGFyYXRvcgESa2V5U3RhdHNVc2Vyc0NvdW50AAkAuQkCCQDMCAICBCVzJXMJAMwIAgIFc3RhdHMJAMwIAgIQYWN0aXZlVXNlcnNDb3VudAUDbmlsBQlzZXBhcmF0b3IBF2tleVN0YXRzRGVwb3NpdEFtdEJ5RGF5AQl0aW1lc3RhbXAJALkJAgkAzAgCAgYlcyVzJWQJAMwIAgIFc3RhdHMJAMwIAgIPZGVwb3NpdEFtdEJ5RGF5CQDMCAIJAKQDAQUJdGltZXN0YW1wBQNuaWwFCXNlcGFyYXRvcgEYa2V5U3RhdHNEZXBvc2l0QW10VG90YWxzAAkAuQkCCQDMCAICBiVzJXMlZAkAzAgCAgVzdGF0cwkAzAgCAhBkZXBvc2l0QW10VG90YWxzBQNuaWwFCXNlcGFyYXRvcgENa2V5TmV4dFBlcmlvZAACDiVzX19uZXh0UGVyaW9kARhrZXlTdXBwb3J0ZWRSZXdhcmRBc3NldHMAAhVzdXBwb3J0ZWRSZXdhcmRBc3NldHMBEWtleURlcG9zaXROdW1MYXN0AAkAuQkCCQDMCAICBiVzJXMlcwkAzAgCAgNkZXAJAMwIAgIHbGFzdE51bQUDbmlsBQlzZXBhcmF0b3IBG2tleVVzZXJSZXdhcmRGcm9tRGVwb3NpdE51bQELdXNlckFkZHJlc3MJALkJAgkAzAgCAgYlcyVzJXMJAMwIAgIRdXNlclJ3ZEZyb21EZXBOdW0JAMwIAgULdXNlckFkZHJlc3MFA25pbAUJc2VwYXJhdG9yARVrZXlSZXdhcmRQZXJOc2J0U3VtQXQCCmRlcG9zaXROdW0DdGtuCQC5CQIJAMwIAgIEJXMlZAkAzAgCAhVyd2RQZXJOc2J0U3VtQnlEZXBOdW0JAMwIAgkApAMBBQpkZXBvc2l0TnVtCQDMCAIFA3RrbgUDbmlsBQlzZXBhcmF0b3IBCWtleVJld2FyZAILdXNlckFkZHJlc3MDdGtuCQC5CQIJAMwIAgIGJXMlcyVzCQDMCAICA3J3ZAkAzAgCBQt1c2VyQWRkcmVzcwkAzAgCBQN0a24FA25pbAUJc2VwYXJhdG9yAQprZXlDbGFpbWVkAgt1c2VyQWRkcmVzcwN0a24JALkJAgkAzAgCAgYlcyVzJXMJAMwIAgIDY2xtCQDMCAIFC3VzZXJBZGRyZXNzCQDMCAIFA3RrbgUDbmlsBQlzZXBhcmF0b3IBF2tleU5vdERpc3RyaWJ1dGVkUmV3YXJkAQN0a24JALkJAgkAzAgCAgQlcyVzCQDMCAICDm5vdERpc3RyaWJ1dGVkCQDMCAIFA3RrbgUDbmlsBQlzZXBhcmF0b3IBBXRvWDE4AgdvcmlnVmFsCG9yaWdNdWx0CQC8AgMJALYCAQUHb3JpZ1ZhbAUHTVVMVFgxOAUIb3JpZ011bHQBDGdldEludE9yWmVybwEDa2V5CQELdmFsdWVPckVsc2UCCQCaCAIFBHRoaXMFA2tleQAAAQxnZXRJbnRPckVsc2UCA2tleQpkZWZhdWx0VmFsCQELdmFsdWVPckVsc2UCCQCaCAIFBHRoaXMFA2tleQUKZGVmYXVsdFZhbAEMZ2V0SW50T3JGYWlsAQNrZXkJARN2YWx1ZU9yRXJyb3JNZXNzYWdlAgkAmggCBQR0aGlzBQNrZXkJAKwCAgkArAICAg9NYW5kYXRvcnkgdGhpcy4FA2tleQIPIGlzIG5vdCBkZWZpbmVkAQxnZXRTdHJPckVsc2UCA2tleQpkZWZhdWx0VmFsCQELdmFsdWVPckVsc2UCCQCdCAIFBHRoaXMFA2tleQUKZGVmYXVsdFZhbAEPdG9BZGRyZXNzT3JGYWlsAQphZGRyZXNzU3RyCQETdmFsdWVPckVycm9yTWVzc2FnZQIJAKYIAQUKYWRkcmVzc1N0cgkArAICAiFjb3VsZG4ndCBwYXJzZSBwYXNzZWQgYWRkcmVzc1N0cj0FCmFkZHJlc3NTdHIBC3RvQXNzZXRWZWN0AQhhc3NldFN0cgMJAAACBQhhc3NldFN0cgUKV0FWRVNJRFNUUgUEdW5pdAkA2QQBBQhhc3NldFN0cgEFYXNJbnQBA3ZhbAQHJG1hdGNoMAUDdmFsAwkAAQIFByRtYXRjaDACA0ludAQGdmFsSW50BQckbWF0Y2gwBQZ2YWxJbnQJAAIBAhVmYWlsIHRvIGNhc3QgaW50byBJbnQBE2Zvcm1hdEhpc3RvcnlSZWNvcmQECW9sZEFtb3VudAhvbGRTdGFydAluZXdBbW91bnQIbmV3U3RhcnQJALkJAgkAzAgCAgwlZCVkJWQlZCVkJWQJAMwIAgkApAMBCAUJbGFzdEJsb2NrBmhlaWdodAkAzAgCCQCkAwEIBQlsYXN0QmxvY2sJdGltZXN0YW1wCQDMCAIJAKQDAQUJb2xkQW1vdW50CQDMCAIJAKQDAQUIb2xkU3RhcnQJAMwIAgkApAMBBQluZXdBbW91bnQJAMwIAgkApAMBBQhuZXdTdGFydAUDbmlsBQlzZXBhcmF0b3IBGGZvcm1hdENsYWltSGlzdG9yeVJlY29yZAIEdXNlcg5jbGFpbWVkUmV3YXJkcwkAuQkCCQDMCAICCCVzJWQlZCVzCQDMCAIFBHVzZXIJAMwIAgkApAMBCAUJbGFzdEJsb2NrBmhlaWdodAkAzAgCCQCkAwEIBQlsYXN0QmxvY2sJdGltZXN0YW1wCQDMCAIFDmNsYWltZWRSZXdhcmRzBQNuaWwFCXNlcGFyYXRvcgESSGlzdG9yeVJlY29yZEVudHJ5BwR0eXBlC3VzZXJBZGRyZXNzBHR4SWQJb2xkQW1vdW50CG9sZFN0YXJ0CW5ld0Ftb3VudAhuZXdTdGFydAkBC1N0cmluZ0VudHJ5AgkBEGtleUhpc3RvcnlSZWNvcmQDBQR0eXBlBQt1c2VyQWRkcmVzcwUEdHhJZAkBE2Zvcm1hdEhpc3RvcnlSZWNvcmQEBQlvbGRBbW91bnQFCG9sZFN0YXJ0BQluZXdBbW91bnQFCG5ld1N0YXJ0ARFDbGFpbUhpc3RvcnlFbnRyeQMLdXNlckFkZHJlc3MEdHhJZA5jbGFpbWVkUmV3YXJkcwkBC1N0cmluZ0VudHJ5AgkBEGtleUhpc3RvcnlSZWNvcmQDAgVjbGFpbQULdXNlckFkZHJlc3MFBHR4SWQJARhmb3JtYXRDbGFpbUhpc3RvcnlSZWNvcmQCCQClCAEFC3VzZXJBZGRyZXNzBQ5jbGFpbWVkUmV3YXJkcwELU3RhdHNSZXN1bHQEDnRvdGFsTG9ja2VkSW5jDGxvY2tDb3VudEluYw11c2Vyc0NvdW50SW5jDXRvdGFsR25zYnRJbmMECmxvY2tzQ291bnQJAQxnZXRJbnRPclplcm8BCQESa2V5U3RhdHNMb2Nrc0NvdW50AAQKdXNlcnNDb3VudAkBDGdldEludE9yWmVybwEJARJrZXlTdGF0c1VzZXJzQ291bnQABAt0b3RhbEFtb3VudAkBDGdldEludE9yWmVybwEJARdrZXlMb2NrUGFyYW1Ub3RhbEFtb3VudAAEDnRvdGFsQW1vdW50TmV3CQBkAgULdG90YWxBbW91bnQFDnRvdGFsTG9ja2VkSW5jBAp0b3RhbEduc2J0CQEMZ2V0SW50T3JFbHNlAgkBFmtleUxvY2tQYXJhbVRvdGFsR25zYnQABQt0b3RhbEFtb3VudAkAlQoDCQDMCAIJAQxJbnRlZ2VyRW50cnkCCQESa2V5U3RhdHNMb2Nrc0NvdW50AAkAZAIFCmxvY2tzQ291bnQFDGxvY2tDb3VudEluYwkAzAgCCQEMSW50ZWdlckVudHJ5AgkBEmtleVN0YXRzVXNlcnNDb3VudAAJAGQCBQp1c2Vyc0NvdW50BQ11c2Vyc0NvdW50SW5jCQDMCAIJAQxJbnRlZ2VyRW50cnkCCQEXa2V5TG9ja1BhcmFtVG90YWxBbW91bnQABQ50b3RhbEFtb3VudE5ldwkAzAgCCQEMSW50ZWdlckVudHJ5AgkBFmtleUxvY2tQYXJhbVRvdGFsR25zYnQACQBkAgUKdG90YWxHbnNidAUNdG90YWxHbnNidEluYwUDbmlsBQt0b3RhbEFtb3VudAUOdG90YWxBbW91bnROZXcBD0xvY2tQYXJhbXNFbnRyeQQLdXNlckFkZHJlc3MKbnNidEFtb3VudAVzdGFydAtnTnNidEFtb3VudAkAzAgCCQEMSW50ZWdlckVudHJ5AgkBFmtleUxvY2tQYXJhbVVzZXJBbW91bnQBBQt1c2VyQWRkcmVzcwUKbnNidEFtb3VudAkAzAgCCQEMSW50ZWdlckVudHJ5AgkBFWtleUxvY2tQYXJhbVVzZXJHbnNidAEFC3VzZXJBZGRyZXNzBQtnTnNidEFtb3VudAkAzAgCCQEMSW50ZWdlckVudHJ5AgkBFmtleUxvY2tQYXJhbVN0YXJ0QmxvY2sBBQt1c2VyQWRkcmVzcwUFc3RhcnQFA25pbAEPZ2V0UGFyYW1zT3JGYWlsAAkAlQoDCQDZBAEJARFAZXh0ck5hdGl2ZSgxMDUzKQIFEG5ldXRyaW5vQ29udHJhY3QJAQxrZXlCb25kQXNzZXQACQEMZ2V0SW50T3JGYWlsAQkBEGtleU1pbkxvY2tBbW91bnQACQEMZ2V0SW50T3JGYWlsAQkBC2tleUhhbGZMaWZlAAEMaXNBY3RpdmVVc2VyAQt1c2VyQWRkcmVzcwkAZgIJAQxnZXRJbnRPckVsc2UCCQEWa2V5TG9ja1BhcmFtVXNlckFtb3VudAEFC3VzZXJBZGRyZXNzAAAAAAENaXNCb251c1BlcmlvZAEBaAMJAGcCBQFoBRJSRU5FV19TVEFSVF9IRUlHSFQJAGcCBRBSRU5FV19FTkRfSEVJR0hUBQFoBwETZ2V0VXNlclBhcmFtc09yVW5pdAELdXNlckFkZHJlc3MDCQEMaXNBY3RpdmVVc2VyAQULdXNlckFkZHJlc3MEBmFtb3VudAkBDGdldEludE9yRmFpbAEJARZrZXlMb2NrUGFyYW1Vc2VyQW1vdW50AQULdXNlckFkZHJlc3MJAJYKBAcFBmFtb3VudAkBDGdldEludE9yRmFpbAEJARZrZXlMb2NrUGFyYW1TdGFydEJsb2NrAQULdXNlckFkZHJlc3MJAQxnZXRJbnRPckVsc2UCCQEVa2V5TG9ja1BhcmFtVXNlckduc2J0AQULdXNlckFkZHJlc3MFBmFtb3VudAUEdW5pdAETZ2V0VXNlclBhcmFtc09yRmFpbAELdXNlckFkZHJlc3MJARN2YWx1ZU9yRXJyb3JNZXNzYWdlAgkBE2dldFVzZXJQYXJhbXNPclVuaXQBBQt1c2VyQWRkcmVzcwkArAICCQCsAgICBVVzZXIgCQClCAEFC3VzZXJBZGRyZXNzAg8gaXMgbm90IGRlZmluZWQAEnN1cHBvcnRlZEFzc2V0c1N0cgkBDGdldFN0ck9yRWxzZQIJARhrZXlTdXBwb3J0ZWRSZXdhcmRBc3NldHMAAgAAE3N1cHBvcnRlZEFzc2V0c0xpc3QJALUJAgUSc3VwcG9ydGVkQXNzZXRzU3RyAgFfAQpjYWxjUmV3YXJkBQt1c2VyQWRkcmVzcwdhc3NldElkDXN0YWtlZEFtb3VudFgOZGVwb3NpdE51bVVzZXIOZGVwb3NpdE51bUxhc3QEF3Jld2FyZFBlck5zYnRTdW1MYXN0S0VZCQEVa2V5UmV3YXJkUGVyTnNidFN1bUF0AgUOZGVwb3NpdE51bUxhc3QFB2Fzc2V0SWQECnN1bUxhc3RYMTgJAKcDAQkBDGdldFN0ck9yRWxzZQIJARVrZXlSZXdhcmRQZXJOc2J0U3VtQXQCBQ5kZXBvc2l0TnVtTGFzdAUHYXNzZXRJZAIBMAQKc3VtVXNlclgxOAkApwMBCQEMZ2V0U3RyT3JFbHNlAgkBFWtleVJld2FyZFBlck5zYnRTdW1BdAIFDmRlcG9zaXROdW1Vc2VyBQdhc3NldElkAgEwBBFyZXdhcmREeW5hbWljUGFydAkAoAMBCQC8AgMJALgCAgUKc3VtTGFzdFgxOAUKc3VtVXNlclgxOAUNc3Rha2VkQW1vdW50WAUHTVVMVFgxOAQTcmV3YXJkQ2FjaGVkUGFydEtFWQkBCWtleVJld2FyZAIFC3VzZXJBZGRyZXNzBQdhc3NldElkBBByZXdhcmRDYWNoZWRQYXJ0CQEMZ2V0SW50T3JFbHNlAgUTcmV3YXJkQ2FjaGVkUGFydEtFWQAACQCWCgQJAGQCBRByZXdhcmRDYWNoZWRQYXJ0BRFyZXdhcmREeW5hbWljUGFydAUQcmV3YXJkQ2FjaGVkUGFydAURcmV3YXJkRHluYW1pY1BhcnQFE3Jld2FyZENhY2hlZFBhcnRLRVkBDHRvU3RhcnRPZkRheQEJdGltZXN0YW1wCQBoAgkAaQIFCXRpbWVzdGFtcAUJREFZTUlMTElTBQlEQVlNSUxMSVMBE2ZpbmRFbGVtZW50UG9zaXRpb24DA3NyYwdlbGVtZW50A3NlcAQMZWxlbWVudFN0YXJ0CQETdmFsdWVPckVycm9yTWVzc2FnZQIJALMJAgUDc3JjBQdlbGVtZW50CQCsAgIJAKwCAgkArAICAhZ0aGVyZSBpcyBubyBzdWJzdHJpbmcgBQdlbGVtZW50AgQgaW4gBQNzcmMDCQAAAgUMZWxlbWVudFN0YXJ0AAAAAAQEbGVmdAkArwICBQNzcmMFDGVsZW1lbnRTdGFydAkAZQIJAJADAQkAtQkCBQRsZWZ0BQNzZXAAAQATRGVwb3NpdFRvdGFsc1BSRUZJWAIkJWQlZCVkJWQlZCVkJWQlZCVkJWQlZCVkJWQlZCVkJWQlZCVkABFkZWZhdWx0VG90YWxzREFUQQkArAICBRNEZXBvc2l0VG90YWxzUFJFRklYAjZfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzBfXzABB3BhZExpc3QBAmluBAhjdXJyU2l6ZQkAZQIJAJADAQUCaW4AAQoBCmxpc3RQYWRkZXICA2FjYwNpZHgDCQBmAgUIY3VyclNpemUFA2lkeAUDYWNjCQDNCAIFA2FjYwIBMAoAAiRsCQDMCAIAAAkAzAgCAAEJAMwIAgACCQDMCAIAAwkAzAgCAAQJAMwIAgAFCQDMCAIABgkAzAgCAAcJAMwIAgAICQDMCAIACQkAzAgCAAoJAMwIAgALCQDMCAIADAkAzAgCAA0JAMwIAgAOCQDMCAIADwkAzAgCABAJAMwIAgARBQNuaWwKAAIkcwkAkAMBBQIkbAoABSRhY2MwBQJpbgoBBSRmMF8xAgIkYQIkaQMJAGcCBQIkaQUCJHMFAiRhCQEKbGlzdFBhZGRlcgIFAiRhCQCRAwIFAiRsBQIkaQoBBSRmMF8yAgIkYQIkaQMJAGcCBQIkaQUCJHMFAiRhCQACAQIUTGlzdCBzaXplIGV4Y2VlZHMgMTgJAQUkZjBfMgIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIFBSRhY2MwAAAAAQACAAMABAAFAAYABwAIAAkACgALAAwADQAOAA8AEAARABIBCXBhZFN0cmluZwECaW4ECGN1cnJTaXplCQBlAgkAkAMBCQC8CQIFAmluBQNTRVAAAQoBCXN0clBhZGRlcgIDYWNjA2lkeAMJAGYCBQhjdXJyU2l6ZQUDaWR4BQNhY2MJAKwCAgUDYWNjAgNfXzAKAAIkbAkAzAgCAAAJAMwIAgABCQDMCAIAAgkAzAgCAAMJAMwIAgAECQDMCAIABQkAzAgCAAYJAMwIAgAHCQDMCAIACAkAzAgCAAkJAMwIAgAKCQDMCAIACwkAzAgCAAwJAMwIAgANCQDMCAIADgkAzAgCAA8JAMwIAgAQCQDMCAIAEQUDbmlsCgACJHMJAJADAQUCJGwKAAUkYWNjMAUCaW4KAQUkZjBfMQICJGECJGkDCQBnAgUCJGkFAiRzBQIkYQkBCXN0clBhZGRlcgIFAiRhCQCRAwIFAiRsBQIkaQoBBSRmMF8yAgIkYQIkaQMJAGcCBQIkaQUCJHMFAiRhCQACAQIUTGlzdCBzaXplIGV4Y2VlZHMgMTgJAQUkZjBfMgIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIFBSRhY2MwAAAAAQACAAMABAAFAAYABwAIAAkACgALAAwADQAOAA8AEAARABIBDVJld2FyZEVudHJpZXMDCWlzTmV3VXNlcgt1c2VyQWRkcmVzcwxzdGFrZWRBbW91bnQEDXN0YWtlZEFtb3VudFgJALYCAQUMc3Rha2VkQW1vdW50BBt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkJARtrZXlVc2VyUmV3YXJkRnJvbURlcG9zaXROdW0BBQt1c2VyQWRkcmVzcwQOZGVwb3NpdE51bVVzZXIJAQxnZXRJbnRPckVsc2UCBRt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkA////////////AQQOZGVwb3NpdE51bUxhc3QJAQxnZXRJbnRPckVsc2UCCQERa2V5RGVwb3NpdE51bUxhc3QAAP///////////wEKARtmb3JFYWNoQXNzZXRDYWNoZVVzZXJSZXdhcmQCBWFjY3VtBWFzc2V0BA0kdDAxMTQ4MzExNjE4CQEKY2FsY1Jld2FyZAUFC3VzZXJBZGRyZXNzBQVhc3NldAUNc3Rha2VkQW1vdW50WAUOZGVwb3NpdE51bVVzZXIFDmRlcG9zaXROdW1MYXN0BAtyZXdhcmRUb3RhbAgFDSR0MDExNDgzMTE2MTgCXzEEBmNhY2hlZAgFDSR0MDExNDgzMTE2MTgCXzIEB2R5bmFtaWMIBQ0kdDAxMTQ4MzExNjE4Al8zBBNyZXdhcmRDYWNoZWRQYXJ0S0VZCAUNJHQwMTE0ODMxMTYxOAJfNAkAzQgCBQVhY2N1bQkBDEludGVnZXJFbnRyeQIFE3Jld2FyZENhY2hlZFBhcnRLRVkFC3Jld2FyZFRvdGFsAwMJAAACBQ5kZXBvc2l0TnVtTGFzdAD///////////8BCQAAAgUOZGVwb3NpdE51bVVzZXIA////////////AQcFA25pbAMDCQAAAgUOZGVwb3NpdE51bUxhc3QA////////////AQkAZgIFDmRlcG9zaXROdW1Vc2VyAP///////////wEHCQACAQIvaW52YWxpZCBkZXBvc2l0TnVtTGFzdCBhbmQgZGVwb3NpdE51bVVzZXIgc3RhdGUDAwkAZgIFDmRlcG9zaXROdW1MYXN0AP///////////wEJAGcCBQ5kZXBvc2l0TnVtVXNlcgD///////////8BBwMFCWlzTmV3VXNlcgkAzAgCCQEMSW50ZWdlckVudHJ5AgUbdXNlclJld2FyZEZyb21EZXBvc2l0TnVtS0VZBQ5kZXBvc2l0TnVtTGFzdAUDbmlsCQDNCAIKAAIkbAUTc3VwcG9ydGVkQXNzZXRzTGlzdAoAAiRzCQCQAwEFAiRsCgAFJGFjYzAFA25pbAoBBSRmMF8xAgIkYQIkaQMJAGcCBQIkaQUCJHMFAiRhCQEbZm9yRWFjaEFzc2V0Q2FjaGVVc2VyUmV3YXJkAgUCJGEJAJEDAgUCJGwFAiRpCgEFJGYwXzICAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAAIBAhNMaXN0IHNpemUgZXhjZWVkcyA5CQEFJGYwXzICCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECBQUkYWNjMAAAAAEAAgADAAQABQAGAAcACAAJCQEMSW50ZWdlckVudHJ5AgUbdXNlclJld2FyZEZyb21EZXBvc2l0TnVtS0VZBQ5kZXBvc2l0TnVtTGFzdAkAAgEJAKwCAgkArAICCQCsAgICJHVuY292ZXJlZCBjb25kaXRpb246IGRlcG9zaXROdW1MYXN0PQkApAMBBQ5kZXBvc2l0TnVtTGFzdAIQIGRlcG9zaXROdW1Vc2VyPQkApAMBBQ5kZXBvc2l0TnVtVXNlcgEiSW5jcmVtZW50Tm90RGlzdHJpYnV0ZWRSZXdhcmRFbnRyeQIDdGtuCWFtb3VudEluYwQXbm90RGlzdHJpYnV0ZWRSZXdhcmRLRVkJARdrZXlOb3REaXN0cmlidXRlZFJld2FyZAEFA3RrbgQUbm90RGlzdHJpYnV0ZWRSZXdhcmQJAQxnZXRJbnRPckVsc2UCBRdub3REaXN0cmlidXRlZFJld2FyZEtFWQAACQEMSW50ZWdlckVudHJ5AgUXbm90RGlzdHJpYnV0ZWRSZXdhcmRLRVkJAGQCBRRub3REaXN0cmlidXRlZFJld2FyZAUJYW1vdW50SW5jAQtjb21tb25DbGFpbQILdXNlckFkZHJlc3MBaQQOdXNlckFkZHJlc3NTdHIJAKUIAQULdXNlckFkZHJlc3MDCQBmAgkAkAMBCAUBaQhwYXltZW50cwAACQACAQIZcGF5bWVudHMgYXJlIG5vdCBhY2NlcHRlZAQNJHQwMTQ1NTkxNDY4MAkBC3ZhbHVlT3JFbHNlAgkBE2dldFVzZXJQYXJhbXNPclVuaXQBBQt1c2VyQWRkcmVzcwkAlgoEBgAAAAAAAAQJaXNOZXdVc2VyCAUNJHQwMTQ1NTkxNDY4MAJfMQQMc3Rha2VkQW1vdW50CAUNJHQwMTQ1NTkxNDY4MAJfMgQMc3Rha2luZ1N0YXJ0CAUNJHQwMTQ1NTkxNDY4MAJfMwQLZ05zYnRBbW91bnQIBQ0kdDAxNDU1OTE0NjgwAl80BA1zdGFrZWRBbW91bnRYCQC2AgEFC2dOc2J0QW1vdW50BBt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkJARtrZXlVc2VyUmV3YXJkRnJvbURlcG9zaXROdW0BBQ51c2VyQWRkcmVzc1N0cgQOZGVwb3NpdE51bVVzZXIJAQxnZXRJbnRPckVsc2UCBRt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkA////////////AQQOZGVwb3NpdE51bUxhc3QJAQxnZXRJbnRPckVsc2UCCQERa2V5RGVwb3NpdE51bUxhc3QAAP///////////wEKAR9mb3JFYWNoQXNzZXRDYWxjVW5jbGFpbWVkUmV3YXJkAgVhY2N1bQVhc3NldAQNJHQwMTUwNTAxNTE4OAkBCmNhbGNSZXdhcmQFBQ51c2VyQWRkcmVzc1N0cgUFYXNzZXQFDXN0YWtlZEFtb3VudFgFDmRlcG9zaXROdW1Vc2VyBQ5kZXBvc2l0TnVtTGFzdAQLcmV3YXJkVG90YWwIBQ0kdDAxNTA1MDE1MTg4Al8xBAZjYWNoZWQIBQ0kdDAxNTA1MDE1MTg4Al8yBAdkeW5hbWljCAUNJHQwMTUwNTAxNTE4OAJfMwQTcmV3YXJkQ2FjaGVkUGFydEtFWQgFDSR0MDE1MDUwMTUxODgCXzQECmNsYWltZWRLRVkJAQprZXlDbGFpbWVkAgUOdXNlckFkZHJlc3NTdHIFBWFzc2V0BA0kdDAxNTI0ODE1Mjg1BQVhY2N1bQQEZGF0YQgFDSR0MDE1MjQ4MTUyODUCXzEEEWNsYWltZWRBbXRCeUFzc2V0CAUNJHQwMTUyNDgxNTI4NQJfMgQHbmV3UGFydAkAuQkCCQDMCAIFBWFzc2V0CQDMCAIJAKQDAQULcmV3YXJkVG90YWwFA25pbAIBOgQUY2xhaW1lZEFtdEJ5QXNzZXROZXcJALkJAgkAzAgCBRFjbGFpbWVkQW10QnlBc3NldAkAzAgCBQduZXdQYXJ0BQNuaWwCAV8DCQBnAgAABQtyZXdhcmRUb3RhbAkAlAoCBQRkYXRhBRRjbGFpbWVkQW10QnlBc3NldE5ldwkAlAoCCQDNCAIJAM0IAgkAzQgCBQRkYXRhCQEOU2NyaXB0VHJhbnNmZXIDBQt1c2VyQWRkcmVzcwULcmV3YXJkVG90YWwJAQt0b0Fzc2V0VmVjdAEFBWFzc2V0CQEMSW50ZWdlckVudHJ5AgUKY2xhaW1lZEtFWQkAZAIJAQt2YWx1ZU9yRWxzZQIJAJ8IAQUKY2xhaW1lZEtFWQAABQtyZXdhcmRUb3RhbAkBDEludGVnZXJFbnRyeQIFE3Jld2FyZENhY2hlZFBhcnRLRVkAAAUUY2xhaW1lZEFtdEJ5QXNzZXROZXcEDSR0MDE1NzQ1MTU4NTgKAAIkbAUTc3VwcG9ydGVkQXNzZXRzTGlzdAoAAiRzCQCQAwEFAiRsCgAFJGFjYzAJAJQKAgUDbmlsAgAKAQUkZjBfMQICJGECJGkDCQBnAgUCJGkFAiRzBQIkYQkBH2ZvckVhY2hBc3NldENhbGNVbmNsYWltZWRSZXdhcmQCBQIkYQkAkQMCBQIkbAUCJGkKAQUkZjBfMgICJGECJGkDCQBnAgUCJGkFAiRzBQIkYQkAAgECE0xpc3Qgc2l6ZSBleGNlZWRzIDkJAQUkZjBfMgIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIJAQUkZjBfMQIFBSRhY2MwAAAAAQACAAMABAAFAAYABwAIAAkECXRyYW5zZmVycwgFDSR0MDE1NzQ1MTU4NTgCXzEEF2NsYWltZWRBbXRCeUFzc2V0UmVzdWx0CAUNJHQwMTU3NDUxNTg1OAJfMgMJAGcCAAAJAJADAQUJdHJhbnNmZXJzCQCUCgIFA25pbAAACQCUCgIJAM0IAgkAzQgCBQl0cmFuc2ZlcnMJAQxJbnRlZ2VyRW50cnkCBRt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkFDmRlcG9zaXROdW1MYXN0CQERQ2xhaW1IaXN0b3J5RW50cnkDBQt1c2VyQWRkcmVzcwgFAWkNdHJhbnNhY3Rpb25JZAkAsAICBRdjbGFpbWVkQW10QnlBc3NldFJlc3VsdAABCQCQAwEFCXRyYW5zZmVycwEYcmVhZFVzZXJDb25zZW50VG9YMkduc2J0AQt1c2VyQWRkcmVzcwQDa2V5CQEZa2V5VXNlckNvbnNlbnRlZFRvWDJHbnNidAEFC3VzZXJBZGRyZXNzBAN2YWwJAQt2YWx1ZU9yRWxzZQIJAJsIAgUEdGhpcwUDa2V5BwkAlAoCBQNrZXkFA3ZhbAENY29tbW9uWDJHbnNidAILdXNlckFkZHJlc3MBaQMJAQEhAQkBDWlzQm9udXNQZXJpb2QBBQZoZWlnaHQJAAIBAiZObyAnRG91YmxlIGdOU0JUIGFjdGlvbicgYXZhaWxhYmxlIG5vdwQNJHQwMTY0MjAxNjQ4MQkBC2NvbW1vbkNsYWltAgULdXNlckFkZHJlc3MFAWkEDGNsYWltQWN0aW9ucwgFDSR0MDE2NDIwMTY0ODECXzEEC2NsYWltUmVzdWx0CAUNJHQwMTY0MjAxNjQ4MQJfMgQNJHQwMTY0ODQxNjYwOQkBC3ZhbHVlT3JFbHNlAgkBE2dldFVzZXJQYXJhbXNPclVuaXQBBQt1c2VyQWRkcmVzcwkAlgoEBgAAAP///////////wEAAAQJaXNOZXdVc2VyCAUNJHQwMTY0ODQxNjYwOQJfMQQKbG9ja0Ftb3VudAgFDSR0MDE2NDg0MTY2MDkCXzIED2xvY2tTdGFydEhlaWdodAgFDSR0MDE2NDg0MTY2MDkCXzMEDWN1cnJVc2VyR25zYnQIBQ0kdDAxNjQ4NDE2NjA5Al80AwUJaXNOZXdVc2VyCQACAQIbWW91IGhhdmUgbm90aGluZyB0byByZXN0YWtlBA5kZWx0YVVzZXJHbnNidAUNY3VyclVzZXJHbnNidAQMbmV3VXNlckduc2J0CQBkAgUNY3VyclVzZXJHbnNidAUOZGVsdGFVc2VyR25zYnQEEHVzZXJDb25zZW50VHVwbGUJARhyZWFkVXNlckNvbnNlbnRUb1gyR25zYnQBBQt1c2VyQWRkcmVzcwQZdXNlckNvbnNlbnRlZFRvWDJHbnNidEtFWQgFEHVzZXJDb25zZW50VHVwbGUCXzEEFnVzZXJDb25zZW50ZWRUb1gyR25zYnQIBRB1c2VyQ29uc2VudFR1cGxlAl8yAwUWdXNlckNvbnNlbnRlZFRvWDJHbnNidAkAAgECKFVzZXIgaGFzIGFscmVhZHkgZG91YmxlZCBpdHMgZ05TQlQgdmFsdWUEDSR0MDE3MDI2MTcxMTIJAQtTdGF0c1Jlc3VsdAQAAAAAAAAFDmRlbHRhVXNlckduc2J0BAxzdGF0c0VudHJpZXMIBQ0kdDAxNzAyNjE3MTEyAl8xBAt0b3RhbFN0YWtlZAgFDSR0MDE3MDI2MTcxMTICXzIEDnRvdGFsU3Rha2VkTmV3CAUNJHQwMTcwMjYxNzExMgJfMwkAlAoCCQDNCAIJAM4IAgkAzggCBQxjbGFpbUFjdGlvbnMJAQ9Mb2NrUGFyYW1zRW50cnkEBQt1c2VyQWRkcmVzcwUKbG9ja0Ftb3VudAUGaGVpZ2h0BQxuZXdVc2VyR25zYnQFDHN0YXRzRW50cmllcwkBDEJvb2xlYW5FbnRyeQIFGXVzZXJDb25zZW50ZWRUb1gyR25zYnRLRVkGBQtjbGFpbVJlc3VsdAwBaQENY29uc3RydWN0b3JWMQUXbmV1dHJpbm9Db250cmFjdEFkZHJlc3MTbWF0aENvbnRyYWN0QWRkcmVzcw1taW5Mb2NrQW1vdW50CGhhbGZMaWZlFXN1cHBvcnRlZFJld2FyZEFzc2V0cwMJAQIhPQIIBQFpBmNhbGxlcgUEdGhpcwkAAgECEVBlcm1pc3Npb24gZGVuaWVkCQDMCAIJAQtTdHJpbmdFbnRyeQIJARprZXlOZXV0cmlub0NvbnRyYWN0QWRkcmVzcwAFF25ldXRyaW5vQ29udHJhY3RBZGRyZXNzCQDMCAIJAQtTdHJpbmdFbnRyeQIJARZrZXlNYXRoQ29udHJhY3RBZGRyZXNzAAUTbWF0aENvbnRyYWN0QWRkcmVzcwkAzAgCCQEMSW50ZWdlckVudHJ5AgkBEGtleU1pbkxvY2tBbW91bnQABQ1taW5Mb2NrQW1vdW50CQDMCAIJAQxJbnRlZ2VyRW50cnkCCQELa2V5SGFsZkxpZmUABQhoYWxmTGlmZQkAzAgCCQELU3RyaW5nRW50cnkCCQEYa2V5U3VwcG9ydGVkUmV3YXJkQXNzZXRzAAUVc3VwcG9ydGVkUmV3YXJkQXNzZXRzBQNuaWwBaQENY29uc3RydWN0b3JWMgIXeDJHbnNidE9mZmVySGVpZ2h0U3RhcnQVeDJHbnNidE9mZmVySGVpZ2h0RW5kAwkBAiE9AggFAWkGY2FsbGVyBQR0aGlzCQACAQIRUGVybWlzc2lvbiBkZW5pZWQJAMwIAgkBDEludGVnZXJFbnRyeQIJAR1rZXlDZmdYMkduc2J0T2ZmZXJIZWlnaHRTdGFydAAFF3gyR25zYnRPZmZlckhlaWdodFN0YXJ0CQDMCAIJAQxJbnRlZ2VyRW50cnkCCQEba2V5Q2ZnWDJHbnNidE9mZmVySGVpZ2h0RW5kAAUVeDJHbnNidE9mZmVySGVpZ2h0RW5kBQNuaWwBaQEFc3Rha2UABA0kdDAxODIxODE4MjgwCQEPZ2V0UGFyYW1zT3JGYWlsAAQLYm9uZEFzc2V0SWQIBQ0kdDAxODIxODE4MjgwAl8xBA1taW5Mb2NrQW1vdW50CAUNJHQwMTgyMTgxODI4MAJfMgQIaGFsZkxpZmUIBQ0kdDAxODIxODE4MjgwAl8zAwkBAiE9AgkAkAMBCAUBaQhwYXltZW50cwABCQACAQIVSW52YWxpZCBwYXltZW50cyBzaXplBAdwYXltZW50CQCRAwIIBQFpCHBheW1lbnRzAAAEBmFtb3VudAgFB3BheW1lbnQGYW1vdW50BBNpbnZhbGlkQXNzZXRNZXNzYWdlCQCsAgIJAKwCAgIPSW52YWxpZCBhc3NldC4gCQDYBAEFC2JvbmRBc3NldElkAgwgaXMgZXhwZWN0ZWQEB2Fzc2V0SWQJARN2YWx1ZU9yRXJyb3JNZXNzYWdlAggFB3BheW1lbnQHYXNzZXRJZAUTaW52YWxpZEFzc2V0TWVzc2FnZQMJAQIhPQIFB2Fzc2V0SWQFC2JvbmRBc3NldElkCQACAQUTaW52YWxpZEFzc2V0TWVzc2FnZQQLdXNlckFkZHJlc3MIBQFpBmNhbGxlcgQOdXNlckFkZHJlc3NTdHIJAKUIAQgFAWkGY2FsbGVyBA0kdDAxODgyMjE4OTQ3CQELdmFsdWVPckVsc2UCCQETZ2V0VXNlclBhcmFtc09yVW5pdAEFC3VzZXJBZGRyZXNzCQCWCgQGAAAA////////////AQAABAlpc05ld1VzZXIIBQ0kdDAxODgyMjE4OTQ3Al8xBApsb2NrQW1vdW50CAUNJHQwMTg4MjIxODk0NwJfMgQPbG9ja1N0YXJ0SGVpZ2h0CAUNJHQwMTg4MjIxODk0NwJfMwQNY3VyclVzZXJHbnNidAgFDSR0MDE4ODIyMTg5NDcCXzQEDG1lcmdlZEFtb3VudAMFCWlzTmV3VXNlcgUGYW1vdW50CQBkAgUGYW1vdW50BQpsb2NrQW1vdW50BBFtZXJnZWRTdGFydEhlaWdodAMFCWlzTmV3VXNlcgUGaGVpZ2h0CQEFYXNJbnQBCQD8BwQFDG1hdGhDb250cmFjdAITbWVyZ2VTdGFrZXNSRUFET05MWQkAzAgCBQZhbW91bnQJAMwIAgUGaGVpZ2h0CQDMCAIFCmxvY2tBbW91bnQJAMwIAgUPbG9ja1N0YXJ0SGVpZ2h0CQDMCAIFCGhhbGZMaWZlBQNuaWwFA25pbAMJAGYCBQ1taW5Mb2NrQW1vdW50BQxtZXJnZWRBbW91bnQJAAIBCQCsAgICE01pbiBsb2NrIGFtb3VudCBpcyAJAKQDAQUNbWluTG9ja0Ftb3VudAQQdXNlckNvbnNlbnRUdXBsZQkBGHJlYWRVc2VyQ29uc2VudFRvWDJHbnNidAEFC3VzZXJBZGRyZXNzBBl1c2VyQ29uc2VudGVkVG9YMkduc2J0S0VZCAUQdXNlckNvbnNlbnRUdXBsZQJfMQQWdXNlckNvbnNlbnRlZFRvWDJHbnNidAgFEHVzZXJDb25zZW50VHVwbGUCXzIEDmRlbHRhVXNlckduc2J0AwMJAQ1pc0JvbnVzUGVyaW9kAQUGaGVpZ2h0AwUJaXNOZXdVc2VyBgUWdXNlckNvbnNlbnRlZFRvWDJHbnNidAcJAGgCAAIFBmFtb3VudAUGYW1vdW50BBN4Mkduc2J0Q29uc2VudEVudHJ5AwUJaXNOZXdVc2VyCQDMCAIJAQxCb29sZWFuRW50cnkCBRl1c2VyQ29uc2VudGVkVG9YMkduc2J0S0VZBgUDbmlsBQNuaWwEDSR0MDE5OTUxMjAwNjkJAQtTdGF0c1Jlc3VsdAQFBmFtb3VudAABAwUJaXNOZXdVc2VyAAEAAAUOZGVsdGFVc2VyR25zYnQEDHN0YXRzRW50cmllcwgFDSR0MDE5OTUxMjAwNjkCXzEEC3RvdGFsU3Rha2VkCAUNJHQwMTk5NTEyMDA2OQJfMgQOdG90YWxTdGFrZWROZXcIBQ0kdDAxOTk1MTIwMDY5Al8zCQDOCAIJAM4IAgkAzggCCQDOCAIJAMwIAgkBEkhpc3RvcnlSZWNvcmRFbnRyeQcCBXN0YWtlBQt1c2VyQWRkcmVzcwgFAWkNdHJhbnNhY3Rpb25JZAUKbG9ja0Ftb3VudAUPbG9ja1N0YXJ0SGVpZ2h0BQxtZXJnZWRBbW91bnQFEW1lcmdlZFN0YXJ0SGVpZ2h0BQNuaWwJAQ1SZXdhcmRFbnRyaWVzAwUJaXNOZXdVc2VyBQ51c2VyQWRkcmVzc1N0cgUNY3VyclVzZXJHbnNidAkBD0xvY2tQYXJhbXNFbnRyeQQFC3VzZXJBZGRyZXNzBQxtZXJnZWRBbW91bnQFEW1lcmdlZFN0YXJ0SGVpZ2h0CQBkAgUNY3VyclVzZXJHbnNidAUOZGVsdGFVc2VyR25zYnQFDHN0YXRzRW50cmllcwUTeDJHbnNidENvbnNlbnRFbnRyeQFpAQd1bnN0YWtlAQZhbW91bnQDCQECIT0CCQCQAwEIBQFpCHBheW1lbnRzAAAJAAIBAiN1bnN0YWtlIGRvZXNuJ3QgcmVxdWlyZSBhbnkgcGF5bWVudAQLdXNlckFkZHJlc3MIBQFpBmNhbGxlcgQOdXNlckFkZHJlc3NTdHIJAKUIAQULdXNlckFkZHJlc3MEDSR0MDIwNjE1MjA2NzcJAQ9nZXRQYXJhbXNPckZhaWwABAtib25kQXNzZXRJZAgFDSR0MDIwNjE1MjA2NzcCXzEEDW1pbkxvY2tBbW91bnQIBQ0kdDAyMDYxNTIwNjc3Al8yBAhoYWxmTGlmZQgFDSR0MDIwNjE1MjA2NzcCXzMEDSR0MDIwNjgwMjA3NjkJARNnZXRVc2VyUGFyYW1zT3JGYWlsAQULdXNlckFkZHJlc3MECWlzTmV3VXNlcggFDSR0MDIwNjgwMjA3NjkCXzEECmxvY2tBbW91bnQIBQ0kdDAyMDY4MDIwNzY5Al8yBAlsb2NrU3RhcnQIBQ0kdDAyMDY4MDIwNzY5Al8zBA1jdXJyVXNlckduc2J0CAUNJHQwMjA2ODAyMDc2OQJfNAMJAGcCAAAFCmxvY2tBbW91bnQJAAIBAhJOb3RoaW5nIHRvIHVuc3Rha2UDCQBmAgUGYW1vdW50BQpsb2NrQW1vdW50CQACAQkArAICCQCsAgIJAKwCAgIKUmVxdWVzdGVkIAkApAMBBQZhbW91bnQCEiwgYnV0IHN0YWtlZCBvbmx5IAkApAMBBQpsb2NrQW1vdW50BAF0CAkBBXZhbHVlAQkA7QcBBQZoZWlnaHQJdGltZXN0YW1wBAtyZWxlYXNlVGltZQkBC3ZhbHVlT3JFbHNlAgkAmggCBQtnb3ZDb250cmFjdAkBF2tleVVzZXJHbnNidFJlbGVhc2VUaW1lAQUOdXNlckFkZHJlc3NTdHIAAAMJAGcCBQtyZWxlYXNlVGltZQUBdAkAAgEJAKwCAgI7WW91ciBnTnNidCBhcmUgdGFraW5nIHBhcnQgaW4gdm90aW5nLCBjYW5ub3QgdW5zdGFrZSB1bnRpbCAJAKQDAQULcmVsZWFzZVRpbWUED2NvbWlzc2lvbkFtb3VudAkBBWFzSW50AQkA/AcEBQxtYXRoQ29udHJhY3QCIWdldFVuc3Rha2VDb21pc3Npb25BbW91bnRSRUFET05MWQkAzAgCBQZhbW91bnQJAMwIAgUJbG9ja1N0YXJ0CQDMCAIFCGhhbGZMaWZlBQNuaWwFA25pbAQOYm9udXNHbnNidFBhcnQJAGUCBQ1jdXJyVXNlckduc2J0BQpsb2NrQW1vdW50BA9ib251c05zYnRBbW91bnQJAJcDAQkAzAgCBQZhbW91bnQJAMwIAgUOYm9udXNHbnNidFBhcnQFA25pbAQKZGVsdGFHbnNidAkAZAIFD2JvbnVzTnNidEFtb3VudAUGYW1vdW50BA0kdDAyMTYwNzIxNzc4CQELU3RhdHNSZXN1bHQECQEBLQEFBmFtb3VudAMJAAACBQZhbW91bnQFCmxvY2tBbW91bnQA////////////AQAAAwkAAAIFBmFtb3VudAUKbG9ja0Ftb3VudAD///////////8BAAAJAQEtAQUKZGVsdGFHbnNidAQMc3RhdHNFbnRyaWVzCAUNJHQwMjE2MDcyMTc3OAJfMQQLdG90YWxTdGFrZWQIBQ0kdDAyMTYwNzIxNzc4Al8yBA50b3RhbFN0YWtlZE5ldwgFDSR0MDIxNjA3MjE3NzgCXzMJAM4IAgkAzggCCQDOCAIJAMwIAgkBDlNjcmlwdFRyYW5zZmVyAwULdXNlckFkZHJlc3MJAGUCBQZhbW91bnQFD2NvbWlzc2lvbkFtb3VudAULYm9uZEFzc2V0SWQJAMwIAgkBDlNjcmlwdFRyYW5zZmVyAwUTbmV1dHJpbm9EYW9Db250cmFjdAUPY29taXNzaW9uQW1vdW50BQtib25kQXNzZXRJZAkAzAgCCQESSGlzdG9yeVJlY29yZEVudHJ5BwIHdW5zdGFrZQULdXNlckFkZHJlc3MIBQFpDXRyYW5zYWN0aW9uSWQFCmxvY2tBbW91bnQFCWxvY2tTdGFydAkAZQIFCmxvY2tBbW91bnQFBmFtb3VudAUJbG9ja1N0YXJ0BQNuaWwJAQ1SZXdhcmRFbnRyaWVzAwcFDnVzZXJBZGRyZXNzU3RyBQ1jdXJyVXNlckduc2J0CQEPTG9ja1BhcmFtc0VudHJ5BAULdXNlckFkZHJlc3MJAGUCBQpsb2NrQW1vdW50BQZhbW91bnQFCWxvY2tTdGFydAkAZQIFDWN1cnJVc2VyR25zYnQFCmRlbHRhR25zYnQFDHN0YXRzRW50cmllcwFpAQdkZXBvc2l0AAQLdG90YWxTdGFrZWQJAQxnZXRJbnRPckVsc2UCCQEWa2V5TG9ja1BhcmFtVG90YWxHbnNidAAJAQxnZXRJbnRPckVsc2UCCQEXa2V5TG9ja1BhcmFtVG90YWxBbW91bnQAAAADCQBmAgAABQt0b3RhbFN0YWtlZAkAAgECG1RPRE86IGNhc2UgaXMgbm90IHN1cHBvcnRlZAQRZGVwb3NpdE51bUxhc3RLRVkJARFrZXlEZXBvc2l0TnVtTGFzdAAEDmRlcG9zaXROdW1MYXN0CQEMZ2V0SW50T3JFbHNlAgURZGVwb3NpdE51bUxhc3RLRVkA////////////AQQNZGVwb3NpdE51bU5ldwkAZAIFDmRlcG9zaXROdW1MYXN0AAEECXRvdGFsc0tFWQkBGGtleVN0YXRzRGVwb3NpdEFtdFRvdGFscwAECGJ5RGF5S0VZCQEXa2V5U3RhdHNEZXBvc2l0QW10QnlEYXkBCQEMdG9TdGFydE9mRGF5AQgFCWxhc3RCbG9jawl0aW1lc3RhbXAECmN1cnJUb3RhbHMJAQdwYWRMaXN0AQkAtQkCCQELdmFsdWVPckVsc2UCCQCiCAEFCXRvdGFsc0tFWQURZGVmYXVsdFRvdGFsc0RBVEEFA1NFUAoBA2RlcAIDYWNjA3BtdAQGYW1vdW50CAUDcG10BmFtb3VudAQNcG10QXNzZXRJZFN0cgkA2AQBCQELdmFsdWVPckVsc2UCCAUDcG10B2Fzc2V0SWQFB1dBVkVTSUQDCQEBIQEJAQhjb250YWlucwIFEnN1cHBvcnRlZEFzc2V0c1N0cgUNcG10QXNzZXRJZFN0cgkAAgEJAKwCAgkArAICBRJzdXBwb3J0ZWRBc3NldHNTdHICESBkb2Vzbid0IGNvbnRhaW4gBQ1wbXRBc3NldElkU3RyAwkAAAIFC3RvdGFsU3Rha2VkAAAJAJYKBAkAzQgCCAUDYWNjAl8xCQEiSW5jcmVtZW50Tm90RGlzdHJpYnV0ZWRSZXdhcmRFbnRyeQIFDXBtdEFzc2V0SWRTdHIFBmFtb3VudAkAzQgCCAUDYWNjAl8yBQ1wbXRBc3NldElkU3RyCQDNCAIIBQNhY2MCXzMJALYCAQAACQDNCAIIBQNhY2MCXzQFBmFtb3VudAQQcmV3YXJkUGVyTnNidFgxOAkAvAIDCQC2AgEFBmFtb3VudAUHTVVMVFgxOAkAtgIBBQt0b3RhbFN0YWtlZAkAlgoECAUDYWNjAl8xCQDNCAIIBQNhY2MCXzIFDXBtdEFzc2V0SWRTdHIJAM0IAggFA2FjYwJfMwUQcmV3YXJkUGVyTnNidFgxOAkAzQgCCAUDYWNjAl80BQZhbW91bnQECnBtdHNSZXN1bHQKAAIkbAgFAWkIcGF5bWVudHMKAAIkcwkAkAMBBQIkbAoABSRhY2MwCQCWCgQFA25pbAUDbmlsBQNuaWwFA25pbAoBBSRmMF8xAgIkYQIkaQMJAGcCBQIkaQUCJHMFAiRhCQEDZGVwAgUCJGEJAJEDAgUCJGwFAiRpCgEFJGYwXzICAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAAIBAhRMaXN0IHNpemUgZXhjZWVkcyAxMAkBBSRmMF8yAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgkBBSRmMF8xAgUFJGFjYzAAAAABAAIAAwAEAAUABgAHAAgACQAKCgEZcmVmcmVzaFJld2FyZFVwZGF0ZVRvdGFscwIFYWNjdW0JbmV4dEFzc2V0BAFrCAUFYWNjdW0CXzMECnN1bUxhc3RTdHIJAQxnZXRTdHJPckVsc2UCCQEVa2V5UmV3YXJkUGVyTnNidFN1bUF0AgUOZGVwb3NpdE51bUxhc3QFCW5leHRBc3NldAIBMAQDaWR4CQDPCAIIBQpwbXRzUmVzdWx0Al8yBQluZXh0QXNzZXQEA3N1bQMJAQlpc0RlZmluZWQBBQNpZHgEAWoJAQV2YWx1ZQEFA2lkeAQKc3RhdHNEZWx0YQkAkQMCCAUKcG10c1Jlc3VsdAJfNAUBagkAlAoCCQCmAwEJALcCAgkApwMBBQpzdW1MYXN0U3RyCQCRAwIIBQpwbXRzUmVzdWx0Al8zBQFqCQCkAwEJAGQCCQENcGFyc2VJbnRWYWx1ZQEJAJEDAgUKY3VyclRvdGFscwkAZAIFAWsAAQUKc3RhdHNEZWx0YQkAlAoCBQpzdW1MYXN0U3RyCQCRAwIFCmN1cnJUb3RhbHMJAGQCBQFrAAEJAJUKAwkAzQgCCAUFYWNjdW0CXzEJAQtTdHJpbmdFbnRyeQIJARVrZXlSZXdhcmRQZXJOc2J0U3VtQXQCBQ1kZXBvc2l0TnVtTmV3BQluZXh0QXNzZXQIBQNzdW0CXzEJAKwCAgkArAICCAUFYWNjdW0CXzIFA1NFUAgFA3N1bQJfMgkAZAIFAWsAAQQMYXNzZXRzUmVzdWx0CgACJGwFE3N1cHBvcnRlZEFzc2V0c0xpc3QKAAIkcwkAkAMBBQIkbAoABSRhY2MwCQCVCgMFA25pbAUTRGVwb3NpdFRvdGFsc1BSRUZJWAAACgEFJGYxXzECAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJARlyZWZyZXNoUmV3YXJkVXBkYXRlVG90YWxzAgUCJGEJAJEDAgUCJGwFAiRpCgEFJGYxXzICAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAAIBAhNMaXN0IHNpemUgZXhjZWVkcyA5CQEFJGYxXzICCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECCQEFJGYxXzECBQUkYWNjMAAAAAEAAgADAAQABQAGAAcACAAJBAZ0b3RhbHMJAQlwYWRTdHJpbmcBCAUMYXNzZXRzUmVzdWx0Al8yCQCUCgIJAM0IAgkAzQgCCQDNCAIJAM4IAggFCnBtdHNSZXN1bHQCXzEIBQxhc3NldHNSZXN1bHQCXzEJAQxJbnRlZ2VyRW50cnkCBRFkZXBvc2l0TnVtTGFzdEtFWQUNZGVwb3NpdE51bU5ldwkBC1N0cmluZ0VudHJ5AgUJdG90YWxzS0VZBQZ0b3RhbHMJAQtTdHJpbmdFbnRyeQIFCGJ5RGF5S0VZBQZ0b3RhbHMFDWRlcG9zaXROdW1OZXcBaQEMY2xhaW1SZXdhcmRzAAkBC2NvbW1vbkNsYWltAggFAWkGY2FsbGVyBQFpAWkBGmNsYWltUmV3YXJkc0J5T3JpZ2luQ2FsbGVyAAkBC2NvbW1vbkNsYWltAggFAWkMb3JpZ2luQ2FsbGVyBQFpAWkBB3gyR25zYnQACQENY29tbW9uWDJHbnNidAIIBQFpBmNhbGxlcgUBaQFpARV4Mkduc2J0QnlPcmlnaW5DYWxsZXIACQENY29tbW9uWDJHbnNidAIIBQFpDG9yaWdpbkNhbGxlcgUBaQFpARh1bmNsYWltZWRSZXdhcmRzUkVBRE9OTFkBDnVzZXJBZGRyZXNzU3RyCgEWZm9yRWFjaEFzc2V0WmVyb1Jld2FyZAIFYWNjdW0FYXNzZXQJAKwCAgkArAICBQVhY2N1bQkAuQkCCQDMCAIFBWFzc2V0CQDMCAICATAJAMwIAgIBMAUDbmlsAgE6AgFfBBJ1bmNsYWltZWRSZXdhcmRTdHIDCQAAAgUOdXNlckFkZHJlc3NTdHICAAoAAiRsBRNzdXBwb3J0ZWRBc3NldHNMaXN0CgACJHMJAJADAQUCJGwKAAUkYWNjMAIACgEFJGYwXzECAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJARZmb3JFYWNoQXNzZXRaZXJvUmV3YXJkAgUCJGEJAJEDAgUCJGwFAiRpCgEFJGYwXzICAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAAIBAhNMaXN0IHNpemUgZXhjZWVkcyA5CQEFJGYwXzICCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECBQUkYWNjMAAAAAEAAgADAAQABQAGAAcACAAJBAt1c2VyQWRkcmVzcwkBEUBleHRyTmF0aXZlKDEwNjIpAQUOdXNlckFkZHJlc3NTdHIEDSR0MDI1ODQ5MjU5NjgJAQt2YWx1ZU9yRWxzZQIJARNnZXRVc2VyUGFyYW1zT3JVbml0AQULdXNlckFkZHJlc3MJAJYKBAYAAAAAAAAECWlzTmV3VXNlcggFDSR0MDI1ODQ5MjU5NjgCXzEEDHN0YWtlZEFtb3VudAgFDSR0MDI1ODQ5MjU5NjgCXzIEDHN0YWtpbmdTdGFydAgFDSR0MDI1ODQ5MjU5NjgCXzMECXVzZXJHbnNidAgFDSR0MDI1ODQ5MjU5NjgCXzQEDXN0YWtlZEFtb3VudFgJALYCAQUJdXNlckduc2J0BBt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkJARtrZXlVc2VyUmV3YXJkRnJvbURlcG9zaXROdW0BBQ51c2VyQWRkcmVzc1N0cgQOZGVwb3NpdE51bVVzZXIJAQxnZXRJbnRPckVsc2UCBRt1c2VyUmV3YXJkRnJvbURlcG9zaXROdW1LRVkA////////////AQQOZGVwb3NpdE51bUxhc3QJAQxnZXRJbnRPckVsc2UCCQERa2V5RGVwb3NpdE51bUxhc3QAAP///////////wEKAR9mb3JFYWNoQXNzZXRDYWxjVW5jbGFpbWVkUmV3YXJkAgVhY2N1bQVhc3NldAQNJHQwMjYzMTEyNjQ0OQkBCmNhbGNSZXdhcmQFBQ51c2VyQWRkcmVzc1N0cgUFYXNzZXQFDXN0YWtlZEFtb3VudFgFDmRlcG9zaXROdW1Vc2VyBQ5kZXBvc2l0TnVtTGFzdAQLcmV3YXJkVG90YWwIBQ0kdDAyNjMxMTI2NDQ5Al8xBAZjYWNoZWQIBQ0kdDAyNjMxMTI2NDQ5Al8yBAdkeW5hbWljCAUNJHQwMjYzMTEyNjQ0OQJfMwQTcmV3YXJkQ2FjaGVkUGFydEtFWQgFDSR0MDI2MzExMjY0NDkCXzQEB2NsYWltZWQJAQt2YWx1ZU9yRWxzZQIJAJ8IAQkBCmtleUNsYWltZWQCBQ51c2VyQWRkcmVzc1N0cgUFYXNzZXQAAAkArAICCQCsAgIFBWFjY3VtCQC5CQIJAMwIAgUFYXNzZXQJAMwIAgkApAMBBQtyZXdhcmRUb3RhbAkAzAgCCQCkAwEFB2NsYWltZWQFA25pbAIBOgIBXwoAAiRsBRNzdXBwb3J0ZWRBc3NldHNMaXN0CgACJHMJAJADAQUCJGwKAAUkYWNjMAIACgEFJGYwXzECAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAR9mb3JFYWNoQXNzZXRDYWxjVW5jbGFpbWVkUmV3YXJkAgUCJGEJAJEDAgUCJGwFAiRpCgEFJGYwXzICAiRhAiRpAwkAZwIFAiRpBQIkcwUCJGEJAAIBAhNMaXN0IHNpemUgZXhjZWVkcyA5CQEFJGYwXzICCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECCQEFJGYwXzECBQUkYWNjMAAAAAEAAgADAAQABQAGAAcACAAJCQCUCgIFA25pbAkAswICBRJ1bmNsYWltZWRSZXdhcmRTdHIAAQFpARhuc2J0VW5zdGFraW5nU1lTUkVBRE9OTFkCFXVzZXJBZGRyZXNzU3RyT3JFbXB0eQt1bnN0YWtlQW10UAQLcmVzdWx0QXJyYXkDCQAAAgUVdXNlckFkZHJlc3NTdHJPckVtcHR5AgAJAMwIAgAACQDMCAIAAAkAzAgCAAAJAMwIAgAABQNuaWwEC3VzZXJBZGRyZXNzCQERQGV4dHJOYXRpdmUoMTA2MikBBRV1c2VyQWRkcmVzc1N0ck9yRW1wdHkEB2NmZ0RBVEEJAQ9nZXRQYXJhbXNPckZhaWwABAtuc2J0QXNzZXRJZAgFB2NmZ0RBVEECXzEEDW1pbkxvY2tBbW91bnQIBQdjZmdEQVRBAl8yBAhoYWxmTGlmZQgFB2NmZ0RBVEECXzMECHVzZXJEQVRBCQELdmFsdWVPckVsc2UCCQETZ2V0VXNlclBhcmFtc09yVW5pdAEFC3VzZXJBZGRyZXNzCQCWCgQGAAAAAAAABAlpc05ld1VzZXIIBQh1c2VyREFUQQJfMQQMc3Rha2VkQW1vdW50CAUIdXNlckRBVEECXzIECWxvY2tTdGFydAgFCHVzZXJEQVRBAl8zBAp1bnN0YWtlQW10AwkAZgIFC3Vuc3Rha2VBbXRQBQxzdGFrZWRBbW91bnQFDHN0YWtlZEFtb3VudAULdW5zdGFrZUFtdFAED3N0YWtlZEFtb3VudE5FVwkAZQIFDHN0YWtlZEFtb3VudAUKdW5zdGFrZUFtdAQPY29taXNzaW9uQW1vdW50AwkAAAIFCnVuc3Rha2VBbXQAAAAACQEFYXNJbnQBCQD8BwQFDG1hdGhDb250cmFjdAIhZ2V0VW5zdGFrZUNvbWlzc2lvbkFtb3VudFJFQURPTkxZCQDMCAIFCnVuc3Rha2VBbXQJAMwIAgUJbG9ja1N0YXJ0CQDMCAIFCGhhbGZMaWZlBQNuaWwFA25pbAQNcmVjZWl2ZUFtb3VudAkAZQIFCnVuc3Rha2VBbXQFD2NvbWlzc2lvbkFtb3VudAkAzAgCBQxzdGFrZWRBbW91bnQJAMwIAgUPc3Rha2VkQW1vdW50TkVXCQDMCAIFDXJlY2VpdmVBbW91bnQJAMwIAgUPY29taXNzaW9uQW1vdW50BQNuaWwJAJQKAgUDbmlsBQtyZXN1bHRBcnJheQFpARZuc2J0U3Rha2luZ1NZU1JFQURPTkxZAg51c2VyQWRkcmVzc1N0cghuc2J0RGlmZgQMdG90YWxOc2J0QW10CQEMZ2V0SW50T3JFbHNlAgkBF2tleUxvY2tQYXJhbVRvdGFsQW1vdW50AAAABAp0b3RhbEduc2J0CQEMZ2V0SW50T3JFbHNlAgkBFmtleUxvY2tQYXJhbVRvdGFsR25zYnQABQx0b3RhbE5zYnRBbXQDCQAAAgUOdXNlckFkZHJlc3NTdHICAAkAlAoCBQNuaWwJAMwIAgAACQDMCAIFDHRvdGFsTnNidEFtdAkAzAgCAAAJAMwIAgAACQDMCAIFCnRvdGFsR25zYnQJAMwIAgkAaAIFCG5zYnREaWZmAAIFA25pbAQLdXNlckFkZHJlc3MJAQ90b0FkZHJlc3NPckZhaWwBBQ51c2VyQWRkcmVzc1N0cgQNJHQwMjgyNTEyODM3NgkBC3ZhbHVlT3JFbHNlAgkBE2dldFVzZXJQYXJhbXNPclVuaXQBBQt1c2VyQWRkcmVzcwkAlgoEBgAAAAAAAAQJaXNOZXdVc2VyCAUNJHQwMjgyNTEyODM3NgJfMQQLdXNlck5zYnRBbXQIBQ0kdDAyODI1MTI4Mzc2Al8yBAxzdGFraW5nU3RhcnQIBQ0kdDAyODI1MTI4Mzc2Al8zBBBjdXJyZW50VXNlckduc2J0CAUNJHQwMjgyNTEyODM3NgJfNAQQdXNlckNvbnNlbnRUdXBsZQkBGHJlYWRVc2VyQ29uc2VudFRvWDJHbnNidAEJARFAZXh0ck5hdGl2ZSgxMDYyKQEFDnVzZXJBZGRyZXNzU3RyBBl1c2VyQ29uc2VudGVkVG9YMkduc2J0S0VZCAUQdXNlckNvbnNlbnRUdXBsZQJfMQQWdXNlckNvbnNlbnRlZFRvWDJHbnNidAgFEHVzZXJDb25zZW50VHVwbGUCXzIEDmRlbHRhVXNlckduc2J0AwMJAQ1pc0JvbnVzUGVyaW9kAQUGaGVpZ2h0AwUJaXNOZXdVc2VyBgUWdXNlckNvbnNlbnRlZFRvWDJHbnNidAcJAGgCAAIFCG5zYnREaWZmBQhuc2J0RGlmZgkAlAoCBQNuaWwJAMwIAgULdXNlck5zYnRBbXQJAMwIAgUMdG90YWxOc2J0QW10CQDMCAIFDHN0YWtpbmdTdGFydAkAzAgCBRBjdXJyZW50VXNlckduc2J0CQDMCAIFCnRvdGFsR25zYnQJAMwIAgUOZGVsdGFVc2VyR25zYnQFA25pbAECdHgBBnZlcmlmeQAEE3B1YktleUFkbWluc0xpc3RTdHIJALkJAgkAzAgCAixHSmRMU2FMaXY1Szd4dWVqYWM4bWNSY0hveW8zZFByRVNydmt0RzNhNk1BUgkAzAgCAixFWXdabVVSZDVLS2FRUkJqc1ZhNmc4RFBpc0ZvUzZTb3ZSSnRGaUw1Z01IVQkAzAgCAixEdG1BZnVEZENySEs4c3BkQWVBWXpxNk1zWmVnZUQ5Z25zcnB1VFJrQ2JWQQkAzAgCAiw1V1JYRlNqd2NUYk5mS2NKczhacVhtU1NXWXNTVkpVdE12TXFaajVoSDROYwUDbmlsBQNTRVAEEHB1YktleUFkbWluc0xpc3QJALUJAgkBC3ZhbHVlT3JFbHNlAgkAnQgCBQ9jb250cm9sQ29udHJhY3QCDCVzX19tdWx0aXNpZwUTcHViS2V5QWRtaW5zTGlzdFN0cgUDU0VQBAVjb3VudAkAZAIJAGQCCQBkAgMJAPQDAwgFAnR4CWJvZHlCeXRlcwkAkQMCCAUCdHgGcHJvb2ZzAAAJANkEAQkAkQMCBRBwdWJLZXlBZG1pbnNMaXN0AAAAAQAAAwkA9AMDCAUCdHgJYm9keUJ5dGVzCQCRAwIIBQJ0eAZwcm9vZnMAAQkA2QQBCQCRAwIFEHB1YktleUFkbWluc0xpc3QAAQABAAADCQD0AwMIBQJ0eAlib2R5Qnl0ZXMJAJEDAggFAnR4BnByb29mcwACCQDZBAEJAJEDAgUQcHViS2V5QWRtaW5zTGlzdAACAAEAAAMJAPQDAwgFAnR4CWJvZHlCeXRlcwkAkQMCCAUCdHgGcHJvb2ZzAAMJANkEAQkAkQMCBRBwdWJLZXlBZG1pbnNMaXN0AAMAAgAACQBnAgUFY291bnQAA8SS8WU=", "height": 3860132, "applicationStatus": "succeeded", "spentComplexity": 0 } View: original | compacted Prev: J9KULedbcmqhz56d14WC1vaWZa3nmWTEB9xyY2peXXtK Next: none Diff:
OldNewDifferences
760760 let totalNsbtAmt = getIntOrElse(keyLockParamTotalAmount(), 0)
761761 let totalGnsbt = getIntOrElse(keyLockParamTotalGnsbt(), totalNsbtAmt)
762762 if ((userAddressStr == ""))
763- then $Tuple2(nil, [0, totalNsbtAmt, 0, 0, totalGnsbt])
763+ then $Tuple2(nil, [0, totalNsbtAmt, 0, 0, totalGnsbt, (nsbtDiff * 2)])
764764 else {
765765 let userAddress = toAddressOrFail(userAddressStr)
766- let $t02823928364 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
767- let isNewUser = $t02823928364._1
768- let userNsbtAmt = $t02823928364._2
769- let stakingStart = $t02823928364._3
770- let currentUserGnsbt = $t02823928364._4
766+ let $t02825128376 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
767+ let isNewUser = $t02825128376._1
768+ let userNsbtAmt = $t02825128376._2
769+ let stakingStart = $t02825128376._3
770+ let currentUserGnsbt = $t02825128376._4
771771 let userConsentTuple = readUserConsentToX2Gnsbt(addressFromStringValue(userAddressStr))
772772 let userConsentedToX2GnsbtKEY = userConsentTuple._1
773773 let userConsentedToX2Gnsbt = userConsentTuple._2
Full:
OldNewDifferences
11 {-# STDLIB_VERSION 6 #-}
22 {-# SCRIPT_TYPE ACCOUNT #-}
33 {-# CONTENT_TYPE DAPP #-}
44 let revisionNum = ""
55
66 let separator = "__"
77
88 let SEP = "__"
99
1010 let MULT6 = 1000000
1111
1212 let MULT8 = 100000000
1313
1414 let MULTX6 = toBigInt(MULT6)
1515
1616 let MULTX8 = toBigInt(MULT8)
1717
1818 let MULTX18 = toBigInt(1000000000000000000)
1919
2020 let WAVESIDSTR = "WAVES"
2121
2222 let WAVESID = fromBase58String(WAVESIDSTR)
2323
2424 let DAYMILLIS = 86400000
2525
2626 let MAXBASKET = 9
2727
2828 let IdxControlCfgNeutrinoDapp = 1
2929
3030 let IdxControlCfgAuctionDapp = 2
3131
3232 let IdxControlCfgRpdDapp = 3
3333
3434 let IdxControlCfgMathDapp = 4
3535
3636 let IdxControlCfgLiquidationDapp = 5
3737
3838 let IdxControlCfgRestDapp = 6
3939
4040 let IdxControlCfgNodeRegistryDapp = 7
4141
4242 let IdxControlCfgNsbtStakingDapp = 8
4343
4444 let IdxControlCfgMediatorDapp = 9
4545
4646 let IdxControlCfgGovernanceDapp = 13
4747
4848 func getStringOrFail (address,key) = valueOrErrorMessage(getString(address, key), (((("mandatory " + toString(address)) + ".") + key) + " is not defined"))
4949
5050
5151 func keyCfgX2GnsbtOfferHeightStart () = "%s%s__config__x2GnsbtOfferHeightStart"
5252
5353
5454 func keyCfgX2GnsbtOfferHeightEnd () = "%s%s__config__x2GnsbtOfferHeightEnd"
5555
5656
5757 func keyControlAddress () = "%s%s__config__controlAddress"
5858
5959
6060 func keyControlCfg () = "%s__controlConfig"
6161
6262
6363 func readControlCfgOrFail (control) = split_4C(getStringOrFail(control, keyControlCfg()), SEP)
6464
6565
6666 func getContractAddressOrFail (controlCfg,idx) = valueOrErrorMessage(addressFromString(controlCfg[idx]), ("Control cfg doesn't contain address at index " + toString(idx)))
6767
6868
6969 let controlContract = addressFromStringValue(valueOrElse(getString(this, keyControlAddress()), "3P5Bfd58PPfNvBM2Hy8QfbcDqMeNtzg7KfP"))
7070
7171 let controlCfg = readControlCfgOrFail(controlContract)
7272
7373 let mathContract = getContractAddressOrFail(controlCfg, IdxControlCfgMathDapp)
7474
7575 let neutrinoContract = getContractAddressOrFail(controlCfg, IdxControlCfgNeutrinoDapp)
7676
7777 let auctionContract = getContractAddressOrFail(controlCfg, IdxControlCfgAuctionDapp)
7878
7979 let govContract = getContractAddressOrFail(controlCfg, IdxControlCfgGovernanceDapp)
8080
8181 let neutrinoDaoContract = addressFromStringValue("3PEiiJRkV66T1NW7MoY3DGgCaxoDRCez8fL")
8282
8383 let RENEW_START_HEIGHT = valueOrElse(getInteger(this, keyCfgX2GnsbtOfferHeightStart()), 0)
8484
8585 let RENEW_END_HEIGHT = valueOrElse(getInteger(this, keyCfgX2GnsbtOfferHeightEnd()), 0)
8686
8787 func keyBondAsset () = "bond_asset_id"
8888
8989
9090 func keyUserGnsbtReleaseTime (userAddr) = ("%s%s_userGnsbtReleaseTime__" + userAddr)
9191
9292
9393 func keyNeutrinoContractAddress () = "%s__neutrinoContractAddress"
9494
9595
9696 func keyMathContractAddress () = "%s__mathContract"
9797
9898
9999 func keyMinLockAmount () = "%s__minLockAmount"
100100
101101
102102 func keyHalfLife () = "%s__halfLife"
103103
104104
105105 func keyLockParamUserAmount (userAddress) = makeString(["%s%s%s", "paramByUser", toString(userAddress), "amount"], separator)
106106
107107
108108 func keyLockParamStartBlock (userAddress) = makeString(["%s%s%s", "paramByUser", toString(userAddress), "start"], separator)
109109
110110
111111 func keyLockParamUserGnsbt (userAddress) = makeString(["%s%s%s", "paramByUser", toString(userAddress), "gNsbt"], separator)
112112
113113
114114 func keyUserConsentedToX2Gnsbt (userAddress) = makeString(["%s%s%s", "paramByUser", toString(userAddress), "consentedToX2Gnsbt"], separator)
115115
116116
117117 func keyHistoryRecord (type,userAddress,txId) = makeString(["%s%s%s%s", "history", type, toString(userAddress), toBase58String(txId)], separator)
118118
119119
120120 func keyLockParamTotalAmount () = makeString(["%s%s", "stats", "activeTotalLocked"], separator)
121121
122122
123123 func keyLockParamTotalGnsbt () = makeString(["%s%s", "stats", "activeTotalGnsbt"], separator)
124124
125125
126126 func keyStatsLocksCount () = makeString(["%s%s", "stats", "locksCount"], separator)
127127
128128
129129 func keyStatsUsersCount () = makeString(["%s%s", "stats", "activeUsersCount"], separator)
130130
131131
132132 func keyStatsDepositAmtByDay (timestamp) = makeString(["%s%s%d", "stats", "depositAmtByDay", toString(timestamp)], separator)
133133
134134
135135 func keyStatsDepositAmtTotals () = makeString(["%s%s%d", "stats", "depositAmtTotals"], separator)
136136
137137
138138 func keyNextPeriod () = "%s__nextPeriod"
139139
140140
141141 func keySupportedRewardAssets () = "supportedRewardAssets"
142142
143143
144144 func keyDepositNumLast () = makeString(["%s%s%s", "dep", "lastNum"], separator)
145145
146146
147147 func keyUserRewardFromDepositNum (userAddress) = makeString(["%s%s%s", "userRwdFromDepNum", userAddress], separator)
148148
149149
150150 func keyRewardPerNsbtSumAt (depositNum,tkn) = makeString(["%s%d", "rwdPerNsbtSumByDepNum", toString(depositNum), tkn], separator)
151151
152152
153153 func keyReward (userAddress,tkn) = makeString(["%s%s%s", "rwd", userAddress, tkn], separator)
154154
155155
156156 func keyClaimed (userAddress,tkn) = makeString(["%s%s%s", "clm", userAddress, tkn], separator)
157157
158158
159159 func keyNotDistributedReward (tkn) = makeString(["%s%s", "notDistributed", tkn], separator)
160160
161161
162162 func toX18 (origVal,origMult) = fraction(toBigInt(origVal), MULTX18, origMult)
163163
164164
165165 func getIntOrZero (key) = valueOrElse(getInteger(this, key), 0)
166166
167167
168168 func getIntOrElse (key,defaultVal) = valueOrElse(getInteger(this, key), defaultVal)
169169
170170
171171 func getIntOrFail (key) = valueOrErrorMessage(getInteger(this, key), (("Mandatory this." + key) + " is not defined"))
172172
173173
174174 func getStrOrElse (key,defaultVal) = valueOrElse(getString(this, key), defaultVal)
175175
176176
177177 func toAddressOrFail (addressStr) = valueOrErrorMessage(addressFromString(addressStr), ("couldn't parse passed addressStr=" + addressStr))
178178
179179
180180 func toAssetVect (assetStr) = if ((assetStr == WAVESIDSTR))
181181 then unit
182182 else fromBase58String(assetStr)
183183
184184
185185 func asInt (val) = match val {
186186 case valInt: Int =>
187187 valInt
188188 case _ =>
189189 throw("fail to cast into Int")
190190 }
191191
192192
193193 func formatHistoryRecord (oldAmount,oldStart,newAmount,newStart) = makeString(["%d%d%d%d%d%d", toString(lastBlock.height), toString(lastBlock.timestamp), toString(oldAmount), toString(oldStart), toString(newAmount), toString(newStart)], separator)
194194
195195
196196 func formatClaimHistoryRecord (user,claimedRewards) = makeString(["%s%d%d%s", user, toString(lastBlock.height), toString(lastBlock.timestamp), claimedRewards], separator)
197197
198198
199199 func HistoryRecordEntry (type,userAddress,txId,oldAmount,oldStart,newAmount,newStart) = StringEntry(keyHistoryRecord(type, userAddress, txId), formatHistoryRecord(oldAmount, oldStart, newAmount, newStart))
200200
201201
202202 func ClaimHistoryEntry (userAddress,txId,claimedRewards) = StringEntry(keyHistoryRecord("claim", userAddress, txId), formatClaimHistoryRecord(toString(userAddress), claimedRewards))
203203
204204
205205 func StatsResult (totalLockedInc,lockCountInc,usersCountInc,totalGnsbtInc) = {
206206 let locksCount = getIntOrZero(keyStatsLocksCount())
207207 let usersCount = getIntOrZero(keyStatsUsersCount())
208208 let totalAmount = getIntOrZero(keyLockParamTotalAmount())
209209 let totalAmountNew = (totalAmount + totalLockedInc)
210210 let totalGnsbt = getIntOrElse(keyLockParamTotalGnsbt(), totalAmount)
211211 $Tuple3([IntegerEntry(keyStatsLocksCount(), (locksCount + lockCountInc)), IntegerEntry(keyStatsUsersCount(), (usersCount + usersCountInc)), IntegerEntry(keyLockParamTotalAmount(), totalAmountNew), IntegerEntry(keyLockParamTotalGnsbt(), (totalGnsbt + totalGnsbtInc))], totalAmount, totalAmountNew)
212212 }
213213
214214
215215 func LockParamsEntry (userAddress,nsbtAmount,start,gNsbtAmount) = [IntegerEntry(keyLockParamUserAmount(userAddress), nsbtAmount), IntegerEntry(keyLockParamUserGnsbt(userAddress), gNsbtAmount), IntegerEntry(keyLockParamStartBlock(userAddress), start)]
216216
217217
218218 func getParamsOrFail () = $Tuple3(fromBase58String(getStringValue(neutrinoContract, keyBondAsset())), getIntOrFail(keyMinLockAmount()), getIntOrFail(keyHalfLife()))
219219
220220
221221 func isActiveUser (userAddress) = (getIntOrElse(keyLockParamUserAmount(userAddress), 0) > 0)
222222
223223
224224 func isBonusPeriod (h) = if ((h >= RENEW_START_HEIGHT))
225225 then (RENEW_END_HEIGHT >= h)
226226 else false
227227
228228
229229 func getUserParamsOrUnit (userAddress) = if (isActiveUser(userAddress))
230230 then {
231231 let amount = getIntOrFail(keyLockParamUserAmount(userAddress))
232232 $Tuple4(false, amount, getIntOrFail(keyLockParamStartBlock(userAddress)), getIntOrElse(keyLockParamUserGnsbt(userAddress), amount))
233233 }
234234 else unit
235235
236236
237237 func getUserParamsOrFail (userAddress) = valueOrErrorMessage(getUserParamsOrUnit(userAddress), (("User " + toString(userAddress)) + " is not defined"))
238238
239239
240240 let supportedAssetsStr = getStrOrElse(keySupportedRewardAssets(), "")
241241
242242 let supportedAssetsList = split(supportedAssetsStr, "_")
243243
244244 func calcReward (userAddress,assetId,stakedAmountX,depositNumUser,depositNumLast) = {
245245 let rewardPerNsbtSumLastKEY = keyRewardPerNsbtSumAt(depositNumLast, assetId)
246246 let sumLastX18 = parseBigIntValue(getStrOrElse(keyRewardPerNsbtSumAt(depositNumLast, assetId), "0"))
247247 let sumUserX18 = parseBigIntValue(getStrOrElse(keyRewardPerNsbtSumAt(depositNumUser, assetId), "0"))
248248 let rewardDynamicPart = toInt(fraction((sumLastX18 - sumUserX18), stakedAmountX, MULTX18))
249249 let rewardCachedPartKEY = keyReward(userAddress, assetId)
250250 let rewardCachedPart = getIntOrElse(rewardCachedPartKEY, 0)
251251 $Tuple4((rewardCachedPart + rewardDynamicPart), rewardCachedPart, rewardDynamicPart, rewardCachedPartKEY)
252252 }
253253
254254
255255 func toStartOfDay (timestamp) = ((timestamp / DAYMILLIS) * DAYMILLIS)
256256
257257
258258 func findElementPosition (src,element,sep) = {
259259 let elementStart = valueOrErrorMessage(indexOf(src, element), ((("there is no substring " + element) + " in ") + src))
260260 if ((elementStart == 0))
261261 then 0
262262 else {
263263 let left = take(src, elementStart)
264264 (size(split(left, sep)) - 1)
265265 }
266266 }
267267
268268
269269 let DepositTotalsPREFIX = "%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d"
270270
271271 let defaultTotalsDATA = (DepositTotalsPREFIX + "__0__0__0__0__0__0__0__0__0__0__0__0__0__0__0__0__0__0")
272272
273273 func padList (in) = {
274274 let currSize = (size(in) - 1)
275275 func listPadder (acc,idx) = if ((currSize > idx))
276276 then acc
277277 else (acc :+ "0")
278278
279279 let $l = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]
280280 let $s = size($l)
281281 let $acc0 = in
282282 func $f0_1 ($a,$i) = if (($i >= $s))
283283 then $a
284284 else listPadder($a, $l[$i])
285285
286286 func $f0_2 ($a,$i) = if (($i >= $s))
287287 then $a
288288 else throw("List size exceeds 18")
289289
290290 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9), 10), 11), 12), 13), 14), 15), 16), 17), 18)
291291 }
292292
293293
294294 func padString (in) = {
295295 let currSize = (size(split_4C(in, SEP)) - 1)
296296 func strPadder (acc,idx) = if ((currSize > idx))
297297 then acc
298298 else (acc + "__0")
299299
300300 let $l = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]
301301 let $s = size($l)
302302 let $acc0 = in
303303 func $f0_1 ($a,$i) = if (($i >= $s))
304304 then $a
305305 else strPadder($a, $l[$i])
306306
307307 func $f0_2 ($a,$i) = if (($i >= $s))
308308 then $a
309309 else throw("List size exceeds 18")
310310
311311 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9), 10), 11), 12), 13), 14), 15), 16), 17), 18)
312312 }
313313
314314
315315 func RewardEntries (isNewUser,userAddress,stakedAmount) = {
316316 let stakedAmountX = toBigInt(stakedAmount)
317317 let userRewardFromDepositNumKEY = keyUserRewardFromDepositNum(userAddress)
318318 let depositNumUser = getIntOrElse(userRewardFromDepositNumKEY, -1)
319319 let depositNumLast = getIntOrElse(keyDepositNumLast(), -1)
320320 func forEachAssetCacheUserReward (accum,asset) = {
321321 let $t01148311618 = calcReward(userAddress, asset, stakedAmountX, depositNumUser, depositNumLast)
322322 let rewardTotal = $t01148311618._1
323323 let cached = $t01148311618._2
324324 let dynamic = $t01148311618._3
325325 let rewardCachedPartKEY = $t01148311618._4
326326 (accum :+ IntegerEntry(rewardCachedPartKEY, rewardTotal))
327327 }
328328
329329 if (if ((depositNumLast == -1))
330330 then (depositNumUser == -1)
331331 else false)
332332 then nil
333333 else if (if ((depositNumLast == -1))
334334 then (depositNumUser > -1)
335335 else false)
336336 then throw("invalid depositNumLast and depositNumUser state")
337337 else if (if ((depositNumLast > -1))
338338 then (depositNumUser >= -1)
339339 else false)
340340 then if (isNewUser)
341341 then [IntegerEntry(userRewardFromDepositNumKEY, depositNumLast)]
342342 else ({
343343 let $l = supportedAssetsList
344344 let $s = size($l)
345345 let $acc0 = nil
346346 func $f0_1 ($a,$i) = if (($i >= $s))
347347 then $a
348348 else forEachAssetCacheUserReward($a, $l[$i])
349349
350350 func $f0_2 ($a,$i) = if (($i >= $s))
351351 then $a
352352 else throw("List size exceeds 9")
353353
354354 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9)
355355 } :+ IntegerEntry(userRewardFromDepositNumKEY, depositNumLast))
356356 else throw(((("uncovered condition: depositNumLast=" + toString(depositNumLast)) + " depositNumUser=") + toString(depositNumUser)))
357357 }
358358
359359
360360 func IncrementNotDistributedRewardEntry (tkn,amountInc) = {
361361 let notDistributedRewardKEY = keyNotDistributedReward(tkn)
362362 let notDistributedReward = getIntOrElse(notDistributedRewardKEY, 0)
363363 IntegerEntry(notDistributedRewardKEY, (notDistributedReward + amountInc))
364364 }
365365
366366
367367 func commonClaim (userAddress,i) = {
368368 let userAddressStr = toString(userAddress)
369369 if ((size(i.payments) > 0))
370370 then throw("payments are not accepted")
371371 else {
372372 let $t01455914680 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
373373 let isNewUser = $t01455914680._1
374374 let stakedAmount = $t01455914680._2
375375 let stakingStart = $t01455914680._3
376376 let gNsbtAmount = $t01455914680._4
377377 let stakedAmountX = toBigInt(gNsbtAmount)
378378 let userRewardFromDepositNumKEY = keyUserRewardFromDepositNum(userAddressStr)
379379 let depositNumUser = getIntOrElse(userRewardFromDepositNumKEY, -1)
380380 let depositNumLast = getIntOrElse(keyDepositNumLast(), -1)
381381 func forEachAssetCalcUnclaimedReward (accum,asset) = {
382382 let $t01505015188 = calcReward(userAddressStr, asset, stakedAmountX, depositNumUser, depositNumLast)
383383 let rewardTotal = $t01505015188._1
384384 let cached = $t01505015188._2
385385 let dynamic = $t01505015188._3
386386 let rewardCachedPartKEY = $t01505015188._4
387387 let claimedKEY = keyClaimed(userAddressStr, asset)
388388 let $t01524815285 = accum
389389 let data = $t01524815285._1
390390 let claimedAmtByAsset = $t01524815285._2
391391 let newPart = makeString([asset, toString(rewardTotal)], ":")
392392 let claimedAmtByAssetNew = makeString([claimedAmtByAsset, newPart], "_")
393393 if ((0 >= rewardTotal))
394394 then $Tuple2(data, claimedAmtByAssetNew)
395395 else $Tuple2((((data :+ ScriptTransfer(userAddress, rewardTotal, toAssetVect(asset))) :+ IntegerEntry(claimedKEY, (valueOrElse(getInteger(claimedKEY), 0) + rewardTotal))) :+ IntegerEntry(rewardCachedPartKEY, 0)), claimedAmtByAssetNew)
396396 }
397397
398398 let $t01574515858 = {
399399 let $l = supportedAssetsList
400400 let $s = size($l)
401401 let $acc0 = $Tuple2(nil, "")
402402 func $f0_1 ($a,$i) = if (($i >= $s))
403403 then $a
404404 else forEachAssetCalcUnclaimedReward($a, $l[$i])
405405
406406 func $f0_2 ($a,$i) = if (($i >= $s))
407407 then $a
408408 else throw("List size exceeds 9")
409409
410410 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9)
411411 }
412412 let transfers = $t01574515858._1
413413 let claimedAmtByAssetResult = $t01574515858._2
414414 if ((0 >= size(transfers)))
415415 then $Tuple2(nil, 0)
416416 else $Tuple2(((transfers :+ IntegerEntry(userRewardFromDepositNumKEY, depositNumLast)) :+ ClaimHistoryEntry(userAddress, i.transactionId, drop(claimedAmtByAssetResult, 1))), size(transfers))
417417 }
418418 }
419419
420420
421421 func readUserConsentToX2Gnsbt (userAddress) = {
422422 let key = keyUserConsentedToX2Gnsbt(userAddress)
423423 let val = valueOrElse(getBoolean(this, key), false)
424424 $Tuple2(key, val)
425425 }
426426
427427
428428 func commonX2Gnsbt (userAddress,i) = if (!(isBonusPeriod(height)))
429429 then throw("No 'Double gNSBT action' available now")
430430 else {
431431 let $t01642016481 = commonClaim(userAddress, i)
432432 let claimActions = $t01642016481._1
433433 let claimResult = $t01642016481._2
434434 let $t01648416609 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, -1, 0))
435435 let isNewUser = $t01648416609._1
436436 let lockAmount = $t01648416609._2
437437 let lockStartHeight = $t01648416609._3
438438 let currUserGnsbt = $t01648416609._4
439439 if (isNewUser)
440440 then throw("You have nothing to restake")
441441 else {
442442 let deltaUserGnsbt = currUserGnsbt
443443 let newUserGnsbt = (currUserGnsbt + deltaUserGnsbt)
444444 let userConsentTuple = readUserConsentToX2Gnsbt(userAddress)
445445 let userConsentedToX2GnsbtKEY = userConsentTuple._1
446446 let userConsentedToX2Gnsbt = userConsentTuple._2
447447 if (userConsentedToX2Gnsbt)
448448 then throw("User has already doubled its gNSBT value")
449449 else {
450450 let $t01702617112 = StatsResult(0, 0, 0, deltaUserGnsbt)
451451 let statsEntries = $t01702617112._1
452452 let totalStaked = $t01702617112._2
453453 let totalStakedNew = $t01702617112._3
454454 $Tuple2((((claimActions ++ LockParamsEntry(userAddress, lockAmount, height, newUserGnsbt)) ++ statsEntries) :+ BooleanEntry(userConsentedToX2GnsbtKEY, true)), claimResult)
455455 }
456456 }
457457 }
458458
459459
460460 @Callable(i)
461461 func constructorV1 (neutrinoContractAddress,mathContractAddress,minLockAmount,halfLife,supportedRewardAssets) = if ((i.caller != this))
462462 then throw("Permission denied")
463463 else [StringEntry(keyNeutrinoContractAddress(), neutrinoContractAddress), StringEntry(keyMathContractAddress(), mathContractAddress), IntegerEntry(keyMinLockAmount(), minLockAmount), IntegerEntry(keyHalfLife(), halfLife), StringEntry(keySupportedRewardAssets(), supportedRewardAssets)]
464464
465465
466466
467467 @Callable(i)
468468 func constructorV2 (x2GnsbtOfferHeightStart,x2GnsbtOfferHeightEnd) = if ((i.caller != this))
469469 then throw("Permission denied")
470470 else [IntegerEntry(keyCfgX2GnsbtOfferHeightStart(), x2GnsbtOfferHeightStart), IntegerEntry(keyCfgX2GnsbtOfferHeightEnd(), x2GnsbtOfferHeightEnd)]
471471
472472
473473
474474 @Callable(i)
475475 func stake () = {
476476 let $t01821818280 = getParamsOrFail()
477477 let bondAssetId = $t01821818280._1
478478 let minLockAmount = $t01821818280._2
479479 let halfLife = $t01821818280._3
480480 if ((size(i.payments) != 1))
481481 then throw("Invalid payments size")
482482 else {
483483 let payment = i.payments[0]
484484 let amount = payment.amount
485485 let invalidAssetMessage = (("Invalid asset. " + toBase58String(bondAssetId)) + " is expected")
486486 let assetId = valueOrErrorMessage(payment.assetId, invalidAssetMessage)
487487 if ((assetId != bondAssetId))
488488 then throw(invalidAssetMessage)
489489 else {
490490 let userAddress = i.caller
491491 let userAddressStr = toString(i.caller)
492492 let $t01882218947 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, -1, 0))
493493 let isNewUser = $t01882218947._1
494494 let lockAmount = $t01882218947._2
495495 let lockStartHeight = $t01882218947._3
496496 let currUserGnsbt = $t01882218947._4
497497 let mergedAmount = if (isNewUser)
498498 then amount
499499 else (amount + lockAmount)
500500 let mergedStartHeight = if (isNewUser)
501501 then height
502502 else asInt(invoke(mathContract, "mergeStakesREADONLY", [amount, height, lockAmount, lockStartHeight, halfLife], nil))
503503 if ((minLockAmount > mergedAmount))
504504 then throw(("Min lock amount is " + toString(minLockAmount)))
505505 else {
506506 let userConsentTuple = readUserConsentToX2Gnsbt(userAddress)
507507 let userConsentedToX2GnsbtKEY = userConsentTuple._1
508508 let userConsentedToX2Gnsbt = userConsentTuple._2
509509 let deltaUserGnsbt = if (if (isBonusPeriod(height))
510510 then if (isNewUser)
511511 then true
512512 else userConsentedToX2Gnsbt
513513 else false)
514514 then (2 * amount)
515515 else amount
516516 let x2GnsbtConsentEntry = if (isNewUser)
517517 then [BooleanEntry(userConsentedToX2GnsbtKEY, true)]
518518 else nil
519519 let $t01995120069 = StatsResult(amount, 1, if (isNewUser)
520520 then 1
521521 else 0, deltaUserGnsbt)
522522 let statsEntries = $t01995120069._1
523523 let totalStaked = $t01995120069._2
524524 let totalStakedNew = $t01995120069._3
525525 (((([HistoryRecordEntry("stake", userAddress, i.transactionId, lockAmount, lockStartHeight, mergedAmount, mergedStartHeight)] ++ RewardEntries(isNewUser, userAddressStr, currUserGnsbt)) ++ LockParamsEntry(userAddress, mergedAmount, mergedStartHeight, (currUserGnsbt + deltaUserGnsbt))) ++ statsEntries) ++ x2GnsbtConsentEntry)
526526 }
527527 }
528528 }
529529 }
530530
531531
532532
533533 @Callable(i)
534534 func unstake (amount) = if ((size(i.payments) != 0))
535535 then throw("unstake doesn't require any payment")
536536 else {
537537 let userAddress = i.caller
538538 let userAddressStr = toString(userAddress)
539539 let $t02061520677 = getParamsOrFail()
540540 let bondAssetId = $t02061520677._1
541541 let minLockAmount = $t02061520677._2
542542 let halfLife = $t02061520677._3
543543 let $t02068020769 = getUserParamsOrFail(userAddress)
544544 let isNewUser = $t02068020769._1
545545 let lockAmount = $t02068020769._2
546546 let lockStart = $t02068020769._3
547547 let currUserGnsbt = $t02068020769._4
548548 if ((0 >= lockAmount))
549549 then throw("Nothing to unstake")
550550 else if ((amount > lockAmount))
551551 then throw(((("Requested " + toString(amount)) + ", but staked only ") + toString(lockAmount)))
552552 else {
553553 let t = value(blockInfoByHeight(height)).timestamp
554554 let releaseTime = valueOrElse(getInteger(govContract, keyUserGnsbtReleaseTime(userAddressStr)), 0)
555555 if ((releaseTime >= t))
556556 then throw(("Your gNsbt are taking part in voting, cannot unstake until " + toString(releaseTime)))
557557 else {
558558 let comissionAmount = asInt(invoke(mathContract, "getUnstakeComissionAmountREADONLY", [amount, lockStart, halfLife], nil))
559559 let bonusGnsbtPart = (currUserGnsbt - lockAmount)
560560 let bonusNsbtAmount = min([amount, bonusGnsbtPart])
561561 let deltaGnsbt = (bonusNsbtAmount + amount)
562562 let $t02160721778 = StatsResult(-(amount), if ((amount == lockAmount))
563563 then -1
564564 else 0, if ((amount == lockAmount))
565565 then -1
566566 else 0, -(deltaGnsbt))
567567 let statsEntries = $t02160721778._1
568568 let totalStaked = $t02160721778._2
569569 let totalStakedNew = $t02160721778._3
570570 ((([ScriptTransfer(userAddress, (amount - comissionAmount), bondAssetId), ScriptTransfer(neutrinoDaoContract, comissionAmount, bondAssetId), HistoryRecordEntry("unstake", userAddress, i.transactionId, lockAmount, lockStart, (lockAmount - amount), lockStart)] ++ RewardEntries(false, userAddressStr, currUserGnsbt)) ++ LockParamsEntry(userAddress, (lockAmount - amount), lockStart, (currUserGnsbt - deltaGnsbt))) ++ statsEntries)
571571 }
572572 }
573573 }
574574
575575
576576
577577 @Callable(i)
578578 func deposit () = {
579579 let totalStaked = getIntOrElse(keyLockParamTotalGnsbt(), getIntOrElse(keyLockParamTotalAmount(), 0))
580580 if ((0 > totalStaked))
581581 then throw("TODO: case is not supported")
582582 else {
583583 let depositNumLastKEY = keyDepositNumLast()
584584 let depositNumLast = getIntOrElse(depositNumLastKEY, -1)
585585 let depositNumNew = (depositNumLast + 1)
586586 let totalsKEY = keyStatsDepositAmtTotals()
587587 let byDayKEY = keyStatsDepositAmtByDay(toStartOfDay(lastBlock.timestamp))
588588 let currTotals = padList(split(valueOrElse(getString(totalsKEY), defaultTotalsDATA), SEP))
589589 func dep (acc,pmt) = {
590590 let amount = pmt.amount
591591 let pmtAssetIdStr = toBase58String(valueOrElse(pmt.assetId, WAVESID))
592592 if (!(contains(supportedAssetsStr, pmtAssetIdStr)))
593593 then throw(((supportedAssetsStr + " doesn't contain ") + pmtAssetIdStr))
594594 else if ((totalStaked == 0))
595595 then $Tuple4((acc._1 :+ IncrementNotDistributedRewardEntry(pmtAssetIdStr, amount)), (acc._2 :+ pmtAssetIdStr), (acc._3 :+ toBigInt(0)), (acc._4 :+ amount))
596596 else {
597597 let rewardPerNsbtX18 = fraction(toBigInt(amount), MULTX18, toBigInt(totalStaked))
598598 $Tuple4(acc._1, (acc._2 :+ pmtAssetIdStr), (acc._3 :+ rewardPerNsbtX18), (acc._4 :+ amount))
599599 }
600600 }
601601
602602 let pmtsResult = {
603603 let $l = i.payments
604604 let $s = size($l)
605605 let $acc0 = $Tuple4(nil, nil, nil, nil)
606606 func $f0_1 ($a,$i) = if (($i >= $s))
607607 then $a
608608 else dep($a, $l[$i])
609609
610610 func $f0_2 ($a,$i) = if (($i >= $s))
611611 then $a
612612 else throw("List size exceeds 10")
613613
614614 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9), 10)
615615 }
616616 func refreshRewardUpdateTotals (accum,nextAsset) = {
617617 let k = accum._3
618618 let sumLastStr = getStrOrElse(keyRewardPerNsbtSumAt(depositNumLast, nextAsset), "0")
619619 let idx = indexOf(pmtsResult._2, nextAsset)
620620 let sum = if (isDefined(idx))
621621 then {
622622 let j = value(idx)
623623 let statsDelta = pmtsResult._4[j]
624624 $Tuple2(toString((parseBigIntValue(sumLastStr) + pmtsResult._3[j])), toString((parseIntValue(currTotals[(k + 1)]) + statsDelta)))
625625 }
626626 else $Tuple2(sumLastStr, currTotals[(k + 1)])
627627 $Tuple3((accum._1 :+ StringEntry(keyRewardPerNsbtSumAt(depositNumNew, nextAsset), sum._1)), ((accum._2 + SEP) + sum._2), (k + 1))
628628 }
629629
630630 let assetsResult = {
631631 let $l = supportedAssetsList
632632 let $s = size($l)
633633 let $acc0 = $Tuple3(nil, DepositTotalsPREFIX, 0)
634634 func $f1_1 ($a,$i) = if (($i >= $s))
635635 then $a
636636 else refreshRewardUpdateTotals($a, $l[$i])
637637
638638 func $f1_2 ($a,$i) = if (($i >= $s))
639639 then $a
640640 else throw("List size exceeds 9")
641641
642642 $f1_2($f1_1($f1_1($f1_1($f1_1($f1_1($f1_1($f1_1($f1_1($f1_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9)
643643 }
644644 let totals = padString(assetsResult._2)
645645 $Tuple2(((((pmtsResult._1 ++ assetsResult._1) :+ IntegerEntry(depositNumLastKEY, depositNumNew)) :+ StringEntry(totalsKEY, totals)) :+ StringEntry(byDayKEY, totals)), depositNumNew)
646646 }
647647 }
648648
649649
650650
651651 @Callable(i)
652652 func claimRewards () = commonClaim(i.caller, i)
653653
654654
655655
656656 @Callable(i)
657657 func claimRewardsByOriginCaller () = commonClaim(i.originCaller, i)
658658
659659
660660
661661 @Callable(i)
662662 func x2Gnsbt () = commonX2Gnsbt(i.caller, i)
663663
664664
665665
666666 @Callable(i)
667667 func x2GnsbtByOriginCaller () = commonX2Gnsbt(i.originCaller, i)
668668
669669
670670
671671 @Callable(i)
672672 func unclaimedRewardsREADONLY (userAddressStr) = {
673673 func forEachAssetZeroReward (accum,asset) = ((accum + makeString([asset, "0", "0"], ":")) + "_")
674674
675675 let unclaimedRewardStr = if ((userAddressStr == ""))
676676 then {
677677 let $l = supportedAssetsList
678678 let $s = size($l)
679679 let $acc0 = ""
680680 func $f0_1 ($a,$i) = if (($i >= $s))
681681 then $a
682682 else forEachAssetZeroReward($a, $l[$i])
683683
684684 func $f0_2 ($a,$i) = if (($i >= $s))
685685 then $a
686686 else throw("List size exceeds 9")
687687
688688 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9)
689689 }
690690 else {
691691 let userAddress = addressFromStringValue(userAddressStr)
692692 let $t02584925968 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
693693 let isNewUser = $t02584925968._1
694694 let stakedAmount = $t02584925968._2
695695 let stakingStart = $t02584925968._3
696696 let userGnsbt = $t02584925968._4
697697 let stakedAmountX = toBigInt(userGnsbt)
698698 let userRewardFromDepositNumKEY = keyUserRewardFromDepositNum(userAddressStr)
699699 let depositNumUser = getIntOrElse(userRewardFromDepositNumKEY, -1)
700700 let depositNumLast = getIntOrElse(keyDepositNumLast(), -1)
701701 func forEachAssetCalcUnclaimedReward (accum,asset) = {
702702 let $t02631126449 = calcReward(userAddressStr, asset, stakedAmountX, depositNumUser, depositNumLast)
703703 let rewardTotal = $t02631126449._1
704704 let cached = $t02631126449._2
705705 let dynamic = $t02631126449._3
706706 let rewardCachedPartKEY = $t02631126449._4
707707 let claimed = valueOrElse(getInteger(keyClaimed(userAddressStr, asset)), 0)
708708 ((accum + makeString([asset, toString(rewardTotal), toString(claimed)], ":")) + "_")
709709 }
710710
711711 let $l = supportedAssetsList
712712 let $s = size($l)
713713 let $acc0 = ""
714714 func $f0_1 ($a,$i) = if (($i >= $s))
715715 then $a
716716 else forEachAssetCalcUnclaimedReward($a, $l[$i])
717717
718718 func $f0_2 ($a,$i) = if (($i >= $s))
719719 then $a
720720 else throw("List size exceeds 9")
721721
722722 $f0_2($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($f0_1($acc0, 0), 1), 2), 3), 4), 5), 6), 7), 8), 9)
723723 }
724724 $Tuple2(nil, dropRight(unclaimedRewardStr, 1))
725725 }
726726
727727
728728
729729 @Callable(i)
730730 func nsbtUnstakingSYSREADONLY (userAddressStrOrEmpty,unstakeAmtP) = {
731731 let resultArray = if ((userAddressStrOrEmpty == ""))
732732 then [0, 0, 0, 0]
733733 else {
734734 let userAddress = addressFromStringValue(userAddressStrOrEmpty)
735735 let cfgDATA = getParamsOrFail()
736736 let nsbtAssetId = cfgDATA._1
737737 let minLockAmount = cfgDATA._2
738738 let halfLife = cfgDATA._3
739739 let userDATA = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
740740 let isNewUser = userDATA._1
741741 let stakedAmount = userDATA._2
742742 let lockStart = userDATA._3
743743 let unstakeAmt = if ((unstakeAmtP > stakedAmount))
744744 then stakedAmount
745745 else unstakeAmtP
746746 let stakedAmountNEW = (stakedAmount - unstakeAmt)
747747 let comissionAmount = if ((unstakeAmt == 0))
748748 then 0
749749 else asInt(invoke(mathContract, "getUnstakeComissionAmountREADONLY", [unstakeAmt, lockStart, halfLife], nil))
750750 let receiveAmount = (unstakeAmt - comissionAmount)
751751 [stakedAmount, stakedAmountNEW, receiveAmount, comissionAmount]
752752 }
753753 $Tuple2(nil, resultArray)
754754 }
755755
756756
757757
758758 @Callable(i)
759759 func nsbtStakingSYSREADONLY (userAddressStr,nsbtDiff) = {
760760 let totalNsbtAmt = getIntOrElse(keyLockParamTotalAmount(), 0)
761761 let totalGnsbt = getIntOrElse(keyLockParamTotalGnsbt(), totalNsbtAmt)
762762 if ((userAddressStr == ""))
763- then $Tuple2(nil, [0, totalNsbtAmt, 0, 0, totalGnsbt])
763+ then $Tuple2(nil, [0, totalNsbtAmt, 0, 0, totalGnsbt, (nsbtDiff * 2)])
764764 else {
765765 let userAddress = toAddressOrFail(userAddressStr)
766- let $t02823928364 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
767- let isNewUser = $t02823928364._1
768- let userNsbtAmt = $t02823928364._2
769- let stakingStart = $t02823928364._3
770- let currentUserGnsbt = $t02823928364._4
766+ let $t02825128376 = valueOrElse(getUserParamsOrUnit(userAddress), $Tuple4(true, 0, 0, 0))
767+ let isNewUser = $t02825128376._1
768+ let userNsbtAmt = $t02825128376._2
769+ let stakingStart = $t02825128376._3
770+ let currentUserGnsbt = $t02825128376._4
771771 let userConsentTuple = readUserConsentToX2Gnsbt(addressFromStringValue(userAddressStr))
772772 let userConsentedToX2GnsbtKEY = userConsentTuple._1
773773 let userConsentedToX2Gnsbt = userConsentTuple._2
774774 let deltaUserGnsbt = if (if (isBonusPeriod(height))
775775 then if (isNewUser)
776776 then true
777777 else userConsentedToX2Gnsbt
778778 else false)
779779 then (2 * nsbtDiff)
780780 else nsbtDiff
781781 $Tuple2(nil, [userNsbtAmt, totalNsbtAmt, stakingStart, currentUserGnsbt, totalGnsbt, deltaUserGnsbt])
782782 }
783783 }
784784
785785
786786 @Verifier(tx)
787787 func verify () = {
788788 let pubKeyAdminsListStr = makeString(["GJdLSaLiv5K7xuejac8mcRcHoyo3dPrESrvktG3a6MAR", "EYwZmURd5KKaQRBjsVa6g8DPisFoS6SovRJtFiL5gMHU", "DtmAfuDdCrHK8spdAeAYzq6MsZegeD9gnsrpuTRkCbVA", "5WRXFSjwcTbNfKcJs8ZqXmSSWYsSVJUtMvMqZj5hH4Nc"], SEP)
789789 let pubKeyAdminsList = split(valueOrElse(getString(controlContract, "%s__multisig"), pubKeyAdminsListStr), SEP)
790790 let count = ((((if (sigVerify(tx.bodyBytes, tx.proofs[0], fromBase58String(pubKeyAdminsList[0])))
791791 then 1
792792 else 0) + (if (sigVerify(tx.bodyBytes, tx.proofs[1], fromBase58String(pubKeyAdminsList[1])))
793793 then 1
794794 else 0)) + (if (sigVerify(tx.bodyBytes, tx.proofs[2], fromBase58String(pubKeyAdminsList[2])))
795795 then 1
796796 else 0)) + (if (sigVerify(tx.bodyBytes, tx.proofs[3], fromBase58String(pubKeyAdminsList[3])))
797797 then 2
798798 else 0))
799799 (count >= 3)
800800 }
801801

github/deemru/w8io/786bc32 
76.75 ms