tx · CgH4buDCd78U4f4CW2aVuTYT8RwtVwUhVKDNTGwy3BNy 3N6ALE8YyAYnRk9f38mdWRTvW77rFkg5hN1: -0.03200000 Waves 2024.02.08 18:23 [2967446] smart account 3N6ALE8YyAYnRk9f38mdWRTvW77rFkg5hN1 > SELF 0.00000000 Waves
{ "type": 13, "id": "CgH4buDCd78U4f4CW2aVuTYT8RwtVwUhVKDNTGwy3BNy", "fee": 3200000, "feeAssetId": null, "timestamp": 1707405690309, "version": 2, "chainId": 84, "sender": "3N6ALE8YyAYnRk9f38mdWRTvW77rFkg5hN1", "senderPublicKey": "HMMF9zUpZPBGLAhpc1yDdcJNJychSarGHS79P2mGvq7J", "proofs": [ "4423DUNdtTMGCsJZNpsUPeuDZHqYkC52H8jKRLEqPnYy9cPFoQstZk6rMvZLGyjdVz8ttAh47cpoJnFRNWoKnMCJ" ], "script": "base64:BgJTCAISBgoECAgICBIHCgUICAgICBIDCgEIEgMKAQESBgoECAEBARIECgIBARIDCgEIEgMKAQgSBAoCCAgSAwoBCBIDCgEIEgASABIDCgEIEgMKAQiDAQAJU0VQQVJBVE9SAgJfXwAFV0FWRVMCBVdBVkVTAAxLRVlfTVVMVElTSUcCCE1VTFRJU0lHAApLRVlfU1RBVFVTAgZTVEFUVVMACEtFWV9JTklUAgRJTklUAApLRVlfUEFVU0VEAgZQQVVTRUQACktFWV9QQVVTRVICBlBBVVNFUgALS0VZX01BTkFHRVICB01BTkFHRVIAC0tFWV9SRUZFUkVSAgdSRUZFUkVSAAxLRVlfRVhFQ1VUT1ICCEVYRUNVVE9SAApLRVlfT1JBQ0xFAgZPUkFDTEUAE0tFWV9DQUxMRVJfQ09OVFJBQ1QCD0NBTExFUl9DT05UUkFDVAAJS0VZX1BSSUNFAgVQUklDRQAPS0VZX1VOSVRTX0FTU0VUAgtVTklUU19BU1NFVAARS0VZX1VTRVJfUE9TSVRJT04CDVVTRVJfUE9TSVRJT04AFEtFWV9VU0VSX1VTRF9CQUxBTkNFAhBVU0VSX1VTRF9CQUxBTkNFACdLRVlfVVNFUl9VTklUU19QRVJfVVNEX0JBTEFOQ0VfSU5URUdSQUwCI1VTRVJfVU5JVFNfUEVSX1VTRF9CQUxBTkNFX0lOVEVHUkFMAClLRVlfVVNFUl9VTklUU19QRVJfUkVGRVJBTF9TSEFSRV9JTlRFR1JBTAIlVVNFUl9VTklUU19QRVJfUkVGRVJBTF9TSEFSRV9JTlRFR1JBTAAWS0VZX1VTRVJfQ0hFQ0tQT0lOVF9BVAISVVNFUl9DSEVDS1BPSU5UX0FUACJLRVlfVVNFUl9VTklUU19CQUxBTkNFX0RJU1RSSUJVVEVEAh5VU0VSX1VOSVRTX0JBTEFOQ0VfRElTVFJJQlVURUQAHUtFWV9VU0VSX1VOSVRTX1NIQVJFU19SRUZFUkFMAhlVU0VSX1VOSVRTX1NIQVJFU19SRUZFUkFMABdLRVlfVVNFUl9TSEFSRVNfUkVGRVJBTAITVVNFUl9TSEFSRVNfUkVGRVJBTAAPS0VZX1NUQVJUX0JMT0NLAgtTVEFSVF9CTE9DSwAQS0VZX0ZJTklTSF9CTE9DSwIMRklOSVNIX0JMT0NLABZLRVlfVE9UQUxfVU5JVFNfRk9SX0xQAhJUT1RBTF9VTklUU19GT1JfTFAAG0tFWV9UT1RBTF9VTklUU19GT1JfUkVGRVJBTAIXVE9UQUxfVU5JVFNfRk9SX1JFRkVSQUwAFUtFWV9UT1RBTF9VU0RfQkFMQU5DRQIRVE9UQUxfVVNEX0JBTEFOQ0UAIktFWV9VTklUU19QRVJfVVNEX0JBTEFOQ0VfSU5URUdSQUwCHlVOSVRTX1BFUl9VU0RfQkFMQU5DRV9JTlRFR1JBTAARS0VZX0NIRUNLUE9JTlRfQVQCDUNIRUNLUE9JTlRfQVQAHUtFWV9VTklUU19CQUxBTkNFX0RJU1RSSUJVVEVEAhlVTklUU19CQUxBTkNFX0RJU1RSSUJVVEVEABFLRVlfVE9LRU5fQkFMQU5DRQINVE9LRU5fQkFMQU5DRQAPS0VZX1VTRVJTX0NPVU5UAgtVU0VSU19DT1VOVAAkS0VZX1VOSVRTX1BFUl9SRUZFUkFMX1NIQVJFX0lOVEVHUkFMAiBVTklUU19QRVJfUkVGRVJBTF9TSEFSRV9JTlRFR1JBTAAYS0VZX1VOSVRTX1NIQVJFU19SRUZFUkFMAhRVTklUU19TSEFSRVNfUkVGRVJBTAAYS0VZX1RPVEFMX1NIQVJFU19SRUZFUkFMAhRUT1RBTF9TSEFSRVNfUkVGRVJBTAATS0VZX1NXQVZFU19DT05UUkFDVAIPU1dBVkVTX0NPTlRSQUNUABBLRVlfU1dBVkVTX0FTU0VUAgVBU1NFVAAMRlVOQ19ERVBPU0lUAgdkZXBvc2l0AA1GVU5DX0dFVF9SQVRFAgdnZXRSYXRlAA1GVU5DX1dJVEhEUkFXAgh3aXRoZHJhdwAHTUFYX0lOVAD//////////38ADlBFUkNFTlRfRkFDVE9SCQC2AgEAgKCUpY0dAAtaRVJPX0JJR0lOVAkAtgIBAAAACk9ORV9CSUdJTlQJALYCAQABABJTV0FWRVNfUkFURV9GQUNUT1IJALYCAQCAoJSljR0BEF92YWxpZGF0ZUFkZHJlc3MCCGFkZHJlc3NfBGVycl8EByRtYXRjaDAJAKYIAQUIYWRkcmVzc18DCQABAgUHJG1hdGNoMAIHQWRkcmVzcwQBYQUHJG1hdGNoMAYJAAIBBQRlcnJfAQxfdmFsaWRhdGVJbnQEBHZhbF8ObG93ZXJCb3VuZGFyeV8OdXBwZXJCb3VuZGFyeV8EZXJyXwMDCQBmAgUObG93ZXJCb3VuZGFyeV8FBHZhbF8GCQBmAgUEdmFsXwUOdXBwZXJCb3VuZGFyeV8JAAIBBQRlcnJfBgEPX3ZhbGlkYXRlQmlnSW50BAR2YWxfDmxvd2VyQm91bmRhcnlfDnVwcGVyQm91bmRhcnlfBGVycl8DAwkAvwICBQ5sb3dlckJvdW5kYXJ5XwUEdmFsXwYJAL8CAgUEdmFsXwUOdXBwZXJCb3VuZGFyeV8JAAIBBQRlcnJfBgEVX3ZhbGlkYXRlUGF5bWVudHNTaXplAwlwYXltZW50c18HdGFyZ2V0XwRlcnJfAwkBAiE9AgkAkAMBBQlwYXltZW50c18FB3RhcmdldF8JAAIBBQRlcnJfBgEVX3ZhbGlkYXRlV2F2ZXNQYXltZW50AghwYXltZW50XwRlcnJfBAckbWF0Y2gwCAUIcGF5bWVudF8HYXNzZXRJZAMJAAECBQckbWF0Y2gwAgpCeXRlVmVjdG9yBAFhBQckbWF0Y2gwCQACAQUEZXJyXwMJAAECBQckbWF0Y2gwAgRVbml0BgkAAgECC01hdGNoIGVycm9yARFfdmFsaWRhdGVFcUJpZ0ludAMFdmFsMV8FdmFsMl8EZXJyXwMJAQIhPQIFBXZhbDFfBQV2YWwyXwkAAgEFBGVycl8GAQ5fdmFsaWRhdGVBc3NldAIGYXNzZXRfBGVycl8EByRtYXRjaDAJAOwHAQkA2QQBBQZhc3NldF8DCQABAgUHJG1hdGNoMAIFQXNzZXQEAWEFByRtYXRjaDAGCQACAQUEZXJyXwEJX2xvYWRJbml0AAQHJG1hdGNoMAkAoAgBBQhLRVlfSU5JVAMJAAECBQckbWF0Y2gwAgdCb29sZWFuBAFhBQckbWF0Y2gwBQFhBwEJX3NhdmVJbml0AQdpc0luaXRfCQDMCAIJAQxCb29sZWFuRW50cnkCBQhLRVlfSU5JVAUHaXNJbml0XwUDbmlsAQpfbG9hZFBhdXNlAAQHJG1hdGNoMAkAoAgBBQpLRVlfUEFVU0VEAwkAAQIFByRtYXRjaDACB0Jvb2xlYW4EAWEFByRtYXRjaDAFAWEHAQpfc2F2ZVBhdXNlAQlpc1BhdXNlZF8JAMwIAgkBDEJvb2xlYW5FbnRyeQIFCktFWV9QQVVTRUQFCWlzUGF1c2VkXwUDbmlsAQtfbG9hZFBhdXNlcgAEByRtYXRjaDAJAKIIAQUKS0VZX1BBVVNFUgMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJARFAZXh0ck5hdGl2ZSgxMDYyKQEFAWEJAQdBZGRyZXNzAQEAAQtfc2F2ZVBhdXNlcgEHcGF1c2VyXwkAzAgCCQELU3RyaW5nRW50cnkCBQpLRVlfUEFVU0VSCQClCAEFB3BhdXNlcl8FA25pbAENX2xvYWRNdWx0aXNpZwAEByRtYXRjaDAJAKIIAQUMS0VZX01VTFRJU0lHAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkBEUBleHRyTmF0aXZlKDEwNjIpAQUBYQkBB0FkZHJlc3MBAQABDV9zYXZlTXVsdGlzaWcBCW11bHRpc2lnXwkAzAgCCQELU3RyaW5nRW50cnkCBQxLRVlfTVVMVElTSUcJAKUIAQUJbXVsdGlzaWdfBQNuaWwBDV9sb2FkRXhlY3V0b3IABAckbWF0Y2gwCQCiCAEFDEtFWV9FWEVDVVRPUgMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJARFAZXh0ck5hdGl2ZSgxMDYyKQEFAWEJAQdBZGRyZXNzAQEAAQ1fc2F2ZUV4ZWN1dG9yAQlleGVjdXRvcl8JAMwIAgkBC1N0cmluZ0VudHJ5AgUMS0VZX0VYRUNVVE9SCQClCAEFCWV4ZWN1dG9yXwUDbmlsAQtfbG9hZE9yYWNsZQAEByRtYXRjaDAJAKIIAQUKS0VZX09SQUNMRQMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJARFAZXh0ck5hdGl2ZSgxMDYyKQEFAWEJAQdBZGRyZXNzAQEAAQtfc2F2ZU9yYWNsZQEHb3JhY2xlXwkAzAgCCQELU3RyaW5nRW50cnkCBQpLRVlfT1JBQ0xFCQClCAEFB29yYWNsZV8FA25pbAETX2xvYWRDYWxsZXJDb250cmFjdAAEByRtYXRjaDAJAKIIAQUTS0VZX0NBTExFUl9DT05UUkFDVAMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAFAWECAAETX3NhdmVDYWxsZXJDb250cmFjdAEHY2FsbGVyXwkAzAgCCQELU3RyaW5nRW50cnkCBRNLRVlfQ0FMTEVSX0NPTlRSQUNUBQdjYWxsZXJfBQNuaWwBEV9sb2FkVXNlclBvc2l0aW9uAgZ0b2tlbl8FdXNlcl8EByRtYXRjaDAJAKIIAQkAuQkCCQDMCAIFEUtFWV9VU0VSX1BPU0lUSU9OCQDMCAIFBnRva2VuXwkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwBAZzdHJ1Y3QJAL0JAgUBYQUJU0VQQVJBVE9SCQCUCgIJAKcDAQkAkQMCBQZzdHJ1Y3QAAAkApwMBCQCRAwIFBnN0cnVjdAABCQCUCgIFC1pFUk9fQklHSU5UBQtaRVJPX0JJR0lOVAERX3NhdmVVc2VyUG9zaXRpb24DBnRva2VuXwV1c2VyXwlwb3NpdGlvbl8JAMwIAgkBC1N0cmluZ0VudHJ5AgkAuQkCCQDMCAIFEUtFWV9VU0VSX1BPU0lUSU9OCQDMCAIFBnRva2VuXwkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IJALsJAgkAzAgCCQCmAwEIBQlwb3NpdGlvbl8CXzEJAMwIAgkApgMBCAUJcG9zaXRpb25fAl8yBQNuaWwFCVNFUEFSQVRPUgUDbmlsARNfbG9hZFVzZXJVU0RCYWxhbmNlAQV1c2VyXwQHJG1hdGNoMAkAoggBCQC5CQIJAMwIAgUUS0VZX1VTRVJfVVNEX0JBTEFOQ0UJAMwIAgUFdXNlcl8FA25pbAUJU0VQQVJBVE9SAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAETX3NhdmVVc2VyVVNEQmFsYW5jZQIFdXNlcl8GdmFsdWVfCQDMCAIJAQtTdHJpbmdFbnRyeQIJALkJAgkAzAgCBRRLRVlfVVNFUl9VU0RfQkFMQU5DRQkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IJAKYDAQUGdmFsdWVfBQNuaWwBFl9sb2FkVXNlclNoYXJlc1JlZmVyYWwBBXVzZXJfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBRdLRVlfVVNFUl9TSEFSRVNfUkVGRVJBTAkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UARZfc2F2ZVVzZXJTaGFyZXNSZWZlcmFsAgV1c2VyXwZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgkAuQkCCQDMCAIFF0tFWV9VU0VSX1NIQVJFU19SRUZFUkFMCQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgkApgMBBQZ2YWx1ZV8FA25pbAEfX2xvYWRVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAAEByRtYXRjaDAJAKIIAQUiS0VZX1VOSVRTX1BFUl9VU0RfQkFMQU5DRV9JTlRFR1JBTAMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBH19zYXZlVW5pdHNQZXJVU0RCYWxhbmNlSW50ZWdyYWwBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBSJLRVlfVU5JVFNfUEVSX1VTRF9CQUxBTkNFX0lOVEVHUkFMCQCmAwEFBnZhbHVlXwUDbmlsASNfbG9hZFVzZXJVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAEFdXNlcl8EByRtYXRjaDAJAKIIAQkAuQkCCQDMCAIFJ0tFWV9VU0VSX1VOSVRTX1BFUl9VU0RfQkFMQU5DRV9JTlRFR1JBTAkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UASNfc2F2ZVVzZXJVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAIFdXNlcl8GdmFsdWVfCQDMCAIJAQtTdHJpbmdFbnRyeQIJALkJAgkAzAgCBSdLRVlfVVNFUl9VTklUU19QRVJfVVNEX0JBTEFOQ0VfSU5URUdSQUwJAMwIAgUFdXNlcl8FA25pbAUJU0VQQVJBVE9SCQCmAwEFBnZhbHVlXwUDbmlsARFfbG9hZENoZWNrcG9pbnRBdAAEByRtYXRjaDAJAKIIAQURS0VZX0NIRUNLUE9JTlRfQVQDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UARFfc2F2ZUNoZWNrcG9pbnRBdAEGdmFsdWVfCQDMCAIJAQtTdHJpbmdFbnRyeQIFEUtFWV9DSEVDS1BPSU5UX0FUCQCmAwEFBnZhbHVlXwUDbmlsARVfbG9hZFVzZXJDaGVja3BvaW50QXQBBXVzZXJfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBRZLRVlfVVNFUl9DSEVDS1BPSU5UX0FUCQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBFV9zYXZlVXNlckNoZWNrcG9pbnRBdAIFdXNlcl8GdmFsdWVfCQDMCAIJAQtTdHJpbmdFbnRyeQIJALkJAgkAzAgCBRZLRVlfVVNFUl9DSEVDS1BPSU5UX0FUCQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgkApgMBBQZ2YWx1ZV8FA25pbAEPX2xvYWRVbml0c0Fzc2V0AAQHJG1hdGNoMAkAoggBBQ9LRVlfVU5JVFNfQVNTRVQDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQDZBAEFAWEBAAEPX3NhdmVVbml0c0Fzc2V0AQZhc3NldF8JAMwIAgkBC1N0cmluZ0VudHJ5AgUPS0VZX1VOSVRTX0FTU0VUCQDYBAEFBmFzc2V0XwUDbmlsAQ9fbG9hZFN0YXJ0QmxvY2sABAckbWF0Y2gwCQCiCAEFD0tFWV9TVEFSVF9CTE9DSwMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBD19zYXZlU3RhcnRCbG9jawEGdmFsdWVfCQDMCAIJAQtTdHJpbmdFbnRyeQIFD0tFWV9TVEFSVF9CTE9DSwkApgMBBQZ2YWx1ZV8FA25pbAEQX2xvYWRGaW5pc2hCbG9jawAEByRtYXRjaDAJAKIIAQUQS0VZX0ZJTklTSF9CTE9DSwMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBEF9zYXZlRmluaXNoQmxvY2sBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBRBLRVlfRklOSVNIX0JMT0NLCQCmAwEFBnZhbHVlXwUDbmlsARxfbG9hZFVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkAAQHJG1hdGNoMAkAoggBBR1LRVlfVU5JVFNfQkFMQU5DRV9ESVNUUklCVVRFRAMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBHF9zYXZlVW5pdHNCYWxhbmNlRGlzdHJpYnV0ZWQBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBR1LRVlfVU5JVFNfQkFMQU5DRV9ESVNUUklCVVRFRAkApgMBBQZ2YWx1ZV8FA25pbAEgX2xvYWRVc2VyVW5pdHNCYWxhbmNlRGlzdHJpYnV0ZWQBBXVzZXJfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBSJLRVlfVVNFUl9VTklUU19CQUxBTkNFX0RJU1RSSUJVVEVECQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJAKcDAQUBYQULWkVST19CSUdJTlQBIF9zYXZlVXNlclVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkAgV1c2VyXwZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgkAuQkCCQDMCAIFIktFWV9VU0VSX1VOSVRTX0JBTEFOQ0VfRElTVFJJQlVURUQJAMwIAgUFdXNlcl8FA25pbAUJU0VQQVJBVE9SCQCmAwEFBnZhbHVlXwUDbmlsARRfbG9hZFRvdGFsVVNEQmFsYW5jZQAEByRtYXRjaDAJAKIIAQUVS0VZX1RPVEFMX1VTRF9CQUxBTkNFAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEUX3NhdmVUb3RhbFVTREJhbGFuY2UBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBRVLRVlfVE9UQUxfVVNEX0JBTEFOQ0UJAKYDAQUGdmFsdWVfBQNuaWwBE19sb2FkU1dhdmVzQ29udHJhY3QABAckbWF0Y2gwCQCiCAEFE0tFWV9TV0FWRVNfQ09OVFJBQ1QDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQERQGV4dHJOYXRpdmUoMTA2MikBBQFhCQEHQWRkcmVzcwEBAAETX3NhdmVTV2F2ZXNDb250cmFjdAEJY29udHJhY3RfCQDMCAIJAQtTdHJpbmdFbnRyeQIFE0tFWV9TV0FWRVNfQ09OVFJBQ1QJAKUIAQUJY29udHJhY3RfBQNuaWwBEF9sb2FkU1dhdmVzQXNzZXQBCWNvbnRyYWN0XwQHJG1hdGNoMAkAnQgCBQljb250cmFjdF8FEEtFWV9TV0FWRVNfQVNTRVQDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQDZBAEFAWEJAAIBAhhfbG9hZFNXYXZlc0Fzc2V0OiByZXZlcnQBEV9sb2FkVG9rZW5CYWxhbmNlAQZ0b2tlbl8EByRtYXRjaDAJAKIIAQkAuQkCCQDMCAIFEUtFWV9UT0tFTl9CQUxBTkNFCQDMCAIFBnRva2VuXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UARFfc2F2ZVRva2VuQmFsYW5jZQIGdG9rZW5fBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCCQC5CQIJAMwIAgURS0VZX1RPS0VOX0JBTEFOQ0UJAMwIAgUGdG9rZW5fBQNuaWwFCVNFUEFSQVRPUgkApgMBBQZ2YWx1ZV8FA25pbAEPX2xvYWRVc2Vyc0NvdW50AAQHJG1hdGNoMAkAoggBBQ9LRVlfVVNFUlNfQ09VTlQDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UAQ9fc2F2ZVVzZXJzQ291bnQBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBQ9LRVlfVVNFUlNfQ09VTlQJAKYDAQUGdmFsdWVfBQNuaWwBIV9sb2FkVW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAAEByRtYXRjaDAJAKIIAQUkS0VZX1VOSVRTX1BFUl9SRUZFUkFMX1NIQVJFX0lOVEVHUkFMAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEhX3NhdmVVbml0c1BlclJlZmVyYWxTaGFyZUludGVncmFsAQZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgUkS0VZX1VOSVRTX1BFUl9SRUZFUkFMX1NIQVJFX0lOVEVHUkFMCQCmAwEFBnZhbHVlXwUDbmlsARdfbG9hZFVuaXRzU2hhcmVzUmVmZXJhbAAEByRtYXRjaDAJAKIIAQUYS0VZX1VOSVRTX1NIQVJFU19SRUZFUkFMAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEXX3NhdmVVbml0c1NoYXJlc1JlZmVyYWwBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBRhLRVlfVU5JVFNfU0hBUkVTX1JFRkVSQUwJAKYDAQUGdmFsdWVfBQNuaWwBFF9sb2FkVG90YWxVbml0c0ZvckxQAAQHJG1hdGNoMAkAoggBBRZLRVlfVE9UQUxfVU5JVFNfRk9SX0xQAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEUX3NhdmVUb3RhbFVuaXRzRm9yTFABBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBRZLRVlfVE9UQUxfVU5JVFNfRk9SX0xQCQCmAwEFBnZhbHVlXwUDbmlsARlfbG9hZFRvdGFsVW5pdHNGb3JSZWZlcmFsAAQHJG1hdGNoMAkAoggBBRtLRVlfVE9UQUxfVU5JVFNfRk9SX1JFRkVSQUwDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UARlfc2F2ZVRvdGFsVW5pdHNGb3JSZWZlcmFsAQZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgUbS0VZX1RPVEFMX1VOSVRTX0ZPUl9SRUZFUkFMCQCmAwEFBnZhbHVlXwUDbmlsARdfbG9hZFRvdGFsU2hhcmVzUmVmZXJhbAAEByRtYXRjaDAJAKIIAQUYS0VZX1RPVEFMX1NIQVJFU19SRUZFUkFMAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEXX3NhdmVUb3RhbFNoYXJlc1JlZmVyYWwBBnZhbHVlXwkAzAgCCQELU3RyaW5nRW50cnkCBRhLRVlfVE9UQUxfU0hBUkVTX1JFRkVSQUwJAKYDAQUGdmFsdWVfBQNuaWwBJV9sb2FkVXNlclVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwBBXVzZXJfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBSlLRVlfVVNFUl9VTklUU19QRVJfUkVGRVJBTF9TSEFSRV9JTlRFR1JBTAkAzAgCBQV1c2VyXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEFC1pFUk9fQklHSU5UASVfc2F2ZVVzZXJVbml0c1BlclJlZmVyYWxTaGFyZUludGVncmFsAgV1c2VyXwZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgkAuQkCCQDMCAIFKUtFWV9VU0VSX1VOSVRTX1BFUl9SRUZFUkFMX1NIQVJFX0lOVEVHUkFMCQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgkApgMBBQZ2YWx1ZV8FA25pbAEbX2xvYWRVc2VyVW5pdHNTaGFyZXNSZWZlcmFsAQV1c2VyXwQHJG1hdGNoMAkAoggBCQC5CQIJAMwIAgUdS0VZX1VTRVJfVU5JVFNfU0hBUkVTX1JFRkVSQUwJAMwIAgUFdXNlcl8FA25pbAUJU0VQQVJBVE9SAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhBQtaRVJPX0JJR0lOVAEbX3NhdmVVc2VyVW5pdHNTaGFyZXNSZWZlcmFsAgV1c2VyXwZ2YWx1ZV8JAMwIAgkBC1N0cmluZ0VudHJ5AgkAuQkCCQDMCAIFHUtFWV9VU0VSX1VOSVRTX1NIQVJFU19SRUZFUkFMCQDMCAIFBXVzZXJfBQNuaWwFCVNFUEFSQVRPUgkApgMBBQZ2YWx1ZV8FA25pbAEMX2xvYWRNYW5hZ2VyAAQHJG1hdGNoMAkAoggBBQtLRVlfTUFOQUdFUgMJAAECBQckbWF0Y2gwAgZTdHJpbmcEAWEFByRtYXRjaDAJARFAZXh0ck5hdGl2ZSgxMDYyKQEFAWEJAQdBZGRyZXNzAQEAAQxfc2F2ZU1hbmFnZXIBCG1hbmFnZXJfCQDMCAIJAQtTdHJpbmdFbnRyeQIFC0tFWV9NQU5BR0VSCQClCAEFCG1hbmFnZXJfBQNuaWwBDF9sb2FkUmVmZXJlcgEJY29kZWhhc2hfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBQtLRVlfUkVGRVJFUgkAzAgCBQljb2RlaGFzaF8FA25pbAUJU0VQQVJBVE9SAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAUBYQkAAgECFF9sb2FkUmVmZXJlcjogcmV2ZXJ0AQxfc2F2ZVJlZmVyZXICCWNvZGVoYXNoXwhhZGRyZXNzXwkAzAgCCQELU3RyaW5nRW50cnkCCQC5CQIJAMwIAgULS0VZX1JFRkVSRVIJAMwIAgUJY29kZWhhc2hfBQNuaWwFCVNFUEFSQVRPUgUIYWRkcmVzc18FA25pbAEWX2NoZWNrUmVmZXJlckV4aXN0ZW5jZQEJY29kZWhhc2hfBAckbWF0Y2gwCQCiCAEJALkJAgkAzAgCBQtLRVlfUkVGRVJFUgkAzAgCBQljb2RlaGFzaF8FA25pbAUJU0VQQVJBVE9SAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAYHARFfb25seVRoaXNDb250cmFjdAEHY2FsbGVyXwMJAQIhPQIFB2NhbGxlcl8FBHRoaXMJAAIBAhlfb25seVRoaXNDb250cmFjdDogcmV2ZXJ0BgEQX3doZW5NdWx0aXNpZ1NldAADCQAAAgkBDV9sb2FkTXVsdGlzaWcACQEHQWRkcmVzcwEBAAkAAgECGF93aGVuTXVsdGlzaWdTZXQ6IHJldmVydAYBE193aGVuTm90SW5pdGlhbGl6ZWQAAwkBCV9sb2FkSW5pdAAJAAIBAhtfd2hlbk5vdEluaXRpYWxpemVkOiByZXZlcnQGARBfd2hlbkluaXRpYWxpemVkAAMJAQEhAQkBCV9sb2FkSW5pdAAJAAIBAhhfd2hlbkluaXRpYWxpemVkOiByZXZlcnQGAQ5fd2hlbk5vdFBhdXNlZAADCQEKX2xvYWRQYXVzZQAJAAIBAhZfd2hlbk5vdFBhdXNlZDogcmV2ZXJ0BgELX3doZW5QYXVzZWQAAwkBASEBCQEKX2xvYWRQYXVzZQAJAAIBAhNfd2hlblBhdXNlZDogcmV2ZXJ0BgELX29ubHlQYXVzZXIBB2NhbGxlcl8DCQECIT0CBQdjYWxsZXJfCQELX2xvYWRQYXVzZXIACQACAQITX29ubHlQYXVzZXI6IHJldmVydAYBDF9vbmx5TWFuYWdlcgEHY2FsbGVyXwMJAQIhPQIFB2NhbGxlcl8JAQxfbG9hZE1hbmFnZXIACQACAQIUX29ubHlNYW5hZ2VyOiByZXZlcnQGARFfdmFsaWRhdGVFeGVjdXRvcgIEdmFsXwRlcnJfAwkBAiE9AgUEdmFsXwkBDV9sb2FkRXhlY3V0b3IACQACAQUEZXJyXwYBD192YWxpZGF0ZUNhbGxlcgIEdmFsXwRlcnJfAwkBAiE9AgUEdmFsXwkBE19sb2FkQ2FsbGVyQ29udHJhY3QACQACAQUEZXJyXwYBDV9nZXRUb2tlblJhdGUBBnRva2VuXwQHJG1hdGNoMAkAnQgCCQELX2xvYWRPcmFjbGUACQC5CQIJAMwIAgUJS0VZX1BSSUNFCQDMCAIFBnRva2VuXwUDbmlsBQlTRVBBUkFUT1IDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAFhBQckbWF0Y2gwCQCnAwEFAWEJAAIBCQCsAgICIV9nZXRUb2tlblJhdGU6IG5vIHJhdGUgZm9yIHRva2VuPQUGdG9rZW5fAQtfY2hlY2twb2ludAAEHnByZXZVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAkBH19sb2FkVW5pdHNQZXJVU0RCYWxhbmNlSW50ZWdyYWwABBBwcmV2Q2hlY2twb2ludEF0CQCYAwEJAMwIAgkBD19sb2FkU3RhcnRCbG9jawAJAMwIAgkBEV9sb2FkQ2hlY2twb2ludEF0AAUDbmlsBBtwcmV2VW5pdHNCYWxhbmNlRGlzdHJpYnV0ZWQJARxfbG9hZFVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkAAQgcHJldlVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwJASFfbG9hZFVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwABBZwcmV2VW5pdHNTaGFyZXNSZWZlcmFsCQEXX2xvYWRVbml0c1NoYXJlc1JlZmVyYWwABAxjdXJyZW50QmxvY2sJAJkDAQkAzAgCCQC2AgEFBmhlaWdodAkAzAgCCQEQX2xvYWRGaW5pc2hCbG9jawAFA25pbAMJAMACAgUQcHJldkNoZWNrcG9pbnRBdAUMY3VycmVudEJsb2NrCQCVCgMFA25pbAUecHJldlVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsBSBwcmV2VW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAQYdW5pdHNCYWxhbmNlVG9EaXN0cmlidXRlCQC8AgMJALgCAgkBFF9sb2FkVG90YWxVbml0c0ZvckxQAAUbcHJldlVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkCQC4AgIFDGN1cnJlbnRCbG9jawUQcHJldkNoZWNrcG9pbnRBdAkAuAICCQEQX2xvYWRGaW5pc2hCbG9jawAFEHByZXZDaGVja3BvaW50QXQEGnVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsCQC3AgIJALoCAgkAuQICBQ5QRVJDRU5UX0ZBQ1RPUgUYdW5pdHNCYWxhbmNlVG9EaXN0cmlidXRlCQEUX2xvYWRUb3RhbFVTREJhbGFuY2UABR5wcmV2VW5pdHNQZXJVU0RCYWxhbmNlSW50ZWdyYWwEDSR0MDE3NzQ4MTgzMDEDCQC/AgIJARdfbG9hZFRvdGFsU2hhcmVzUmVmZXJhbAAFC1pFUk9fQklHSU5UBBJ1bml0c1NoYXJlc1JlZmVyYWwJALwCAwkAuAICCQEZX2xvYWRUb3RhbFVuaXRzRm9yUmVmZXJhbAAFFnByZXZVbml0c1NoYXJlc1JlZmVyYWwJALgCAgUMY3VycmVudEJsb2NrBRBwcmV2Q2hlY2twb2ludEF0CQC4AgIJARBfbG9hZEZpbmlzaEJsb2NrAAUQcHJldkNoZWNrcG9pbnRBdAQcdW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAkAtwICCQC6AgIJALkCAgUOUEVSQ0VOVF9GQUNUT1IFEnVuaXRzU2hhcmVzUmVmZXJhbAkBF19sb2FkVG90YWxTaGFyZXNSZWZlcmFsAAUgcHJldlVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwJAJQKAgUSdW5pdHNTaGFyZXNSZWZlcmFsBRx1bml0c1BlclJlZmVyYWxTaGFyZUludGVncmFsCQCUCgIFC1pFUk9fQklHSU5UBQtaRVJPX0JJR0lOVAQSdW5pdHNTaGFyZXNSZWZlcmFsCAUNJHQwMTc3NDgxODMwMQJfMQQcdW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAgFDSR0MDE3NzQ4MTgzMDECXzIJAJUKAwkAzggCCQDOCAIJAM4IAgkAzggCCQERX3NhdmVDaGVja3BvaW50QXQBBQxjdXJyZW50QmxvY2sJAR9fc2F2ZVVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsAQUadW5pdHNQZXJVU0RCYWxhbmNlSW50ZWdyYWwJARxfc2F2ZVVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkAQkAtwICBRh1bml0c0JhbGFuY2VUb0Rpc3RyaWJ1dGUFG3ByZXZVbml0c0JhbGFuY2VEaXN0cmlidXRlZAkBIV9zYXZlVW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAEFHHVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwJARdfc2F2ZVVuaXRzU2hhcmVzUmVmZXJhbAEJALcCAgUSdW5pdHNTaGFyZXNSZWZlcmFsBRZwcmV2VW5pdHNTaGFyZXNSZWZlcmFsBRp1bml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAUcdW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAEPX3VzZXJDaGVja3BvaW50AwV1c2VyXw91c2VyVVNEQmFsYW5jZV8SdXNlclNoYXJlc1JlZmVyYWxfBA0kdDAxODg4NzE4OTk5CQELX2NoZWNrcG9pbnQABBFjaGVja3BvaW50QWN0aW9ucwgFDSR0MDE4ODg3MTg5OTkCXzEEGnVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsCAUNJHQwMTg4ODcxODk5OQJfMgQcdW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAgFDSR0MDE4ODg3MTg5OTkCXzMEInByZXZVc2VyVW5pdHNQZXJVU0RCYWxhbmNlSW50ZWdyYWwJASNfbG9hZFVzZXJVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAEFBXVzZXJfBBRwcmV2VXNlckNoZWNrcG9pbnRBdAkAmAMBCQDMCAIJAQ9fbG9hZFN0YXJ0QmxvY2sACQDMCAIJARVfbG9hZFVzZXJDaGVja3BvaW50QXQBBQV1c2VyXwUDbmlsBB9wcmV2VXNlclVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkCQEgX2xvYWRVc2VyVW5pdHNCYWxhbmNlRGlzdHJpYnV0ZWQBBQV1c2VyXwQkcHJldlVzZXJVbml0c1BlclJlZmVyYWxTaGFyZUludGVncmFsCQElX2xvYWRVc2VyVW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAEFBXVzZXJfBBpwcmV2VXNlclVuaXRzU2hhcmVzUmVmZXJhbAkBG19sb2FkVXNlclVuaXRzU2hhcmVzUmVmZXJhbAEFBXVzZXJfBAxjdXJyZW50QmxvY2sJAJkDAQkAzAgCCQC2AgEFBmhlaWdodAkAzAgCCQEQX2xvYWRGaW5pc2hCbG9jawAFA25pbAMJAMACAgUUcHJldlVzZXJDaGVja3BvaW50QXQFDGN1cnJlbnRCbG9jawkAlQoDBRFjaGVja3BvaW50QWN0aW9ucwUfcHJldlVzZXJVbml0c0JhbGFuY2VEaXN0cmlidXRlZAUacHJldlVzZXJVbml0c1NoYXJlc1JlZmVyYWwEG3VzZXJVbml0c0JhbGFuY2VEaXN0cmlidXRlZAkAtwICCQC6AgIJALkCAgUPdXNlclVTREJhbGFuY2VfCQC4AgIFGnVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsBSJwcmV2VXNlclVuaXRzUGVyVVNEQmFsYW5jZUludGVncmFsBQ5QRVJDRU5UX0ZBQ1RPUgUfcHJldlVzZXJVbml0c0JhbGFuY2VEaXN0cmlidXRlZAQWdXNlclVuaXRzU2hhcmVzUmVmZXJhbAkAtwICCQC6AgIJALkCAgUSdXNlclNoYXJlc1JlZmVyYWxfCQC4AgIFHHVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwFJHByZXZVc2VyVW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAUOUEVSQ0VOVF9GQUNUT1IFGnByZXZVc2VyVW5pdHNTaGFyZXNSZWZlcmFsCQCVCgMJAM4IAgkAzggCCQDOCAIJAM4IAgkAzggCBRFjaGVja3BvaW50QWN0aW9ucwkBFV9zYXZlVXNlckNoZWNrcG9pbnRBdAIFBXVzZXJfBQxjdXJyZW50QmxvY2sJASNfc2F2ZVVzZXJVbml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAIFBXVzZXJfBRp1bml0c1BlclVTREJhbGFuY2VJbnRlZ3JhbAkBIF9zYXZlVXNlclVuaXRzQmFsYW5jZURpc3RyaWJ1dGVkAgUFdXNlcl8FG3VzZXJVbml0c0JhbGFuY2VEaXN0cmlidXRlZAkBJV9zYXZlVXNlclVuaXRzUGVyUmVmZXJhbFNoYXJlSW50ZWdyYWwCBQV1c2VyXwUcdW5pdHNQZXJSZWZlcmFsU2hhcmVJbnRlZ3JhbAkBG19zYXZlVXNlclVuaXRzU2hhcmVzUmVmZXJhbAIFBXVzZXJfBRZ1c2VyVW5pdHNTaGFyZXNSZWZlcmFsBRt1c2VyVW5pdHNCYWxhbmNlRGlzdHJpYnV0ZWQFFnVzZXJVbml0c1NoYXJlc1JlZmVyYWwPAWkBBGluaXQECWV4ZWN1dG9yXwdvcmFjbGVfB3BhdXNlcl8Pc1dhdmVzQ29udHJhY3RfBANlcnIDAwMDAwMJARFfb25seVRoaXNDb250cmFjdAEIBQFpBmNhbGxlcgkBE193aGVuTm90SW5pdGlhbGl6ZWQABwkBEF93aGVuTXVsdGlzaWdTZXQABwkBEF92YWxpZGF0ZUFkZHJlc3MCBQlleGVjdXRvcl8CFmluaXQ6IGludmFsaWQgZXhlY3V0b3IHCQEQX3ZhbGlkYXRlQWRkcmVzcwIFB29yYWNsZV8CFGluaXQ6IGludmFsaWQgb3JhY2xlBwkBEF92YWxpZGF0ZUFkZHJlc3MCBQdwYXVzZXJfAhRpbml0OiBpbnZhbGlkIHBhdXNlcgcJARBfdmFsaWRhdGVBZGRyZXNzAgUPc1dhdmVzQ29udHJhY3RfAhxpbml0OiBpbnZhbGlkIHNXYXZlc0NvbnRyYWN0BwMJAAACBQNlcnIFA2VycgkAlAoCCQDOCAIJAM4IAgkAzggCCQDOCAIJAQlfc2F2ZUluaXQBBgkBDV9zYXZlRXhlY3V0b3IBCQERQGV4dHJOYXRpdmUoMTA2MikBBQlleGVjdXRvcl8JAQtfc2F2ZU9yYWNsZQEJARFAZXh0ck5hdGl2ZSgxMDYyKQEFB29yYWNsZV8JAQtfc2F2ZVBhdXNlcgEJARFAZXh0ck5hdGl2ZSgxMDYyKQEFB3BhdXNlcl8JARNfc2F2ZVNXYXZlc0NvbnRyYWN0AQkBEUBleHRyTmF0aXZlKDEwNjIpAQUPc1dhdmVzQ29udHJhY3RfBQR1bml0CQACAQIkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAWkBB2RlcG9zaXQFD2NhbGxlckNvbnRyYWN0XwdzZW5kZXJfBnRva2VuXwdhbW91bnRfCXJlZmVycmVyXwQGYW1vdW50CQETdmFsdWVPckVycm9yTWVzc2FnZQIJALYJAQUHYW1vdW50XwIaZGVwb3NpdDogYW1vdW50IGlzIG5vdCBJbnQEA2VycgMDAwMJARBfd2hlbkluaXRpYWxpemVkAAkBDl93aGVuTm90UGF1c2VkAAcJARFfdmFsaWRhdGVFeGVjdXRvcgIIBQFpBmNhbGxlcgIZZGVwb3NpdDogaW52YWxpZCBleGVjdXRvcgcJAQ9fdmFsaWRhdGVDYWxsZXICBQ9jYWxsZXJDb250cmFjdF8CF2RlcG9zaXQ6IGludmFsaWQgY2FsbGVyBwkBDF92YWxpZGF0ZUludAQFBmFtb3VudAAABQdNQVhfSU5UAhdkZXBvc2l0OiBpbnZhbGlkIGFtb3VudAcDCQAAAgUDZXJyBQNlcnIEBHJhdGUJAQ1fZ2V0VG9rZW5SYXRlAQUGdG9rZW5fBA0kdDAyMTkyNjIyMDA4CQERX2xvYWRVc2VyUG9zaXRpb24CBQZ0b2tlbl8FB3NlbmRlcl8EEHVzZXJUb2tlbkJhbGFuY2UIBQ0kdDAyMTkyNjIyMDA4Al8xBBV1c2VyVG9rZW5CYWxhbmNlSW5VU0QIBQ0kdDAyMTkyNjIyMDA4Al8yBA51c2VyVVNEQmFsYW5jZQkBE19sb2FkVXNlclVTREJhbGFuY2UBBQdzZW5kZXJfBBF1c2VyU2hhcmVzUmVmZXJhbAkBFl9sb2FkVXNlclNoYXJlc1JlZmVyYWwBBQdzZW5kZXJfBA0kdDAyMjEyNzIyMjU0CQEPX3VzZXJDaGVja3BvaW50AwUHc2VuZGVyXwUOdXNlclVTREJhbGFuY2UFEXVzZXJTaGFyZXNSZWZlcmFsBBFjaGVja3BvaW50QWN0aW9ucwgFDSR0MDIyMTI3MjIyNTQCXzEEEHVzZXJVbml0c0JhbGFuY2UIBQ0kdDAyMjEyNzIyMjU0Al8yBBZ1c2VyVW5pdHNTaGFyZXNSZWZlcmFsCAUNJHQwMjIxMjcyMjI1NAJfMwQTbmV3VXNlclRva2VuQmFsYW5jZQkAtwICBRB1c2VyVG9rZW5CYWxhbmNlCQC2AgEFBmFtb3VudAQYbmV3VXNlclRva2VuQmFsYW5jZUluVVNECQC9AgQFE25ld1VzZXJUb2tlbkJhbGFuY2UFBHJhdGUFDlBFUkNFTlRfRkFDVE9SBQRET1dOBBFuZXdVc2VyVVNEQmFsYW5jZQkAtwICCQC4AgIFDnVzZXJVU0RCYWxhbmNlBRV1c2VyVG9rZW5CYWxhbmNlSW5VU0QFGG5ld1VzZXJUb2tlbkJhbGFuY2VJblVTRAQTdG90YWxCYWxhbmNlVXBkYXRlZAkAtwICCQC4AgIJARRfbG9hZFRvdGFsVVNEQmFsYW5jZQAFFXVzZXJUb2tlbkJhbGFuY2VJblVTRAUYbmV3VXNlclRva2VuQmFsYW5jZUluVVNEBAp1c2Vyc0NvdW50AwkAAAIFDnVzZXJVU0RCYWxhbmNlBQtaRVJPX0JJR0lOVAkAtwICCQEPX2xvYWRVc2Vyc0NvdW50AAUKT05FX0JJR0lOVAkBD19sb2FkVXNlcnNDb3VudAAEDnJlZmVyZXJBY3Rpb25zAwMJAGYCCQCxAgEFCXJlZmVycmVyXwAACQEWX2NoZWNrUmVmZXJlckV4aXN0ZW5jZQEFCXJlZmVycmVyXwcEDnJlZmVyZXJBZGRyZXNzCQEMX2xvYWRSZWZlcmVyAQUJcmVmZXJyZXJfBBJzaGFyZXNUb0Rpc3RyaWJ1dGUJAL0CBAkAtgIBBQZhbW91bnQFBHJhdGUFDlBFUkNFTlRfRkFDVE9SBQRET1dOBAxzaGFyZXNUb1VzZXIJAL0CBAUSc2hhcmVzVG9EaXN0cmlidXRlCQC2AgEAFAkAtgIBAGQFBERPV04ED3NoYXJlc1RvUmVmZXJlcgkAuAICBRJzaGFyZXNUb0Rpc3RyaWJ1dGUFDHNoYXJlc1RvVXNlcgQUbmV3VXNlclNoYXJlc1JlZmVyYWwJALcCAgURdXNlclNoYXJlc1JlZmVyYWwFDHNoYXJlc1RvVXNlcgQUcmVmZXJlclNoYXJlc1JlZmVyYWwJARZfbG9hZFVzZXJTaGFyZXNSZWZlcmFsAQUOcmVmZXJlckFkZHJlc3MEF25ld1JlZmVyZXJTaGFyZXNSZWZlcmFsCQC3AgIFFHJlZmVyZXJTaGFyZXNSZWZlcmFsBQ9zaGFyZXNUb1JlZmVyZXIEFW5ld1RvdGFsU2hhcmVzUmVmZXJhbAkAtwICCQEXX2xvYWRUb3RhbFNoYXJlc1JlZmVyYWwABRJzaGFyZXNUb0Rpc3RyaWJ1dGUEDSR0MDIzNTg3MjM3NTgJAQ9fdXNlckNoZWNrcG9pbnQDBQ5yZWZlcmVyQWRkcmVzcwkBE19sb2FkVXNlclVTREJhbGFuY2UBBQ5yZWZlcmVyQWRkcmVzcwUUcmVmZXJlclNoYXJlc1JlZmVyYWwEGHJlZmVyZXJDaGVja3BvaW50QWN0aW9ucwgFDSR0MDIzNTg3MjM3NTgCXzEEE3JlZmVyZXJVbml0c0JhbGFuY2UIBQ0kdDAyMzU4NzIzNzU4Al8yBBlyZWZlcmVyVW5pdHNTaGFyZXNSZWZlcmFsCAUNJHQwMjM1ODcyMzc1OAJfMwkAzggCCQDOCAIJAM4IAgUYcmVmZXJlckNoZWNrcG9pbnRBY3Rpb25zCQEWX3NhdmVVc2VyU2hhcmVzUmVmZXJhbAIFB3NlbmRlcl8FFG5ld1VzZXJTaGFyZXNSZWZlcmFsCQEWX3NhdmVVc2VyU2hhcmVzUmVmZXJhbAIFDnJlZmVyZXJBZGRyZXNzBRduZXdSZWZlcmVyU2hhcmVzUmVmZXJhbAkBF19zYXZlVG90YWxTaGFyZXNSZWZlcmFsAQUVbmV3VG90YWxTaGFyZXNSZWZlcmFsBQNuaWwJAJQKAgkAzggCCQDOCAIJAM4IAgkAzggCCQDOCAIJAM4IAgURY2hlY2twb2ludEFjdGlvbnMFDnJlZmVyZXJBY3Rpb25zCQEUX3NhdmVUb3RhbFVTREJhbGFuY2UBBRN0b3RhbEJhbGFuY2VVcGRhdGVkCQERX3NhdmVUb2tlbkJhbGFuY2UCBQZ0b2tlbl8JALcCAgkBEV9sb2FkVG9rZW5CYWxhbmNlAQUGdG9rZW5fCQC2AgEFBmFtb3VudAkBE19zYXZlVXNlclVTREJhbGFuY2UCBQdzZW5kZXJfBRFuZXdVc2VyVVNEQmFsYW5jZQkBD19zYXZlVXNlcnNDb3VudAEFCnVzZXJzQ291bnQJARFfc2F2ZVVzZXJQb3NpdGlvbgMFBnRva2VuXwUHc2VuZGVyXwkAlAoCBRNuZXdVc2VyVG9rZW5CYWxhbmNlBRhuZXdVc2VyVG9rZW5CYWxhbmNlSW5VU0QFEHVzZXJVbml0c0JhbGFuY2UJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQEMZGVwb3NpdFdhdmVzAQlyZWZlcnJlcl8EA2VycgMDAwMJARBfd2hlbkluaXRpYWxpemVkAAkBDl93aGVuTm90UGF1c2VkAAcJARVfdmFsaWRhdGVQYXltZW50c1NpemUDCAUBaQhwYXltZW50cwABAhhkZXBvc2l0V2F2ZXM6IG5vIHBheW1lbnQHCQEVX3ZhbGlkYXRlV2F2ZXNQYXltZW50AgkAkQMCCAUBaQhwYXltZW50cwAAAhtkZXBvc2l0V2F2ZXM6IGludmFsaWQgYXNzZXQHCQEMX3ZhbGlkYXRlSW50BAkAaQIICQCRAwIIBQFpCHBheW1lbnRzAAAGYW1vdW50AGQAAAUHTUFYX0lOVAIcZGVwb3NpdFdhdmVzOiBpbnZhbGlkIGFtb3VudAcDCQAAAgUDZXJyBQNlcnIEBmFtb3VudAkAaQIICQCRAwIIBQFpCHBheW1lbnRzAAAGYW1vdW50AGQEBnNlbmRlcgkApQgBCAUBaQZjYWxsZXIEBXRva2VuBQVXQVZFUwQEcmF0ZQkBDV9nZXRUb2tlblJhdGUBBQV0b2tlbgQNJHQwMjY2MzMyNjcxMwkBEV9sb2FkVXNlclBvc2l0aW9uAgUFdG9rZW4FBnNlbmRlcgQQdXNlclRva2VuQmFsYW5jZQgFDSR0MDI2NjMzMjY3MTMCXzEEFXVzZXJUb2tlbkJhbGFuY2VJblVTRAgFDSR0MDI2NjMzMjY3MTMCXzIEDnVzZXJVU0RCYWxhbmNlCQETX2xvYWRVc2VyVVNEQmFsYW5jZQEFBnNlbmRlcgQRdXNlclNoYXJlc1JlZmVyYWwJARZfbG9hZFVzZXJTaGFyZXNSZWZlcmFsAQUGc2VuZGVyBA0kdDAyNjgzMDI2OTU2CQEPX3VzZXJDaGVja3BvaW50AwUGc2VuZGVyBQ51c2VyVVNEQmFsYW5jZQURdXNlclNoYXJlc1JlZmVyYWwEEWNoZWNrcG9pbnRBY3Rpb25zCAUNJHQwMjY4MzAyNjk1NgJfMQQQdXNlclVuaXRzQmFsYW5jZQgFDSR0MDI2ODMwMjY5NTYCXzIEFnVzZXJVbml0c1NoYXJlc1JlZmVyYWwIBQ0kdDAyNjgzMDI2OTU2Al8zBBNuZXdVc2VyVG9rZW5CYWxhbmNlCQC3AgIFEHVzZXJUb2tlbkJhbGFuY2UJALYCAQUGYW1vdW50BBhuZXdVc2VyVG9rZW5CYWxhbmNlSW5VU0QJAL0CBAUTbmV3VXNlclRva2VuQmFsYW5jZQUEcmF0ZQUOUEVSQ0VOVF9GQUNUT1IFBERPV04EEW5ld1VzZXJVU0RCYWxhbmNlCQC3AgIJALgCAgUOdXNlclVTREJhbGFuY2UFFXVzZXJUb2tlbkJhbGFuY2VJblVTRAUYbmV3VXNlclRva2VuQmFsYW5jZUluVVNEBBN0b3RhbEJhbGFuY2VVcGRhdGVkCQC3AgIJALgCAgkBFF9sb2FkVG90YWxVU0RCYWxhbmNlAAUVdXNlclRva2VuQmFsYW5jZUluVVNEBRhuZXdVc2VyVG9rZW5CYWxhbmNlSW5VU0QECnVzZXJzQ291bnQDCQAAAgUOdXNlclVTREJhbGFuY2UFC1pFUk9fQklHSU5UCQC3AgIJAQ9fbG9hZFVzZXJzQ291bnQABQpPTkVfQklHSU5UCQEPX2xvYWRVc2Vyc0NvdW50AAQOcmVmZXJlckFjdGlvbnMDAwkAZgIJALECAQUJcmVmZXJyZXJfAAAJARZfY2hlY2tSZWZlcmVyRXhpc3RlbmNlAQUJcmVmZXJyZXJfBwQOcmVmZXJlckFkZHJlc3MJAQxfbG9hZFJlZmVyZXIBBQlyZWZlcnJlcl8EEnNoYXJlc1RvRGlzdHJpYnV0ZQkAvQIECQC2AgEFBmFtb3VudAUEcmF0ZQUOUEVSQ0VOVF9GQUNUT1IFBERPV04EDHNoYXJlc1RvVXNlcgkAvQIEBRJzaGFyZXNUb0Rpc3RyaWJ1dGUJALYCAQAUCQC2AgEAZAUERE9XTgQPc2hhcmVzVG9SZWZlcmVyCQC4AgIFEnNoYXJlc1RvRGlzdHJpYnV0ZQUMc2hhcmVzVG9Vc2VyBBRuZXdVc2VyU2hhcmVzUmVmZXJhbAkAtwICBRF1c2VyU2hhcmVzUmVmZXJhbAUMc2hhcmVzVG9Vc2VyBBRyZWZlcmVyU2hhcmVzUmVmZXJhbAkBFl9sb2FkVXNlclNoYXJlc1JlZmVyYWwBBQ5yZWZlcmVyQWRkcmVzcwQXbmV3UmVmZXJlclNoYXJlc1JlZmVyYWwJALcCAgUUcmVmZXJlclNoYXJlc1JlZmVyYWwFD3NoYXJlc1RvUmVmZXJlcgQVbmV3VG90YWxTaGFyZXNSZWZlcmFsCQC3AgIJARdfbG9hZFRvdGFsU2hhcmVzUmVmZXJhbAAFEnNoYXJlc1RvRGlzdHJpYnV0ZQQNJHQwMjgyODkyODQ2MAkBD191c2VyQ2hlY2twb2ludAMFDnJlZmVyZXJBZGRyZXNzCQETX2xvYWRVc2VyVVNEQmFsYW5jZQEFDnJlZmVyZXJBZGRyZXNzBRRyZWZlcmVyU2hhcmVzUmVmZXJhbAQYcmVmZXJlckNoZWNrcG9pbnRBY3Rpb25zCAUNJHQwMjgyODkyODQ2MAJfMQQTcmVmZXJlclVuaXRzQmFsYW5jZQgFDSR0MDI4Mjg5Mjg0NjACXzIEGXJlZmVyZXJVbml0c1NoYXJlc1JlZmVyYWwIBQ0kdDAyODI4OTI4NDYwAl8zCQDOCAIJAM4IAgkAzggCBRhyZWZlcmVyQ2hlY2twb2ludEFjdGlvbnMJARZfc2F2ZVVzZXJTaGFyZXNSZWZlcmFsAgUGc2VuZGVyBRRuZXdVc2VyU2hhcmVzUmVmZXJhbAkBFl9zYXZlVXNlclNoYXJlc1JlZmVyYWwCBQ5yZWZlcmVyQWRkcmVzcwUXbmV3UmVmZXJlclNoYXJlc1JlZmVyYWwJARdfc2F2ZVRvdGFsU2hhcmVzUmVmZXJhbAEFFW5ld1RvdGFsU2hhcmVzUmVmZXJhbAUDbmlsBAppbnZvY2F0aW9uCQD8BwQJARNfbG9hZFNXYXZlc0NvbnRyYWN0AAUMRlVOQ19ERVBPU0lUBQNuaWwJAMwIAgkBD0F0dGFjaGVkUGF5bWVudAIFBHVuaXQICQCRAwIIBQFpCHBheW1lbnRzAAAGYW1vdW50BQNuaWwDCQAAAgUKaW52b2NhdGlvbgUKaW52b2NhdGlvbgkAlAoCCQDOCAIJAM4IAgkAzggCCQDOCAIJAM4IAgkAzggCBRFjaGVja3BvaW50QWN0aW9ucwUOcmVmZXJlckFjdGlvbnMJARRfc2F2ZVRvdGFsVVNEQmFsYW5jZQEFE3RvdGFsQmFsYW5jZVVwZGF0ZWQJARFfc2F2ZVRva2VuQmFsYW5jZQIFBVdBVkVTCQC3AgIJARFfbG9hZFRva2VuQmFsYW5jZQEFBVdBVkVTCQC2AgEFBmFtb3VudAkBE19zYXZlVXNlclVTREJhbGFuY2UCBQZzZW5kZXIFEW5ld1VzZXJVU0RCYWxhbmNlCQEPX3NhdmVVc2Vyc0NvdW50AQUKdXNlcnNDb3VudAkBEV9zYXZlVXNlclBvc2l0aW9uAwUFdG9rZW4FBnNlbmRlcgkAlAoCBRNuZXdVc2VyVG9rZW5CYWxhbmNlBRhuZXdVc2VyVG9rZW5CYWxhbmNlSW5VU0QFEHVzZXJVbml0c0JhbGFuY2UJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4JAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQENd2l0aGRyYXdXYXZlcwEHYW1vdW50XwQDZXJyAwMDCQEQX3doZW5Jbml0aWFsaXplZAAJAQ5fd2hlbk5vdFBhdXNlZAAHCQEMX3ZhbGlkYXRlSW50BAkAaQIFB2Ftb3VudF8AZAAABQdNQVhfSU5UAh13aXRoZHJhd1dhdmVzOiBpbnZhbGlkIGFtb3VudAcDCQDAAgIJARBfbG9hZEZpbmlzaEJsb2NrAAkAtgIBBQZoZWlnaHQJAAIBAhp3aXRoZHJhd1dhdmVzOiBub3QgYWxsb3dlZAYHAwkAAAIFA2VycgUDZXJyBA5pbnRlcm5hbEFtb3VudAkAaQIFB2Ftb3VudF8AZAQGc2VuZGVyCQClCAEIBQFpBmNhbGxlcgQFdG9rZW4FBVdBVkVTBARyYXRlCQENX2dldFRva2VuUmF0ZQEFBXRva2VuBA0kdDAyOTcyODI5ODA4CQERX2xvYWRVc2VyUG9zaXRpb24CBQV0b2tlbgUGc2VuZGVyBBB1c2VyVG9rZW5CYWxhbmNlCAUNJHQwMjk3MjgyOTgwOAJfMQQVdXNlclRva2VuQmFsYW5jZUluVVNECAUNJHQwMjk3MjgyOTgwOAJfMgQOdXNlclVTREJhbGFuY2UJARNfbG9hZFVzZXJVU0RCYWxhbmNlAQUGc2VuZGVyBBF1c2VyU2hhcmVzUmVmZXJhbAkBFl9sb2FkVXNlclNoYXJlc1JlZmVyYWwBBQZzZW5kZXIEDSR0MDI5OTI1MzAwNTEJAQ9fdXNlckNoZWNrcG9pbnQDBQZzZW5kZXIFDnVzZXJVU0RCYWxhbmNlBRF1c2VyU2hhcmVzUmVmZXJhbAQRY2hlY2twb2ludEFjdGlvbnMIBQ0kdDAyOTkyNTMwMDUxAl8xBBB1c2VyVW5pdHNCYWxhbmNlCAUNJHQwMjk5MjUzMDA1MQJfMgQWdXNlclVuaXRzU2hhcmVzUmVmZXJhbAgFDSR0MDI5OTI1MzAwNTECXzMEE25ld1VzZXJUb2tlbkJhbGFuY2UJALgCAgUQdXNlclRva2VuQmFsYW5jZQkAtgIBBQ5pbnRlcm5hbEFtb3VudAQEZXJyMQkBDF92YWxpZGF0ZUludAQJAKADAQUTbmV3VXNlclRva2VuQmFsYW5jZQAABQdNQVhfSU5UAih3aXRoZHJhd1dhdmVzOiBpbnN1ZmZpY2llbnQgdG9rZW4gYW1vdW50AwkAAAIFBGVycjEFBGVycjEEGG5ld1VzZXJUb2tlbkJhbGFuY2VJblVTRAkAvQIEBRNuZXdVc2VyVG9rZW5CYWxhbmNlBQRyYXRlBQ5QRVJDRU5UX0ZBQ1RPUgUERE9XTgQRbmV3VXNlclVTREJhbGFuY2UJALcCAgkAuAICBQ51c2VyVVNEQmFsYW5jZQUVdXNlclRva2VuQmFsYW5jZUluVVNEBRhuZXdVc2VyVG9rZW5CYWxhbmNlSW5VU0QEE3RvdGFsQmFsYW5jZVVwZGF0ZWQJALcCAgkAuAICCQEUX2xvYWRUb3RhbFVTREJhbGFuY2UABRV1c2VyVG9rZW5CYWxhbmNlSW5VU0QFGG5ld1VzZXJUb2tlbkJhbGFuY2VJblVTRAQOc1dhdmVzQ29udHJhY3QJARNfbG9hZFNXYXZlc0NvbnRyYWN0AAQLc1dhdmVzQXNzZXQJARBfbG9hZFNXYXZlc0Fzc2V0AQUOc1dhdmVzQ29udHJhY3QECmludm9jYXRpb24JAPwHBAUOc1dhdmVzQ29udHJhY3QFDUZVTkNfR0VUX1JBVEUFA25pbAUDbmlsBApzd2F2ZXNSYXRlBAckbWF0Y2gwBQppbnZvY2F0aW9uAwkAAQIFByRtYXRjaDACBlN0cmluZwQBYQUHJG1hdGNoMAkApwMBBQFhCQACAQImd2l0aGRyYXdXYXZlczogc1dhdmVzIGdldFJhdGUoKSByZXZlcnQEEHNXYXZlc1RvV2l0aGRyYXcJAKADAQkAvQIECQC2AgEFB2Ftb3VudF8FElNXQVZFU19SQVRFX0ZBQ1RPUgUKc3dhdmVzUmF0ZQUHQ0VJTElORwQLaW52b2NhdGlvbjEJAPwHBAUOc1dhdmVzQ29udHJhY3QFDUZVTkNfV0lUSERSQVcFA25pbAkAzAgCCQEPQXR0YWNoZWRQYXltZW50AgULc1dhdmVzQXNzZXQFEHNXYXZlc1RvV2l0aGRyYXcFA25pbAMJAAACBQtpbnZvY2F0aW9uMQULaW52b2NhdGlvbjEJAJQKAgkAzggCCQDOCAIJAM4IAgkAzggCCQDOCAIJAMwIAgkBDlNjcmlwdFRyYW5zZmVyAwgFAWkGY2FsbGVyBQdhbW91bnRfBQR1bml0BQNuaWwFEWNoZWNrcG9pbnRBY3Rpb25zCQEUX3NhdmVUb3RhbFVTREJhbGFuY2UBBRN0b3RhbEJhbGFuY2VVcGRhdGVkCQERX3NhdmVUb2tlbkJhbGFuY2UCBQVXQVZFUwkAuAICCQERX2xvYWRUb2tlbkJhbGFuY2UBBQVXQVZFUwkAtgIBBQ5pbnRlcm5hbEFtb3VudAkBE19zYXZlVXNlclVTREJhbGFuY2UCBQZzZW5kZXIFEW5ld1VzZXJVU0RCYWxhbmNlCQERX3NhdmVVc2VyUG9zaXRpb24DBQV0b2tlbgUGc2VuZGVyCQCUCgIFE25ld1VzZXJUb2tlbkJhbGFuY2UFGG5ld1VzZXJUb2tlbkJhbGFuY2VJblVTRAUEdW5pdAkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgFpAQ5zdGFydFJldHJvZHJvcAQLdW5pdHNBc3NldF8MYW1vdW50Rm9yTFBfEWFtb3VudEZvclJlZmVyYWxfCWJsb2Nrc0F0XwQDZXJyAwMDAwMDAwkBEV9vbmx5VGhpc0NvbnRyYWN0AQgFAWkGY2FsbGVyCQEQX3doZW5Jbml0aWFsaXplZAAHCQEOX3doZW5Ob3RQYXVzZWQABwkBDl92YWxpZGF0ZUFzc2V0AgULdW5pdHNBc3NldF8CI3N0YXJ0UmV0cm9kcm9wOiBpbnZhbGlkIHVuaXRzIGFzc2V0BwkBDF92YWxpZGF0ZUludAQFDGFtb3VudEZvckxQXwAABQdNQVhfSU5UAiNzdGFydFJldHJvZHJvcDogaW52YWxpZCBhbW91bnRGb3JMUAcJAQxfdmFsaWRhdGVJbnQEBRFhbW91bnRGb3JSZWZlcmFsXwAABQdNQVhfSU5UAihzdGFydFJldHJvZHJvcDogaW52YWxpZCBhbW91bnRGb3JSZWZlcmFsBwkBDF92YWxpZGF0ZUludAQFCWJsb2Nrc0F0XwABBQdNQVhfSU5UAiBzdGFydFJldHJvZHJvcDogaW52YWxpZCBibG9ja3NBdAcJARFfdmFsaWRhdGVFcUJpZ0ludAMJAQ9fbG9hZFN0YXJ0QmxvY2sABQtaRVJPX0JJR0lOVAIfc3RhcnRSZXRyb2Ryb3A6IGFscmVhZHkgc3RhcnRlZAcDCQAAAgUDZXJyBQNlcnIEC3N0YXJ0SGVpZ2h0CQC2AgEFBmhlaWdodAQMZmluaXNoSGVpZ2h0CQC3AgIFC3N0YXJ0SGVpZ2h0CQC2AgEFCWJsb2Nrc0F0XwQEZXJyMQMJAGYCCQBkAgUMYW1vdW50Rm9yTFBfBRFhbW91bnRGb3JSZWZlcmFsXwkA8AcCBQR0aGlzCQDZBAEFC3VuaXRzQXNzZXRfCQACAQIic3RhcnRSZXRyb2Ryb3A6IGluc3VmZmljaWVudCBmdW5kcwYDCQAAAgUEZXJyMQUEZXJyMQkAlAoCCQDOCAIJAM4IAgkAzggCCQDOCAIJAQ9fc2F2ZVVuaXRzQXNzZXQBCQDZBAEFC3VuaXRzQXNzZXRfCQEPX3NhdmVTdGFydEJsb2NrAQULc3RhcnRIZWlnaHQJARBfc2F2ZUZpbmlzaEJsb2NrAQUMZmluaXNoSGVpZ2h0CQEUX3NhdmVUb3RhbFVuaXRzRm9yTFABCQC2AgEFDGFtb3VudEZvckxQXwkBGV9zYXZlVG90YWxVbml0c0ZvclJlZmVyYWwBCQC2AgEFEWFtb3VudEZvclJlZmVyYWxfBQR1bml0CQACAQIkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuCQACAQIkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAWkBE2luY3JlYXNlVW5pdHNTdXBwbHkCDGFtb3VudEZvckxQXxFhbW91bnRGb3JSZWZlcmFsXwQDZXJyAwMDAwkBEF93aGVuSW5pdGlhbGl6ZWQACQEOX3doZW5Ob3RQYXVzZWQABwkBDF92YWxpZGF0ZUludAQFDGFtb3VudEZvckxQXwAABQdNQVhfSU5UAihpbmNyZWFzZVVuaXRzU3VwcGx5OiBpbnZhbGlkIGFtb3VudEZvckxQBwkBDF92YWxpZGF0ZUludAQFEWFtb3VudEZvclJlZmVyYWxfAAAFB01BWF9JTlQCLWluY3JlYXNlVW5pdHNTdXBwbHk6IGludmFsaWQgYW1vdW50Rm9yUmVmZXJhbAcJAQ9fdmFsaWRhdGVCaWdJbnQECQC2AgEFBmhlaWdodAkAtwICCQEPX2xvYWRTdGFydEJsb2NrAAUKT05FX0JJR0lOVAkAuAICCQEQX2xvYWRGaW5pc2hCbG9jawAFCk9ORV9CSUdJTlQCJGluY3JlYXNlVW5pdHNTdXBwbHk6IGRyb3Agbm90IGFjdGl2ZQcDCQAAAgUDZXJyBQNlcnIEDm5ld0Ftb3VudEZvckxQCQC3AgIJARRfbG9hZFRvdGFsVW5pdHNGb3JMUAAJALYCAQUMYW1vdW50Rm9yTFBfBBNuZXdBbW91bnRGb3JSZWZlcmFsCQC3AgIJARlfbG9hZFRvdGFsVW5pdHNGb3JSZWZlcmFsAAkAtgIBBRFhbW91bnRGb3JSZWZlcmFsXwQEZXJyMQMJAL8CAgkAtwICBQ5uZXdBbW91bnRGb3JMUAUTbmV3QW1vdW50Rm9yUmVmZXJhbAkAtgIBCQDwBwIFBHRoaXMJAQ9fbG9hZFVuaXRzQXNzZXQACQACAQInaW5jcmVhc2VVbml0c1N1cHBseTogaW5zdWZmaWNpZW50IGZ1bmRzBgMJAAACBQRlcnIxBQRlcnIxCQCUCgIJAM4IAgkBFF9zYXZlVG90YWxVbml0c0ZvckxQAQUObmV3QW1vdW50Rm9yTFAJARlfc2F2ZVRvdGFsVW5pdHNGb3JSZWZlcmFsAQUTbmV3QW1vdW50Rm9yUmVmZXJhbAUEdW5pdAkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgFpAQpjaGVja3BvaW50AQV1c2VyXwQNJHQwMzM4MjAzMzk1OQkBD191c2VyQ2hlY2twb2ludAMFBXVzZXJfCQETX2xvYWRVc2VyVVNEQmFsYW5jZQEFBXVzZXJfCQEWX2xvYWRVc2VyU2hhcmVzUmVmZXJhbAEFBXVzZXJfBAdhY3Rpb25zCAUNJHQwMzM4MjAzMzk1OQJfMQQQdXNlclVuaXRzQmFsYW5jZQgFDSR0MDMzODIwMzM5NTkCXzIEFnVzZXJVbml0c1NoYXJlc1JlZmVyYWwIBQ0kdDAzMzgyMDMzOTU5Al8zCQCUCgIFB2FjdGlvbnMJAJQKAgUQdXNlclVuaXRzQmFsYW5jZQUWdXNlclVuaXRzU2hhcmVzUmVmZXJhbAFpAQhnZXRVbml0cwEFdXNlcl8EDSR0MDM0MDcyMzQyMTEJAQ9fdXNlckNoZWNrcG9pbnQDBQV1c2VyXwkBE19sb2FkVXNlclVTREJhbGFuY2UBBQV1c2VyXwkBFl9sb2FkVXNlclNoYXJlc1JlZmVyYWwBBQV1c2VyXwQHYWN0aW9ucwgFDSR0MDM0MDcyMzQyMTECXzEEEHVzZXJVbml0c0JhbGFuY2UIBQ0kdDAzNDA3MjM0MjExAl8yBBZ1c2VyVW5pdHNTaGFyZXNSZWZlcmFsCAUNJHQwMzQwNzIzNDIxMQJfMwkAlAoCBQNuaWwJAJQKAgUQdXNlclVuaXRzQmFsYW5jZQUWdXNlclVuaXRzU2hhcmVzUmVmZXJhbAFpAQpzZXRSZWZlcmVyAgljb2RlaGFzaF8IYWRkcmVzc18EA2VycgMJAQxfb25seU1hbmFnZXIBCAUBaQZjYWxsZXIJARBfd2hlbkluaXRpYWxpemVkAAcDCQAAAgUDZXJyBQNlcnIJAJQKAgkBDF9zYXZlUmVmZXJlcgIFCWNvZGVoYXNoXwUIYWRkcmVzc18FBHVuaXQJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQEKc2V0TWFuYWdlcgEIbWFuYWdlcl8EA2VycgMDCQERX29ubHlUaGlzQ29udHJhY3QBCAUBaQZjYWxsZXIJARBfd2hlbkluaXRpYWxpemVkAAcJARBfdmFsaWRhdGVBZGRyZXNzAgUIbWFuYWdlcl8CG3NldE1hbmFnZXI6IGludmFsaWQgbWFuYWdlcgcDCQAAAgUDZXJyBQNlcnIJAJQKAgkBDF9zYXZlTWFuYWdlcgEJARFAZXh0ck5hdGl2ZSgxMDYyKQEFCG1hbmFnZXJfBQR1bml0CQACAQIkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAWkBFHVwZGF0ZUNhbGxlckNvbnRyYWN0AQ9jYWxsZXJDb250cmFjdF8EA2VycgMJARFfb25seVRoaXNDb250cmFjdAEIBQFpBmNhbGxlcgkBEF93aGVuSW5pdGlhbGl6ZWQABwMJAAACBQNlcnIFA2VycgkAlAoCCQETX3NhdmVDYWxsZXJDb250cmFjdAEFD2NhbGxlckNvbnRyYWN0XwUEdW5pdAkAAgECJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgFpAQVwYXVzZQAEA2VycgMDCQELX29ubHlQYXVzZXIBCAUBaQZjYWxsZXIJARBfd2hlbkluaXRpYWxpemVkAAcJAQ5fd2hlbk5vdFBhdXNlZAAHAwkAAAIFA2VycgUDZXJyCQCUCgIJAQpfc2F2ZVBhdXNlAQYFBHVuaXQJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQEHdW5wYXVzZQAEA2VycgMDCQELX29ubHlQYXVzZXIBCAUBaQZjYWxsZXIJARBfd2hlbkluaXRpYWxpemVkAAcJAQtfd2hlblBhdXNlZAAHAwkAAAIFA2VycgUDZXJyCQCUCgIJAQpfc2F2ZVBhdXNlAQcFBHVuaXQJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQEMdXBkYXRlUGF1c2VyAQdwYXVzZXJfBANlcnIDAwkBEV9vbmx5VGhpc0NvbnRyYWN0AQgFAWkGY2FsbGVyCQEQX3doZW5Jbml0aWFsaXplZAAHCQEQX3ZhbGlkYXRlQWRkcmVzcwIFB3BhdXNlcl8CHHVwZGF0ZVBhdXNlcjogaW52YWxpZCBwYXVzZXIHAwkAAAIFA2VycgUDZXJyCQCUCgIJAQtfc2F2ZVBhdXNlcgEJARFAZXh0ck5hdGl2ZSgxMDYyKQEFB3BhdXNlcl8FBHVuaXQJAAIBAiRTdHJpY3QgdmFsdWUgaXMgbm90IGVxdWFsIHRvIGl0c2VsZi4BaQELc2V0TXVsdGlzaWcBCW11bHRpc2lnXwQDZXJyAwkBEV9vbmx5VGhpc0NvbnRyYWN0AQgFAWkGY2FsbGVyCQEQX3ZhbGlkYXRlQWRkcmVzcwIFCW11bHRpc2lnXwIdc2V0TXVsdGlzaWc6IGludmFsaWQgbXVsdGlzaWcHAwkAAAIFA2VycgUDZXJyCQCUCgIJAQ1fc2F2ZU11bHRpc2lnAQkBEUBleHRyTmF0aXZlKDEwNjIpAQUJbXVsdGlzaWdfBQR1bml0CQACAQIkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAQJ0eAEGdmVyaWZ5AAQHJG1hdGNoMAkAoggBBQxLRVlfTVVMVElTSUcDCQABAgUHJG1hdGNoMAIGU3RyaW5nBAhtdWx0aXNpZwUHJG1hdGNoMAkBC3ZhbHVlT3JFbHNlAgkAmwgCCQERQGV4dHJOYXRpdmUoMTA2MikBBQhtdWx0aXNpZwkAuQkCCQDMCAIFCktFWV9TVEFUVVMJAMwIAgkApQgBBQR0aGlzCQDMCAIJANgEAQgFAnR4AmlkBQNuaWwFCVNFUEFSQVRPUgcJAPQDAwgFAnR4CWJvZHlCeXRlcwkAkQMCCAUCdHgGcHJvb2ZzAAAIBQJ0eA9zZW5kZXJQdWJsaWNLZXlgIwbR", "height": 2967446, "applicationStatus": "succeeded", "spentComplexity": 0 } View: original | compacted Prev: 8kcReFwfsRJrzi6D6hVpGw48Q1gUeegTiGRjbGPWEZTs Next: GJKZ9F3aAnjj3dzt71c98cwobkn3otifNnvpgci5NaKY Diff:
Old | New | Differences | |
---|---|---|---|
15 | 15 | ||
16 | 16 | let KEY_PAUSER = "PAUSER" | |
17 | 17 | ||
18 | + | let KEY_MANAGER = "MANAGER" | |
19 | + | ||
20 | + | let KEY_REFERER = "REFERER" | |
21 | + | ||
18 | 22 | let KEY_EXECUTOR = "EXECUTOR" | |
19 | 23 | ||
20 | 24 | let KEY_ORACLE = "ORACLE" | |
23 | 27 | ||
24 | 28 | let KEY_PRICE = "PRICE" | |
25 | 29 | ||
30 | + | let KEY_UNITS_ASSET = "UNITS_ASSET" | |
31 | + | ||
26 | 32 | let KEY_USER_POSITION = "USER_POSITION" | |
27 | 33 | ||
28 | 34 | let KEY_USER_USD_BALANCE = "USER_USD_BALANCE" | |
29 | 35 | ||
30 | 36 | let KEY_USER_UNITS_PER_USD_BALANCE_INTEGRAL = "USER_UNITS_PER_USD_BALANCE_INTEGRAL" | |
31 | 37 | ||
38 | + | let KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL = "USER_UNITS_PER_REFERAL_SHARE_INTEGRAL" | |
39 | + | ||
32 | 40 | let KEY_USER_CHECKPOINT_AT = "USER_CHECKPOINT_AT" | |
33 | 41 | ||
34 | - | let KEY_USER_UNITS_BALANCE = "USER_UNITS_BALANCE" | |
42 | + | let KEY_USER_UNITS_BALANCE_DISTRIBUTED = "USER_UNITS_BALANCE_DISTRIBUTED" | |
43 | + | ||
44 | + | let KEY_USER_UNITS_SHARES_REFERAL = "USER_UNITS_SHARES_REFERAL" | |
45 | + | ||
46 | + | let KEY_USER_SHARES_REFERAL = "USER_SHARES_REFERAL" | |
35 | 47 | ||
36 | 48 | let KEY_START_BLOCK = "START_BLOCK" | |
37 | 49 | ||
38 | 50 | let KEY_FINISH_BLOCK = "FINISH_BLOCK" | |
39 | 51 | ||
40 | - | let KEY_UNITS_PER_BLOCK = "UNITS_PER_BLOCK" | |
52 | + | let KEY_TOTAL_UNITS_FOR_LP = "TOTAL_UNITS_FOR_LP" | |
53 | + | ||
54 | + | let KEY_TOTAL_UNITS_FOR_REFERAL = "TOTAL_UNITS_FOR_REFERAL" | |
41 | 55 | ||
42 | 56 | let KEY_TOTAL_USD_BALANCE = "TOTAL_USD_BALANCE" | |
43 | 57 | ||
45 | 59 | ||
46 | 60 | let KEY_CHECKPOINT_AT = "CHECKPOINT_AT" | |
47 | 61 | ||
48 | - | let KEY_UNITS_BALANCE = "UNITS_BALANCE" | |
62 | + | let KEY_UNITS_BALANCE_DISTRIBUTED = "UNITS_BALANCE_DISTRIBUTED" | |
49 | 63 | ||
50 | 64 | let KEY_TOKEN_BALANCE = "TOKEN_BALANCE" | |
65 | + | ||
66 | + | let KEY_USERS_COUNT = "USERS_COUNT" | |
67 | + | ||
68 | + | let KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL = "UNITS_PER_REFERAL_SHARE_INTEGRAL" | |
69 | + | ||
70 | + | let KEY_UNITS_SHARES_REFERAL = "UNITS_SHARES_REFERAL" | |
71 | + | ||
72 | + | let KEY_TOTAL_SHARES_REFERAL = "TOTAL_SHARES_REFERAL" | |
51 | 73 | ||
52 | 74 | let KEY_SWAVES_CONTRACT = "SWAVES_CONTRACT" | |
53 | 75 | ||
65 | 87 | ||
66 | 88 | let ZERO_BIGINT = toBigInt(0) | |
67 | 89 | ||
90 | + | let ONE_BIGINT = toBigInt(1) | |
91 | + | ||
68 | 92 | let SWAVES_RATE_FACTOR = toBigInt(1000000000000) | |
69 | 93 | ||
70 | 94 | func _validateAddress (address_,err_) = match addressFromString(address_) { | |
76 | 100 | ||
77 | 101 | ||
78 | 102 | func _validateInt (val_,lowerBoundary_,upperBoundary_,err_) = if (if ((lowerBoundary_ > val_)) | |
103 | + | then true | |
104 | + | else (val_ > upperBoundary_)) | |
105 | + | then throw(err_) | |
106 | + | else true | |
107 | + | ||
108 | + | ||
109 | + | func _validateBigInt (val_,lowerBoundary_,upperBoundary_,err_) = if (if ((lowerBoundary_ > val_)) | |
79 | 110 | then true | |
80 | 111 | else (val_ > upperBoundary_)) | |
81 | 112 | then throw(err_) | |
100 | 131 | func _validateEqBigInt (val1_,val2_,err_) = if ((val1_ != val2_)) | |
101 | 132 | then throw(err_) | |
102 | 133 | else true | |
134 | + | ||
135 | + | ||
136 | + | func _validateAsset (asset_,err_) = match assetInfo(fromBase58String(asset_)) { | |
137 | + | case a: Asset => | |
138 | + | true | |
139 | + | case _ => | |
140 | + | throw(err_) | |
141 | + | } | |
103 | 142 | ||
104 | 143 | ||
105 | 144 | func _loadInit () = match getBoolean(KEY_INIT) { | |
202 | 241 | func _saveUserUSDBalance (user_,value_) = [StringEntry(makeString([KEY_USER_USD_BALANCE, user_], SEPARATOR), toString(value_))] | |
203 | 242 | ||
204 | 243 | ||
244 | + | func _loadUserSharesReferal (user_) = match getString(makeString([KEY_USER_SHARES_REFERAL, user_], SEPARATOR)) { | |
245 | + | case a: String => | |
246 | + | parseBigIntValue(a) | |
247 | + | case _ => | |
248 | + | ZERO_BIGINT | |
249 | + | } | |
250 | + | ||
251 | + | ||
252 | + | func _saveUserSharesReferal (user_,value_) = [StringEntry(makeString([KEY_USER_SHARES_REFERAL, user_], SEPARATOR), toString(value_))] | |
253 | + | ||
254 | + | ||
205 | 255 | func _loadUnitsPerUSDBalanceIntegral () = match getString(KEY_UNITS_PER_USD_BALANCE_INTEGRAL) { | |
206 | 256 | case a: String => | |
207 | 257 | parseBigIntValue(a) | |
246 | 296 | func _saveUserCheckpointAt (user_,value_) = [StringEntry(makeString([KEY_USER_CHECKPOINT_AT, user_], SEPARATOR), toString(value_))] | |
247 | 297 | ||
248 | 298 | ||
299 | + | func _loadUnitsAsset () = match getString(KEY_UNITS_ASSET) { | |
300 | + | case a: String => | |
301 | + | fromBase58String(a) | |
302 | + | case _ => | |
303 | + | base58'' | |
304 | + | } | |
305 | + | ||
306 | + | ||
307 | + | func _saveUnitsAsset (asset_) = [StringEntry(KEY_UNITS_ASSET, toBase58String(asset_))] | |
308 | + | ||
309 | + | ||
249 | 310 | func _loadStartBlock () = match getString(KEY_START_BLOCK) { | |
250 | 311 | case a: String => | |
251 | 312 | parseBigIntValue(a) | |
268 | 329 | func _saveFinishBlock (value_) = [StringEntry(KEY_FINISH_BLOCK, toString(value_))] | |
269 | 330 | ||
270 | 331 | ||
271 | - | func _ | |
332 | + | func _loadUnitsBalanceDistributed () = match getString(KEY_UNITS_BALANCE_DISTRIBUTED) { | |
272 | 333 | case a: String => | |
273 | 334 | parseBigIntValue(a) | |
274 | 335 | case _ => | |
276 | 337 | } | |
277 | 338 | ||
278 | 339 | ||
279 | - | func _ | |
340 | + | func _saveUnitsBalanceDistributed (value_) = [StringEntry(KEY_UNITS_BALANCE_DISTRIBUTED, toString(value_))] | |
280 | 341 | ||
281 | 342 | ||
282 | - | func _ | |
343 | + | func _loadUserUnitsBalanceDistributed (user_) = match getString(makeString([KEY_USER_UNITS_BALANCE_DISTRIBUTED, user_], SEPARATOR)) { | |
283 | 344 | case a: String => | |
284 | 345 | parseBigIntValue(a) | |
285 | 346 | case _ => | |
287 | 348 | } | |
288 | 349 | ||
289 | 350 | ||
290 | - | func _saveUnitsBalance (value_) = [StringEntry(KEY_UNITS_BALANCE, toString(value_))] | |
291 | - | ||
292 | - | ||
293 | - | func _loadUserUnitsBalance (user_) = match getString(makeString([KEY_USER_UNITS_BALANCE, user_], SEPARATOR)) { | |
294 | - | case a: String => | |
295 | - | parseBigIntValue(a) | |
296 | - | case _ => | |
297 | - | ZERO_BIGINT | |
298 | - | } | |
299 | - | ||
300 | - | ||
301 | - | func _saveUserUnitsBalance (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_BALANCE, user_], SEPARATOR), toString(value_))] | |
351 | + | func _saveUserUnitsBalanceDistributed (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_BALANCE_DISTRIBUTED, user_], SEPARATOR), toString(value_))] | |
302 | 352 | ||
303 | 353 | ||
304 | 354 | func _loadTotalUSDBalance () = match getString(KEY_TOTAL_USD_BALANCE) { | |
342 | 392 | func _saveTokenBalance (token_,value_) = [StringEntry(makeString([KEY_TOKEN_BALANCE, token_], SEPARATOR), toString(value_))] | |
343 | 393 | ||
344 | 394 | ||
395 | + | func _loadUsersCount () = match getString(KEY_USERS_COUNT) { | |
396 | + | case a: String => | |
397 | + | parseBigIntValue(a) | |
398 | + | case _ => | |
399 | + | ZERO_BIGINT | |
400 | + | } | |
401 | + | ||
402 | + | ||
403 | + | func _saveUsersCount (value_) = [StringEntry(KEY_USERS_COUNT, toString(value_))] | |
404 | + | ||
405 | + | ||
406 | + | func _loadUnitsPerReferalShareIntegral () = match getString(KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL) { | |
407 | + | case a: String => | |
408 | + | parseBigIntValue(a) | |
409 | + | case _ => | |
410 | + | ZERO_BIGINT | |
411 | + | } | |
412 | + | ||
413 | + | ||
414 | + | func _saveUnitsPerReferalShareIntegral (value_) = [StringEntry(KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL, toString(value_))] | |
415 | + | ||
416 | + | ||
417 | + | func _loadUnitsSharesReferal () = match getString(KEY_UNITS_SHARES_REFERAL) { | |
418 | + | case a: String => | |
419 | + | parseBigIntValue(a) | |
420 | + | case _ => | |
421 | + | ZERO_BIGINT | |
422 | + | } | |
423 | + | ||
424 | + | ||
425 | + | func _saveUnitsSharesReferal (value_) = [StringEntry(KEY_UNITS_SHARES_REFERAL, toString(value_))] | |
426 | + | ||
427 | + | ||
428 | + | func _loadTotalUnitsForLP () = match getString(KEY_TOTAL_UNITS_FOR_LP) { | |
429 | + | case a: String => | |
430 | + | parseBigIntValue(a) | |
431 | + | case _ => | |
432 | + | ZERO_BIGINT | |
433 | + | } | |
434 | + | ||
435 | + | ||
436 | + | func _saveTotalUnitsForLP (value_) = [StringEntry(KEY_TOTAL_UNITS_FOR_LP, toString(value_))] | |
437 | + | ||
438 | + | ||
439 | + | func _loadTotalUnitsForReferal () = match getString(KEY_TOTAL_UNITS_FOR_REFERAL) { | |
440 | + | case a: String => | |
441 | + | parseBigIntValue(a) | |
442 | + | case _ => | |
443 | + | ZERO_BIGINT | |
444 | + | } | |
445 | + | ||
446 | + | ||
447 | + | func _saveTotalUnitsForReferal (value_) = [StringEntry(KEY_TOTAL_UNITS_FOR_REFERAL, toString(value_))] | |
448 | + | ||
449 | + | ||
450 | + | func _loadTotalSharesReferal () = match getString(KEY_TOTAL_SHARES_REFERAL) { | |
451 | + | case a: String => | |
452 | + | parseBigIntValue(a) | |
453 | + | case _ => | |
454 | + | ZERO_BIGINT | |
455 | + | } | |
456 | + | ||
457 | + | ||
458 | + | func _saveTotalSharesReferal (value_) = [StringEntry(KEY_TOTAL_SHARES_REFERAL, toString(value_))] | |
459 | + | ||
460 | + | ||
461 | + | func _loadUserUnitsPerReferalShareIntegral (user_) = match getString(makeString([KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL, user_], SEPARATOR)) { | |
462 | + | case a: String => | |
463 | + | parseBigIntValue(a) | |
464 | + | case _ => | |
465 | + | ZERO_BIGINT | |
466 | + | } | |
467 | + | ||
468 | + | ||
469 | + | func _saveUserUnitsPerReferalShareIntegral (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL, user_], SEPARATOR), toString(value_))] | |
470 | + | ||
471 | + | ||
472 | + | func _loadUserUnitsSharesReferal (user_) = match getString(makeString([KEY_USER_UNITS_SHARES_REFERAL, user_], SEPARATOR)) { | |
473 | + | case a: String => | |
474 | + | parseBigIntValue(a) | |
475 | + | case _ => | |
476 | + | ZERO_BIGINT | |
477 | + | } | |
478 | + | ||
479 | + | ||
480 | + | func _saveUserUnitsSharesReferal (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_SHARES_REFERAL, user_], SEPARATOR), toString(value_))] | |
481 | + | ||
482 | + | ||
483 | + | func _loadManager () = match getString(KEY_MANAGER) { | |
484 | + | case a: String => | |
485 | + | addressFromStringValue(a) | |
486 | + | case _ => | |
487 | + | Address(base58'') | |
488 | + | } | |
489 | + | ||
490 | + | ||
491 | + | func _saveManager (manager_) = [StringEntry(KEY_MANAGER, toString(manager_))] | |
492 | + | ||
493 | + | ||
494 | + | func _loadReferer (codehash_) = match getString(makeString([KEY_REFERER, codehash_], SEPARATOR)) { | |
495 | + | case a: String => | |
496 | + | a | |
497 | + | case _ => | |
498 | + | throw("_loadReferer: revert") | |
499 | + | } | |
500 | + | ||
501 | + | ||
502 | + | func _saveReferer (codehash_,address_) = [StringEntry(makeString([KEY_REFERER, codehash_], SEPARATOR), address_)] | |
503 | + | ||
504 | + | ||
505 | + | func _checkRefererExistence (codehash_) = match getString(makeString([KEY_REFERER, codehash_], SEPARATOR)) { | |
506 | + | case a: String => | |
507 | + | true | |
508 | + | case _ => | |
509 | + | false | |
510 | + | } | |
511 | + | ||
512 | + | ||
345 | 513 | func _onlyThisContract (caller_) = if ((caller_ != this)) | |
346 | 514 | then throw("_onlyThisContract: revert") | |
347 | 515 | else true | |
377 | 545 | else true | |
378 | 546 | ||
379 | 547 | ||
548 | + | func _onlyManager (caller_) = if ((caller_ != _loadManager())) | |
549 | + | then throw("_onlyManager: revert") | |
550 | + | else true | |
551 | + | ||
552 | + | ||
380 | 553 | func _validateExecutor (val_,err_) = if ((val_ != _loadExecutor())) | |
381 | 554 | then throw(err_) | |
382 | 555 | else true | |
398 | 571 | func _checkpoint () = { | |
399 | 572 | let prevUnitsPerUSDBalanceIntegral = _loadUnitsPerUSDBalanceIntegral() | |
400 | 573 | let prevCheckpointAt = max([_loadStartBlock(), _loadCheckpointAt()]) | |
401 | - | let prevUnitsBalance = _loadUnitsBalance() | |
574 | + | let prevUnitsBalanceDistributed = _loadUnitsBalanceDistributed() | |
575 | + | let prevUnitsPerReferalShareIntegral = _loadUnitsPerReferalShareIntegral() | |
576 | + | let prevUnitsSharesReferal = _loadUnitsSharesReferal() | |
402 | 577 | let currentBlock = min([toBigInt(height), _loadFinishBlock()]) | |
403 | 578 | if ((prevCheckpointAt >= currentBlock)) | |
404 | - | then $ | |
579 | + | then $Tuple3(nil, prevUnitsPerUSDBalanceIntegral, prevUnitsPerReferalShareIntegral) | |
405 | 580 | else { | |
406 | - | let unitsBalance = (_loadUnitsPerBlock() * (currentBlock - _loadStartBlock())) | |
407 | - | let unitsPerUSDBalanceIntegral = ((((PERCENT_FACTOR * (currentBlock - prevCheckpointAt)) * (unitsBalance - prevUnitsBalance)) / _loadTotalUSDBalance()) + prevUnitsPerUSDBalanceIntegral) | |
408 | - | $Tuple2(((_saveUnitsPerUSDBalanceIntegral(unitsPerUSDBalanceIntegral) ++ _saveCheckpointAt(currentBlock)) ++ _saveUnitsBalance(unitsBalance)), unitsPerUSDBalanceIntegral) | |
581 | + | let unitsBalanceToDistribute = fraction((_loadTotalUnitsForLP() - prevUnitsBalanceDistributed), (currentBlock - prevCheckpointAt), (_loadFinishBlock() - prevCheckpointAt)) | |
582 | + | let unitsPerUSDBalanceIntegral = (((PERCENT_FACTOR * unitsBalanceToDistribute) / _loadTotalUSDBalance()) + prevUnitsPerUSDBalanceIntegral) | |
583 | + | let $t01774818301 = if ((_loadTotalSharesReferal() > ZERO_BIGINT)) | |
584 | + | then { | |
585 | + | let unitsSharesReferal = fraction((_loadTotalUnitsForReferal() - prevUnitsSharesReferal), (currentBlock - prevCheckpointAt), (_loadFinishBlock() - prevCheckpointAt)) | |
586 | + | let unitsPerReferalShareIntegral = (((PERCENT_FACTOR * unitsSharesReferal) / _loadTotalSharesReferal()) + prevUnitsPerReferalShareIntegral) | |
587 | + | $Tuple2(unitsSharesReferal, unitsPerReferalShareIntegral) | |
588 | + | } | |
589 | + | else $Tuple2(ZERO_BIGINT, ZERO_BIGINT) | |
590 | + | let unitsSharesReferal = $t01774818301._1 | |
591 | + | let unitsPerReferalShareIntegral = $t01774818301._2 | |
592 | + | $Tuple3(((((_saveCheckpointAt(currentBlock) ++ _saveUnitsPerUSDBalanceIntegral(unitsPerUSDBalanceIntegral)) ++ _saveUnitsBalanceDistributed((unitsBalanceToDistribute + prevUnitsBalanceDistributed))) ++ _saveUnitsPerReferalShareIntegral(unitsPerReferalShareIntegral)) ++ _saveUnitsSharesReferal((unitsSharesReferal + prevUnitsSharesReferal))), unitsPerUSDBalanceIntegral, unitsPerReferalShareIntegral) | |
409 | 593 | } | |
410 | 594 | } | |
411 | 595 | ||
412 | 596 | ||
413 | - | func _userCheckpoint (user_,userUSDBalance_) = { | |
414 | - | let $t01275212819 = _checkpoint() | |
415 | - | let checkpointActions = $t01275212819._1 | |
416 | - | let unitsPerUSDBalanceIntegral = $t01275212819._2 | |
597 | + | func _userCheckpoint (user_,userUSDBalance_,userSharesReferal_) = { | |
598 | + | let $t01888718999 = _checkpoint() | |
599 | + | let checkpointActions = $t01888718999._1 | |
600 | + | let unitsPerUSDBalanceIntegral = $t01888718999._2 | |
601 | + | let unitsPerReferalShareIntegral = $t01888718999._3 | |
417 | 602 | let prevUserUnitsPerUSDBalanceIntegral = _loadUserUnitsPerUSDBalanceIntegral(user_) | |
418 | 603 | let prevUserCheckpointAt = max([_loadStartBlock(), _loadUserCheckpointAt(user_)]) | |
419 | - | let prevUserUnitsBalance = _loadUserUnitsBalance(user_) | |
604 | + | let prevUserUnitsBalanceDistributed = _loadUserUnitsBalanceDistributed(user_) | |
605 | + | let prevUserUnitsPerReferalShareIntegral = _loadUserUnitsPerReferalShareIntegral(user_) | |
606 | + | let prevUserUnitsSharesReferal = _loadUserUnitsSharesReferal(user_) | |
420 | 607 | let currentBlock = min([toBigInt(height), _loadFinishBlock()]) | |
421 | 608 | if ((prevUserCheckpointAt >= currentBlock)) | |
422 | - | then $ | |
609 | + | then $Tuple3(checkpointActions, prevUserUnitsBalanceDistributed, prevUserUnitsSharesReferal) | |
423 | 610 | else { | |
424 | - | let userUnitsBalance = ((((userUSDBalance_ * (unitsPerUSDBalanceIntegral - prevUserUnitsPerUSDBalanceIntegral)) / (currentBlock - prevUserCheckpointAt)) / PERCENT_FACTOR) + prevUserUnitsBalance) | |
425 | - | $Tuple2((((checkpointActions ++ _saveUserUnitsPerUSDBalanceIntegral(user_, unitsPerUSDBalanceIntegral)) ++ _saveUserCheckpointAt(user_, currentBlock)) ++ _saveUserUnitsBalance(user_, userUnitsBalance)), userUnitsBalance) | |
611 | + | let userUnitsBalanceDistributed = (((userUSDBalance_ * (unitsPerUSDBalanceIntegral - prevUserUnitsPerUSDBalanceIntegral)) / PERCENT_FACTOR) + prevUserUnitsBalanceDistributed) | |
612 | + | let userUnitsSharesReferal = (((userSharesReferal_ * (unitsPerReferalShareIntegral - prevUserUnitsPerReferalShareIntegral)) / PERCENT_FACTOR) + prevUserUnitsSharesReferal) | |
613 | + | $Tuple3((((((checkpointActions ++ _saveUserCheckpointAt(user_, currentBlock)) ++ _saveUserUnitsPerUSDBalanceIntegral(user_, unitsPerUSDBalanceIntegral)) ++ _saveUserUnitsBalanceDistributed(user_, userUnitsBalanceDistributed)) ++ _saveUserUnitsPerReferalShareIntegral(user_, unitsPerReferalShareIntegral)) ++ _saveUserUnitsSharesReferal(user_, userUnitsSharesReferal)), userUnitsBalanceDistributed, userUnitsSharesReferal) | |
426 | 614 | } | |
427 | 615 | } | |
428 | 616 | ||
464 | 652 | if ((err == err)) | |
465 | 653 | then { | |
466 | 654 | let rate = _getTokenRate(token_) | |
467 | - | let $ | |
468 | - | let userTokenBalance = $ | |
469 | - | let userTokenBalanceInUSD = $ | |
655 | + | let $t02192622008 = _loadUserPosition(token_, sender_) | |
656 | + | let userTokenBalance = $t02192622008._1 | |
657 | + | let userTokenBalanceInUSD = $t02192622008._2 | |
470 | 658 | let userUSDBalance = _loadUserUSDBalance(sender_) | |
471 | - | let $t01525315337 = _userCheckpoint(sender_, userUSDBalance) | |
472 | - | let checkpointActions = $t01525315337._1 | |
473 | - | let userUnitsBalance = $t01525315337._2 | |
659 | + | let userSharesReferal = _loadUserSharesReferal(sender_) | |
660 | + | let $t02212722254 = _userCheckpoint(sender_, userUSDBalance, userSharesReferal) | |
661 | + | let checkpointActions = $t02212722254._1 | |
662 | + | let userUnitsBalance = $t02212722254._2 | |
663 | + | let userUnitsSharesReferal = $t02212722254._3 | |
474 | 664 | let newUserTokenBalance = (userTokenBalance + toBigInt(amount)) | |
475 | 665 | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
476 | 666 | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
477 | 667 | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
478 | - | $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
668 | + | let usersCount = if ((userUSDBalance == ZERO_BIGINT)) | |
669 | + | then (_loadUsersCount() + ONE_BIGINT) | |
670 | + | else _loadUsersCount() | |
671 | + | let refererActions = if (if ((size(referrer_) > 0)) | |
672 | + | then _checkRefererExistence(referrer_) | |
673 | + | else false) | |
674 | + | then { | |
675 | + | let refererAddress = _loadReferer(referrer_) | |
676 | + | let sharesToDistribute = fraction(toBigInt(amount), rate, PERCENT_FACTOR, DOWN) | |
677 | + | let sharesToUser = fraction(sharesToDistribute, toBigInt(20), toBigInt(100), DOWN) | |
678 | + | let sharesToReferer = (sharesToDistribute - sharesToUser) | |
679 | + | let newUserSharesReferal = (userSharesReferal + sharesToUser) | |
680 | + | let refererSharesReferal = _loadUserSharesReferal(refererAddress) | |
681 | + | let newRefererSharesReferal = (refererSharesReferal + sharesToReferer) | |
682 | + | let newTotalSharesReferal = (_loadTotalSharesReferal() + sharesToDistribute) | |
683 | + | let $t02358723758 = _userCheckpoint(refererAddress, _loadUserUSDBalance(refererAddress), refererSharesReferal) | |
684 | + | let refererCheckpointActions = $t02358723758._1 | |
685 | + | let refererUnitsBalance = $t02358723758._2 | |
686 | + | let refererUnitsSharesReferal = $t02358723758._3 | |
687 | + | (((refererCheckpointActions ++ _saveUserSharesReferal(sender_, newUserSharesReferal)) ++ _saveUserSharesReferal(refererAddress, newRefererSharesReferal)) ++ _saveTotalSharesReferal(newTotalSharesReferal)) | |
688 | + | } | |
689 | + | else nil | |
690 | + | $Tuple2(((((((checkpointActions ++ refererActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUsersCount(usersCount)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
479 | 691 | } | |
480 | 692 | else throw("Strict value is not equal to itself.") | |
481 | 693 | } | |
483 | 695 | ||
484 | 696 | ||
485 | 697 | @Callable(i) | |
486 | - | func withdraw (callerContract_,sender_,token_,amount_) = { | |
487 | - | let amount = valueOrErrorMessage(parseInt(amount_), "withdraw: amount is not Int") | |
488 | - | let err = if (if (if (if (_whenInitialized()) | |
489 | - | then _whenNotPaused() | |
490 | - | else false) | |
491 | - | then _validateExecutor(i.caller, "withdraw: invalid executor") | |
492 | - | else false) | |
493 | - | then _validateCaller(callerContract_, "withdraw: invalid caller") | |
494 | - | else false) | |
495 | - | then _validateInt(amount, 0, MAX_INT, "withdraw: invalid amount") | |
496 | - | else false | |
497 | - | if ((err == err)) | |
498 | - | then { | |
499 | - | let rate = _getTokenRate(token_) | |
500 | - | let $t01659516677 = _loadUserPosition(token_, sender_) | |
501 | - | let userTokenBalance = $t01659516677._1 | |
502 | - | let userTokenBalanceInUSD = $t01659516677._2 | |
503 | - | let userUSDBalance = _loadUserUSDBalance(sender_) | |
504 | - | let $t01673616820 = _userCheckpoint(sender_, userUSDBalance) | |
505 | - | let checkpointActions = $t01673616820._1 | |
506 | - | let userUnitsBalance = $t01673616820._2 | |
507 | - | let newUserTokenBalance = (userTokenBalance - toBigInt(amount)) | |
508 | - | let err1 = _validateInt(toInt(newUserTokenBalance), 0, MAX_INT, "withdraw: insufficient token amount") | |
509 | - | if ((err1 == err1)) | |
510 | - | then { | |
511 | - | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
512 | - | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
513 | - | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
514 | - | $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) - toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), unit) | |
515 | - | } | |
516 | - | else throw("Strict value is not equal to itself.") | |
517 | - | } | |
518 | - | else throw("Strict value is not equal to itself.") | |
519 | - | } | |
520 | - | ||
521 | - | ||
522 | - | ||
523 | - | @Callable(i) | |
524 | - | func depositWaves () = { | |
698 | + | func depositWaves (referrer_) = { | |
525 | 699 | let err = if (if (if (if (_whenInitialized()) | |
526 | 700 | then _whenNotPaused() | |
527 | 701 | else false) | |
529 | 703 | else false) | |
530 | 704 | then _validateWavesPayment(i.payments[0], "depositWaves: invalid asset") | |
531 | 705 | else false) | |
532 | - | then _validateInt(i.payments[0].amount, 0, MAX_INT, "depositWaves: invalid amount") | |
706 | + | then _validateInt((i.payments[0].amount / 100), 0, MAX_INT, "depositWaves: invalid amount") | |
533 | 707 | else false | |
534 | 708 | if ((err == err)) | |
535 | 709 | then { | |
536 | - | let amount = i.payments[0].amount | |
710 | + | let amount = (i.payments[0].amount / 100) | |
537 | 711 | let sender = toString(i.caller) | |
538 | 712 | let token = WAVES | |
539 | 713 | let rate = _getTokenRate(token) | |
540 | - | let $ | |
541 | - | let userTokenBalance = $ | |
542 | - | let userTokenBalanceInUSD = $ | |
714 | + | let $t02663326713 = _loadUserPosition(token, sender) | |
715 | + | let userTokenBalance = $t02663326713._1 | |
716 | + | let userTokenBalanceInUSD = $t02663326713._2 | |
543 | 717 | let userUSDBalance = _loadUserUSDBalance(sender) | |
544 | - | let $t01827018353 = _userCheckpoint(sender, userUSDBalance) | |
545 | - | let checkpointActions = $t01827018353._1 | |
546 | - | let userUnitsBalance = $t01827018353._2 | |
718 | + | let userSharesReferal = _loadUserSharesReferal(sender) | |
719 | + | let $t02683026956 = _userCheckpoint(sender, userUSDBalance, userSharesReferal) | |
720 | + | let checkpointActions = $t02683026956._1 | |
721 | + | let userUnitsBalance = $t02683026956._2 | |
722 | + | let userUnitsSharesReferal = $t02683026956._3 | |
547 | 723 | let newUserTokenBalance = (userTokenBalance + toBigInt(amount)) | |
548 | 724 | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
549 | 725 | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
550 | 726 | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
551 | - | let invocation = invoke(_loadSWavesContract(), FUNC_DEPOSIT, nil, [AttachedPayment(unit, amount)]) | |
727 | + | let usersCount = if ((userUSDBalance == ZERO_BIGINT)) | |
728 | + | then (_loadUsersCount() + ONE_BIGINT) | |
729 | + | else _loadUsersCount() | |
730 | + | let refererActions = if (if ((size(referrer_) > 0)) | |
731 | + | then _checkRefererExistence(referrer_) | |
732 | + | else false) | |
733 | + | then { | |
734 | + | let refererAddress = _loadReferer(referrer_) | |
735 | + | let sharesToDistribute = fraction(toBigInt(amount), rate, PERCENT_FACTOR, DOWN) | |
736 | + | let sharesToUser = fraction(sharesToDistribute, toBigInt(20), toBigInt(100), DOWN) | |
737 | + | let sharesToReferer = (sharesToDistribute - sharesToUser) | |
738 | + | let newUserSharesReferal = (userSharesReferal + sharesToUser) | |
739 | + | let refererSharesReferal = _loadUserSharesReferal(refererAddress) | |
740 | + | let newRefererSharesReferal = (refererSharesReferal + sharesToReferer) | |
741 | + | let newTotalSharesReferal = (_loadTotalSharesReferal() + sharesToDistribute) | |
742 | + | let $t02828928460 = _userCheckpoint(refererAddress, _loadUserUSDBalance(refererAddress), refererSharesReferal) | |
743 | + | let refererCheckpointActions = $t02828928460._1 | |
744 | + | let refererUnitsBalance = $t02828928460._2 | |
745 | + | let refererUnitsSharesReferal = $t02828928460._3 | |
746 | + | (((refererCheckpointActions ++ _saveUserSharesReferal(sender, newUserSharesReferal)) ++ _saveUserSharesReferal(refererAddress, newRefererSharesReferal)) ++ _saveTotalSharesReferal(newTotalSharesReferal)) | |
747 | + | } | |
748 | + | else nil | |
749 | + | let invocation = invoke(_loadSWavesContract(), FUNC_DEPOSIT, nil, [AttachedPayment(unit, i.payments[0].amount)]) | |
552 | 750 | if ((invocation == invocation)) | |
553 | - | then $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
751 | + | then $Tuple2(((((((checkpointActions ++ refererActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUsersCount(usersCount)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
554 | 752 | else throw("Strict value is not equal to itself.") | |
555 | 753 | } | |
556 | 754 | else throw("Strict value is not equal to itself.") | |
560 | 758 | ||
561 | 759 | @Callable(i) | |
562 | 760 | func withdrawWaves (amount_) = { | |
563 | - | let err = if (if (_whenInitialized()) | |
761 | + | let err = if (if (if (_whenInitialized()) | |
564 | 762 | then _whenNotPaused() | |
565 | 763 | else false) | |
566 | - | then _validateInt(amount_, 0, MAX_INT, "withdrawWaves: invalid amount") | |
764 | + | then _validateInt((amount_ / 100), 0, MAX_INT, "withdrawWaves: invalid amount") | |
765 | + | else false) | |
766 | + | then if ((_loadFinishBlock() >= toBigInt(height))) | |
767 | + | then throw("withdrawWaves: not allowed") | |
768 | + | else true | |
567 | 769 | else false | |
568 | 770 | if ((err == err)) | |
569 | 771 | then { | |
772 | + | let internalAmount = (amount_ / 100) | |
570 | 773 | let sender = toString(i.caller) | |
571 | 774 | let token = WAVES | |
572 | 775 | let rate = _getTokenRate(token) | |
573 | - | let $ | |
574 | - | let userTokenBalance = $ | |
575 | - | let userTokenBalanceInUSD = $ | |
776 | + | let $t02972829808 = _loadUserPosition(token, sender) | |
777 | + | let userTokenBalance = $t02972829808._1 | |
778 | + | let userTokenBalanceInUSD = $t02972829808._2 | |
576 | 779 | let userUSDBalance = _loadUserUSDBalance(sender) | |
577 | - | let $t01962619709 = _userCheckpoint(sender, userUSDBalance) | |
578 | - | let checkpointActions = $t01962619709._1 | |
579 | - | let userUnitsBalance = $t01962619709._2 | |
580 | - | let newUserTokenBalance = (userTokenBalance - toBigInt(amount_)) | |
780 | + | let userSharesReferal = _loadUserSharesReferal(sender) | |
781 | + | let $t02992530051 = _userCheckpoint(sender, userUSDBalance, userSharesReferal) | |
782 | + | let checkpointActions = $t02992530051._1 | |
783 | + | let userUnitsBalance = $t02992530051._2 | |
784 | + | let userUnitsSharesReferal = $t02992530051._3 | |
785 | + | let newUserTokenBalance = (userTokenBalance - toBigInt(internalAmount)) | |
581 | 786 | let err1 = _validateInt(toInt(newUserTokenBalance), 0, MAX_INT, "withdrawWaves: insufficient token amount") | |
582 | 787 | if ((err1 == err1)) | |
583 | 788 | then { | |
596 | 801 | let sWavesToWithdraw = toInt(fraction(toBigInt(amount_), SWAVES_RATE_FACTOR, swavesRate, CEILING)) | |
597 | 802 | let invocation1 = invoke(sWavesContract, FUNC_WITHDRAW, nil, [AttachedPayment(sWavesAsset, sWavesToWithdraw)]) | |
598 | 803 | if ((invocation1 == invocation1)) | |
599 | - | then $Tuple2(((((([ScriptTransfer(i.caller, amount_, unit)] ++ checkpointActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) - toBigInt( | |
804 | + | then $Tuple2(((((([ScriptTransfer(i.caller, amount_, unit)] ++ checkpointActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) - toBigInt(internalAmount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), unit) | |
600 | 805 | else throw("Strict value is not equal to itself.") | |
601 | 806 | } | |
602 | 807 | else throw("Strict value is not equal to itself.") | |
607 | 812 | ||
608 | 813 | ||
609 | 814 | @Callable(i) | |
610 | - | func startRetrodrop ( | |
611 | - | let err = if (if (if (if (if (_onlyThisContract(i.caller)) | |
815 | + | func startRetrodrop (unitsAsset_,amountForLP_,amountForReferal_,blocksAt_) = { | |
816 | + | let err = if (if (if (if (if (if (if (_onlyThisContract(i.caller)) | |
612 | 817 | then _whenInitialized() | |
613 | 818 | else false) | |
614 | 819 | then _whenNotPaused() | |
615 | 820 | else false) | |
616 | - | then _validateInt(amount_, 1, MAX_INT, "startRetrodrop: invalid amount") | |
821 | + | then _validateAsset(unitsAsset_, "startRetrodrop: invalid units asset") | |
822 | + | else false) | |
823 | + | then _validateInt(amountForLP_, 0, MAX_INT, "startRetrodrop: invalid amountForLP") | |
824 | + | else false) | |
825 | + | then _validateInt(amountForReferal_, 0, MAX_INT, "startRetrodrop: invalid amountForReferal") | |
617 | 826 | else false) | |
618 | 827 | then _validateInt(blocksAt_, 1, MAX_INT, "startRetrodrop: invalid blocksAt") | |
619 | 828 | else false) | |
623 | 832 | then { | |
624 | 833 | let startHeight = toBigInt(height) | |
625 | 834 | let finishHeight = (startHeight + toBigInt(blocksAt_)) | |
626 | - | let unitsPerBlock = fraction(toBigInt(amount_), PERCENT_FACTOR, toBigInt(blocksAt_)) | |
627 | - | $Tuple2(((_saveStartBlock(startHeight) ++ _saveFinishBlock(finishHeight)) ++ _saveUnitsPerBlock(unitsPerBlock)), unit) | |
835 | + | let err1 = if (((amountForLP_ + amountForReferal_) > assetBalance(this, fromBase58String(unitsAsset_)))) | |
836 | + | then throw("startRetrodrop: insufficient funds") | |
837 | + | else true | |
838 | + | if ((err1 == err1)) | |
839 | + | then $Tuple2(((((_saveUnitsAsset(fromBase58String(unitsAsset_)) ++ _saveStartBlock(startHeight)) ++ _saveFinishBlock(finishHeight)) ++ _saveTotalUnitsForLP(toBigInt(amountForLP_))) ++ _saveTotalUnitsForReferal(toBigInt(amountForReferal_))), unit) | |
840 | + | else throw("Strict value is not equal to itself.") | |
628 | 841 | } | |
629 | 842 | else throw("Strict value is not equal to itself.") | |
630 | 843 | } | |
632 | 845 | ||
633 | 846 | ||
634 | 847 | @Callable(i) | |
848 | + | func increaseUnitsSupply (amountForLP_,amountForReferal_) = { | |
849 | + | let err = if (if (if (if (_whenInitialized()) | |
850 | + | then _whenNotPaused() | |
851 | + | else false) | |
852 | + | then _validateInt(amountForLP_, 0, MAX_INT, "increaseUnitsSupply: invalid amountForLP") | |
853 | + | else false) | |
854 | + | then _validateInt(amountForReferal_, 0, MAX_INT, "increaseUnitsSupply: invalid amountForReferal") | |
855 | + | else false) | |
856 | + | then _validateBigInt(toBigInt(height), (_loadStartBlock() + ONE_BIGINT), (_loadFinishBlock() - ONE_BIGINT), "increaseUnitsSupply: drop not active") | |
857 | + | else false | |
858 | + | if ((err == err)) | |
859 | + | then { | |
860 | + | let newAmountForLP = (_loadTotalUnitsForLP() + toBigInt(amountForLP_)) | |
861 | + | let newAmountForReferal = (_loadTotalUnitsForReferal() + toBigInt(amountForReferal_)) | |
862 | + | let err1 = if (((newAmountForLP + newAmountForReferal) > toBigInt(assetBalance(this, _loadUnitsAsset())))) | |
863 | + | then throw("increaseUnitsSupply: insufficient funds") | |
864 | + | else true | |
865 | + | if ((err1 == err1)) | |
866 | + | then $Tuple2((_saveTotalUnitsForLP(newAmountForLP) ++ _saveTotalUnitsForReferal(newAmountForReferal)), unit) | |
867 | + | else throw("Strict value is not equal to itself.") | |
868 | + | } | |
869 | + | else throw("Strict value is not equal to itself.") | |
870 | + | } | |
871 | + | ||
872 | + | ||
873 | + | ||
874 | + | @Callable(i) | |
875 | + | func checkpoint (user_) = { | |
876 | + | let $t03382033959 = _userCheckpoint(user_, _loadUserUSDBalance(user_), _loadUserSharesReferal(user_)) | |
877 | + | let actions = $t03382033959._1 | |
878 | + | let userUnitsBalance = $t03382033959._2 | |
879 | + | let userUnitsSharesReferal = $t03382033959._3 | |
880 | + | $Tuple2(actions, $Tuple2(userUnitsBalance, userUnitsSharesReferal)) | |
881 | + | } | |
882 | + | ||
883 | + | ||
884 | + | ||
885 | + | @Callable(i) | |
635 | 886 | func getUnits (user_) = { | |
636 | - | let $t02197822062 = _userCheckpoint(user_, _loadUserUSDBalance(user_)) | |
637 | - | let actions = $t02197822062._1 | |
638 | - | let userUnitsBalance = $t02197822062._2 | |
639 | - | $Tuple2(nil, userUnitsBalance) | |
887 | + | let $t03407234211 = _userCheckpoint(user_, _loadUserUSDBalance(user_), _loadUserSharesReferal(user_)) | |
888 | + | let actions = $t03407234211._1 | |
889 | + | let userUnitsBalance = $t03407234211._2 | |
890 | + | let userUnitsSharesReferal = $t03407234211._3 | |
891 | + | $Tuple2(nil, $Tuple2(userUnitsBalance, userUnitsSharesReferal)) | |
892 | + | } | |
893 | + | ||
894 | + | ||
895 | + | ||
896 | + | @Callable(i) | |
897 | + | func setReferer (codehash_,address_) = { | |
898 | + | let err = if (_onlyManager(i.caller)) | |
899 | + | then _whenInitialized() | |
900 | + | else false | |
901 | + | if ((err == err)) | |
902 | + | then $Tuple2(_saveReferer(codehash_, address_), unit) | |
903 | + | else throw("Strict value is not equal to itself.") | |
904 | + | } | |
905 | + | ||
906 | + | ||
907 | + | ||
908 | + | @Callable(i) | |
909 | + | func setManager (manager_) = { | |
910 | + | let err = if (if (_onlyThisContract(i.caller)) | |
911 | + | then _whenInitialized() | |
912 | + | else false) | |
913 | + | then _validateAddress(manager_, "setManager: invalid manager") | |
914 | + | else false | |
915 | + | if ((err == err)) | |
916 | + | then $Tuple2(_saveManager(addressFromStringValue(manager_)), unit) | |
917 | + | else throw("Strict value is not equal to itself.") | |
640 | 918 | } | |
641 | 919 | ||
642 | 920 |
Old | New | Differences | |
---|---|---|---|
1 | 1 | {-# STDLIB_VERSION 6 #-} | |
2 | 2 | {-# SCRIPT_TYPE ACCOUNT #-} | |
3 | 3 | {-# CONTENT_TYPE DAPP #-} | |
4 | 4 | let SEPARATOR = "__" | |
5 | 5 | ||
6 | 6 | let WAVES = "WAVES" | |
7 | 7 | ||
8 | 8 | let KEY_MULTISIG = "MULTISIG" | |
9 | 9 | ||
10 | 10 | let KEY_STATUS = "STATUS" | |
11 | 11 | ||
12 | 12 | let KEY_INIT = "INIT" | |
13 | 13 | ||
14 | 14 | let KEY_PAUSED = "PAUSED" | |
15 | 15 | ||
16 | 16 | let KEY_PAUSER = "PAUSER" | |
17 | 17 | ||
18 | + | let KEY_MANAGER = "MANAGER" | |
19 | + | ||
20 | + | let KEY_REFERER = "REFERER" | |
21 | + | ||
18 | 22 | let KEY_EXECUTOR = "EXECUTOR" | |
19 | 23 | ||
20 | 24 | let KEY_ORACLE = "ORACLE" | |
21 | 25 | ||
22 | 26 | let KEY_CALLER_CONTRACT = "CALLER_CONTRACT" | |
23 | 27 | ||
24 | 28 | let KEY_PRICE = "PRICE" | |
25 | 29 | ||
30 | + | let KEY_UNITS_ASSET = "UNITS_ASSET" | |
31 | + | ||
26 | 32 | let KEY_USER_POSITION = "USER_POSITION" | |
27 | 33 | ||
28 | 34 | let KEY_USER_USD_BALANCE = "USER_USD_BALANCE" | |
29 | 35 | ||
30 | 36 | let KEY_USER_UNITS_PER_USD_BALANCE_INTEGRAL = "USER_UNITS_PER_USD_BALANCE_INTEGRAL" | |
31 | 37 | ||
38 | + | let KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL = "USER_UNITS_PER_REFERAL_SHARE_INTEGRAL" | |
39 | + | ||
32 | 40 | let KEY_USER_CHECKPOINT_AT = "USER_CHECKPOINT_AT" | |
33 | 41 | ||
34 | - | let KEY_USER_UNITS_BALANCE = "USER_UNITS_BALANCE" | |
42 | + | let KEY_USER_UNITS_BALANCE_DISTRIBUTED = "USER_UNITS_BALANCE_DISTRIBUTED" | |
43 | + | ||
44 | + | let KEY_USER_UNITS_SHARES_REFERAL = "USER_UNITS_SHARES_REFERAL" | |
45 | + | ||
46 | + | let KEY_USER_SHARES_REFERAL = "USER_SHARES_REFERAL" | |
35 | 47 | ||
36 | 48 | let KEY_START_BLOCK = "START_BLOCK" | |
37 | 49 | ||
38 | 50 | let KEY_FINISH_BLOCK = "FINISH_BLOCK" | |
39 | 51 | ||
40 | - | let KEY_UNITS_PER_BLOCK = "UNITS_PER_BLOCK" | |
52 | + | let KEY_TOTAL_UNITS_FOR_LP = "TOTAL_UNITS_FOR_LP" | |
53 | + | ||
54 | + | let KEY_TOTAL_UNITS_FOR_REFERAL = "TOTAL_UNITS_FOR_REFERAL" | |
41 | 55 | ||
42 | 56 | let KEY_TOTAL_USD_BALANCE = "TOTAL_USD_BALANCE" | |
43 | 57 | ||
44 | 58 | let KEY_UNITS_PER_USD_BALANCE_INTEGRAL = "UNITS_PER_USD_BALANCE_INTEGRAL" | |
45 | 59 | ||
46 | 60 | let KEY_CHECKPOINT_AT = "CHECKPOINT_AT" | |
47 | 61 | ||
48 | - | let KEY_UNITS_BALANCE = "UNITS_BALANCE" | |
62 | + | let KEY_UNITS_BALANCE_DISTRIBUTED = "UNITS_BALANCE_DISTRIBUTED" | |
49 | 63 | ||
50 | 64 | let KEY_TOKEN_BALANCE = "TOKEN_BALANCE" | |
65 | + | ||
66 | + | let KEY_USERS_COUNT = "USERS_COUNT" | |
67 | + | ||
68 | + | let KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL = "UNITS_PER_REFERAL_SHARE_INTEGRAL" | |
69 | + | ||
70 | + | let KEY_UNITS_SHARES_REFERAL = "UNITS_SHARES_REFERAL" | |
71 | + | ||
72 | + | let KEY_TOTAL_SHARES_REFERAL = "TOTAL_SHARES_REFERAL" | |
51 | 73 | ||
52 | 74 | let KEY_SWAVES_CONTRACT = "SWAVES_CONTRACT" | |
53 | 75 | ||
54 | 76 | let KEY_SWAVES_ASSET = "ASSET" | |
55 | 77 | ||
56 | 78 | let FUNC_DEPOSIT = "deposit" | |
57 | 79 | ||
58 | 80 | let FUNC_GET_RATE = "getRate" | |
59 | 81 | ||
60 | 82 | let FUNC_WITHDRAW = "withdraw" | |
61 | 83 | ||
62 | 84 | let MAX_INT = 9223372036854775807 | |
63 | 85 | ||
64 | 86 | let PERCENT_FACTOR = toBigInt(1000000000000) | |
65 | 87 | ||
66 | 88 | let ZERO_BIGINT = toBigInt(0) | |
67 | 89 | ||
90 | + | let ONE_BIGINT = toBigInt(1) | |
91 | + | ||
68 | 92 | let SWAVES_RATE_FACTOR = toBigInt(1000000000000) | |
69 | 93 | ||
70 | 94 | func _validateAddress (address_,err_) = match addressFromString(address_) { | |
71 | 95 | case a: Address => | |
72 | 96 | true | |
73 | 97 | case _ => | |
74 | 98 | throw(err_) | |
75 | 99 | } | |
76 | 100 | ||
77 | 101 | ||
78 | 102 | func _validateInt (val_,lowerBoundary_,upperBoundary_,err_) = if (if ((lowerBoundary_ > val_)) | |
103 | + | then true | |
104 | + | else (val_ > upperBoundary_)) | |
105 | + | then throw(err_) | |
106 | + | else true | |
107 | + | ||
108 | + | ||
109 | + | func _validateBigInt (val_,lowerBoundary_,upperBoundary_,err_) = if (if ((lowerBoundary_ > val_)) | |
79 | 110 | then true | |
80 | 111 | else (val_ > upperBoundary_)) | |
81 | 112 | then throw(err_) | |
82 | 113 | else true | |
83 | 114 | ||
84 | 115 | ||
85 | 116 | func _validatePaymentsSize (payments_,target_,err_) = if ((size(payments_) != target_)) | |
86 | 117 | then throw(err_) | |
87 | 118 | else true | |
88 | 119 | ||
89 | 120 | ||
90 | 121 | func _validateWavesPayment (payment_,err_) = match payment_.assetId { | |
91 | 122 | case a: ByteVector => | |
92 | 123 | throw(err_) | |
93 | 124 | case _: Unit => | |
94 | 125 | true | |
95 | 126 | case _ => | |
96 | 127 | throw("Match error") | |
97 | 128 | } | |
98 | 129 | ||
99 | 130 | ||
100 | 131 | func _validateEqBigInt (val1_,val2_,err_) = if ((val1_ != val2_)) | |
101 | 132 | then throw(err_) | |
102 | 133 | else true | |
134 | + | ||
135 | + | ||
136 | + | func _validateAsset (asset_,err_) = match assetInfo(fromBase58String(asset_)) { | |
137 | + | case a: Asset => | |
138 | + | true | |
139 | + | case _ => | |
140 | + | throw(err_) | |
141 | + | } | |
103 | 142 | ||
104 | 143 | ||
105 | 144 | func _loadInit () = match getBoolean(KEY_INIT) { | |
106 | 145 | case a: Boolean => | |
107 | 146 | a | |
108 | 147 | case _ => | |
109 | 148 | false | |
110 | 149 | } | |
111 | 150 | ||
112 | 151 | ||
113 | 152 | func _saveInit (isInit_) = [BooleanEntry(KEY_INIT, isInit_)] | |
114 | 153 | ||
115 | 154 | ||
116 | 155 | func _loadPause () = match getBoolean(KEY_PAUSED) { | |
117 | 156 | case a: Boolean => | |
118 | 157 | a | |
119 | 158 | case _ => | |
120 | 159 | false | |
121 | 160 | } | |
122 | 161 | ||
123 | 162 | ||
124 | 163 | func _savePause (isPaused_) = [BooleanEntry(KEY_PAUSED, isPaused_)] | |
125 | 164 | ||
126 | 165 | ||
127 | 166 | func _loadPauser () = match getString(KEY_PAUSER) { | |
128 | 167 | case a: String => | |
129 | 168 | addressFromStringValue(a) | |
130 | 169 | case _ => | |
131 | 170 | Address(base58'') | |
132 | 171 | } | |
133 | 172 | ||
134 | 173 | ||
135 | 174 | func _savePauser (pauser_) = [StringEntry(KEY_PAUSER, toString(pauser_))] | |
136 | 175 | ||
137 | 176 | ||
138 | 177 | func _loadMultisig () = match getString(KEY_MULTISIG) { | |
139 | 178 | case a: String => | |
140 | 179 | addressFromStringValue(a) | |
141 | 180 | case _ => | |
142 | 181 | Address(base58'') | |
143 | 182 | } | |
144 | 183 | ||
145 | 184 | ||
146 | 185 | func _saveMultisig (multisig_) = [StringEntry(KEY_MULTISIG, toString(multisig_))] | |
147 | 186 | ||
148 | 187 | ||
149 | 188 | func _loadExecutor () = match getString(KEY_EXECUTOR) { | |
150 | 189 | case a: String => | |
151 | 190 | addressFromStringValue(a) | |
152 | 191 | case _ => | |
153 | 192 | Address(base58'') | |
154 | 193 | } | |
155 | 194 | ||
156 | 195 | ||
157 | 196 | func _saveExecutor (executor_) = [StringEntry(KEY_EXECUTOR, toString(executor_))] | |
158 | 197 | ||
159 | 198 | ||
160 | 199 | func _loadOracle () = match getString(KEY_ORACLE) { | |
161 | 200 | case a: String => | |
162 | 201 | addressFromStringValue(a) | |
163 | 202 | case _ => | |
164 | 203 | Address(base58'') | |
165 | 204 | } | |
166 | 205 | ||
167 | 206 | ||
168 | 207 | func _saveOracle (oracle_) = [StringEntry(KEY_ORACLE, toString(oracle_))] | |
169 | 208 | ||
170 | 209 | ||
171 | 210 | func _loadCallerContract () = match getString(KEY_CALLER_CONTRACT) { | |
172 | 211 | case a: String => | |
173 | 212 | a | |
174 | 213 | case _ => | |
175 | 214 | "" | |
176 | 215 | } | |
177 | 216 | ||
178 | 217 | ||
179 | 218 | func _saveCallerContract (caller_) = [StringEntry(KEY_CALLER_CONTRACT, caller_)] | |
180 | 219 | ||
181 | 220 | ||
182 | 221 | func _loadUserPosition (token_,user_) = match getString(makeString([KEY_USER_POSITION, token_, user_], SEPARATOR)) { | |
183 | 222 | case a: String => | |
184 | 223 | let struct = split_51C(a, SEPARATOR) | |
185 | 224 | $Tuple2(parseBigIntValue(struct[0]), parseBigIntValue(struct[1])) | |
186 | 225 | case _ => | |
187 | 226 | $Tuple2(ZERO_BIGINT, ZERO_BIGINT) | |
188 | 227 | } | |
189 | 228 | ||
190 | 229 | ||
191 | 230 | func _saveUserPosition (token_,user_,position_) = [StringEntry(makeString([KEY_USER_POSITION, token_, user_], SEPARATOR), makeString_11C([toString(position_._1), toString(position_._2)], SEPARATOR))] | |
192 | 231 | ||
193 | 232 | ||
194 | 233 | func _loadUserUSDBalance (user_) = match getString(makeString([KEY_USER_USD_BALANCE, user_], SEPARATOR)) { | |
195 | 234 | case a: String => | |
196 | 235 | parseBigIntValue(a) | |
197 | 236 | case _ => | |
198 | 237 | ZERO_BIGINT | |
199 | 238 | } | |
200 | 239 | ||
201 | 240 | ||
202 | 241 | func _saveUserUSDBalance (user_,value_) = [StringEntry(makeString([KEY_USER_USD_BALANCE, user_], SEPARATOR), toString(value_))] | |
203 | 242 | ||
204 | 243 | ||
244 | + | func _loadUserSharesReferal (user_) = match getString(makeString([KEY_USER_SHARES_REFERAL, user_], SEPARATOR)) { | |
245 | + | case a: String => | |
246 | + | parseBigIntValue(a) | |
247 | + | case _ => | |
248 | + | ZERO_BIGINT | |
249 | + | } | |
250 | + | ||
251 | + | ||
252 | + | func _saveUserSharesReferal (user_,value_) = [StringEntry(makeString([KEY_USER_SHARES_REFERAL, user_], SEPARATOR), toString(value_))] | |
253 | + | ||
254 | + | ||
205 | 255 | func _loadUnitsPerUSDBalanceIntegral () = match getString(KEY_UNITS_PER_USD_BALANCE_INTEGRAL) { | |
206 | 256 | case a: String => | |
207 | 257 | parseBigIntValue(a) | |
208 | 258 | case _ => | |
209 | 259 | ZERO_BIGINT | |
210 | 260 | } | |
211 | 261 | ||
212 | 262 | ||
213 | 263 | func _saveUnitsPerUSDBalanceIntegral (value_) = [StringEntry(KEY_UNITS_PER_USD_BALANCE_INTEGRAL, toString(value_))] | |
214 | 264 | ||
215 | 265 | ||
216 | 266 | func _loadUserUnitsPerUSDBalanceIntegral (user_) = match getString(makeString([KEY_USER_UNITS_PER_USD_BALANCE_INTEGRAL, user_], SEPARATOR)) { | |
217 | 267 | case a: String => | |
218 | 268 | parseBigIntValue(a) | |
219 | 269 | case _ => | |
220 | 270 | ZERO_BIGINT | |
221 | 271 | } | |
222 | 272 | ||
223 | 273 | ||
224 | 274 | func _saveUserUnitsPerUSDBalanceIntegral (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_PER_USD_BALANCE_INTEGRAL, user_], SEPARATOR), toString(value_))] | |
225 | 275 | ||
226 | 276 | ||
227 | 277 | func _loadCheckpointAt () = match getString(KEY_CHECKPOINT_AT) { | |
228 | 278 | case a: String => | |
229 | 279 | parseBigIntValue(a) | |
230 | 280 | case _ => | |
231 | 281 | ZERO_BIGINT | |
232 | 282 | } | |
233 | 283 | ||
234 | 284 | ||
235 | 285 | func _saveCheckpointAt (value_) = [StringEntry(KEY_CHECKPOINT_AT, toString(value_))] | |
236 | 286 | ||
237 | 287 | ||
238 | 288 | func _loadUserCheckpointAt (user_) = match getString(makeString([KEY_USER_CHECKPOINT_AT, user_], SEPARATOR)) { | |
239 | 289 | case a: String => | |
240 | 290 | parseBigIntValue(a) | |
241 | 291 | case _ => | |
242 | 292 | ZERO_BIGINT | |
243 | 293 | } | |
244 | 294 | ||
245 | 295 | ||
246 | 296 | func _saveUserCheckpointAt (user_,value_) = [StringEntry(makeString([KEY_USER_CHECKPOINT_AT, user_], SEPARATOR), toString(value_))] | |
247 | 297 | ||
248 | 298 | ||
299 | + | func _loadUnitsAsset () = match getString(KEY_UNITS_ASSET) { | |
300 | + | case a: String => | |
301 | + | fromBase58String(a) | |
302 | + | case _ => | |
303 | + | base58'' | |
304 | + | } | |
305 | + | ||
306 | + | ||
307 | + | func _saveUnitsAsset (asset_) = [StringEntry(KEY_UNITS_ASSET, toBase58String(asset_))] | |
308 | + | ||
309 | + | ||
249 | 310 | func _loadStartBlock () = match getString(KEY_START_BLOCK) { | |
250 | 311 | case a: String => | |
251 | 312 | parseBigIntValue(a) | |
252 | 313 | case _ => | |
253 | 314 | ZERO_BIGINT | |
254 | 315 | } | |
255 | 316 | ||
256 | 317 | ||
257 | 318 | func _saveStartBlock (value_) = [StringEntry(KEY_START_BLOCK, toString(value_))] | |
258 | 319 | ||
259 | 320 | ||
260 | 321 | func _loadFinishBlock () = match getString(KEY_FINISH_BLOCK) { | |
261 | 322 | case a: String => | |
262 | 323 | parseBigIntValue(a) | |
263 | 324 | case _ => | |
264 | 325 | ZERO_BIGINT | |
265 | 326 | } | |
266 | 327 | ||
267 | 328 | ||
268 | 329 | func _saveFinishBlock (value_) = [StringEntry(KEY_FINISH_BLOCK, toString(value_))] | |
269 | 330 | ||
270 | 331 | ||
271 | - | func _ | |
332 | + | func _loadUnitsBalanceDistributed () = match getString(KEY_UNITS_BALANCE_DISTRIBUTED) { | |
272 | 333 | case a: String => | |
273 | 334 | parseBigIntValue(a) | |
274 | 335 | case _ => | |
275 | 336 | ZERO_BIGINT | |
276 | 337 | } | |
277 | 338 | ||
278 | 339 | ||
279 | - | func _ | |
340 | + | func _saveUnitsBalanceDistributed (value_) = [StringEntry(KEY_UNITS_BALANCE_DISTRIBUTED, toString(value_))] | |
280 | 341 | ||
281 | 342 | ||
282 | - | func _ | |
343 | + | func _loadUserUnitsBalanceDistributed (user_) = match getString(makeString([KEY_USER_UNITS_BALANCE_DISTRIBUTED, user_], SEPARATOR)) { | |
283 | 344 | case a: String => | |
284 | 345 | parseBigIntValue(a) | |
285 | 346 | case _ => | |
286 | 347 | ZERO_BIGINT | |
287 | 348 | } | |
288 | 349 | ||
289 | 350 | ||
290 | - | func _saveUnitsBalance (value_) = [StringEntry(KEY_UNITS_BALANCE, toString(value_))] | |
291 | - | ||
292 | - | ||
293 | - | func _loadUserUnitsBalance (user_) = match getString(makeString([KEY_USER_UNITS_BALANCE, user_], SEPARATOR)) { | |
294 | - | case a: String => | |
295 | - | parseBigIntValue(a) | |
296 | - | case _ => | |
297 | - | ZERO_BIGINT | |
298 | - | } | |
299 | - | ||
300 | - | ||
301 | - | func _saveUserUnitsBalance (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_BALANCE, user_], SEPARATOR), toString(value_))] | |
351 | + | func _saveUserUnitsBalanceDistributed (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_BALANCE_DISTRIBUTED, user_], SEPARATOR), toString(value_))] | |
302 | 352 | ||
303 | 353 | ||
304 | 354 | func _loadTotalUSDBalance () = match getString(KEY_TOTAL_USD_BALANCE) { | |
305 | 355 | case a: String => | |
306 | 356 | parseBigIntValue(a) | |
307 | 357 | case _ => | |
308 | 358 | ZERO_BIGINT | |
309 | 359 | } | |
310 | 360 | ||
311 | 361 | ||
312 | 362 | func _saveTotalUSDBalance (value_) = [StringEntry(KEY_TOTAL_USD_BALANCE, toString(value_))] | |
313 | 363 | ||
314 | 364 | ||
315 | 365 | func _loadSWavesContract () = match getString(KEY_SWAVES_CONTRACT) { | |
316 | 366 | case a: String => | |
317 | 367 | addressFromStringValue(a) | |
318 | 368 | case _ => | |
319 | 369 | Address(base58'') | |
320 | 370 | } | |
321 | 371 | ||
322 | 372 | ||
323 | 373 | func _saveSWavesContract (contract_) = [StringEntry(KEY_SWAVES_CONTRACT, toString(contract_))] | |
324 | 374 | ||
325 | 375 | ||
326 | 376 | func _loadSWavesAsset (contract_) = match getString(contract_, KEY_SWAVES_ASSET) { | |
327 | 377 | case a: String => | |
328 | 378 | fromBase58String(a) | |
329 | 379 | case _ => | |
330 | 380 | throw("_loadSWavesAsset: revert") | |
331 | 381 | } | |
332 | 382 | ||
333 | 383 | ||
334 | 384 | func _loadTokenBalance (token_) = match getString(makeString([KEY_TOKEN_BALANCE, token_], SEPARATOR)) { | |
335 | 385 | case a: String => | |
336 | 386 | parseBigIntValue(a) | |
337 | 387 | case _ => | |
338 | 388 | ZERO_BIGINT | |
339 | 389 | } | |
340 | 390 | ||
341 | 391 | ||
342 | 392 | func _saveTokenBalance (token_,value_) = [StringEntry(makeString([KEY_TOKEN_BALANCE, token_], SEPARATOR), toString(value_))] | |
343 | 393 | ||
344 | 394 | ||
395 | + | func _loadUsersCount () = match getString(KEY_USERS_COUNT) { | |
396 | + | case a: String => | |
397 | + | parseBigIntValue(a) | |
398 | + | case _ => | |
399 | + | ZERO_BIGINT | |
400 | + | } | |
401 | + | ||
402 | + | ||
403 | + | func _saveUsersCount (value_) = [StringEntry(KEY_USERS_COUNT, toString(value_))] | |
404 | + | ||
405 | + | ||
406 | + | func _loadUnitsPerReferalShareIntegral () = match getString(KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL) { | |
407 | + | case a: String => | |
408 | + | parseBigIntValue(a) | |
409 | + | case _ => | |
410 | + | ZERO_BIGINT | |
411 | + | } | |
412 | + | ||
413 | + | ||
414 | + | func _saveUnitsPerReferalShareIntegral (value_) = [StringEntry(KEY_UNITS_PER_REFERAL_SHARE_INTEGRAL, toString(value_))] | |
415 | + | ||
416 | + | ||
417 | + | func _loadUnitsSharesReferal () = match getString(KEY_UNITS_SHARES_REFERAL) { | |
418 | + | case a: String => | |
419 | + | parseBigIntValue(a) | |
420 | + | case _ => | |
421 | + | ZERO_BIGINT | |
422 | + | } | |
423 | + | ||
424 | + | ||
425 | + | func _saveUnitsSharesReferal (value_) = [StringEntry(KEY_UNITS_SHARES_REFERAL, toString(value_))] | |
426 | + | ||
427 | + | ||
428 | + | func _loadTotalUnitsForLP () = match getString(KEY_TOTAL_UNITS_FOR_LP) { | |
429 | + | case a: String => | |
430 | + | parseBigIntValue(a) | |
431 | + | case _ => | |
432 | + | ZERO_BIGINT | |
433 | + | } | |
434 | + | ||
435 | + | ||
436 | + | func _saveTotalUnitsForLP (value_) = [StringEntry(KEY_TOTAL_UNITS_FOR_LP, toString(value_))] | |
437 | + | ||
438 | + | ||
439 | + | func _loadTotalUnitsForReferal () = match getString(KEY_TOTAL_UNITS_FOR_REFERAL) { | |
440 | + | case a: String => | |
441 | + | parseBigIntValue(a) | |
442 | + | case _ => | |
443 | + | ZERO_BIGINT | |
444 | + | } | |
445 | + | ||
446 | + | ||
447 | + | func _saveTotalUnitsForReferal (value_) = [StringEntry(KEY_TOTAL_UNITS_FOR_REFERAL, toString(value_))] | |
448 | + | ||
449 | + | ||
450 | + | func _loadTotalSharesReferal () = match getString(KEY_TOTAL_SHARES_REFERAL) { | |
451 | + | case a: String => | |
452 | + | parseBigIntValue(a) | |
453 | + | case _ => | |
454 | + | ZERO_BIGINT | |
455 | + | } | |
456 | + | ||
457 | + | ||
458 | + | func _saveTotalSharesReferal (value_) = [StringEntry(KEY_TOTAL_SHARES_REFERAL, toString(value_))] | |
459 | + | ||
460 | + | ||
461 | + | func _loadUserUnitsPerReferalShareIntegral (user_) = match getString(makeString([KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL, user_], SEPARATOR)) { | |
462 | + | case a: String => | |
463 | + | parseBigIntValue(a) | |
464 | + | case _ => | |
465 | + | ZERO_BIGINT | |
466 | + | } | |
467 | + | ||
468 | + | ||
469 | + | func _saveUserUnitsPerReferalShareIntegral (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_PER_REFERAL_SHARE_INTEGRAL, user_], SEPARATOR), toString(value_))] | |
470 | + | ||
471 | + | ||
472 | + | func _loadUserUnitsSharesReferal (user_) = match getString(makeString([KEY_USER_UNITS_SHARES_REFERAL, user_], SEPARATOR)) { | |
473 | + | case a: String => | |
474 | + | parseBigIntValue(a) | |
475 | + | case _ => | |
476 | + | ZERO_BIGINT | |
477 | + | } | |
478 | + | ||
479 | + | ||
480 | + | func _saveUserUnitsSharesReferal (user_,value_) = [StringEntry(makeString([KEY_USER_UNITS_SHARES_REFERAL, user_], SEPARATOR), toString(value_))] | |
481 | + | ||
482 | + | ||
483 | + | func _loadManager () = match getString(KEY_MANAGER) { | |
484 | + | case a: String => | |
485 | + | addressFromStringValue(a) | |
486 | + | case _ => | |
487 | + | Address(base58'') | |
488 | + | } | |
489 | + | ||
490 | + | ||
491 | + | func _saveManager (manager_) = [StringEntry(KEY_MANAGER, toString(manager_))] | |
492 | + | ||
493 | + | ||
494 | + | func _loadReferer (codehash_) = match getString(makeString([KEY_REFERER, codehash_], SEPARATOR)) { | |
495 | + | case a: String => | |
496 | + | a | |
497 | + | case _ => | |
498 | + | throw("_loadReferer: revert") | |
499 | + | } | |
500 | + | ||
501 | + | ||
502 | + | func _saveReferer (codehash_,address_) = [StringEntry(makeString([KEY_REFERER, codehash_], SEPARATOR), address_)] | |
503 | + | ||
504 | + | ||
505 | + | func _checkRefererExistence (codehash_) = match getString(makeString([KEY_REFERER, codehash_], SEPARATOR)) { | |
506 | + | case a: String => | |
507 | + | true | |
508 | + | case _ => | |
509 | + | false | |
510 | + | } | |
511 | + | ||
512 | + | ||
345 | 513 | func _onlyThisContract (caller_) = if ((caller_ != this)) | |
346 | 514 | then throw("_onlyThisContract: revert") | |
347 | 515 | else true | |
348 | 516 | ||
349 | 517 | ||
350 | 518 | func _whenMultisigSet () = if ((_loadMultisig() == Address(base58''))) | |
351 | 519 | then throw("_whenMultisigSet: revert") | |
352 | 520 | else true | |
353 | 521 | ||
354 | 522 | ||
355 | 523 | func _whenNotInitialized () = if (_loadInit()) | |
356 | 524 | then throw("_whenNotInitialized: revert") | |
357 | 525 | else true | |
358 | 526 | ||
359 | 527 | ||
360 | 528 | func _whenInitialized () = if (!(_loadInit())) | |
361 | 529 | then throw("_whenInitialized: revert") | |
362 | 530 | else true | |
363 | 531 | ||
364 | 532 | ||
365 | 533 | func _whenNotPaused () = if (_loadPause()) | |
366 | 534 | then throw("_whenNotPaused: revert") | |
367 | 535 | else true | |
368 | 536 | ||
369 | 537 | ||
370 | 538 | func _whenPaused () = if (!(_loadPause())) | |
371 | 539 | then throw("_whenPaused: revert") | |
372 | 540 | else true | |
373 | 541 | ||
374 | 542 | ||
375 | 543 | func _onlyPauser (caller_) = if ((caller_ != _loadPauser())) | |
376 | 544 | then throw("_onlyPauser: revert") | |
377 | 545 | else true | |
378 | 546 | ||
379 | 547 | ||
548 | + | func _onlyManager (caller_) = if ((caller_ != _loadManager())) | |
549 | + | then throw("_onlyManager: revert") | |
550 | + | else true | |
551 | + | ||
552 | + | ||
380 | 553 | func _validateExecutor (val_,err_) = if ((val_ != _loadExecutor())) | |
381 | 554 | then throw(err_) | |
382 | 555 | else true | |
383 | 556 | ||
384 | 557 | ||
385 | 558 | func _validateCaller (val_,err_) = if ((val_ != _loadCallerContract())) | |
386 | 559 | then throw(err_) | |
387 | 560 | else true | |
388 | 561 | ||
389 | 562 | ||
390 | 563 | func _getTokenRate (token_) = match getString(_loadOracle(), makeString([KEY_PRICE, token_], SEPARATOR)) { | |
391 | 564 | case a: String => | |
392 | 565 | parseBigIntValue(a) | |
393 | 566 | case _ => | |
394 | 567 | throw(("_getTokenRate: no rate for token=" + token_)) | |
395 | 568 | } | |
396 | 569 | ||
397 | 570 | ||
398 | 571 | func _checkpoint () = { | |
399 | 572 | let prevUnitsPerUSDBalanceIntegral = _loadUnitsPerUSDBalanceIntegral() | |
400 | 573 | let prevCheckpointAt = max([_loadStartBlock(), _loadCheckpointAt()]) | |
401 | - | let prevUnitsBalance = _loadUnitsBalance() | |
574 | + | let prevUnitsBalanceDistributed = _loadUnitsBalanceDistributed() | |
575 | + | let prevUnitsPerReferalShareIntegral = _loadUnitsPerReferalShareIntegral() | |
576 | + | let prevUnitsSharesReferal = _loadUnitsSharesReferal() | |
402 | 577 | let currentBlock = min([toBigInt(height), _loadFinishBlock()]) | |
403 | 578 | if ((prevCheckpointAt >= currentBlock)) | |
404 | - | then $ | |
579 | + | then $Tuple3(nil, prevUnitsPerUSDBalanceIntegral, prevUnitsPerReferalShareIntegral) | |
405 | 580 | else { | |
406 | - | let unitsBalance = (_loadUnitsPerBlock() * (currentBlock - _loadStartBlock())) | |
407 | - | let unitsPerUSDBalanceIntegral = ((((PERCENT_FACTOR * (currentBlock - prevCheckpointAt)) * (unitsBalance - prevUnitsBalance)) / _loadTotalUSDBalance()) + prevUnitsPerUSDBalanceIntegral) | |
408 | - | $Tuple2(((_saveUnitsPerUSDBalanceIntegral(unitsPerUSDBalanceIntegral) ++ _saveCheckpointAt(currentBlock)) ++ _saveUnitsBalance(unitsBalance)), unitsPerUSDBalanceIntegral) | |
581 | + | let unitsBalanceToDistribute = fraction((_loadTotalUnitsForLP() - prevUnitsBalanceDistributed), (currentBlock - prevCheckpointAt), (_loadFinishBlock() - prevCheckpointAt)) | |
582 | + | let unitsPerUSDBalanceIntegral = (((PERCENT_FACTOR * unitsBalanceToDistribute) / _loadTotalUSDBalance()) + prevUnitsPerUSDBalanceIntegral) | |
583 | + | let $t01774818301 = if ((_loadTotalSharesReferal() > ZERO_BIGINT)) | |
584 | + | then { | |
585 | + | let unitsSharesReferal = fraction((_loadTotalUnitsForReferal() - prevUnitsSharesReferal), (currentBlock - prevCheckpointAt), (_loadFinishBlock() - prevCheckpointAt)) | |
586 | + | let unitsPerReferalShareIntegral = (((PERCENT_FACTOR * unitsSharesReferal) / _loadTotalSharesReferal()) + prevUnitsPerReferalShareIntegral) | |
587 | + | $Tuple2(unitsSharesReferal, unitsPerReferalShareIntegral) | |
588 | + | } | |
589 | + | else $Tuple2(ZERO_BIGINT, ZERO_BIGINT) | |
590 | + | let unitsSharesReferal = $t01774818301._1 | |
591 | + | let unitsPerReferalShareIntegral = $t01774818301._2 | |
592 | + | $Tuple3(((((_saveCheckpointAt(currentBlock) ++ _saveUnitsPerUSDBalanceIntegral(unitsPerUSDBalanceIntegral)) ++ _saveUnitsBalanceDistributed((unitsBalanceToDistribute + prevUnitsBalanceDistributed))) ++ _saveUnitsPerReferalShareIntegral(unitsPerReferalShareIntegral)) ++ _saveUnitsSharesReferal((unitsSharesReferal + prevUnitsSharesReferal))), unitsPerUSDBalanceIntegral, unitsPerReferalShareIntegral) | |
409 | 593 | } | |
410 | 594 | } | |
411 | 595 | ||
412 | 596 | ||
413 | - | func _userCheckpoint (user_,userUSDBalance_) = { | |
414 | - | let $t01275212819 = _checkpoint() | |
415 | - | let checkpointActions = $t01275212819._1 | |
416 | - | let unitsPerUSDBalanceIntegral = $t01275212819._2 | |
597 | + | func _userCheckpoint (user_,userUSDBalance_,userSharesReferal_) = { | |
598 | + | let $t01888718999 = _checkpoint() | |
599 | + | let checkpointActions = $t01888718999._1 | |
600 | + | let unitsPerUSDBalanceIntegral = $t01888718999._2 | |
601 | + | let unitsPerReferalShareIntegral = $t01888718999._3 | |
417 | 602 | let prevUserUnitsPerUSDBalanceIntegral = _loadUserUnitsPerUSDBalanceIntegral(user_) | |
418 | 603 | let prevUserCheckpointAt = max([_loadStartBlock(), _loadUserCheckpointAt(user_)]) | |
419 | - | let prevUserUnitsBalance = _loadUserUnitsBalance(user_) | |
604 | + | let prevUserUnitsBalanceDistributed = _loadUserUnitsBalanceDistributed(user_) | |
605 | + | let prevUserUnitsPerReferalShareIntegral = _loadUserUnitsPerReferalShareIntegral(user_) | |
606 | + | let prevUserUnitsSharesReferal = _loadUserUnitsSharesReferal(user_) | |
420 | 607 | let currentBlock = min([toBigInt(height), _loadFinishBlock()]) | |
421 | 608 | if ((prevUserCheckpointAt >= currentBlock)) | |
422 | - | then $ | |
609 | + | then $Tuple3(checkpointActions, prevUserUnitsBalanceDistributed, prevUserUnitsSharesReferal) | |
423 | 610 | else { | |
424 | - | let userUnitsBalance = ((((userUSDBalance_ * (unitsPerUSDBalanceIntegral - prevUserUnitsPerUSDBalanceIntegral)) / (currentBlock - prevUserCheckpointAt)) / PERCENT_FACTOR) + prevUserUnitsBalance) | |
425 | - | $Tuple2((((checkpointActions ++ _saveUserUnitsPerUSDBalanceIntegral(user_, unitsPerUSDBalanceIntegral)) ++ _saveUserCheckpointAt(user_, currentBlock)) ++ _saveUserUnitsBalance(user_, userUnitsBalance)), userUnitsBalance) | |
611 | + | let userUnitsBalanceDistributed = (((userUSDBalance_ * (unitsPerUSDBalanceIntegral - prevUserUnitsPerUSDBalanceIntegral)) / PERCENT_FACTOR) + prevUserUnitsBalanceDistributed) | |
612 | + | let userUnitsSharesReferal = (((userSharesReferal_ * (unitsPerReferalShareIntegral - prevUserUnitsPerReferalShareIntegral)) / PERCENT_FACTOR) + prevUserUnitsSharesReferal) | |
613 | + | $Tuple3((((((checkpointActions ++ _saveUserCheckpointAt(user_, currentBlock)) ++ _saveUserUnitsPerUSDBalanceIntegral(user_, unitsPerUSDBalanceIntegral)) ++ _saveUserUnitsBalanceDistributed(user_, userUnitsBalanceDistributed)) ++ _saveUserUnitsPerReferalShareIntegral(user_, unitsPerReferalShareIntegral)) ++ _saveUserUnitsSharesReferal(user_, userUnitsSharesReferal)), userUnitsBalanceDistributed, userUnitsSharesReferal) | |
426 | 614 | } | |
427 | 615 | } | |
428 | 616 | ||
429 | 617 | ||
430 | 618 | @Callable(i) | |
431 | 619 | func init (executor_,oracle_,pauser_,sWavesContract_) = { | |
432 | 620 | let err = if (if (if (if (if (if (_onlyThisContract(i.caller)) | |
433 | 621 | then _whenNotInitialized() | |
434 | 622 | else false) | |
435 | 623 | then _whenMultisigSet() | |
436 | 624 | else false) | |
437 | 625 | then _validateAddress(executor_, "init: invalid executor") | |
438 | 626 | else false) | |
439 | 627 | then _validateAddress(oracle_, "init: invalid oracle") | |
440 | 628 | else false) | |
441 | 629 | then _validateAddress(pauser_, "init: invalid pauser") | |
442 | 630 | else false) | |
443 | 631 | then _validateAddress(sWavesContract_, "init: invalid sWavesContract") | |
444 | 632 | else false | |
445 | 633 | if ((err == err)) | |
446 | 634 | then $Tuple2(((((_saveInit(true) ++ _saveExecutor(addressFromStringValue(executor_))) ++ _saveOracle(addressFromStringValue(oracle_))) ++ _savePauser(addressFromStringValue(pauser_))) ++ _saveSWavesContract(addressFromStringValue(sWavesContract_))), unit) | |
447 | 635 | else throw("Strict value is not equal to itself.") | |
448 | 636 | } | |
449 | 637 | ||
450 | 638 | ||
451 | 639 | ||
452 | 640 | @Callable(i) | |
453 | 641 | func deposit (callerContract_,sender_,token_,amount_,referrer_) = { | |
454 | 642 | let amount = valueOrErrorMessage(parseInt(amount_), "deposit: amount is not Int") | |
455 | 643 | let err = if (if (if (if (_whenInitialized()) | |
456 | 644 | then _whenNotPaused() | |
457 | 645 | else false) | |
458 | 646 | then _validateExecutor(i.caller, "deposit: invalid executor") | |
459 | 647 | else false) | |
460 | 648 | then _validateCaller(callerContract_, "deposit: invalid caller") | |
461 | 649 | else false) | |
462 | 650 | then _validateInt(amount, 0, MAX_INT, "deposit: invalid amount") | |
463 | 651 | else false | |
464 | 652 | if ((err == err)) | |
465 | 653 | then { | |
466 | 654 | let rate = _getTokenRate(token_) | |
467 | - | let $ | |
468 | - | let userTokenBalance = $ | |
469 | - | let userTokenBalanceInUSD = $ | |
655 | + | let $t02192622008 = _loadUserPosition(token_, sender_) | |
656 | + | let userTokenBalance = $t02192622008._1 | |
657 | + | let userTokenBalanceInUSD = $t02192622008._2 | |
470 | 658 | let userUSDBalance = _loadUserUSDBalance(sender_) | |
471 | - | let $t01525315337 = _userCheckpoint(sender_, userUSDBalance) | |
472 | - | let checkpointActions = $t01525315337._1 | |
473 | - | let userUnitsBalance = $t01525315337._2 | |
659 | + | let userSharesReferal = _loadUserSharesReferal(sender_) | |
660 | + | let $t02212722254 = _userCheckpoint(sender_, userUSDBalance, userSharesReferal) | |
661 | + | let checkpointActions = $t02212722254._1 | |
662 | + | let userUnitsBalance = $t02212722254._2 | |
663 | + | let userUnitsSharesReferal = $t02212722254._3 | |
474 | 664 | let newUserTokenBalance = (userTokenBalance + toBigInt(amount)) | |
475 | 665 | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
476 | 666 | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
477 | 667 | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
478 | - | $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
668 | + | let usersCount = if ((userUSDBalance == ZERO_BIGINT)) | |
669 | + | then (_loadUsersCount() + ONE_BIGINT) | |
670 | + | else _loadUsersCount() | |
671 | + | let refererActions = if (if ((size(referrer_) > 0)) | |
672 | + | then _checkRefererExistence(referrer_) | |
673 | + | else false) | |
674 | + | then { | |
675 | + | let refererAddress = _loadReferer(referrer_) | |
676 | + | let sharesToDistribute = fraction(toBigInt(amount), rate, PERCENT_FACTOR, DOWN) | |
677 | + | let sharesToUser = fraction(sharesToDistribute, toBigInt(20), toBigInt(100), DOWN) | |
678 | + | let sharesToReferer = (sharesToDistribute - sharesToUser) | |
679 | + | let newUserSharesReferal = (userSharesReferal + sharesToUser) | |
680 | + | let refererSharesReferal = _loadUserSharesReferal(refererAddress) | |
681 | + | let newRefererSharesReferal = (refererSharesReferal + sharesToReferer) | |
682 | + | let newTotalSharesReferal = (_loadTotalSharesReferal() + sharesToDistribute) | |
683 | + | let $t02358723758 = _userCheckpoint(refererAddress, _loadUserUSDBalance(refererAddress), refererSharesReferal) | |
684 | + | let refererCheckpointActions = $t02358723758._1 | |
685 | + | let refererUnitsBalance = $t02358723758._2 | |
686 | + | let refererUnitsSharesReferal = $t02358723758._3 | |
687 | + | (((refererCheckpointActions ++ _saveUserSharesReferal(sender_, newUserSharesReferal)) ++ _saveUserSharesReferal(refererAddress, newRefererSharesReferal)) ++ _saveTotalSharesReferal(newTotalSharesReferal)) | |
688 | + | } | |
689 | + | else nil | |
690 | + | $Tuple2(((((((checkpointActions ++ refererActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUsersCount(usersCount)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
479 | 691 | } | |
480 | 692 | else throw("Strict value is not equal to itself.") | |
481 | 693 | } | |
482 | 694 | ||
483 | 695 | ||
484 | 696 | ||
485 | 697 | @Callable(i) | |
486 | - | func withdraw (callerContract_,sender_,token_,amount_) = { | |
487 | - | let amount = valueOrErrorMessage(parseInt(amount_), "withdraw: amount is not Int") | |
488 | - | let err = if (if (if (if (_whenInitialized()) | |
489 | - | then _whenNotPaused() | |
490 | - | else false) | |
491 | - | then _validateExecutor(i.caller, "withdraw: invalid executor") | |
492 | - | else false) | |
493 | - | then _validateCaller(callerContract_, "withdraw: invalid caller") | |
494 | - | else false) | |
495 | - | then _validateInt(amount, 0, MAX_INT, "withdraw: invalid amount") | |
496 | - | else false | |
497 | - | if ((err == err)) | |
498 | - | then { | |
499 | - | let rate = _getTokenRate(token_) | |
500 | - | let $t01659516677 = _loadUserPosition(token_, sender_) | |
501 | - | let userTokenBalance = $t01659516677._1 | |
502 | - | let userTokenBalanceInUSD = $t01659516677._2 | |
503 | - | let userUSDBalance = _loadUserUSDBalance(sender_) | |
504 | - | let $t01673616820 = _userCheckpoint(sender_, userUSDBalance) | |
505 | - | let checkpointActions = $t01673616820._1 | |
506 | - | let userUnitsBalance = $t01673616820._2 | |
507 | - | let newUserTokenBalance = (userTokenBalance - toBigInt(amount)) | |
508 | - | let err1 = _validateInt(toInt(newUserTokenBalance), 0, MAX_INT, "withdraw: insufficient token amount") | |
509 | - | if ((err1 == err1)) | |
510 | - | then { | |
511 | - | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
512 | - | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
513 | - | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
514 | - | $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(token_, (_loadTokenBalance(token_) - toBigInt(amount)))) ++ _saveUserUSDBalance(sender_, newUserUSDBalance)) ++ _saveUserPosition(token_, sender_, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), unit) | |
515 | - | } | |
516 | - | else throw("Strict value is not equal to itself.") | |
517 | - | } | |
518 | - | else throw("Strict value is not equal to itself.") | |
519 | - | } | |
520 | - | ||
521 | - | ||
522 | - | ||
523 | - | @Callable(i) | |
524 | - | func depositWaves () = { | |
698 | + | func depositWaves (referrer_) = { | |
525 | 699 | let err = if (if (if (if (_whenInitialized()) | |
526 | 700 | then _whenNotPaused() | |
527 | 701 | else false) | |
528 | 702 | then _validatePaymentsSize(i.payments, 1, "depositWaves: no payment") | |
529 | 703 | else false) | |
530 | 704 | then _validateWavesPayment(i.payments[0], "depositWaves: invalid asset") | |
531 | 705 | else false) | |
532 | - | then _validateInt(i.payments[0].amount, 0, MAX_INT, "depositWaves: invalid amount") | |
706 | + | then _validateInt((i.payments[0].amount / 100), 0, MAX_INT, "depositWaves: invalid amount") | |
533 | 707 | else false | |
534 | 708 | if ((err == err)) | |
535 | 709 | then { | |
536 | - | let amount = i.payments[0].amount | |
710 | + | let amount = (i.payments[0].amount / 100) | |
537 | 711 | let sender = toString(i.caller) | |
538 | 712 | let token = WAVES | |
539 | 713 | let rate = _getTokenRate(token) | |
540 | - | let $ | |
541 | - | let userTokenBalance = $ | |
542 | - | let userTokenBalanceInUSD = $ | |
714 | + | let $t02663326713 = _loadUserPosition(token, sender) | |
715 | + | let userTokenBalance = $t02663326713._1 | |
716 | + | let userTokenBalanceInUSD = $t02663326713._2 | |
543 | 717 | let userUSDBalance = _loadUserUSDBalance(sender) | |
544 | - | let $t01827018353 = _userCheckpoint(sender, userUSDBalance) | |
545 | - | let checkpointActions = $t01827018353._1 | |
546 | - | let userUnitsBalance = $t01827018353._2 | |
718 | + | let userSharesReferal = _loadUserSharesReferal(sender) | |
719 | + | let $t02683026956 = _userCheckpoint(sender, userUSDBalance, userSharesReferal) | |
720 | + | let checkpointActions = $t02683026956._1 | |
721 | + | let userUnitsBalance = $t02683026956._2 | |
722 | + | let userUnitsSharesReferal = $t02683026956._3 | |
547 | 723 | let newUserTokenBalance = (userTokenBalance + toBigInt(amount)) | |
548 | 724 | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
549 | 725 | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
550 | 726 | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
551 | - | let invocation = invoke(_loadSWavesContract(), FUNC_DEPOSIT, nil, [AttachedPayment(unit, amount)]) | |
727 | + | let usersCount = if ((userUSDBalance == ZERO_BIGINT)) | |
728 | + | then (_loadUsersCount() + ONE_BIGINT) | |
729 | + | else _loadUsersCount() | |
730 | + | let refererActions = if (if ((size(referrer_) > 0)) | |
731 | + | then _checkRefererExistence(referrer_) | |
732 | + | else false) | |
733 | + | then { | |
734 | + | let refererAddress = _loadReferer(referrer_) | |
735 | + | let sharesToDistribute = fraction(toBigInt(amount), rate, PERCENT_FACTOR, DOWN) | |
736 | + | let sharesToUser = fraction(sharesToDistribute, toBigInt(20), toBigInt(100), DOWN) | |
737 | + | let sharesToReferer = (sharesToDistribute - sharesToUser) | |
738 | + | let newUserSharesReferal = (userSharesReferal + sharesToUser) | |
739 | + | let refererSharesReferal = _loadUserSharesReferal(refererAddress) | |
740 | + | let newRefererSharesReferal = (refererSharesReferal + sharesToReferer) | |
741 | + | let newTotalSharesReferal = (_loadTotalSharesReferal() + sharesToDistribute) | |
742 | + | let $t02828928460 = _userCheckpoint(refererAddress, _loadUserUSDBalance(refererAddress), refererSharesReferal) | |
743 | + | let refererCheckpointActions = $t02828928460._1 | |
744 | + | let refererUnitsBalance = $t02828928460._2 | |
745 | + | let refererUnitsSharesReferal = $t02828928460._3 | |
746 | + | (((refererCheckpointActions ++ _saveUserSharesReferal(sender, newUserSharesReferal)) ++ _saveUserSharesReferal(refererAddress, newRefererSharesReferal)) ++ _saveTotalSharesReferal(newTotalSharesReferal)) | |
747 | + | } | |
748 | + | else nil | |
749 | + | let invocation = invoke(_loadSWavesContract(), FUNC_DEPOSIT, nil, [AttachedPayment(unit, i.payments[0].amount)]) | |
552 | 750 | if ((invocation == invocation)) | |
553 | - | then $Tuple2(((((checkpointActions ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
751 | + | then $Tuple2(((((((checkpointActions ++ refererActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) + toBigInt(amount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUsersCount(usersCount)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), userUnitsBalance) | |
554 | 752 | else throw("Strict value is not equal to itself.") | |
555 | 753 | } | |
556 | 754 | else throw("Strict value is not equal to itself.") | |
557 | 755 | } | |
558 | 756 | ||
559 | 757 | ||
560 | 758 | ||
561 | 759 | @Callable(i) | |
562 | 760 | func withdrawWaves (amount_) = { | |
563 | - | let err = if (if (_whenInitialized()) | |
761 | + | let err = if (if (if (_whenInitialized()) | |
564 | 762 | then _whenNotPaused() | |
565 | 763 | else false) | |
566 | - | then _validateInt(amount_, 0, MAX_INT, "withdrawWaves: invalid amount") | |
764 | + | then _validateInt((amount_ / 100), 0, MAX_INT, "withdrawWaves: invalid amount") | |
765 | + | else false) | |
766 | + | then if ((_loadFinishBlock() >= toBigInt(height))) | |
767 | + | then throw("withdrawWaves: not allowed") | |
768 | + | else true | |
567 | 769 | else false | |
568 | 770 | if ((err == err)) | |
569 | 771 | then { | |
772 | + | let internalAmount = (amount_ / 100) | |
570 | 773 | let sender = toString(i.caller) | |
571 | 774 | let token = WAVES | |
572 | 775 | let rate = _getTokenRate(token) | |
573 | - | let $ | |
574 | - | let userTokenBalance = $ | |
575 | - | let userTokenBalanceInUSD = $ | |
776 | + | let $t02972829808 = _loadUserPosition(token, sender) | |
777 | + | let userTokenBalance = $t02972829808._1 | |
778 | + | let userTokenBalanceInUSD = $t02972829808._2 | |
576 | 779 | let userUSDBalance = _loadUserUSDBalance(sender) | |
577 | - | let $t01962619709 = _userCheckpoint(sender, userUSDBalance) | |
578 | - | let checkpointActions = $t01962619709._1 | |
579 | - | let userUnitsBalance = $t01962619709._2 | |
580 | - | let newUserTokenBalance = (userTokenBalance - toBigInt(amount_)) | |
780 | + | let userSharesReferal = _loadUserSharesReferal(sender) | |
781 | + | let $t02992530051 = _userCheckpoint(sender, userUSDBalance, userSharesReferal) | |
782 | + | let checkpointActions = $t02992530051._1 | |
783 | + | let userUnitsBalance = $t02992530051._2 | |
784 | + | let userUnitsSharesReferal = $t02992530051._3 | |
785 | + | let newUserTokenBalance = (userTokenBalance - toBigInt(internalAmount)) | |
581 | 786 | let err1 = _validateInt(toInt(newUserTokenBalance), 0, MAX_INT, "withdrawWaves: insufficient token amount") | |
582 | 787 | if ((err1 == err1)) | |
583 | 788 | then { | |
584 | 789 | let newUserTokenBalanceInUSD = fraction(newUserTokenBalance, rate, PERCENT_FACTOR, DOWN) | |
585 | 790 | let newUserUSDBalance = ((userUSDBalance - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
586 | 791 | let totalBalanceUpdated = ((_loadTotalUSDBalance() - userTokenBalanceInUSD) + newUserTokenBalanceInUSD) | |
587 | 792 | let sWavesContract = _loadSWavesContract() | |
588 | 793 | let sWavesAsset = _loadSWavesAsset(sWavesContract) | |
589 | 794 | let invocation = invoke(sWavesContract, FUNC_GET_RATE, nil, nil) | |
590 | 795 | let swavesRate = match invocation { | |
591 | 796 | case a: String => | |
592 | 797 | parseBigIntValue(a) | |
593 | 798 | case _ => | |
594 | 799 | throw("withdrawWaves: sWaves getRate() revert") | |
595 | 800 | } | |
596 | 801 | let sWavesToWithdraw = toInt(fraction(toBigInt(amount_), SWAVES_RATE_FACTOR, swavesRate, CEILING)) | |
597 | 802 | let invocation1 = invoke(sWavesContract, FUNC_WITHDRAW, nil, [AttachedPayment(sWavesAsset, sWavesToWithdraw)]) | |
598 | 803 | if ((invocation1 == invocation1)) | |
599 | - | then $Tuple2(((((([ScriptTransfer(i.caller, amount_, unit)] ++ checkpointActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) - toBigInt( | |
804 | + | then $Tuple2(((((([ScriptTransfer(i.caller, amount_, unit)] ++ checkpointActions) ++ _saveTotalUSDBalance(totalBalanceUpdated)) ++ _saveTokenBalance(WAVES, (_loadTokenBalance(WAVES) - toBigInt(internalAmount)))) ++ _saveUserUSDBalance(sender, newUserUSDBalance)) ++ _saveUserPosition(token, sender, $Tuple2(newUserTokenBalance, newUserTokenBalanceInUSD))), unit) | |
600 | 805 | else throw("Strict value is not equal to itself.") | |
601 | 806 | } | |
602 | 807 | else throw("Strict value is not equal to itself.") | |
603 | 808 | } | |
604 | 809 | else throw("Strict value is not equal to itself.") | |
605 | 810 | } | |
606 | 811 | ||
607 | 812 | ||
608 | 813 | ||
609 | 814 | @Callable(i) | |
610 | - | func startRetrodrop ( | |
611 | - | let err = if (if (if (if (if (_onlyThisContract(i.caller)) | |
815 | + | func startRetrodrop (unitsAsset_,amountForLP_,amountForReferal_,blocksAt_) = { | |
816 | + | let err = if (if (if (if (if (if (if (_onlyThisContract(i.caller)) | |
612 | 817 | then _whenInitialized() | |
613 | 818 | else false) | |
614 | 819 | then _whenNotPaused() | |
615 | 820 | else false) | |
616 | - | then _validateInt(amount_, 1, MAX_INT, "startRetrodrop: invalid amount") | |
821 | + | then _validateAsset(unitsAsset_, "startRetrodrop: invalid units asset") | |
822 | + | else false) | |
823 | + | then _validateInt(amountForLP_, 0, MAX_INT, "startRetrodrop: invalid amountForLP") | |
824 | + | else false) | |
825 | + | then _validateInt(amountForReferal_, 0, MAX_INT, "startRetrodrop: invalid amountForReferal") | |
617 | 826 | else false) | |
618 | 827 | then _validateInt(blocksAt_, 1, MAX_INT, "startRetrodrop: invalid blocksAt") | |
619 | 828 | else false) | |
620 | 829 | then _validateEqBigInt(_loadStartBlock(), ZERO_BIGINT, "startRetrodrop: already started") | |
621 | 830 | else false | |
622 | 831 | if ((err == err)) | |
623 | 832 | then { | |
624 | 833 | let startHeight = toBigInt(height) | |
625 | 834 | let finishHeight = (startHeight + toBigInt(blocksAt_)) | |
626 | - | let unitsPerBlock = fraction(toBigInt(amount_), PERCENT_FACTOR, toBigInt(blocksAt_)) | |
627 | - | $Tuple2(((_saveStartBlock(startHeight) ++ _saveFinishBlock(finishHeight)) ++ _saveUnitsPerBlock(unitsPerBlock)), unit) | |
835 | + | let err1 = if (((amountForLP_ + amountForReferal_) > assetBalance(this, fromBase58String(unitsAsset_)))) | |
836 | + | then throw("startRetrodrop: insufficient funds") | |
837 | + | else true | |
838 | + | if ((err1 == err1)) | |
839 | + | then $Tuple2(((((_saveUnitsAsset(fromBase58String(unitsAsset_)) ++ _saveStartBlock(startHeight)) ++ _saveFinishBlock(finishHeight)) ++ _saveTotalUnitsForLP(toBigInt(amountForLP_))) ++ _saveTotalUnitsForReferal(toBigInt(amountForReferal_))), unit) | |
840 | + | else throw("Strict value is not equal to itself.") | |
628 | 841 | } | |
629 | 842 | else throw("Strict value is not equal to itself.") | |
630 | 843 | } | |
631 | 844 | ||
632 | 845 | ||
633 | 846 | ||
634 | 847 | @Callable(i) | |
848 | + | func increaseUnitsSupply (amountForLP_,amountForReferal_) = { | |
849 | + | let err = if (if (if (if (_whenInitialized()) | |
850 | + | then _whenNotPaused() | |
851 | + | else false) | |
852 | + | then _validateInt(amountForLP_, 0, MAX_INT, "increaseUnitsSupply: invalid amountForLP") | |
853 | + | else false) | |
854 | + | then _validateInt(amountForReferal_, 0, MAX_INT, "increaseUnitsSupply: invalid amountForReferal") | |
855 | + | else false) | |
856 | + | then _validateBigInt(toBigInt(height), (_loadStartBlock() + ONE_BIGINT), (_loadFinishBlock() - ONE_BIGINT), "increaseUnitsSupply: drop not active") | |
857 | + | else false | |
858 | + | if ((err == err)) | |
859 | + | then { | |
860 | + | let newAmountForLP = (_loadTotalUnitsForLP() + toBigInt(amountForLP_)) | |
861 | + | let newAmountForReferal = (_loadTotalUnitsForReferal() + toBigInt(amountForReferal_)) | |
862 | + | let err1 = if (((newAmountForLP + newAmountForReferal) > toBigInt(assetBalance(this, _loadUnitsAsset())))) | |
863 | + | then throw("increaseUnitsSupply: insufficient funds") | |
864 | + | else true | |
865 | + | if ((err1 == err1)) | |
866 | + | then $Tuple2((_saveTotalUnitsForLP(newAmountForLP) ++ _saveTotalUnitsForReferal(newAmountForReferal)), unit) | |
867 | + | else throw("Strict value is not equal to itself.") | |
868 | + | } | |
869 | + | else throw("Strict value is not equal to itself.") | |
870 | + | } | |
871 | + | ||
872 | + | ||
873 | + | ||
874 | + | @Callable(i) | |
875 | + | func checkpoint (user_) = { | |
876 | + | let $t03382033959 = _userCheckpoint(user_, _loadUserUSDBalance(user_), _loadUserSharesReferal(user_)) | |
877 | + | let actions = $t03382033959._1 | |
878 | + | let userUnitsBalance = $t03382033959._2 | |
879 | + | let userUnitsSharesReferal = $t03382033959._3 | |
880 | + | $Tuple2(actions, $Tuple2(userUnitsBalance, userUnitsSharesReferal)) | |
881 | + | } | |
882 | + | ||
883 | + | ||
884 | + | ||
885 | + | @Callable(i) | |
635 | 886 | func getUnits (user_) = { | |
636 | - | let $t02197822062 = _userCheckpoint(user_, _loadUserUSDBalance(user_)) | |
637 | - | let actions = $t02197822062._1 | |
638 | - | let userUnitsBalance = $t02197822062._2 | |
639 | - | $Tuple2(nil, userUnitsBalance) | |
887 | + | let $t03407234211 = _userCheckpoint(user_, _loadUserUSDBalance(user_), _loadUserSharesReferal(user_)) | |
888 | + | let actions = $t03407234211._1 | |
889 | + | let userUnitsBalance = $t03407234211._2 | |
890 | + | let userUnitsSharesReferal = $t03407234211._3 | |
891 | + | $Tuple2(nil, $Tuple2(userUnitsBalance, userUnitsSharesReferal)) | |
892 | + | } | |
893 | + | ||
894 | + | ||
895 | + | ||
896 | + | @Callable(i) | |
897 | + | func setReferer (codehash_,address_) = { | |
898 | + | let err = if (_onlyManager(i.caller)) | |
899 | + | then _whenInitialized() | |
900 | + | else false | |
901 | + | if ((err == err)) | |
902 | + | then $Tuple2(_saveReferer(codehash_, address_), unit) | |
903 | + | else throw("Strict value is not equal to itself.") | |
904 | + | } | |
905 | + | ||
906 | + | ||
907 | + | ||
908 | + | @Callable(i) | |
909 | + | func setManager (manager_) = { | |
910 | + | let err = if (if (_onlyThisContract(i.caller)) | |
911 | + | then _whenInitialized() | |
912 | + | else false) | |
913 | + | then _validateAddress(manager_, "setManager: invalid manager") | |
914 | + | else false | |
915 | + | if ((err == err)) | |
916 | + | then $Tuple2(_saveManager(addressFromStringValue(manager_)), unit) | |
917 | + | else throw("Strict value is not equal to itself.") | |
640 | 918 | } | |
641 | 919 | ||
642 | 920 | ||
643 | 921 | ||
644 | 922 | @Callable(i) | |
645 | 923 | func updateCallerContract (callerContract_) = { | |
646 | 924 | let err = if (_onlyThisContract(i.caller)) | |
647 | 925 | then _whenInitialized() | |
648 | 926 | else false | |
649 | 927 | if ((err == err)) | |
650 | 928 | then $Tuple2(_saveCallerContract(callerContract_), unit) | |
651 | 929 | else throw("Strict value is not equal to itself.") | |
652 | 930 | } | |
653 | 931 | ||
654 | 932 | ||
655 | 933 | ||
656 | 934 | @Callable(i) | |
657 | 935 | func pause () = { | |
658 | 936 | let err = if (if (_onlyPauser(i.caller)) | |
659 | 937 | then _whenInitialized() | |
660 | 938 | else false) | |
661 | 939 | then _whenNotPaused() | |
662 | 940 | else false | |
663 | 941 | if ((err == err)) | |
664 | 942 | then $Tuple2(_savePause(true), unit) | |
665 | 943 | else throw("Strict value is not equal to itself.") | |
666 | 944 | } | |
667 | 945 | ||
668 | 946 | ||
669 | 947 | ||
670 | 948 | @Callable(i) | |
671 | 949 | func unpause () = { | |
672 | 950 | let err = if (if (_onlyPauser(i.caller)) | |
673 | 951 | then _whenInitialized() | |
674 | 952 | else false) | |
675 | 953 | then _whenPaused() | |
676 | 954 | else false | |
677 | 955 | if ((err == err)) | |
678 | 956 | then $Tuple2(_savePause(false), unit) | |
679 | 957 | else throw("Strict value is not equal to itself.") | |
680 | 958 | } | |
681 | 959 | ||
682 | 960 | ||
683 | 961 | ||
684 | 962 | @Callable(i) | |
685 | 963 | func updatePauser (pauser_) = { | |
686 | 964 | let err = if (if (_onlyThisContract(i.caller)) | |
687 | 965 | then _whenInitialized() | |
688 | 966 | else false) | |
689 | 967 | then _validateAddress(pauser_, "updatePauser: invalid pauser") | |
690 | 968 | else false | |
691 | 969 | if ((err == err)) | |
692 | 970 | then $Tuple2(_savePauser(addressFromStringValue(pauser_)), unit) | |
693 | 971 | else throw("Strict value is not equal to itself.") | |
694 | 972 | } | |
695 | 973 | ||
696 | 974 | ||
697 | 975 | ||
698 | 976 | @Callable(i) | |
699 | 977 | func setMultisig (multisig_) = { | |
700 | 978 | let err = if (_onlyThisContract(i.caller)) | |
701 | 979 | then _validateAddress(multisig_, "setMultisig: invalid multisig") | |
702 | 980 | else false | |
703 | 981 | if ((err == err)) | |
704 | 982 | then $Tuple2(_saveMultisig(addressFromStringValue(multisig_)), unit) | |
705 | 983 | else throw("Strict value is not equal to itself.") | |
706 | 984 | } | |
707 | 985 | ||
708 | 986 | ||
709 | 987 | @Verifier(tx) | |
710 | 988 | func verify () = match getString(KEY_MULTISIG) { | |
711 | 989 | case multisig: String => | |
712 | 990 | valueOrElse(getBoolean(addressFromStringValue(multisig), makeString([KEY_STATUS, toString(this), toBase58String(tx.id)], SEPARATOR)), false) | |
713 | 991 | case _ => | |
714 | 992 | sigVerify(tx.bodyBytes, tx.proofs[0], tx.senderPublicKey) | |
715 | 993 | } | |
716 | 994 |
github/deemru/w8io/c3f4982 100.42 ms ◑