{
  "address": "0xd09713b05410d353d12E35D678c51540F5097a67",
  "abi": [
    {
      "inputs": [
        {
          "internalType": "contract IPropelCore",
          "name": "_PropelCore",
          "type": "address"
        },
        {
          "internalType": "contract IPropelUSD",
          "name": "_PropelUSDAddress",
          "type": "address"
        },
        {
          "internalType": "address",
          "name": "_factory",
          "type": "address"
        },
        {
          "internalType": "address",
          "name": "_liquidationManager",
          "type": "address"
        },
        {
          "internalType": "address",
          "name": "_communityIssuance",
          "type": "address"
        }
      ],
      "stateMutability": "nonpayable",
      "type": "constructor"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": true,
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        },
        {
          "indexed": false,
          "internalType": "uint256[]",
          "name": "_collateral",
          "type": "uint256[]"
        }
      ],
      "name": "CollateralGainWithdrawn",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "address",
          "name": "oldCollateral",
          "type": "address"
        },
        {
          "indexed": false,
          "internalType": "address",
          "name": "newCollateral",
          "type": "address"
        }
      ],
      "name": "CollateralOverwritten",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": true,
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        },
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_P",
          "type": "uint256"
        },
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_G",
          "type": "uint256"
        }
      ],
      "name": "DepositSnapshotUpdated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_currentEpoch",
          "type": "uint128"
        }
      ],
      "name": "EpochUpdated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_G",
          "type": "uint256"
        },
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_epoch",
          "type": "uint128"
        },
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_scale",
          "type": "uint128"
        }
      ],
      "name": "G_Updated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_P",
          "type": "uint256"
        }
      ],
      "name": "P_Updated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": true,
          "internalType": "address",
          "name": "account",
          "type": "address"
        },
        {
          "indexed": true,
          "internalType": "address",
          "name": "recipient",
          "type": "address"
        },
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "claimed",
          "type": "uint256"
        }
      ],
      "name": "RewardClaimed",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "idx",
          "type": "uint256"
        },
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_S",
          "type": "uint256"
        },
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_epoch",
          "type": "uint128"
        },
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_scale",
          "type": "uint128"
        }
      ],
      "name": "S_Updated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint128",
          "name": "_currentScale",
          "type": "uint128"
        }
      ],
      "name": "ScaleUpdated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_newBalance",
          "type": "uint256"
        }
      ],
      "name": "StabilityPoolPropelUSDBalanceUpdated",
      "type": "event"
    },
    {
      "anonymous": false,
      "inputs": [
        {
          "indexed": true,
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        },
        {
          "indexed": false,
          "internalType": "uint256",
          "name": "_newDeposit",
          "type": "uint256"
        }
      ],
      "name": "UserDepositChanged",
      "type": "event"
    },
    {
      "inputs": [],
      "name": "DECIMAL_PRECISION",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "P",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "PropelCore",
      "outputs": [
        {
          "internalType": "contract IPropelCore",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "PropelUSD",
      "outputs": [
        {
          "internalType": "contract IPropelUSD",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "SCALE_FACTOR",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "SUNSET_DURATION",
      "outputs": [
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "WETH",
      "outputs": [
        {
          "internalType": "contract IWETH",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint16",
          "name": "",
          "type": "uint16"
        }
      ],
      "name": "_sunsetIndexes",
      "outputs": [
        {
          "internalType": "uint128",
          "name": "idx",
          "type": "uint128"
        },
        {
          "internalType": "uint128",
          "name": "expiry",
          "type": "uint128"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "name": "accountDeposits",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "blast",
      "outputs": [
        {
          "internalType": "contract IBlast",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "recipient",
          "type": "address"
        },
        {
          "internalType": "uint256[]",
          "name": "collateralIndexes",
          "type": "uint256[]"
        }
      ],
      "name": "claim",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "to",
          "type": "address"
        }
      ],
      "name": "claimAllGas",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "to",
          "type": "address"
        }
      ],
      "name": "claimAllYield",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        }
      ],
      "name": "claimableReward",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        },
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "name": "collateralGainsByDepositor",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "name": "collateralTokens",
      "outputs": [
        {
          "internalType": "contract IERC20",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "communityIssuance",
      "outputs": [
        {
          "internalType": "contract ICommunityIssuance",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "currentEpoch",
      "outputs": [
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "currentScale",
      "outputs": [
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "name": "depositSnapshots",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "P",
          "type": "uint256"
        },
        {
          "internalType": "uint256",
          "name": "G",
          "type": "uint256"
        },
        {
          "internalType": "uint128",
          "name": "scale",
          "type": "uint128"
        },
        {
          "internalType": "uint128",
          "name": "epoch",
          "type": "uint128"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        },
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "name": "depositSums",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "contract IERC20",
          "name": "_collateral",
          "type": "address"
        }
      ],
      "name": "enableCollateral",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        },
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        }
      ],
      "name": "epochToScaleToG",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        },
        {
          "internalType": "uint128",
          "name": "",
          "type": "uint128"
        },
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "name": "epochToScaleToSums",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "factory",
      "outputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "getClaimableWETH",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        }
      ],
      "name": "getCompoundedDeposit",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "_depositor",
          "type": "address"
        }
      ],
      "name": "getDepositorCollateralGain",
      "outputs": [
        {
          "internalType": "uint256[]",
          "name": "collateralGains",
          "type": "uint256[]"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "getTotalPropelUSDDeposits",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "guardian",
      "outputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "contract IERC20",
          "name": "",
          "type": "address"
        }
      ],
      "name": "indexByCollateral",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "name": "lastCollateralError_Offset",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "lastDebtLossError_Offset",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "lastEsPropelError",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "liquidationManager",
      "outputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "name": "lockTime",
      "outputs": [
        {
          "internalType": "uint256",
          "name": "",
          "type": "uint256"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "contract IERC20",
          "name": "collateral",
          "type": "address"
        },
        {
          "internalType": "uint256",
          "name": "_debtToOffset",
          "type": "uint256"
        },
        {
          "internalType": "uint256",
          "name": "_collToAdd",
          "type": "uint256"
        }
      ],
      "name": "offset",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "owner",
      "outputs": [
        {
          "internalType": "address",
          "name": "",
          "type": "address"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint256",
          "name": "_amount",
          "type": "uint256"
        }
      ],
      "name": "provideToSP",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [],
      "name": "queue",
      "outputs": [
        {
          "internalType": "uint16",
          "name": "firstSunsetIndexKey",
          "type": "uint16"
        },
        {
          "internalType": "uint16",
          "name": "nextSunsetIndexKey",
          "type": "uint16"
        }
      ],
      "stateMutability": "view",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "contract IERC20",
          "name": "collateral",
          "type": "address"
        }
      ],
      "name": "startCollateralSunset",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    },
    {
      "inputs": [
        {
          "internalType": "uint256",
          "name": "_amount",
          "type": "uint256"
        }
      ],
      "name": "withdrawFromSP",
      "outputs": [],
      "stateMutability": "nonpayable",
      "type": "function"
    }
  ],
  "transactionHash": "0xdd760e10a0bc6f8e8ee859227ebb32ff4daeddd28847b7e7a07e267ab3a31fed",
  "receipt": {
    "to": null,
    "from": "0xF1658C608708172655A8e70a1624c29F956Ee63D",
    "contractAddress": "0xd09713b05410d353d12E35D678c51540F5097a67",
    "transactionIndex": 17,
    "gasUsed": "3294249",
    "logsBloom": "0x00000000000000000000000000000000000000000000000000000000002000000000000000000000000000010000000000000000000000000008000000000000000000000000000002080000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000400000000000040000000000000000000000000000000000000000010000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
    "blockHash": "0xffebc3e3c772eded1db0fe208fba1ac71a031aa9a711295229fe95eb2d0cedfc",
    "transactionHash": "0xdd760e10a0bc6f8e8ee859227ebb32ff4daeddd28847b7e7a07e267ab3a31fed",
    "logs": [
      {
        "transactionIndex": 17,
        "blockNumber": 2166427,
        "transactionHash": "0xdd760e10a0bc6f8e8ee859227ebb32ff4daeddd28847b7e7a07e267ab3a31fed",
        "address": "0x4200000000000000000000000000000000000023",
        "topics": [
          "0xcaa97ab28bae75adcb5a02786c64b44d0d3139aa521bf831cdfbe280ef246e36",
          "0x000000000000000000000000d09713b05410d353d12e35d678c51540f5097a67"
        ],
        "data": "0x0000000000000000000000000000000000000000000000000000000000000002",
        "logIndex": 36,
        "blockHash": "0xffebc3e3c772eded1db0fe208fba1ac71a031aa9a711295229fe95eb2d0cedfc"
      }
    ],
    "blockNumber": 2166427,
    "cumulativeGasUsed": "5120586",
    "status": 1,
    "byzantium": true
  },
  "args": [
    "0x8E92506660a9e523FE144e21d2A50B43045fdEFd",
    "0x47c6413161E35ab40744453957d95063051a97A0",
    "0x3ee1d388d4b7d5f0798f4720a4bb382ed3beee0b",
    "0xb92fcffb30fb16517439e667e045eef041d5a48f",
    "0x0b1955c41AcC0137237077fB46c036A09e2a78e5"
  ],
  "numDeployments": 1,
  "solcInputHash": "4de37676d1c004b36b5963ce08e9eb57",
  "metadata": "{\"compiler\":{\"version\":\"0.8.19+commit.7dd6d404\"},\"language\":\"Solidity\",\"output\":{\"abi\":[{\"inputs\":[{\"internalType\":\"contract IPropelCore\",\"name\":\"_PropelCore\",\"type\":\"address\"},{\"internalType\":\"contract IPropelUSD\",\"name\":\"_PropelUSDAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_factory\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_liquidationManager\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"_communityIssuance\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256[]\",\"name\":\"_collateral\",\"type\":\"uint256[]\"}],\"name\":\"CollateralGainWithdrawn\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"address\",\"name\":\"oldCollateral\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"newCollateral\",\"type\":\"address\"}],\"name\":\"CollateralOverwritten\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_P\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_G\",\"type\":\"uint256\"}],\"name\":\"DepositSnapshotUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_currentEpoch\",\"type\":\"uint128\"}],\"name\":\"EpochUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_G\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_epoch\",\"type\":\"uint128\"},{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_scale\",\"type\":\"uint128\"}],\"name\":\"G_Updated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_P\",\"type\":\"uint256\"}],\"name\":\"P_Updated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"account\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"claimed\",\"type\":\"uint256\"}],\"name\":\"RewardClaimed\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"idx\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_S\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_epoch\",\"type\":\"uint128\"},{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_scale\",\"type\":\"uint128\"}],\"name\":\"S_Updated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint128\",\"name\":\"_currentScale\",\"type\":\"uint128\"}],\"name\":\"ScaleUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_newBalance\",\"type\":\"uint256\"}],\"name\":\"StabilityPoolPropelUSDBalanceUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"_newDeposit\",\"type\":\"uint256\"}],\"name\":\"UserDepositChanged\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"DECIMAL_PRECISION\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"P\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"PropelCore\",\"outputs\":[{\"internalType\":\"contract IPropelCore\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"PropelUSD\",\"outputs\":[{\"internalType\":\"contract IPropelUSD\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"SCALE_FACTOR\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"SUNSET_DURATION\",\"outputs\":[{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"WETH\",\"outputs\":[{\"internalType\":\"contract IWETH\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint16\",\"name\":\"\",\"type\":\"uint16\"}],\"name\":\"_sunsetIndexes\",\"outputs\":[{\"internalType\":\"uint128\",\"name\":\"idx\",\"type\":\"uint128\"},{\"internalType\":\"uint128\",\"name\":\"expiry\",\"type\":\"uint128\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"name\":\"accountDeposits\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"blast\",\"outputs\":[{\"internalType\":\"contract IBlast\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"internalType\":\"uint256[]\",\"name\":\"collateralIndexes\",\"type\":\"uint256[]\"}],\"name\":\"claim\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"to\",\"type\":\"address\"}],\"name\":\"claimAllGas\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"to\",\"type\":\"address\"}],\"name\":\"claimAllYield\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"}],\"name\":\"claimableReward\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"collateralGainsByDepositor\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"collateralTokens\",\"outputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"communityIssuance\",\"outputs\":[{\"internalType\":\"contract ICommunityIssuance\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"currentEpoch\",\"outputs\":[{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"currentScale\",\"outputs\":[{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"name\":\"depositSnapshots\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"P\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"G\",\"type\":\"uint256\"},{\"internalType\":\"uint128\",\"name\":\"scale\",\"type\":\"uint128\"},{\"internalType\":\"uint128\",\"name\":\"epoch\",\"type\":\"uint128\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"depositSums\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"_collateral\",\"type\":\"address\"}],\"name\":\"enableCollateral\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"},{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"}],\"name\":\"epochToScaleToG\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"},{\"internalType\":\"uint128\",\"name\":\"\",\"type\":\"uint128\"},{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"epochToScaleToSums\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"factory\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getClaimableWETH\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"}],\"name\":\"getCompoundedDeposit\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"_depositor\",\"type\":\"address\"}],\"name\":\"getDepositorCollateralGain\",\"outputs\":[{\"internalType\":\"uint256[]\",\"name\":\"collateralGains\",\"type\":\"uint256[]\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"getTotalPropelUSDDeposits\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"guardian\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"\",\"type\":\"address\"}],\"name\":\"indexByCollateral\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"name\":\"lastCollateralError_Offset\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lastDebtLossError_Offset\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"lastEsPropelError\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"liquidationManager\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"name\":\"lockTime\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"collateral\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"_debtToOffset\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"_collToAdd\",\"type\":\"uint256\"}],\"name\":\"offset\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"_amount\",\"type\":\"uint256\"}],\"name\":\"provideToSP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"queue\",\"outputs\":[{\"internalType\":\"uint16\",\"name\":\"firstSunsetIndexKey\",\"type\":\"uint16\"},{\"internalType\":\"uint16\",\"name\":\"nextSunsetIndexKey\",\"type\":\"uint16\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"contract IERC20\",\"name\":\"collateral\",\"type\":\"address\"}],\"name\":\"startCollateralSunset\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"_amount\",\"type\":\"uint256\"}],\"name\":\"withdrawFromSP\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}],\"devdoc\":{\"kind\":\"dev\",\"methods\":{\"startCollateralSunset(address)\":{\"details\":\"IMPORTANT: When sunsetting a collateral, `TroveManager.startSunset` should be called on all TM linked to that collateral\",\"params\":{\"collateral\":\"Collateral to sunset\"}}},\"title\":\"Propel Stability Pool\",\"version\":1},\"userdoc\":{\"kind\":\"user\",\"methods\":{\"startCollateralSunset(address)\":{\"notice\":\"Starts sunsetting a collateral         During sunsetting liquidated collateral handoff to the SP will revert\"}},\"notice\":\"Based on Liquity's `StabilityPool` https://github.com/liquity/dev/blob/main/packages/contracts/contracts/StabilityPool.sol Propel's implementation is modified to support multiple collaterals. Deposits into the stability pool may be used to liquidate any supported collateral type.\",\"version\":1}},\"settings\":{\"compilationTarget\":{\"contracts/core/StabilityPool.sol\":\"StabilityPool\"},\"evmVersion\":\"paris\",\"libraries\":{},\"metadata\":{\"bytecodeHash\":\"ipfs\",\"useLiteralContent\":true},\"optimizer\":{\"enabled\":true,\"runs\":2000},\"remappings\":[]},\"sources\":{\"@openzeppelin/contracts/token/ERC20/IERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.9.0) (token/ERC20/IERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 standard as defined in the EIP.\\n */\\ninterface IERC20 {\\n    /**\\n     * @dev Emitted when `value` tokens are moved from one account (`from`) to\\n     * another (`to`).\\n     *\\n     * Note that `value` may be zero.\\n     */\\n    event Transfer(address indexed from, address indexed to, uint256 value);\\n\\n    /**\\n     * @dev Emitted when the allowance of a `spender` for an `owner` is set by\\n     * a call to {approve}. `value` is the new allowance.\\n     */\\n    event Approval(address indexed owner, address indexed spender, uint256 value);\\n\\n    /**\\n     * @dev Returns the amount of tokens in existence.\\n     */\\n    function totalSupply() external view returns (uint256);\\n\\n    /**\\n     * @dev Returns the amount of tokens owned by `account`.\\n     */\\n    function balanceOf(address account) external view returns (uint256);\\n\\n    /**\\n     * @dev Moves `amount` tokens from the caller's account to `to`.\\n     *\\n     * Returns a boolean value indicating whether the operation succeeded.\\n     *\\n     * Emits a {Transfer} event.\\n     */\\n    function transfer(address to, uint256 amount) external returns (bool);\\n\\n    /**\\n     * @dev Returns the remaining number of tokens that `spender` will be\\n     * allowed to spend on behalf of `owner` through {transferFrom}. This is\\n     * zero by default.\\n     *\\n     * This value changes when {approve} or {transferFrom} are called.\\n     */\\n    function allowance(address owner, address spender) external view returns (uint256);\\n\\n    /**\\n     * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.\\n     *\\n     * Returns a boolean value indicating whether the operation succeeded.\\n     *\\n     * IMPORTANT: Beware that changing an allowance with this method brings the risk\\n     * that someone may use both the old and the new allowance by unfortunate\\n     * transaction ordering. One possible solution to mitigate this race\\n     * condition is to first reduce the spender's allowance to 0 and set the\\n     * desired value afterwards:\\n     * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729\\n     *\\n     * Emits an {Approval} event.\\n     */\\n    function approve(address spender, uint256 amount) external returns (bool);\\n\\n    /**\\n     * @dev Moves `amount` tokens from `from` to `to` using the\\n     * allowance mechanism. `amount` is then deducted from the caller's\\n     * allowance.\\n     *\\n     * Returns a boolean value indicating whether the operation succeeded.\\n     *\\n     * Emits a {Transfer} event.\\n     */\\n    function transferFrom(address from, address to, uint256 amount) external returns (bool);\\n}\\n\",\"keccak256\":\"0x287b55befed2961a7eabd7d7b1b2839cbca8a5b80ef8dcbb25ed3d4c2002c305\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/extensions/IERC20Permit.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.9.4) (token/ERC20/extensions/IERC20Permit.sol)\\n\\npragma solidity ^0.8.0;\\n\\n/**\\n * @dev Interface of the ERC20 Permit extension allowing approvals to be made via signatures, as defined in\\n * https://eips.ethereum.org/EIPS/eip-2612[EIP-2612].\\n *\\n * Adds the {permit} method, which can be used to change an account's ERC20 allowance (see {IERC20-allowance}) by\\n * presenting a message signed by the account. By not relying on {IERC20-approve}, the token holder account doesn't\\n * need to send a transaction, and thus is not required to hold Ether at all.\\n *\\n * ==== Security Considerations\\n *\\n * There are two important considerations concerning the use of `permit`. The first is that a valid permit signature\\n * expresses an allowance, and it should not be assumed to convey additional meaning. In particular, it should not be\\n * considered as an intention to spend the allowance in any specific way. The second is that because permits have\\n * built-in replay protection and can be submitted by anyone, they can be frontrun. A protocol that uses permits should\\n * take this into consideration and allow a `permit` call to fail. Combining these two aspects, a pattern that may be\\n * generally recommended is:\\n *\\n * ```solidity\\n * function doThingWithPermit(..., uint256 value, uint256 deadline, uint8 v, bytes32 r, bytes32 s) public {\\n *     try token.permit(msg.sender, address(this), value, deadline, v, r, s) {} catch {}\\n *     doThing(..., value);\\n * }\\n *\\n * function doThing(..., uint256 value) public {\\n *     token.safeTransferFrom(msg.sender, address(this), value);\\n *     ...\\n * }\\n * ```\\n *\\n * Observe that: 1) `msg.sender` is used as the owner, leaving no ambiguity as to the signer intent, and 2) the use of\\n * `try/catch` allows the permit to fail and makes the code tolerant to frontrunning. (See also\\n * {SafeERC20-safeTransferFrom}).\\n *\\n * Additionally, note that smart contract wallets (such as Argent or Safe) are not able to produce permit signatures, so\\n * contracts should have entry points that don't rely on permit.\\n */\\ninterface IERC20Permit {\\n    /**\\n     * @dev Sets `value` as the allowance of `spender` over ``owner``'s tokens,\\n     * given ``owner``'s signed approval.\\n     *\\n     * IMPORTANT: The same issues {IERC20-approve} has related to transaction\\n     * ordering also apply here.\\n     *\\n     * Emits an {Approval} event.\\n     *\\n     * Requirements:\\n     *\\n     * - `spender` cannot be the zero address.\\n     * - `deadline` must be a timestamp in the future.\\n     * - `v`, `r` and `s` must be a valid `secp256k1` signature from `owner`\\n     * over the EIP712-formatted function arguments.\\n     * - the signature must use ``owner``'s current nonce (see {nonces}).\\n     *\\n     * For more information on the signature format, see the\\n     * https://eips.ethereum.org/EIPS/eip-2612#specification[relevant EIP\\n     * section].\\n     *\\n     * CAUTION: See Security Considerations above.\\n     */\\n    function permit(\\n        address owner,\\n        address spender,\\n        uint256 value,\\n        uint256 deadline,\\n        uint8 v,\\n        bytes32 r,\\n        bytes32 s\\n    ) external;\\n\\n    /**\\n     * @dev Returns the current nonce for `owner`. This value must be\\n     * included whenever a signature is generated for {permit}.\\n     *\\n     * Every successful call to {permit} increases ``owner``'s nonce by one. This\\n     * prevents a signature from being used multiple times.\\n     */\\n    function nonces(address owner) external view returns (uint256);\\n\\n    /**\\n     * @dev Returns the domain separator used in the encoding of the signature for {permit}, as defined by {EIP712}.\\n     */\\n    // solhint-disable-next-line func-name-mixedcase\\n    function DOMAIN_SEPARATOR() external view returns (bytes32);\\n}\\n\",\"keccak256\":\"0xb264c03a3442eb37a68ad620cefd1182766b58bee6cec40343480392d6b14d69\",\"license\":\"MIT\"},\"@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.9.3) (token/ERC20/utils/SafeERC20.sol)\\n\\npragma solidity ^0.8.0;\\n\\nimport \\\"../IERC20.sol\\\";\\nimport \\\"../extensions/IERC20Permit.sol\\\";\\nimport \\\"../../../utils/Address.sol\\\";\\n\\n/**\\n * @title SafeERC20\\n * @dev Wrappers around ERC20 operations that throw on failure (when the token\\n * contract returns false). Tokens that return no value (and instead revert or\\n * throw on failure) are also supported, non-reverting calls are assumed to be\\n * successful.\\n * To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,\\n * which allows you to call the safe operations as `token.safeTransfer(...)`, etc.\\n */\\nlibrary SafeERC20 {\\n    using Address for address;\\n\\n    /**\\n     * @dev Transfer `value` amount of `token` from the calling contract to `to`. If `token` returns no value,\\n     * non-reverting calls are assumed to be successful.\\n     */\\n    function safeTransfer(IERC20 token, address to, uint256 value) internal {\\n        _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));\\n    }\\n\\n    /**\\n     * @dev Transfer `value` amount of `token` from `from` to `to`, spending the approval given by `from` to the\\n     * calling contract. If `token` returns no value, non-reverting calls are assumed to be successful.\\n     */\\n    function safeTransferFrom(IERC20 token, address from, address to, uint256 value) internal {\\n        _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));\\n    }\\n\\n    /**\\n     * @dev Deprecated. This function has issues similar to the ones found in\\n     * {IERC20-approve}, and its usage is discouraged.\\n     *\\n     * Whenever possible, use {safeIncreaseAllowance} and\\n     * {safeDecreaseAllowance} instead.\\n     */\\n    function safeApprove(IERC20 token, address spender, uint256 value) internal {\\n        // safeApprove should only be called when setting an initial allowance,\\n        // or when resetting it to zero. To increase and decrease it, use\\n        // 'safeIncreaseAllowance' and 'safeDecreaseAllowance'\\n        require(\\n            (value == 0) || (token.allowance(address(this), spender) == 0),\\n            \\\"SafeERC20: approve from non-zero to non-zero allowance\\\"\\n        );\\n        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));\\n    }\\n\\n    /**\\n     * @dev Increase the calling contract's allowance toward `spender` by `value`. If `token` returns no value,\\n     * non-reverting calls are assumed to be successful.\\n     */\\n    function safeIncreaseAllowance(IERC20 token, address spender, uint256 value) internal {\\n        uint256 oldAllowance = token.allowance(address(this), spender);\\n        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, oldAllowance + value));\\n    }\\n\\n    /**\\n     * @dev Decrease the calling contract's allowance toward `spender` by `value`. If `token` returns no value,\\n     * non-reverting calls are assumed to be successful.\\n     */\\n    function safeDecreaseAllowance(IERC20 token, address spender, uint256 value) internal {\\n        unchecked {\\n            uint256 oldAllowance = token.allowance(address(this), spender);\\n            require(oldAllowance >= value, \\\"SafeERC20: decreased allowance below zero\\\");\\n            _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, oldAllowance - value));\\n        }\\n    }\\n\\n    /**\\n     * @dev Set the calling contract's allowance toward `spender` to `value`. If `token` returns no value,\\n     * non-reverting calls are assumed to be successful. Meant to be used with tokens that require the approval\\n     * to be set to zero before setting it to a non-zero value, such as USDT.\\n     */\\n    function forceApprove(IERC20 token, address spender, uint256 value) internal {\\n        bytes memory approvalCall = abi.encodeWithSelector(token.approve.selector, spender, value);\\n\\n        if (!_callOptionalReturnBool(token, approvalCall)) {\\n            _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, 0));\\n            _callOptionalReturn(token, approvalCall);\\n        }\\n    }\\n\\n    /**\\n     * @dev Use a ERC-2612 signature to set the `owner` approval toward `spender` on `token`.\\n     * Revert on invalid signature.\\n     */\\n    function safePermit(\\n        IERC20Permit token,\\n        address owner,\\n        address spender,\\n        uint256 value,\\n        uint256 deadline,\\n        uint8 v,\\n        bytes32 r,\\n        bytes32 s\\n    ) internal {\\n        uint256 nonceBefore = token.nonces(owner);\\n        token.permit(owner, spender, value, deadline, v, r, s);\\n        uint256 nonceAfter = token.nonces(owner);\\n        require(nonceAfter == nonceBefore + 1, \\\"SafeERC20: permit did not succeed\\\");\\n    }\\n\\n    /**\\n     * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement\\n     * on the return value: the return value is optional (but if data is returned, it must not be false).\\n     * @param token The token targeted by the call.\\n     * @param data The call data (encoded using abi.encode or one of its variants).\\n     */\\n    function _callOptionalReturn(IERC20 token, bytes memory data) private {\\n        // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since\\n        // we're implementing it ourselves. We use {Address-functionCall} to perform this call, which verifies that\\n        // the target address contains contract code and also asserts for success in the low-level call.\\n\\n        bytes memory returndata = address(token).functionCall(data, \\\"SafeERC20: low-level call failed\\\");\\n        require(returndata.length == 0 || abi.decode(returndata, (bool)), \\\"SafeERC20: ERC20 operation did not succeed\\\");\\n    }\\n\\n    /**\\n     * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement\\n     * on the return value: the return value is optional (but if data is returned, it must not be false).\\n     * @param token The token targeted by the call.\\n     * @param data The call data (encoded using abi.encode or one of its variants).\\n     *\\n     * This is a variant of {_callOptionalReturn} that silents catches all reverts and returns a bool instead.\\n     */\\n    function _callOptionalReturnBool(IERC20 token, bytes memory data) private returns (bool) {\\n        // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since\\n        // we're implementing it ourselves. We cannot use {Address-functionCall} here since this should return false\\n        // and not revert is the subcall reverts.\\n\\n        (bool success, bytes memory returndata) = address(token).call(data);\\n        return\\n            success && (returndata.length == 0 || abi.decode(returndata, (bool))) && Address.isContract(address(token));\\n    }\\n}\\n\",\"keccak256\":\"0xabefac93435967b4d36a4fabcbdbb918d1f0b7ae3c3d85bc30923b326c927ed1\",\"license\":\"MIT\"},\"@openzeppelin/contracts/utils/Address.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n// OpenZeppelin Contracts (last updated v4.9.0) (utils/Address.sol)\\n\\npragma solidity ^0.8.1;\\n\\n/**\\n * @dev Collection of functions related to the address type\\n */\\nlibrary Address {\\n    /**\\n     * @dev Returns true if `account` is a contract.\\n     *\\n     * [IMPORTANT]\\n     * ====\\n     * It is unsafe to assume that an address for which this function returns\\n     * false is an externally-owned account (EOA) and not a contract.\\n     *\\n     * Among others, `isContract` will return false for the following\\n     * types of addresses:\\n     *\\n     *  - an externally-owned account\\n     *  - a contract in construction\\n     *  - an address where a contract will be created\\n     *  - an address where a contract lived, but was destroyed\\n     *\\n     * Furthermore, `isContract` will also return true if the target contract within\\n     * the same transaction is already scheduled for destruction by `SELFDESTRUCT`,\\n     * which only has an effect at the end of a transaction.\\n     * ====\\n     *\\n     * [IMPORTANT]\\n     * ====\\n     * You shouldn't rely on `isContract` to protect against flash loan attacks!\\n     *\\n     * Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets\\n     * like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract\\n     * constructor.\\n     * ====\\n     */\\n    function isContract(address account) internal view returns (bool) {\\n        // This method relies on extcodesize/address.code.length, which returns 0\\n        // for contracts in construction, since the code is only stored at the end\\n        // of the constructor execution.\\n\\n        return account.code.length > 0;\\n    }\\n\\n    /**\\n     * @dev Replacement for Solidity's `transfer`: sends `amount` wei to\\n     * `recipient`, forwarding all available gas and reverting on errors.\\n     *\\n     * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost\\n     * of certain opcodes, possibly making contracts go over the 2300 gas limit\\n     * imposed by `transfer`, making them unable to receive funds via\\n     * `transfer`. {sendValue} removes this limitation.\\n     *\\n     * https://consensys.net/diligence/blog/2019/09/stop-using-soliditys-transfer-now/[Learn more].\\n     *\\n     * IMPORTANT: because control is transferred to `recipient`, care must be\\n     * taken to not create reentrancy vulnerabilities. Consider using\\n     * {ReentrancyGuard} or the\\n     * https://solidity.readthedocs.io/en/v0.8.0/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].\\n     */\\n    function sendValue(address payable recipient, uint256 amount) internal {\\n        require(address(this).balance >= amount, \\\"Address: insufficient balance\\\");\\n\\n        (bool success, ) = recipient.call{value: amount}(\\\"\\\");\\n        require(success, \\\"Address: unable to send value, recipient may have reverted\\\");\\n    }\\n\\n    /**\\n     * @dev Performs a Solidity function call using a low level `call`. A\\n     * plain `call` is an unsafe replacement for a function call: use this\\n     * function instead.\\n     *\\n     * If `target` reverts with a revert reason, it is bubbled up by this\\n     * function (like regular Solidity function calls).\\n     *\\n     * Returns the raw returned data. To convert to the expected return value,\\n     * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].\\n     *\\n     * Requirements:\\n     *\\n     * - `target` must be a contract.\\n     * - calling `target` with `data` must not revert.\\n     *\\n     * _Available since v3.1._\\n     */\\n    function functionCall(address target, bytes memory data) internal returns (bytes memory) {\\n        return functionCallWithValue(target, data, 0, \\\"Address: low-level call failed\\\");\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with\\n     * `errorMessage` as a fallback revert reason when `target` reverts.\\n     *\\n     * _Available since v3.1._\\n     */\\n    function functionCall(\\n        address target,\\n        bytes memory data,\\n        string memory errorMessage\\n    ) internal returns (bytes memory) {\\n        return functionCallWithValue(target, data, 0, errorMessage);\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\\n     * but also transferring `value` wei to `target`.\\n     *\\n     * Requirements:\\n     *\\n     * - the calling contract must have an ETH balance of at least `value`.\\n     * - the called Solidity function must be `payable`.\\n     *\\n     * _Available since v3.1._\\n     */\\n    function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) {\\n        return functionCallWithValue(target, data, value, \\\"Address: low-level call with value failed\\\");\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but\\n     * with `errorMessage` as a fallback revert reason when `target` reverts.\\n     *\\n     * _Available since v3.1._\\n     */\\n    function functionCallWithValue(\\n        address target,\\n        bytes memory data,\\n        uint256 value,\\n        string memory errorMessage\\n    ) internal returns (bytes memory) {\\n        require(address(this).balance >= value, \\\"Address: insufficient balance for call\\\");\\n        (bool success, bytes memory returndata) = target.call{value: value}(data);\\n        return verifyCallResultFromTarget(target, success, returndata, errorMessage);\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\\n     * but performing a static call.\\n     *\\n     * _Available since v3.3._\\n     */\\n    function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {\\n        return functionStaticCall(target, data, \\\"Address: low-level static call failed\\\");\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\\n     * but performing a static call.\\n     *\\n     * _Available since v3.3._\\n     */\\n    function functionStaticCall(\\n        address target,\\n        bytes memory data,\\n        string memory errorMessage\\n    ) internal view returns (bytes memory) {\\n        (bool success, bytes memory returndata) = target.staticcall(data);\\n        return verifyCallResultFromTarget(target, success, returndata, errorMessage);\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],\\n     * but performing a delegate call.\\n     *\\n     * _Available since v3.4._\\n     */\\n    function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {\\n        return functionDelegateCall(target, data, \\\"Address: low-level delegate call failed\\\");\\n    }\\n\\n    /**\\n     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],\\n     * but performing a delegate call.\\n     *\\n     * _Available since v3.4._\\n     */\\n    function functionDelegateCall(\\n        address target,\\n        bytes memory data,\\n        string memory errorMessage\\n    ) internal returns (bytes memory) {\\n        (bool success, bytes memory returndata) = target.delegatecall(data);\\n        return verifyCallResultFromTarget(target, success, returndata, errorMessage);\\n    }\\n\\n    /**\\n     * @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling\\n     * the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract.\\n     *\\n     * _Available since v4.8._\\n     */\\n    function verifyCallResultFromTarget(\\n        address target,\\n        bool success,\\n        bytes memory returndata,\\n        string memory errorMessage\\n    ) internal view returns (bytes memory) {\\n        if (success) {\\n            if (returndata.length == 0) {\\n                // only check isContract if the call was successful and the return data is empty\\n                // otherwise we already know that it was a contract\\n                require(isContract(target), \\\"Address: call to non-contract\\\");\\n            }\\n            return returndata;\\n        } else {\\n            _revert(returndata, errorMessage);\\n        }\\n    }\\n\\n    /**\\n     * @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the\\n     * revert reason or using the provided one.\\n     *\\n     * _Available since v4.3._\\n     */\\n    function verifyCallResult(\\n        bool success,\\n        bytes memory returndata,\\n        string memory errorMessage\\n    ) internal pure returns (bytes memory) {\\n        if (success) {\\n            return returndata;\\n        } else {\\n            _revert(returndata, errorMessage);\\n        }\\n    }\\n\\n    function _revert(bytes memory returndata, string memory errorMessage) private pure {\\n        // Look for revert reason and bubble it up if present\\n        if (returndata.length > 0) {\\n            // The easiest way to bubble the revert reason is using memory via assembly\\n            /// @solidity memory-safe-assembly\\n            assembly {\\n                let returndata_size := mload(returndata)\\n                revert(add(32, returndata), returndata_size)\\n            }\\n        } else {\\n            revert(errorMessage);\\n        }\\n    }\\n}\\n\",\"keccak256\":\"0x006dd67219697fe68d7fbfdea512e7c4cb64a43565ed86171d67e844982da6fa\",\"license\":\"MIT\"},\"contracts/core/StabilityPool.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol\\\";\\nimport \\\"../dependencies/BlastWrapper.sol\\\";\\nimport \\\"../dependencies/SystemStart.sol\\\";\\nimport \\\"../dependencies/PropelMath.sol\\\";\\nimport \\\"../interfaces/IPropelUSD.sol\\\";\\nimport \\\"../interfaces/ICommunityIssuance.sol\\\";\\nimport \\\"../interfaces/IStabilityPool.sol\\\";\\n\\n/**\\n    @title Propel Stability Pool\\n    @notice Based on Liquity's `StabilityPool`\\n            https://github.com/liquity/dev/blob/main/packages/contracts/contracts/StabilityPool.sol\\n\\n            Propel's implementation is modified to support multiple collaterals. Deposits into\\n            the stability pool may be used to liquidate any supported collateral type.\\n */\\ncontract StabilityPool is IStabilityPool, BlastWrapper {\\n\\tusing SafeERC20 for IERC20;\\n\\n\\tuint256 public constant DECIMAL_PRECISION = 1e18;\\n\\tuint128 public constant SUNSET_DURATION = 180 days;\\n\\n\\tIPropelUSD public immutable PropelUSD;\\n\\taddress public immutable factory;\\n\\taddress public immutable liquidationManager;\\n\\tICommunityIssuance public immutable communityIssuance;\\n\\n\\tmapping(IERC20 => uint256) public indexByCollateral;\\n\\tIERC20[] public collateralTokens;\\n\\n\\t// Tracker for Debt held in the pool. Changes when users deposit/withdraw, and when Trove debt is offset.\\n\\tuint256 internal totalPropelUSDDeposits;\\n\\tmapping(address => uint256) public lockTime;\\n\\tmapping(address => uint256) public accountDeposits; // depositor address -> initial deposit\\n\\tmapping(address => Snapshots) public depositSnapshots; // depositor address -> snapshots struct\\n\\n\\t// index values are mapped against the values within `collateralTokens`\\n\\tmapping(address => uint256[256]) public depositSums; // depositor address -> sums\\n\\n\\tmapping(address => uint256[256]) public collateralGainsByDepositor;\\n\\n\\tmapping(address => uint256) private storedPendingReward;\\n\\n\\t/*  Product 'P': Running product by which to multiply an initial deposit, in order to find the current compounded deposit,\\n\\t * after a series of liquidations have occurred, each of which cancel some debt with the deposit.\\n\\t *\\n\\t * During its lifetime, a deposit's value evolves from d_t to d_t * P / P_t , where P_t\\n\\t * is the snapshot of P taken at the instant the deposit was made. 18-digit decimal.\\n\\t */\\n\\tuint256 public P = DECIMAL_PRECISION;\\n\\n\\tuint256 public constant SCALE_FACTOR = 1e9;\\n\\n\\t// Each time the scale of P shifts by SCALE_FACTOR, the scale is incremented by 1\\n\\tuint128 public currentScale;\\n\\n\\t// With each offset that fully empties the Pool, the epoch is incremented by 1\\n\\tuint128 public currentEpoch;\\n\\n\\t/* collateral Gain sum 'S': During its lifetime, each deposit d_t earns a collateral gain of ( d_t * [S - S_t] )/P_t, where S_t\\n\\t * is the depositor's snapshot of S taken at the time t when the deposit was made.\\n\\t *\\n\\t * The 'S' sums are stored in a nested mapping (epoch => scale => sum):\\n\\t *\\n\\t * - The inner mapping records the sum S at different scales\\n\\t * - The outer mapping records the (scale => sum) mappings, for different epochs.\\n\\t */\\n\\n\\t// index values are mapped against the values within `collateralTokens`\\n\\tmapping(uint128 => mapping(uint128 => uint256[256])) public epochToScaleToSums;\\n\\n\\t/*\\n\\t * Similarly, the sum 'G' is used to calculate esPropel gains. During it's lifetime, each deposit d_t earns a esPropel gain of\\n\\t *  ( d_t * [G - G_t] )/P_t, where G_t is the depositor's snapshot of G taken at time t when  the deposit was made.\\n\\t *\\n\\t *  esPropel reward events occur are triggered by depositor operations (new deposit, topup, withdrawal), and liquidations.\\n\\t *  In each case, the esPropel reward is issued (i.e. G is updated), before other state changes are made.\\n\\t */\\n\\tmapping(uint128 => mapping(uint128 => uint256)) public epochToScaleToG;\\n\\n\\t// Error tracker for the error correction in the esPropel issuance calculation\\n\\tuint256 public lastEsPropelError;\\n\\t// Error trackers for the error correction in the offset calculation\\n\\tuint256[256] public lastCollateralError_Offset;\\n\\tuint256 public lastDebtLossError_Offset;\\n\\n\\tmapping(uint16 => SunsetIndex) public _sunsetIndexes;\\n\\n\\tQueue public queue;\\n\\n\\tstruct Snapshots {\\n\\t\\tuint256 P;\\n\\t\\tuint256 G;\\n\\t\\tuint128 scale;\\n\\t\\tuint128 epoch;\\n\\t}\\n\\n\\tstruct SunsetIndex {\\n\\t\\tuint128 idx;\\n\\t\\tuint128 expiry;\\n\\t}\\n\\tstruct Queue {\\n\\t\\tuint16 firstSunsetIndexKey;\\n\\t\\tuint16 nextSunsetIndexKey;\\n\\t}\\n\\n\\tconstructor(IPropelCore _PropelCore, IPropelUSD _PropelUSDAddress, address _factory, address _liquidationManager, address _communityIssuance) BlastWrapper(_PropelCore) {\\n\\t\\tPropelUSD = _PropelUSDAddress;\\n\\t\\tfactory = _factory;\\n\\t\\tliquidationManager = _liquidationManager;\\n\\t\\tcommunityIssuance = ICommunityIssuance(_communityIssuance);\\n\\t}\\n\\n\\tfunction enableCollateral(IERC20 _collateral) external {\\n\\t\\trequire(msg.sender == factory, \\\"Not factory\\\");\\n\\t\\tuint256 length = collateralTokens.length;\\n\\t\\tbool collateralEnabled;\\n\\t\\tfor (uint256 i = 0; i < length; i++) {\\n\\t\\t\\tif (collateralTokens[i] == IERC20(_collateral)) {\\n\\t\\t\\t\\tcollateralEnabled = true;\\n\\t\\t\\t\\tbreak;\\n\\t\\t\\t}\\n\\t\\t}\\n\\t\\tif (!collateralEnabled) {\\n\\t\\t\\tQueue memory queueCached = queue;\\n\\t\\t\\tif (queueCached.nextSunsetIndexKey > queueCached.firstSunsetIndexKey) {\\n\\t\\t\\t\\tSunsetIndex memory sIdx = _sunsetIndexes[queueCached.firstSunsetIndexKey];\\n\\t\\t\\t\\tif (sIdx.expiry < block.timestamp) {\\n\\t\\t\\t\\t\\tdelete _sunsetIndexes[queue.firstSunsetIndexKey++];\\n\\t\\t\\t\\t\\t_overwriteCollateral(_collateral, sIdx.idx);\\n\\t\\t\\t\\t\\treturn;\\n\\t\\t\\t\\t}\\n\\t\\t\\t}\\n\\t\\t\\tcollateralTokens.push(_collateral);\\n\\t\\t\\tindexByCollateral[_collateral] = collateralTokens.length;\\n\\t\\t} else {\\n\\t\\t\\t// revert if the factory is trying to deploy a new TM with a sunset collateral\\n\\t\\t\\trequire(indexByCollateral[_collateral] > 0, \\\"Collateral is sunsetting\\\");\\n\\t\\t}\\n\\t}\\n\\n\\tfunction _overwriteCollateral(IERC20 _newCollateral, uint256 idx) internal {\\n\\t\\trequire(indexByCollateral[_newCollateral] == 0, \\\"Collateral must be sunset\\\");\\n\\t\\tuint256 length = collateralTokens.length;\\n\\t\\trequire(idx < length, \\\"Index too large\\\");\\n\\t\\tuint256 externalLoopEnd = currentEpoch;\\n\\t\\tuint256 internalLoopEnd = currentScale;\\n\\t\\tfor (uint128 i; i <= externalLoopEnd; ) {\\n\\t\\t\\tfor (uint128 j; j <= internalLoopEnd; ) {\\n\\t\\t\\t\\tepochToScaleToSums[i][j][idx] = 0;\\n\\t\\t\\t\\tunchecked {\\n\\t\\t\\t\\t\\t++j;\\n\\t\\t\\t\\t}\\n\\t\\t\\t}\\n\\t\\t\\tunchecked {\\n\\t\\t\\t\\t++i;\\n\\t\\t\\t}\\n\\t\\t}\\n\\t\\tindexByCollateral[_newCollateral] = idx + 1;\\n\\t\\temit CollateralOverwritten(address(collateralTokens[idx]), address(_newCollateral));\\n\\t\\tcollateralTokens[idx] = _newCollateral;\\n\\t}\\n\\n\\t/**\\n     * @notice Starts sunsetting a collateral\\n     *         During sunsetting liquidated collateral handoff to the SP will revert\\n        @dev IMPORTANT: When sunsetting a collateral, `TroveManager.startSunset`\\n                        should be called on all TM linked to that collateral\\n        @param collateral Collateral to sunset\\n\\n     */\\n\\tfunction startCollateralSunset(IERC20 collateral) external onlyOwner {\\n\\t\\trequire(indexByCollateral[collateral] > 0, \\\"Collateral already sunsetting\\\");\\n\\t\\t_sunsetIndexes[queue.nextSunsetIndexKey++] = SunsetIndex(uint128(indexByCollateral[collateral] - 1), uint128(block.timestamp + SUNSET_DURATION));\\n\\t\\tdelete indexByCollateral[collateral]; //This will prevent calls to the SP in case of liquidations\\n\\t}\\n\\n\\tfunction getTotalPropelUSDDeposits() external view returns (uint256) {\\n\\t\\treturn totalPropelUSDDeposits;\\n\\t}\\n\\n\\t// --- External Depositor Functions ---\\n\\n\\t/*  provideToSP():\\n\\t *\\n\\t * - Triggers a esPropel issuance, based on time passed since the last issuance. The esPropel issuance is shared between *all* depositors and front ends\\n\\t * - Tags the deposit with the provided front end tag param, if it's a new deposit\\n\\t * - Sends depositor's accumulated gains (esPropel, collateral) to depositor\\n\\t * - Sends the tagged front end's accumulated esPropel gains to the tagged front end\\n\\t * - Increases deposit and tagged front end's stake, and takes new snapshots for each.\\n\\t */\\n\\tfunction provideToSP(uint256 _amount) external {\\n\\t\\trequire(!PropelCore.paused(), \\\"Deposits are paused\\\");\\n\\t\\trequire(_amount > 0, \\\"StabilityPool: Amount must be non-zero\\\");\\n\\t\\tlockTime[msg.sender] = block.timestamp;\\n\\t\\t_triggerRewardIssuance();\\n\\n\\t\\t_accrueDepositorCollateralGain(msg.sender);\\n\\n\\t\\tuint256 compoundedDeposit = getCompoundedDeposit(msg.sender);\\n\\n\\t\\t_accrueRewards(msg.sender);\\n\\n\\t\\tPropelUSD.sendToSP(msg.sender, _amount);\\n\\t\\tuint256 newTotalPropelUSDDeposits = totalPropelUSDDeposits + _amount;\\n\\t\\ttotalPropelUSDDeposits = newTotalPropelUSDDeposits;\\n\\t\\temit StabilityPoolPropelUSDBalanceUpdated(newTotalPropelUSDDeposits);\\n\\n\\t\\tuint256 newDeposit = compoundedDeposit + _amount;\\n\\t\\taccountDeposits[msg.sender] = newDeposit;\\n\\n\\t\\t_updateSnapshots(msg.sender, newDeposit);\\n\\t\\temit UserDepositChanged(msg.sender, newDeposit);\\n\\t}\\n\\n\\t/*  withdrawFromSP():\\n\\t *\\n\\t * - Triggers a esPropel issuance, based on time passed since the last issuance. The esPropel issuance is shared between *all* depositors and front ends\\n\\t * - Removes the deposit's front end tag if it is a full withdrawal\\n\\t * - Sends all depositor's accumulated gains (esPropel, collateral) to depositor\\n\\t * - Sends the tagged front end's accumulated esPropel gains to the tagged front end\\n\\t * - Decreases deposit and tagged front end's stake, and takes new snapshots for each.\\n\\t *\\n\\t * If _amount > userDeposit, the user withdraws all of their compounded deposit.\\n\\t */\\n\\tfunction withdrawFromSP(uint256 _amount) external {\\n\\t\\tuint256 initialDeposit = accountDeposits[msg.sender];\\n\\t\\trequire(initialDeposit > 0, \\\"StabilityPool: User must have a non-zero deposit\\\");\\n\\t\\trequire(lockTime[msg.sender] != block.timestamp, \\\"StabilityPool: Withdrawal is locked\\\");\\n\\t\\t_triggerRewardIssuance();\\n\\n\\t\\t_accrueDepositorCollateralGain(msg.sender);\\n\\n\\t\\tuint256 compoundedDeposit = getCompoundedDeposit(msg.sender);\\n\\t\\tuint256 debtToWithdraw = PropelMath._min(_amount, compoundedDeposit);\\n\\n\\t\\t_accrueRewards(msg.sender);\\n\\n\\t\\tif (debtToWithdraw > 0) {\\n\\t\\t\\tPropelUSD.returnFromPool(address(this), msg.sender, debtToWithdraw);\\n\\t\\t\\t_decreaseDebt(debtToWithdraw);\\n\\t\\t}\\n\\n\\t\\t// Update deposit\\n\\t\\tuint256 newDeposit = compoundedDeposit - debtToWithdraw;\\n\\t\\taccountDeposits[msg.sender] = newDeposit;\\n\\n\\t\\t_updateSnapshots(msg.sender, newDeposit);\\n\\t\\temit UserDepositChanged(msg.sender, newDeposit);\\n\\t}\\n\\n\\tfunction claim(address recipient, uint256[] memory collateralIndexes) external {\\n\\t\\tuint256 initialDeposit = accountDeposits[msg.sender];\\n\\t\\trequire(initialDeposit > 0, \\\"StabilityPool: User must have a non-zero deposit\\\");\\n\\n\\t\\t_triggerRewardIssuance();\\n\\n\\t\\t_accrueDepositorCollateralGain(msg.sender);\\n\\n\\t\\tuint256 compoundedDeposit = getCompoundedDeposit(msg.sender);\\n\\t\\t_accrueRewards(msg.sender);\\n\\n\\t\\t// Update deposit\\n\\t\\tuint256 newDeposit = compoundedDeposit;\\n\\t\\taccountDeposits[msg.sender] = newDeposit;\\n\\n\\t\\t_updateSnapshots(msg.sender, newDeposit);\\n\\t\\temit UserDepositChanged(msg.sender, newDeposit);\\n\\t\\tuint256 amount = _claimReward(msg.sender);\\n\\t\\tif (amount > 0) {\\n\\t\\t\\tcommunityIssuance.sendEsPropel(recipient, amount);\\n\\t\\t}\\n\\t\\temit RewardClaimed(msg.sender, recipient, amount);\\n\\t\\t_claimCollateralGains(recipient, collateralIndexes);\\n\\t}\\n\\n\\t// --- esPropel issuance functions ---\\n\\n\\tfunction _triggerRewardIssuance() internal {\\n\\t\\t_updateG(communityIssuance.issueEsPropel());\\n\\t}\\n\\n\\tfunction _updateG(uint256 _esPropelIssuance) internal {\\n\\t\\tuint256 totalDebt = totalPropelUSDDeposits; // cached to save an SLOAD\\n\\t\\t/*\\n\\t\\t * When total deposits is 0, G is not updated. In this case, the Propel issued can not be obtained by later\\n\\t\\t * depositors - it is missed out on, and remains in the balanceof the Treasury contract.\\n\\t\\t *\\n\\t\\t */\\n\\t\\tif (totalDebt == 0 || _esPropelIssuance == 0) {\\n\\t\\t\\treturn;\\n\\t\\t}\\n\\n\\t\\tuint256 esPropelPerUnitStaked = _computeEsPropelPerUnitStaked(_esPropelIssuance, totalDebt);\\n\\t\\tuint128 currentEpochCached = currentEpoch;\\n\\t\\tuint128 currentScaleCached = currentScale;\\n\\t\\tuint256 marginalPropelGain = esPropelPerUnitStaked * P;\\n\\t\\tuint256 newG = epochToScaleToG[currentEpochCached][currentScaleCached] + marginalPropelGain;\\n\\t\\tepochToScaleToG[currentEpochCached][currentScaleCached] = newG;\\n\\n\\t\\temit G_Updated(newG, currentEpochCached, currentScaleCached);\\n\\t}\\n\\n\\tfunction _computeEsPropelPerUnitStaked(uint256 _esPropelIssuance, uint256 _totalPropelUSDDeposits) internal returns (uint256) {\\n\\t\\t/*\\n\\t\\t * Calculate the esPropel-per-unit staked.  Division uses a \\\"feedback\\\" error correction, to keep the\\n\\t\\t * cumulative error low in the running total G:\\n\\t\\t *\\n\\t\\t * 1) Form a numerator which compensates for the floor division error that occurred the last time this\\n\\t\\t * function was called.\\n\\t\\t * 2) Calculate \\\"per-unit-staked\\\" ratio.\\n\\t\\t * 3) Multiply the ratio back by its denominator, to reveal the current floor division error.\\n\\t\\t * 4) Store this error for use in the next correction when this function is called.\\n\\t\\t * 5) Note: static analysis tools complain about this \\\"division before multiplication\\\", however, it is intended.\\n\\t\\t */\\n\\t\\tuint256 esPropelNumerator = (_esPropelIssuance * DECIMAL_PRECISION) + lastEsPropelError;\\n\\n\\t\\tuint256 esPropelPerUnitStaked = esPropelNumerator / _totalPropelUSDDeposits;\\n\\t\\tlastEsPropelError = esPropelNumerator - (esPropelPerUnitStaked * _totalPropelUSDDeposits);\\n\\n\\t\\treturn esPropelPerUnitStaked;\\n\\t}\\n\\n\\t// --- Liquidation functions ---\\n\\n\\t/*\\n\\t * Cancels out the specified debt against the Debt contained in the Stability Pool (as far as possible)\\n\\t */\\n\\tfunction offset(IERC20 collateral, uint256 _debtToOffset, uint256 _collToAdd) external virtual {\\n\\t\\t_offset(collateral, _debtToOffset, _collToAdd);\\n\\t}\\n\\n\\tfunction _offset(IERC20 collateral, uint256 _debtToOffset, uint256 _collToAdd) internal {\\n\\t\\trequire(msg.sender == liquidationManager, \\\"StabilityPool: Caller is not Liquidation Manager\\\");\\n\\t\\tuint256 idx = indexByCollateral[collateral];\\n\\t\\tidx -= 1;\\n\\n\\t\\tuint256 totalDebt = totalPropelUSDDeposits; // cached to save an SLOAD\\n\\t\\tif (totalDebt == 0 || _debtToOffset == 0) {\\n\\t\\t\\treturn;\\n\\t\\t}\\n\\n\\t\\t_triggerRewardIssuance();\\n\\n\\t\\t(uint256 collateralGainPerUnitStaked, uint256 debtLossPerUnitStaked) = _computeRewardsPerUnitStaked(_collToAdd, _debtToOffset, totalDebt, idx);\\n\\n\\t\\t_updateRewardSumAndProduct(collateralGainPerUnitStaked, debtLossPerUnitStaked, idx); // updates S and P\\n\\n\\t\\t// Cancel the liquidated Debt debt with the Debt in the stability pool\\n\\t\\t_decreaseDebt(_debtToOffset);\\n\\t}\\n\\n\\t// --- Offset helper functions ---\\n\\n\\tfunction _computeRewardsPerUnitStaked(uint256 _collToAdd, uint256 _debtToOffset, uint256 _totalPropelUSDDeposits, uint256 idx) internal returns (uint256 collateralGainPerUnitStaked, uint256 debtLossPerUnitStaked) {\\n\\t\\t/*\\n\\t\\t * Compute the Debt and collateral rewards. Uses a \\\"feedback\\\" error correction, to keep\\n\\t\\t * the cumulative error in the P and S state variables low:\\n\\t\\t *\\n\\t\\t * 1) Form numerators which compensate for the floor division errors that occurred the last time this\\n\\t\\t * function was called.\\n\\t\\t * 2) Calculate \\\"per-unit-staked\\\" ratios.\\n\\t\\t * 3) Multiply each ratio back by its denominator, to reveal the current floor division error.\\n\\t\\t * 4) Store these errors for use in the next correction when this function is called.\\n\\t\\t * 5) Note: static analysis tools complain about this \\\"division before multiplication\\\", however, it is intended.\\n\\t\\t */\\n\\t\\tuint256 collateralNumerator = (_collToAdd * DECIMAL_PRECISION) + lastCollateralError_Offset[idx];\\n\\n\\t\\tif (_debtToOffset == _totalPropelUSDDeposits) {\\n\\t\\t\\tdebtLossPerUnitStaked = DECIMAL_PRECISION; // When the Pool depletes to 0, so does each deposit\\n\\t\\t\\tlastDebtLossError_Offset = 0;\\n\\t\\t} else {\\n\\t\\t\\tuint256 debtLossNumerator = (_debtToOffset * DECIMAL_PRECISION) - lastDebtLossError_Offset;\\n\\t\\t\\t/*\\n\\t\\t\\t * Add 1 to make error in quotient positive. We want \\\"slightly too much\\\" Debt loss,\\n\\t\\t\\t * which ensures the error in any given CompoundedDeposit favors the Stability Pool.\\n\\t\\t\\t */\\n\\t\\t\\tdebtLossPerUnitStaked = (debtLossNumerator / _totalPropelUSDDeposits) + 1;\\n\\t\\t\\tlastDebtLossError_Offset = (debtLossPerUnitStaked * _totalPropelUSDDeposits) - debtLossNumerator;\\n\\t\\t}\\n\\n\\t\\tcollateralGainPerUnitStaked = collateralNumerator / _totalPropelUSDDeposits;\\n\\t\\tlastCollateralError_Offset[idx] = collateralNumerator - (collateralGainPerUnitStaked * _totalPropelUSDDeposits);\\n\\n\\t\\treturn (collateralGainPerUnitStaked, debtLossPerUnitStaked);\\n\\t}\\n\\n\\t// Update the Stability Pool reward sum S and product P\\n\\tfunction _updateRewardSumAndProduct(uint256 _collateralGainPerUnitStaked, uint256 _debtLossPerUnitStaked, uint256 idx) internal {\\n\\t\\tuint256 currentP = P;\\n\\t\\tuint256 newP;\\n\\n\\t\\t/*\\n\\t\\t * The newProductFactor is the factor by which to change all deposits, due to the depletion of Stability Pool Debt in the liquidation.\\n\\t\\t * We make the product factor 0 if there was a pool-emptying. Otherwise, it is (1 - DebtLossPerUnitStaked)\\n\\t\\t */\\n\\t\\tuint256 newProductFactor = uint256(DECIMAL_PRECISION) - _debtLossPerUnitStaked;\\n\\n\\t\\tuint128 currentScaleCached = currentScale;\\n\\t\\tuint128 currentEpochCached = currentEpoch;\\n\\t\\tuint256 currentS = epochToScaleToSums[currentEpochCached][currentScaleCached][idx];\\n\\n\\t\\t/*\\n\\t\\t * Calculate the new S first, before we update P.\\n\\t\\t * The collateral gain for any given depositor from a liquidation depends on the value of their deposit\\n\\t\\t * (and the value of totalDeposits) prior to the Stability being depleted by the debt in the liquidation.\\n\\t\\t *\\n\\t\\t * Since S corresponds to collateral gain, and P to deposit loss, we update S first.\\n\\t\\t */\\n\\t\\tuint256 marginalCollateralGain = _collateralGainPerUnitStaked * currentP;\\n\\t\\tuint256 newS = currentS + marginalCollateralGain;\\n\\t\\tepochToScaleToSums[currentEpochCached][currentScaleCached][idx] = newS;\\n\\t\\temit S_Updated(idx, newS, currentEpochCached, currentScaleCached);\\n\\n\\t\\t// If the Stability Pool was emptied, increment the epoch, and reset the scale and product P\\n\\t\\tif (newProductFactor == 0) {\\n\\t\\t\\tcurrentEpoch = currentEpochCached + 1;\\n\\t\\t\\temit EpochUpdated(currentEpoch);\\n\\t\\t\\tcurrentScale = 0;\\n\\t\\t\\temit ScaleUpdated(currentScale);\\n\\t\\t\\tnewP = DECIMAL_PRECISION;\\n\\n\\t\\t\\t// If multiplying P by a non-zero product factor would reduce P below the scale boundary, increment the scale\\n\\t\\t} else if ((currentP * newProductFactor) / DECIMAL_PRECISION < SCALE_FACTOR) {\\n\\t\\t\\tnewP = (currentP * newProductFactor * SCALE_FACTOR) / DECIMAL_PRECISION;\\n\\t\\t\\tcurrentScale = currentScaleCached + 1;\\n\\t\\t\\temit ScaleUpdated(currentScale);\\n\\t\\t} else {\\n\\t\\t\\tnewP = (currentP * newProductFactor) / DECIMAL_PRECISION;\\n\\t\\t}\\n\\n\\t\\trequire(newP > 0, \\\"NewP\\\");\\n\\t\\tP = newP;\\n\\t\\temit P_Updated(newP);\\n\\t}\\n\\n\\tfunction _decreaseDebt(uint256 _amount) internal {\\n\\t\\tuint256 newTotalPropelUSDDeposits = totalPropelUSDDeposits - _amount;\\n\\t\\ttotalPropelUSDDeposits = newTotalPropelUSDDeposits;\\n\\t\\temit StabilityPoolPropelUSDBalanceUpdated(newTotalPropelUSDDeposits);\\n\\t}\\n\\n\\t// --- Reward calculator functions for depositor and front end ---\\n\\n\\t/* Calculates the collateral gain earned by the deposit since its last snapshots were taken.\\n\\t * Given by the formula:  E = d0 * (S - S(0))/P(0)\\n\\t * where S(0) and P(0) are the depositor's snapshots of the sum S and product P, respectively.\\n\\t * d0 is the last recorded deposit value.\\n\\t */\\n\\tfunction getDepositorCollateralGain(address _depositor) external view returns (uint256[] memory collateralGains) {\\n\\t\\tcollateralGains = new uint256[](collateralTokens.length);\\n\\n\\t\\tuint256 P_Snapshot = depositSnapshots[_depositor].P;\\n\\t\\tif (P_Snapshot == 0) return collateralGains;\\n\\t\\tuint256[256] memory depositorGains = collateralGainsByDepositor[_depositor];\\n\\t\\tuint256 initialDeposit = accountDeposits[_depositor];\\n\\t\\tuint128 epochSnapshot = depositSnapshots[_depositor].epoch;\\n\\t\\tuint128 scaleSnapshot = depositSnapshots[_depositor].scale;\\n\\t\\tuint256[256] memory sums = epochToScaleToSums[epochSnapshot][scaleSnapshot];\\n\\t\\tuint256[256] memory nextSums = epochToScaleToSums[epochSnapshot][scaleSnapshot + 1];\\n\\t\\tuint256[256] memory depSums = depositSums[_depositor];\\n\\n\\t\\tfor (uint256 i = 0; i < collateralGains.length; i++) {\\n\\t\\t\\tcollateralGains[i] = depositorGains[i];\\n\\t\\t\\tif (sums[i] == 0) continue; // Collateral was overwritten or not gains\\n\\t\\t\\tuint256 firstPortion = sums[i] - depSums[i];\\n\\t\\t\\tuint256 secondPortion = nextSums[i] / SCALE_FACTOR;\\n\\t\\t\\tcollateralGains[i] += (initialDeposit * (firstPortion + secondPortion)) / P_Snapshot / DECIMAL_PRECISION;\\n\\t\\t}\\n\\t\\treturn collateralGains;\\n\\t}\\n\\n\\tfunction _accrueDepositorCollateralGain(address _depositor) private returns (bool hasGains) {\\n\\t\\tuint256[256] storage depositorGains = collateralGainsByDepositor[_depositor];\\n\\t\\tuint256 collaterals = collateralTokens.length;\\n\\t\\tuint256 initialDeposit = accountDeposits[_depositor];\\n\\t\\thasGains = false;\\n\\t\\tif (initialDeposit == 0) {\\n\\t\\t\\treturn hasGains;\\n\\t\\t}\\n\\n\\t\\tuint128 epochSnapshot = depositSnapshots[_depositor].epoch;\\n\\t\\tuint128 scaleSnapshot = depositSnapshots[_depositor].scale;\\n\\t\\tuint256 P_Snapshot = depositSnapshots[_depositor].P;\\n\\n\\t\\tuint256[256] storage sums = epochToScaleToSums[epochSnapshot][scaleSnapshot];\\n\\t\\tuint256[256] storage nextSums = epochToScaleToSums[epochSnapshot][scaleSnapshot + 1];\\n\\t\\tuint256[256] storage depSums = depositSums[_depositor];\\n\\n\\t\\tfor (uint256 i = 0; i < collaterals; i++) {\\n\\t\\t\\tif (sums[i] == 0) continue; // Collateral was overwritten or not gains\\n\\t\\t\\thasGains = true;\\n\\t\\t\\tuint256 firstPortion = sums[i] - depSums[i];\\n\\t\\t\\tuint256 secondPortion = nextSums[i] / SCALE_FACTOR;\\n\\t\\t\\tdepositorGains[i] += (initialDeposit * (firstPortion + secondPortion)) / P_Snapshot / DECIMAL_PRECISION;\\n\\t\\t}\\n\\t\\treturn (hasGains);\\n\\t}\\n\\n\\t/*\\n\\t * Calculate the esPropel gain earned by a deposit since its last snapshots were taken.\\n\\t * Given by the formula:  esPropel = d0 * (G - G(0))/P(0)\\n\\t * where G(0) and P(0) are the depositor's snapshots of the sum G and product P, respectively.\\n\\t * d0 is the last recorded deposit value.\\n\\t */\\n\\tfunction claimableReward(address _depositor) external view returns (uint256) {\\n\\t\\tuint256 totalDebt = totalPropelUSDDeposits;\\n\\t\\tuint256 initialDeposit = accountDeposits[_depositor];\\n\\n\\t\\tif (totalDebt == 0 || initialDeposit == 0) {\\n\\t\\t\\treturn 0;\\n\\t\\t}\\n\\t\\tuint256 esPropelNumerator = (communityIssuance.pendingReward() * DECIMAL_PRECISION) + lastEsPropelError;\\n\\t\\tuint256 esPropelPerUnitStaked = esPropelNumerator / totalDebt;\\n\\t\\tuint256 marginalEsPropelGain = esPropelPerUnitStaked * P;\\n\\n\\t\\tSnapshots memory snapshots = depositSnapshots[_depositor];\\n\\t\\tuint128 epochSnapshot = snapshots.epoch;\\n\\t\\tuint128 scaleSnapshot = snapshots.scale;\\n\\t\\tuint256 firstPortion;\\n\\t\\tuint256 secondPortion;\\n\\t\\tif (scaleSnapshot == currentScale) {\\n\\t\\t\\tfirstPortion = epochToScaleToG[epochSnapshot][scaleSnapshot] - snapshots.G + marginalEsPropelGain;\\n\\t\\t\\tsecondPortion = epochToScaleToG[epochSnapshot][scaleSnapshot + 1] / SCALE_FACTOR;\\n\\t\\t} else {\\n\\t\\t\\tfirstPortion = epochToScaleToG[epochSnapshot][scaleSnapshot] - snapshots.G;\\n\\t\\t\\tsecondPortion = (epochToScaleToG[epochSnapshot][scaleSnapshot + 1] + marginalEsPropelGain) / SCALE_FACTOR;\\n\\t\\t}\\n\\n\\t\\treturn (initialDeposit * (firstPortion + secondPortion)) / snapshots.P / DECIMAL_PRECISION;\\n\\t}\\n\\n\\tfunction _claimableReward(address _depositor) private view returns (uint256) {\\n\\t\\tuint256 initialDeposit = accountDeposits[_depositor];\\n\\t\\tif (initialDeposit == 0) {\\n\\t\\t\\treturn 0;\\n\\t\\t}\\n\\n\\t\\tSnapshots memory snapshots = depositSnapshots[_depositor];\\n\\n\\t\\treturn _getEsPropelGainFromSnapshots(initialDeposit, snapshots);\\n\\t}\\n\\n\\tfunction _getEsPropelGainFromSnapshots(uint256 initialStake, Snapshots memory snapshots) internal view returns (uint256) {\\n\\t\\t/*\\n\\t\\t * Grab the sum 'G' from the epoch at which the stake was made. The esPropel gain may span up to one scale change.\\n\\t\\t * If it does, the second portion of the esPropel gain is scaled by 1e9.\\n\\t\\t * If the gain spans no scale change, the second portion will be 0.\\n\\t\\t */\\n\\t\\tuint128 epochSnapshot = snapshots.epoch;\\n\\t\\tuint128 scaleSnapshot = snapshots.scale;\\n\\t\\tuint256 G_Snapshot = snapshots.G;\\n\\t\\tuint256 P_Snapshot = snapshots.P;\\n\\n\\t\\tuint256 firstPortion = epochToScaleToG[epochSnapshot][scaleSnapshot] - G_Snapshot;\\n\\t\\tuint256 secondPortion = epochToScaleToG[epochSnapshot][scaleSnapshot + 1] / SCALE_FACTOR;\\n\\n\\t\\tuint256 esPropelGain = (initialStake * (firstPortion + secondPortion)) / P_Snapshot / DECIMAL_PRECISION;\\n\\n\\t\\treturn esPropelGain;\\n\\t}\\n\\n\\t// --- Compounded deposit and compounded front end stake ---\\n\\n\\t/*\\n\\t * Return the user's compounded deposit. Given by the formula:  d = d0 * P/P(0)\\n\\t * where P(0) is the depositor's snapshot of the product P, taken when they last updated their deposit.\\n\\t */\\n\\tfunction getCompoundedDeposit(address _depositor) public view returns (uint256) {\\n\\t\\tuint256 initialDeposit = accountDeposits[_depositor];\\n\\t\\tif (initialDeposit == 0) {\\n\\t\\t\\treturn 0;\\n\\t\\t}\\n\\n\\t\\tSnapshots memory snapshots = depositSnapshots[_depositor];\\n\\n\\t\\tuint256 compoundedDeposit = _getCompoundedStakeFromSnapshots(initialDeposit, snapshots);\\n\\t\\treturn compoundedDeposit;\\n\\t}\\n\\n\\t// Internal function, used to calculcate compounded deposits and compounded front end stakes.\\n\\tfunction _getCompoundedStakeFromSnapshots(uint256 initialStake, Snapshots memory snapshots) internal view returns (uint256) {\\n\\t\\tuint256 snapshot_P = snapshots.P;\\n\\t\\tuint128 scaleSnapshot = snapshots.scale;\\n\\t\\tuint128 epochSnapshot = snapshots.epoch;\\n\\n\\t\\t// If stake was made before a pool-emptying event, then it has been fully cancelled with debt -- so, return 0\\n\\t\\tif (epochSnapshot < currentEpoch) {\\n\\t\\t\\treturn 0;\\n\\t\\t}\\n\\n\\t\\tuint256 compoundedStake;\\n\\t\\tuint128 scaleDiff = currentScale - scaleSnapshot;\\n\\n\\t\\t/* Compute the compounded stake. If a scale change in P was made during the stake's lifetime,\\n\\t\\t * account for it. If more than one scale change was made, then the stake has decreased by a factor of\\n\\t\\t * at least 1e-9 -- so return 0.\\n\\t\\t */\\n\\t\\tif (scaleDiff == 0) {\\n\\t\\t\\tcompoundedStake = (initialStake * P) / snapshot_P;\\n\\t\\t} else if (scaleDiff == 1) {\\n\\t\\t\\tcompoundedStake = (initialStake * P) / snapshot_P / SCALE_FACTOR;\\n\\t\\t} else {\\n\\t\\t\\t// if scaleDiff >= 2\\n\\t\\t\\tcompoundedStake = 0;\\n\\t\\t}\\n\\n\\t\\t/*\\n\\t\\t * If compounded deposit is less than a billionth of the initial deposit, return 0.\\n\\t\\t *\\n\\t\\t * NOTE: originally, this line was in place to stop rounding errors making the deposit too large. However, the error\\n\\t\\t * corrections should ensure the error in P \\\"favors the Pool\\\", i.e. any given compounded deposit should slightly less\\n\\t\\t * than it's theoretical value.\\n\\t\\t *\\n\\t\\t * Thus it's unclear whether this line is still really needed.\\n\\t\\t */\\n\\t\\tif (compoundedStake < initialStake / 1e9) {\\n\\t\\t\\treturn 0;\\n\\t\\t}\\n\\n\\t\\treturn compoundedStake;\\n\\t}\\n\\n\\tfunction _claimCollateralGains(address recipient, uint256[] memory collateralIndexes) internal {\\n\\t\\tuint256 loopEnd = collateralIndexes.length;\\n\\t\\tuint256[] memory collateralGains = new uint256[](collateralTokens.length);\\n\\n\\t\\tuint256[256] storage depositorGains = collateralGainsByDepositor[msg.sender];\\n\\t\\tfor (uint256 i; i < loopEnd; ) {\\n\\t\\t\\tuint256 collateralIndex = collateralIndexes[i];\\n\\t\\t\\tuint256 gains = depositorGains[collateralIndex];\\n\\t\\t\\tif (gains > 0) {\\n\\t\\t\\t\\tcollateralGains[collateralIndex] = gains;\\n\\t\\t\\t\\tdepositorGains[collateralIndex] = 0;\\n\\t\\t\\t\\tcollateralTokens[collateralIndex].safeTransfer(recipient, gains);\\n\\t\\t\\t}\\n\\t\\t\\tunchecked {\\n\\t\\t\\t\\t++i;\\n\\t\\t\\t}\\n\\t\\t}\\n\\t\\temit CollateralGainWithdrawn(msg.sender, collateralGains);\\n\\t}\\n\\n\\t// --- Stability Pool Deposit Functionality ---\\n\\n\\tfunction _updateSnapshots(address _depositor, uint256 _newValue) internal {\\n\\t\\tuint256 length;\\n\\t\\tif (_newValue == 0) {\\n\\t\\t\\tdelete depositSnapshots[_depositor];\\n\\n\\t\\t\\tlength = collateralTokens.length;\\n\\t\\t\\tfor (uint256 i = 0; i < length; i++) {\\n\\t\\t\\t\\tdepositSums[_depositor][i] = 0;\\n\\t\\t\\t}\\n\\t\\t\\temit DepositSnapshotUpdated(_depositor, 0, 0);\\n\\t\\t\\treturn;\\n\\t\\t}\\n\\t\\tuint128 currentScaleCached = currentScale;\\n\\t\\tuint128 currentEpochCached = currentEpoch;\\n\\t\\tuint256 currentP = P;\\n\\n\\t\\t// Get S and G for the current epoch and current scale\\n\\t\\tuint256[256] storage currentS = epochToScaleToSums[currentEpochCached][currentScaleCached];\\n\\t\\tuint256 currentG = epochToScaleToG[currentEpochCached][currentScaleCached];\\n\\n\\t\\t// Record new snapshots of the latest running product P, sum S, and sum G, for the depositor\\n\\t\\tdepositSnapshots[_depositor].P = currentP;\\n\\t\\tdepositSnapshots[_depositor].G = currentG;\\n\\t\\tdepositSnapshots[_depositor].scale = currentScaleCached;\\n\\t\\tdepositSnapshots[_depositor].epoch = currentEpochCached;\\n\\n\\t\\tlength = collateralTokens.length;\\n\\t\\tfor (uint256 i = 0; i < length; i++) {\\n\\t\\t\\tdepositSums[_depositor][i] = currentS[i];\\n\\t\\t}\\n\\n\\t\\temit DepositSnapshotUpdated(_depositor, currentP, currentG);\\n\\t}\\n\\n\\t//This assumes the snapshot gets updated in the caller\\n\\tfunction _accrueRewards(address _depositor) internal {\\n\\t\\tuint256 amount = _claimableReward(_depositor);\\n\\t\\tstoredPendingReward[_depositor] = storedPendingReward[_depositor] + amount;\\n\\t}\\n\\n\\tfunction _claimReward(address account) internal returns (uint256 amount) {\\n\\t\\tuint256 initialDeposit = accountDeposits[account];\\n\\n\\t\\tif (initialDeposit > 0) {\\n\\t\\t\\t_triggerRewardIssuance();\\n\\t\\t\\tbool hasGains = _accrueDepositorCollateralGain(account);\\n\\n\\t\\t\\tuint256 compoundedDeposit = getCompoundedDeposit(account);\\n\\t\\t\\tuint256 debtLoss = initialDeposit - compoundedDeposit;\\n\\n\\t\\t\\tamount = _claimableReward(account);\\n\\t\\t\\t// we update only if the snapshot has changed\\n\\t\\t\\tif (debtLoss > 0 || hasGains || amount > 0) {\\n\\t\\t\\t\\t// Update deposit\\n\\t\\t\\t\\tuint256 newDeposit = compoundedDeposit;\\n\\t\\t\\t\\taccountDeposits[account] = newDeposit;\\n\\t\\t\\t\\t_updateSnapshots(account, newDeposit);\\n\\t\\t\\t}\\n\\t\\t}\\n\\t\\tuint256 pending = storedPendingReward[account];\\n\\t\\tif (pending > 0) {\\n\\t\\t\\tamount += pending;\\n\\t\\t\\tstoredPendingReward[account] = 0;\\n\\t\\t}\\n\\t}\\n}\\n\",\"keccak256\":\"0x571deb817d07da1f790dd99e1cf172b324d7e49802ecba4b2ba0b68d03e76a79\",\"license\":\"MIT\"},\"contracts/dependencies/BlastWrapper.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"./PropelOwnable.sol\\\";\\nimport \\\"../interfaces/IBlast.sol\\\";\\nimport \\\"../interfaces/IWETH.sol\\\";\\n\\ncontract BlastWrapper is PropelOwnable {\\n\\n\\tconstructor(IPropelCore _propelCore) PropelOwnable(_propelCore) {\\n\\t\\tblast().configureClaimableGas();\\n\\t\\tWETH().configure(YieldMode.CLAIMABLE);\\n\\t}\\n\\n\\tfunction getClaimableWETH() public view returns(uint256) {\\n\\t\\treturn WETH().getClaimableAmount(address(this));\\n\\t}\\n\\n\\tfunction claimAllYield(address to) external onlyOwner {\\n\\t\\tuint256 amount = getClaimableWETH();\\n\\t\\trequire(amount > 0, \\\"no claimable amount\\\");\\n\\t\\tWETH().claim(to, amount);\\n\\t}\\n\\n\\tfunction claimAllGas(address to) external onlyOwner {\\n\\t\\tblast().claimAllGas(address(this), to);\\n\\t}\\n}\\n\",\"keccak256\":\"0x2c365e113694b57de3aac7301f9e44b4d911e7e31056093a2164afee2dbb3321\",\"license\":\"MIT\"},\"contracts/dependencies/PropelMath.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nlibrary PropelMath {\\n\\tuint256 internal constant DECIMAL_PRECISION = 1e18;\\n\\n\\t/* Precision for Nominal ICR (independent of price). Rationale for the value:\\n\\t *\\n\\t * - Making it \\u201ctoo high\\u201d could lead to overflows.\\n\\t * - Making it \\u201ctoo low\\u201d could lead to an ICR equal to zero, due to truncation from Solidity floor division.\\n\\t *\\n\\t * This value of 1e20 is chosen for safety: the NICR will only overflow for numerator > ~1e39,\\n\\t * and will only truncate to 0 if the denominator is at least 1e20 times greater than the numerator.\\n\\t *\\n\\t */\\n\\tuint256 internal constant NICR_PRECISION = 1e20;\\n\\n\\tfunction _min(uint256 _a, uint256 _b) internal pure returns (uint256) {\\n\\t\\treturn (_a < _b) ? _a : _b;\\n\\t}\\n\\n\\tfunction _max(uint256 _a, uint256 _b) internal pure returns (uint256) {\\n\\t\\treturn (_a >= _b) ? _a : _b;\\n\\t}\\n\\n\\t/*\\n\\t * Multiply two decimal numbers and use normal rounding rules:\\n\\t * -round product up if 19'th mantissa digit >= 5\\n\\t * -round product down if 19'th mantissa digit < 5\\n\\t *\\n\\t * Used only inside the exponentiation, _decPow().\\n\\t */\\n\\tfunction decMul(uint256 x, uint256 y) internal pure returns (uint256 decProd) {\\n\\t\\tuint256 prod_xy = x * y;\\n\\n\\t\\tdecProd = (prod_xy + (DECIMAL_PRECISION / 2)) / DECIMAL_PRECISION;\\n\\t}\\n\\n\\t/*\\n\\t * _decPow: Exponentiation function for 18-digit decimal base, and integer exponent n.\\n\\t *\\n\\t * Uses the efficient \\\"exponentiation by squaring\\\" algorithm. O(log(n)) complexity.\\n\\t *\\n\\t * TroveManager._calcDecayedBaseRate\\n\\t *\\n\\t * The exponent is capped to avoid reverting due to overflow. The cap 525600000 equals\\n\\t * \\\"minutes in 1000 years\\\": 60 * 24 * 365 * 1000\\n\\t *\\n\\t * If a period of > 1000 years is ever used as an exponent in either of the above functions, the result will be\\n\\t * negligibly different from just passing the cap, since:\\n\\t *\\n\\t * the decayed base rate will be 0 for 1000 years or > 1000 years\\n\\t */\\n\\tfunction _decPow(uint256 _base, uint256 _minutes) internal pure returns (uint256) {\\n\\t\\tif (_minutes > 525600000) {\\n\\t\\t\\t_minutes = 525600000;\\n\\t\\t} // cap to avoid overflow\\n\\n\\t\\tif (_minutes == 0) {\\n\\t\\t\\treturn DECIMAL_PRECISION;\\n\\t\\t}\\n\\n\\t\\tuint256 y = DECIMAL_PRECISION;\\n\\t\\tuint256 x = _base;\\n\\t\\tuint256 n = _minutes;\\n\\n\\t\\t// Exponentiation-by-squaring\\n\\t\\twhile (n > 1) {\\n\\t\\t\\tif (n % 2 == 0) {\\n\\t\\t\\t\\tx = decMul(x, x);\\n\\t\\t\\t\\tn = n / 2;\\n\\t\\t\\t} else {\\n\\t\\t\\t\\t// if (n % 2 != 0)\\n\\t\\t\\t\\ty = decMul(x, y);\\n\\t\\t\\t\\tx = decMul(x, x);\\n\\t\\t\\t\\tn = (n - 1) / 2;\\n\\t\\t\\t}\\n\\t\\t}\\n\\n\\t\\treturn decMul(x, y);\\n\\t}\\n\\n\\tfunction _getAbsoluteDifference(uint256 _a, uint256 _b) internal pure returns (uint256) {\\n\\t\\treturn (_a >= _b) ? _a - _b : _b - _a;\\n\\t}\\n\\n\\tfunction _computeNominalCR(uint256 _coll, uint256 _debt) internal pure returns (uint256) {\\n\\t\\tif (_debt > 0) {\\n\\t\\t\\treturn (_coll * NICR_PRECISION) / _debt;\\n\\t\\t}\\n\\t\\t// Return the maximal value for uint256 if the Trove has a debt of 0. Represents \\\"infinite\\\" CR.\\n\\t\\telse {\\n\\t\\t\\t// if (_debt == 0)\\n\\t\\t\\treturn 2 ** 256 - 1;\\n\\t\\t}\\n\\t}\\n\\n\\tfunction _computeCR(uint256 _coll, uint256 _debt, uint256 _price) internal pure returns (uint256) {\\n\\t\\tif (_debt > 0) {\\n\\t\\t\\tuint256 newCollRatio = (_coll * _price) / _debt;\\n\\n\\t\\t\\treturn newCollRatio;\\n\\t\\t}\\n\\t\\t// Return the maximal value for uint256 if the Trove has a debt of 0. Represents \\\"infinite\\\" CR.\\n\\t\\telse {\\n\\t\\t\\t// if (_debt == 0)\\n\\t\\t\\treturn type(uint256).max;\\n\\t\\t}\\n\\t}\\n\\n\\tfunction _computeCR(uint256 _coll, uint256 _debt) internal pure returns (uint256) {\\n\\t\\tif (_debt > 0) {\\n\\t\\t\\tuint256 newCollRatio = (_coll) / _debt;\\n\\n\\t\\t\\treturn newCollRatio;\\n\\t\\t}\\n\\t\\t// Return the maximal value for uint256 if the Trove has a debt of 0. Represents \\\"infinite\\\" CR.\\n\\t\\telse {\\n\\t\\t\\t// if (_debt == 0)\\n\\t\\t\\treturn type(uint256).max;\\n\\t\\t}\\n\\t}\\n}\\n\",\"keccak256\":\"0xfd2ccf04b9e82e07adb4f601571bc76fa84099d1a39ceddd3934ff520158f368\",\"license\":\"MIT\"},\"contracts/dependencies/PropelOwnable.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"../interfaces/IPropelCore.sol\\\";\\n\\n/**\\n    @title Propel Ownable\\n    @notice Contracts inheriting `PropelOwnable` have the same owner as `PropelCore`.\\n            The ownership cannot be independently modified or renounced.\\n */\\ncontract PropelOwnable {\\n\\tIPropelCore public immutable PropelCore;\\n\\n\\tconstructor(IPropelCore _PropelCore) {\\n\\t\\tPropelCore = _PropelCore;\\n\\t}\\n\\n\\tmodifier onlyOwner() {\\n\\t\\trequire(msg.sender == owner(), \\\"Only owner\\\");\\n\\t\\t_;\\n\\t}\\n\\n\\tmodifier onlyGuardian() {\\n\\t\\trequire(msg.sender == guardian(), \\\"Only guardian\\\");\\n\\t\\t_;\\n\\t}\\n\\n\\tfunction owner() public view returns (address) {\\n\\t\\treturn PropelCore.owner();\\n\\t}\\n\\n\\tfunction guardian() public view returns (address) {\\n\\t\\treturn PropelCore.guardian();\\n\\t}\\n\\n\\tfunction WETH() public view returns(IWETH) {\\n\\t\\treturn PropelCore.WETH();\\n\\t}\\n\\n\\tfunction blast() public view returns(IBlast) {\\n\\t\\treturn PropelCore.blast();\\n\\t}\\n}\\n\",\"keccak256\":\"0x4da3a2231c25589b2d494c2aa78c5784cec15d825ced6cfaaaed8fc8660c322b\",\"license\":\"MIT\"},\"contracts/dependencies/SystemStart.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"../interfaces/IPropelCore.sol\\\";\\n\\n/**\\n    @title Propel System Start Time\\n    @dev Provides a unified `startTime` and `getWeek`, used for emissions.\\n */\\ncontract SystemStart {\\n\\tuint256 public immutable startTime;\\n\\n\\tconstructor(IPropelCore PropelCore) {\\n\\t\\tstartTime = PropelCore.startTime();\\n\\t}\\n}\\n\",\"keccak256\":\"0x988a7273c991093e65eb011f5efe961d12868c43221cc9a420fa08b27aee8bcb\",\"license\":\"MIT\"},\"contracts/interfaces/IBlast.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nenum YieldMode {\\n\\tAUTOMATIC,\\n\\tVOID,\\n\\tCLAIMABLE\\n}\\n\\nenum GasMode {\\n\\tVOID,\\n\\tCLAIMABLE\\n}\\n\\ninterface IERC20Rebasing {\\n\\t// changes the yield mode of the caller and update the balance\\n\\t// to reflect the configuration\\n\\tfunction configure(YieldMode) external returns (uint256);\\n\\n\\t// \\\"claimable\\\" yield mode accounts can call this this claim their yield\\n\\t// to another address\\n\\tfunction claim(address recipient, uint256 amount) external returns (uint256);\\n\\n\\t// read the claimable amount for an account\\n\\tfunction getClaimableAmount(address account) external view returns (uint256);\\n}\\n\\ninterface IBlast {\\n\\t// configure\\n\\tfunction configureContract(address contractAddress, YieldMode _yield, GasMode gasMode, address governor) external;\\n\\n\\tfunction configure(YieldMode _yield, GasMode gasMode, address governor) external;\\n\\n\\t// base configuration options\\n\\tfunction configureClaimableYield() external;\\n\\n\\tfunction configureClaimableYieldOnBehalf(address contractAddress) external;\\n\\n\\tfunction configureAutomaticYield() external;\\n\\n\\tfunction configureAutomaticYieldOnBehalf(address contractAddress) external;\\n\\n\\tfunction configureVoidYield() external;\\n\\n\\tfunction configureVoidYieldOnBehalf(address contractAddress) external;\\n\\n\\tfunction configureClaimableGas() external;\\n\\n\\tfunction configureClaimableGasOnBehalf(address contractAddress) external;\\n\\n\\tfunction configureVoidGas() external;\\n\\n\\tfunction configureVoidGasOnBehalf(address contractAddress) external;\\n\\n\\tfunction configureGovernor(address _governor) external;\\n\\n\\tfunction configureGovernorOnBehalf(address _newGovernor, address contractAddress) external;\\n\\n\\t// claim yield\\n\\tfunction claimYield(address contractAddress, address recipientOfYield, uint256 amount) external returns (uint256);\\n\\n\\tfunction claimAllYield(address contractAddress, address recipientOfYield) external returns (uint256);\\n\\n\\t// claim gas\\n\\tfunction claimAllGas(address contractAddress, address recipientOfGas) external returns (uint256);\\n\\n\\tfunction claimGasAtMinClaimRate(address contractAddress, address recipientOfGas, uint256 minClaimRateBips) external returns (uint256);\\n\\n\\tfunction claimMaxGas(address contractAddress, address recipientOfGas) external returns (uint256);\\n\\n\\tfunction claimGas(address contractAddress, address recipientOfGas, uint256 gasToClaim, uint256 gasSecondsToConsume) external returns (uint256);\\n\\n\\t// read functions\\n\\tfunction readClaimableYield(address contractAddress) external view returns (uint256);\\n\\n\\tfunction readYieldConfiguration(address contractAddress) external view returns (uint8);\\n\\n\\tfunction readGasParams(address contractAddress) external view returns (uint256 etherSeconds, uint256 etherBalance, uint256 lastUpdated, GasMode);\\n}\\n\",\"keccak256\":\"0xffaa54f302ba2c47f29080863318906f4094105afb1d5a57798177a9b34f142a\",\"license\":\"MIT\"},\"contracts/interfaces/ICommunityIssuance.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\ninterface ICommunityIssuance {\\n\\tevent EsPropelIssued(uint256 amount);\\n\\tevent EsPropelSent(address to, uint256 amount);\\n\\tevent RewardPerSecUpdated(uint256 _rewardPerSec);\\n\\n\\tfunction issueEsPropel() external returns (uint256);\\n\\n\\tfunction sendEsPropel(address to, uint256 amount) external;\\n\\n\\tfunction pendingReward() external view returns (uint256 pending);\\n}\\n\",\"keccak256\":\"0x745239a3f95661a43c27e716b950d71acb5f56e3d667801fa92830f7ec6b32e3\",\"license\":\"MIT\"},\"contracts/interfaces/IPropelCore.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"../interfaces/IBlast.sol\\\";\\nimport \\\"../interfaces/IWETH.sol\\\";\\n\\ninterface IPropelCore {\\n\\tevent FeeReceiverSet(address feeReceiver);\\n\\tevent GuardianSet(address guardian);\\n\\tevent NewOwnerAccepted(address oldOwner, address owner);\\n\\tevent NewOwnerCommitted(address owner, address pendingOwner, uint256 deadline);\\n\\tevent NewOwnerRevoked(address owner, address revokedOwner);\\n\\tevent Paused();\\n\\tevent PriceFeedSet(address priceFeed);\\n\\tevent Unpaused();\\n\\n\\tfunction acceptTransferOwnership() external;\\n\\n\\tfunction commitTransferOwnership(address newOwner) external;\\n\\n\\tfunction revokeTransferOwnership() external;\\n\\n\\tfunction setFeeReceiver(address _feeReceiver) external;\\n\\n\\tfunction setGuardian(address _guardian) external;\\n\\n\\tfunction setPaused(bool _paused) external;\\n\\n\\tfunction setPriceFeed(address _priceFeed) external;\\n\\n\\tfunction OWNERSHIP_TRANSFER_DELAY() external view returns (uint256);\\n\\n\\tfunction feeReceiver() external view returns (address);\\n\\n\\tfunction guardian() external view returns (address);\\n\\n\\tfunction owner() external view returns (address);\\n\\n\\tfunction WETH() external view returns(IWETH);\\n\\n\\tfunction blast() external view returns(IBlast);\\n\\n\\tfunction ownershipTransferDeadline() external view returns (uint256);\\n\\n\\tfunction paused() external view returns (bool);\\n\\n\\tfunction pendingOwner() external view returns (address);\\n\\n\\tfunction startTime() external view returns (uint256);\\n}\\n\",\"keccak256\":\"0xe099656468b3bdf731d4f5bd1e8e1cc8cece0d45cdef837194c1282fdbcac177\",\"license\":\"MIT\"},\"contracts/interfaces/IPropelUSD.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\ninterface IPropelUSD {\\n\\tevent Approval(address indexed owner, address indexed spender, uint256 value);\\n\\tevent MessageFailed(uint16 _srcChainId, bytes _srcAddress, uint64 _nonce, bytes _payload, bytes _reason);\\n\\tevent OwnershipTransferred(address indexed previousOwner, address indexed newOwner);\\n\\tevent ReceiveFromChain(uint16 indexed _srcChainId, address indexed _to, uint256 _amount);\\n\\tevent RetryMessageSuccess(uint16 _srcChainId, bytes _srcAddress, uint64 _nonce, bytes32 _payloadHash);\\n\\tevent SendToChain(uint16 indexed _dstChainId, address indexed _from, bytes _toAddress, uint256 _amount);\\n\\tevent SetMinDstGas(uint16 _dstChainId, uint16 _type, uint256 _minDstGas);\\n\\tevent SetPrecrime(address precrime);\\n\\tevent SetTrustedRemote(uint16 _remoteChainId, bytes _path);\\n\\tevent SetTrustedRemoteAddress(uint16 _remoteChainId, bytes _remoteAddress);\\n\\tevent SetUseCustomAdapterParams(bool _useCustomAdapterParams);\\n\\tevent Transfer(address indexed from, address indexed to, uint256 value);\\n\\n\\tfunction approve(address spender, uint256 amount) external returns (bool);\\n\\n\\tfunction burn(address _account, uint256 _amount) external;\\n\\n\\tfunction burnWithGasCompensation(address _account, uint256 _amount) external returns (bool);\\n\\n\\tfunction decreaseAllowance(address spender, uint256 subtractedValue) external returns (bool);\\n\\n\\tfunction enableTroveManager(address _troveManager) external;\\n\\n\\tfunction flashLoan(address receiver, address token, uint256 amount, bytes calldata data) external returns (bool);\\n\\n\\tfunction forceResumeReceive(uint16 _srcChainId, bytes calldata _srcAddress) external;\\n\\n\\tfunction increaseAllowance(address spender, uint256 addedValue) external returns (bool);\\n\\n\\tfunction lzReceive(uint16 _srcChainId, bytes calldata _srcAddress, uint64 _nonce, bytes calldata _payload) external;\\n\\n\\tfunction mint(address _account, uint256 _amount) external;\\n\\n\\tfunction mintWithGasCompensation(address _account, uint256 _amount) external returns (bool);\\n\\n\\tfunction nonblockingLzReceive(uint16 _srcChainId, bytes calldata _srcAddress, uint64 _nonce, bytes calldata _payload) external;\\n\\n\\tfunction permit(address owner, address spender, uint256 amount, uint256 deadline, uint8 v, bytes32 r, bytes32 s) external;\\n\\n\\tfunction renounceOwnership() external;\\n\\n\\tfunction returnFromPool(address _poolAddress, address _receiver, uint256 _amount) external;\\n\\n\\tfunction sendToSP(address _sender, uint256 _amount) external;\\n\\n\\tfunction setConfig(uint16 _version, uint16 _chainId, uint256 _configType, bytes calldata _config) external;\\n\\n\\tfunction setMinDstGas(uint16 _dstChainId, uint16 _packetType, uint256 _minGas) external;\\n\\n\\tfunction setPayloadSizeLimit(uint16 _dstChainId, uint256 _size) external;\\n\\n\\tfunction setPrecrime(address _precrime) external;\\n\\n\\tfunction setReceiveVersion(uint16 _version) external;\\n\\n\\tfunction setSendVersion(uint16 _version) external;\\n\\n\\tfunction setTrustedRemote(uint16 _srcChainId, bytes calldata _path) external;\\n\\n\\tfunction setTrustedRemoteAddress(uint16 _remoteChainId, bytes calldata _remoteAddress) external;\\n\\n\\tfunction setUseCustomAdapterParams(bool _useCustomAdapterParams) external;\\n\\n\\tfunction transfer(address recipient, uint256 amount) external returns (bool);\\n\\n\\tfunction transferFrom(address sender, address recipient, uint256 amount) external returns (bool);\\n\\n\\tfunction transferOwnership(address newOwner) external;\\n\\n\\tfunction retryMessage(uint16 _srcChainId, bytes calldata _srcAddress, uint64 _nonce, bytes calldata _payload) external payable;\\n\\n\\tfunction sendFrom(address _from, uint16 _dstChainId, bytes calldata _toAddress, uint256 _amount, address _refundAddress, address _zroPaymentAddress, bytes calldata _adapterParams) external payable;\\n\\n\\tfunction DEBT_GAS_COMPENSATION() external view returns (uint256);\\n\\n\\tfunction DEFAULT_PAYLOAD_SIZE_LIMIT() external view returns (uint256);\\n\\n\\tfunction FLASH_LOAN_FEE() external view returns (uint256);\\n\\n\\tfunction NO_EXTRA_GAS() external view returns (uint256);\\n\\n\\tfunction PT_SEND() external view returns (uint16);\\n\\n\\tfunction allowance(address owner, address spender) external view returns (uint256);\\n\\n\\tfunction balanceOf(address account) external view returns (uint256);\\n\\n\\tfunction borrowerOperationsAddress() external view returns (address);\\n\\n\\tfunction circulatingSupply() external view returns (uint256);\\n\\n\\tfunction decimals() external view returns (uint8);\\n\\n\\tfunction domainSeparator() external view returns (bytes32);\\n\\n\\tfunction estimateSendFee(uint16 _dstChainId, bytes calldata _toAddress, uint256 _amount, bool _useZro, bytes calldata _adapterParams) external view returns (uint256 nativeFee, uint256 zroFee);\\n\\n\\tfunction factory() external view returns (address);\\n\\n\\tfunction failedMessages(uint16, bytes calldata, uint64) external view returns (bytes32);\\n\\n\\tfunction flashFee(address token, uint256 amount) external view returns (uint256);\\n\\n\\tfunction gasPool() external view returns (address);\\n\\n\\tfunction getConfig(uint16 _version, uint16 _chainId, address, uint256 _configType) external view returns (bytes memory);\\n\\n\\tfunction getTrustedRemoteAddress(uint16 _remoteChainId) external view returns (bytes memory);\\n\\n\\tfunction isTrustedRemote(uint16 _srcChainId, bytes calldata _srcAddress) external view returns (bool);\\n\\n\\tfunction lzEndpoint() external view returns (address);\\n\\n\\tfunction maxFlashLoan(address token) external view returns (uint256);\\n\\n\\tfunction minDstGasLookup(uint16, uint16) external view returns (uint256);\\n\\n\\tfunction name() external view returns (string memory);\\n\\n\\tfunction nonces(address owner) external view returns (uint256);\\n\\n\\tfunction owner() external view returns (address);\\n\\n\\tfunction payloadSizeLimitLookup(uint16) external view returns (uint256);\\n\\n\\tfunction permitTypeHash() external view returns (bytes32);\\n\\n\\tfunction precrime() external view returns (address);\\n\\n\\tfunction stabilityPoolAddress() external view returns (address);\\n\\n\\tfunction supportsInterface(bytes4 interfaceId) external view returns (bool);\\n\\n\\tfunction symbol() external view returns (string memory);\\n\\n\\tfunction token() external view returns (address);\\n\\n\\tfunction totalSupply() external view returns (uint256);\\n\\n\\tfunction troveManager(address) external view returns (bool);\\n\\n\\tfunction trustedRemoteLookup(uint16) external view returns (bytes memory);\\n\\n\\tfunction useCustomAdapterParams() external view returns (bool);\\n\\n\\tfunction version() external view returns (string memory);\\n}\\n\",\"keccak256\":\"0xa39f5ca61c6ebd7adbdf39f1e4d9e37496dd0ca2d401244e93ca56fe5a8607ca\",\"license\":\"MIT\"},\"contracts/interfaces/IStabilityPool.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IStabilityPool {\\n\\tevent CollateralGainWithdrawn(address indexed _depositor, uint256[] _collateral);\\n\\tevent CollateralOverwritten(address oldCollateral, address newCollateral);\\n\\tevent DepositSnapshotUpdated(address indexed _depositor, uint256 _P, uint256 _G);\\n\\tevent EpochUpdated(uint128 _currentEpoch);\\n\\tevent G_Updated(uint256 _G, uint128 _epoch, uint128 _scale);\\n\\tevent P_Updated(uint256 _P);\\n\\tevent RewardClaimed(address indexed account, address indexed recipient, uint256 claimed);\\n\\tevent S_Updated(uint256 idx, uint256 _S, uint128 _epoch, uint128 _scale);\\n\\tevent ScaleUpdated(uint128 _currentScale);\\n\\tevent StabilityPoolPropelUSDBalanceUpdated(uint256 _newBalance);\\n\\tevent UserDepositChanged(address indexed _depositor, uint256 _newDeposit);\\n\\n\\t// function claimCollateralGains(address recipient, uint256[] calldata collateralIndexes) external;\\n\\n\\t// function claimReward(address recipient) external returns (uint256 amount);\\n\\n\\tfunction enableCollateral(IERC20 _collateral) external;\\n\\n\\tfunction offset(IERC20 collateral, uint256 _debtToOffset, uint256 _collToAdd) external;\\n\\n\\tfunction provideToSP(uint256 _amount) external;\\n\\n\\tfunction startCollateralSunset(IERC20 collateral) external;\\n\\n\\tfunction withdrawFromSP(uint256 _amount) external;\\n\\n\\tfunction DECIMAL_PRECISION() external view returns (uint256);\\n\\n\\tfunction P() external view returns (uint256);\\n\\n\\tfunction SCALE_FACTOR() external view returns (uint256);\\n\\n\\tfunction SUNSET_DURATION() external view returns (uint128);\\n\\n\\tfunction claimableReward(address _depositor) external view returns (uint256);\\n\\n\\tfunction currentEpoch() external view returns (uint128);\\n\\n\\tfunction currentScale() external view returns (uint128);\\n\\n\\tfunction depositSnapshots(address) external view returns (uint256 P, uint256 G, uint128 scale, uint128 epoch);\\n\\n\\tfunction depositSums(address, uint256) external view returns (uint256);\\n\\n\\tfunction epochToScaleToG(uint128, uint128) external view returns (uint256);\\n\\n\\tfunction epochToScaleToSums(uint128, uint128, uint256) external view returns (uint256);\\n\\n\\tfunction factory() external view returns (address);\\n\\n\\tfunction getCompoundedDeposit(address _depositor) external view returns (uint256);\\n\\n\\tfunction getDepositorCollateralGain(address _depositor) external view returns (uint256[] memory collateralGains);\\n\\n\\tfunction getTotalPropelUSDDeposits() external view returns (uint256);\\n\\n\\tfunction lastDebtLossError_Offset() external view returns (uint256);\\n\\n\\tfunction lastEsPropelError() external view returns (uint256);\\n\\n\\tfunction liquidationManager() external view returns (address);\\n}\\n\",\"keccak256\":\"0x1fcbdf3288009aff76361862f1c0b0131d4c338c04781ece3a6cab426dbc3946\",\"license\":\"MIT\"},\"contracts/interfaces/IWETH.sol\":{\"content\":\"// SPDX-License-Identifier: MIT\\n\\npragma solidity 0.8.19;\\n\\nimport \\\"../interfaces/IBlast.sol\\\";\\nimport \\\"@openzeppelin/contracts/token/ERC20/IERC20.sol\\\";\\n\\ninterface IWETH is IERC20, IERC20Rebasing {\\n\\tfunction deposit() external payable;\\n}\\n\",\"keccak256\":\"0x63d5514ce911f067af3312ed496bb55dae2526835692c6d3e01b2c68c6b28d54\",\"license\":\"MIT\"}},\"version\":1}",
  "bytecode": "0x610120604052670de0b6b3a76400006009553480156200001e57600080fd5b5060405162003c3538038062003c35833981016040819052620000419162000222565b6001600160a01b038516608052846200005962000158565b6001600160a01b0316634e606c476040518163ffffffff1660e01b8152600401600060405180830381600087803b1580156200009457600080fd5b505af1158015620000a9573d6000803e3d6000fd5b50505050620000bd620001c660201b60201c565b6001600160a01b0316631a33757d60026040518263ffffffff1660e01b8152600401620000eb9190620002a2565b6020604051808303816000875af11580156200010b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001319190620002cb565b50506001600160a01b0393841660a05291831660c052821660e0521661010052506200030c565b60006080516001600160a01b031663175e1a7d6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200019b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001c19190620002e5565b905090565b60006080516001600160a01b031663ad5c46486040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200019b573d6000803e3d6000fd5b6001600160a01b03811681146200021f57600080fd5b50565b600080600080600060a086880312156200023b57600080fd5b8551620002488162000209565b60208701519095506200025b8162000209565b60408701519094506200026e8162000209565b6060870151909350620002818162000209565b6080870151909250620002948162000209565b809150509295509295909350565b6020810160038310620002c557634e487b7160e01b600052602160045260246000fd5b91905290565b600060208284031215620002de57600080fd5b5051919050565b600060208284031215620002f857600080fd5b8151620003058162000209565b9392505050565b60805160a05160c05160e05161010051613890620003a56000396000818161057c015281816114c701528181611c0001526120d50152600081816103a6015261291c01526000818161060a01526107770152600081816102fe01528181610f0a015261172a01526000818161072401528181610a560152818161131b01528181611578015281816118d0015261193001526138906000f3fe608060405234801561001057600080fd5b50600436106102dd5760003560e01c806386ad29aa11610186578063c2d94aec116100e3578063dec8d97511610097578063e950342511610071578063e9503425146106f9578063eeb58d0b1461070c578063f2b6db511461071f57600080fd5b8063dec8d9751461065d578063e10d29ee146106b2578063e6666733146106e657600080fd5b8063cd7502fe116100c8578063cd7502fe1461062c578063ce4b5bbe1461063f578063db03fdaa1461064a57600080fd5b8063c2d94aec146105f2578063c45a01551461060557600080fd5b8063a20baee61161013a578063a4e59ac81161011f578063a4e59ac8146105cd578063a7528a03146105e0578063ad5c4648146105ea57600080fd5b8063a20baee61461059e578063a4beda63146105ad57600080fd5b80638b8fbd921161016b5780638b8fbd92146105665780638da5cb5b1461056f57806395fb16bb1461057757600080fd5b806386ad29aa146104ec57806386da0824146104f457600080fd5b80632e54bf951161023f5780635383dfcb116101f357806381bafb31116101cd57806381bafb311461049757806382e0a574146104a1578063835dada0146104cc57600080fd5b80635383dfcb14610432578063766718081461045257806378c77a241461048457600080fd5b806333a3d73f1161022457806333a3d73f1461040e578063452a932014610417578063457182781461041f57600080fd5b80632e54bf95146103db578063307d3612146103ee57600080fd5b8063172c48c71161029657806319f27b3b1161027b57806319f27b3b1461038e5780631ef3a04c146103a1578063272b1323146103c857600080fd5b8063172c48c714610373578063175e1a7d1461038657600080fd5b806309e2acb0116102c757806309e2acb01461033857806311be0de51461034b5780631500d2c31461036057600080fd5b80622dade9146102e2578063086ce520146102f9575b600080fd5b6002545b6040519081526020015b60405180910390f35b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020016102f0565b6102e66103463660046133ea565b610746565b61035e610359366004613416565b61076c565b005b6102e661036e3660046133ea565b610a0b565b61032061038136600461343a565b610a28565b610320610a52565b61035e61039c366004613416565b610adb565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b61035e6103d6366004613416565b610c8a565b61035e6103e936600461343a565b610d8b565b6104016103fc366004613416565b610fdf565b6040516102f09190613453565b6102e6600d5481565b610320611317565b61035e61042d3660046134ad565b611377565b6102e6610440366004613416565b60006020819052908152604090205481565b600a5461046c90600160801b90046001600160801b031681565b6040516001600160801b0390911681526020016102f0565b61035e61049236600461343a565b611576565b6102e661010e5481565b6102e66104af36600461359c565b600c60209081526000928352604080842090915290825290205481565b6102e66104da366004613416565b60046020526000908152604090205481565b6102e661183f565b610537610502366004613416565b6005602052600090815260409020805460018201546002909201549091906001600160801b0380821691600160801b90041684565b6040805194855260208501939093526001600160801b03918216928401929092521660608201526080016102f0565b6102e660095481565b6103206118cc565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6102e6670de0b6b3a764000081565b6102e66105bb366004613416565b60036020526000908152604090205481565b600a5461046c906001600160801b031681565b61046c62ed4e0081565b61032061192c565b61035e610600366004613416565b61198c565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6102e661063a366004613416565b611ae6565b6102e6633b9aca0081565b6102e66106583660046135cf565b611b79565b61069261066b36600461360b565b61010f602052600090815260409020546001600160801b0380821691600160801b90041682565b604080516001600160801b039384168152929091166020830152016102f0565b610110546106cb9061ffff808216916201000090041682565b6040805161ffff9384168152929091166020830152016102f0565b61035e6106f436600461362f565b611bac565b6102e6610707366004613416565b611bb7565b6102e661071a36600461343a565b611ea2565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b600660205281600052604060002081610100811061076357600080fd5b01549150829050565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146107e95760405162461bcd60e51b815260206004820152600b60248201527f4e6f7420666163746f727900000000000000000000000000000000000000000060448201526064015b60405180910390fd5b6001546000805b8281101561084a57836001600160a01b03166001828154811061081557610815613664565b6000918252602090912001546001600160a01b031603610838576001915061084a565b8061084281613690565b9150506107f0565b50806109a157604080518082019091526101105461ffff808216808452620100009092041660208301819052111561092a57805161ffff16600090815261010f60209081526040918290208251808401909352546001600160801b038082168452600160801b9091041690820181905242111561092857610110805461010f9160009161ffff1690826108dc836136c8565b82546101009290920a61ffff818102199093169183160217909155168152602081019190915260400160009081205580516109219086906001600160801b0316611eba565b5050505050565b505b506001805480820182557fb10e2d527612073b26eecdfd717e6a320cf44b4afac2b0732d9fcbe2b7fa0cf60180547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b038616908117909155905460009182526020829052604090912055505050565b6001600160a01b038316600090815260208190526040902054610a065760405162461bcd60e51b815260206004820152601860248201527f436f6c6c61746572616c2069732073756e73657474696e67000000000000000060448201526064016107e0565b505050565b600760205281600052604060002081610100811061076357600080fd5b60018181548110610a3857600080fd5b6000918252602090912001546001600160a01b0316905081565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663175e1a7d6040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad691906136e9565b905090565b610ae36118cc565b6001600160a01b0316336001600160a01b031614610b435760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b6001600160a01b038116600090815260208190526040902054610ba85760405162461bcd60e51b815260206004820152601d60248201527f436f6c6c61746572616c20616c72656164792073756e73657474696e6700000060448201526064016107e0565b6040805180820182526001600160a01b0383166000908152602081905291909120548190610bd890600190613706565b6001600160801b03168152602001610bf362ed4e0042613719565b6001600160801b03169052610110805461010f9160009162010000900461ffff16906002610c20836136c8565b825461ffff9182166101009390930a928302928202191691909117909155168152602080820192909252604090810160009081208451948401516001600160801b03908116600160801b029516949094179093556001600160a01b03909316825281905290812055565b610c926118cc565b6001600160a01b0316336001600160a01b031614610cf25760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b610cfa610a52565b6040517f954fa5ee0000000000000000000000000000000000000000000000000000000081523060048201526001600160a01b038381166024830152919091169063954fa5ee906044016020604051808303816000875af1158015610d63573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610d87919061372c565b5050565b3360009081526004602052604090205480610e0e5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2055736572206d757374206861766520612060448201527f6e6f6e2d7a65726f206465706f7369740000000000000000000000000000000060648201526084016107e0565b33600090815260036020526040902054429003610e935760405162461bcd60e51b815260206004820152602360248201527f53746162696c697479506f6f6c3a205769746864726177616c206973206c6f6360448201527f6b6564000000000000000000000000000000000000000000000000000000000060648201526084016107e0565b610e9b6120d0565b610ea43361215e565b506000610eb033611ae6565b90506000610ebe8483612336565b9050610ec933612350565b8015610f77576040517f20c582be000000000000000000000000000000000000000000000000000000008152306004820152336024820152604481018290527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316906320c582be90606401600060405180830381600087803b158015610f5657600080fd5b505af1158015610f6a573d6000803e3d6000fd5b50505050610f77816123a2565b6000610f838284613706565b336000818152600460205260409020829055909150610fa290826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c9906020015b60405180910390a25050505050565b60015460609067ffffffffffffffff811115610ffd57610ffd613497565b604051908082528060200260200182016040528015611026578160200160208202803683370190505b506001600160a01b0383166000908152600560205260408120549192508190036110505750919050565b6001600160a01b0383166000908152600760205260408082208151612000810192839052916101009082845b81548152602001906001019080831161107c57505050506001600160a01b03861660009081526004602090815260408083205460058352818420600201546001600160801b03600160801b82048116808752600b865284872091909216808752945282852083516120008101948590529798509196909550929392916101009082845b8154815260200190600101908083116110ff57505050506001600160801b0385166000908152600b6020526040812092935091905081611140856001613745565b6001600160801b03168152602081019190915260409081016000208151612000810192839052916101009082845b81548152602001906001019080831161116e57505050506001600160a01b038b166000908152600660205260408082208151612000810192839052949550919392506101009082845b8154815260200190600101908083116111b7575050505050905060005b895181101561130957878161010081106111f0576111f0613664565b60200201518a828151811061120757611207613664565b6020026020010181815250508381610100811061122657611226613664565b6020020151156112f75760008282610100811061124557611245613664565b60200201518583610100811061125d5761125d613664565b602002015161126c9190613706565b90506000633b9aca008584610100811061128857611288613664565b6020020151611297919061376c565b9050670de0b6b3a76400008b6112ad8385613719565b6112b7908c61378e565b6112c1919061376c565b6112cb919061376c565b8c84815181106112dd576112dd613664565b602002602001018181516112f19190613719565b90525050505b8061130181613690565b9150506111d4565b505050505050505050919050565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b33600090815260046020526040902054806113fa5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2055736572206d757374206861766520612060448201527f6e6f6e2d7a65726f206465706f7369740000000000000000000000000000000060648201526084016107e0565b6114026120d0565b61140b3361215e565b50600061141733611ae6565b905061142233612350565b336000818152600460205260409020829055819061144090826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c99060200160405180910390a26000611480336125e3565b90508015611524576040517f70ccf0240000000000000000000000000000000000000000000000000000000081526001600160a01b038781166004830152602482018390527f000000000000000000000000000000000000000000000000000000000000000016906370ccf02490604401600060405180830381600087803b15801561150b57600080fd5b505af115801561151f573d6000803e3d6000fd5b505050505b6040518181526001600160a01b0387169033907f0aa4d283470c904c551d18bb894d37e17674920f3261a7f854be501e25f421b79060200160405180910390a361156e86866126d1565b505050505050565b7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316635c975abb6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156115d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906115f891906137a5565b156116455760405162461bcd60e51b815260206004820152601360248201527f4465706f7369747320617265207061757365640000000000000000000000000060448201526064016107e0565b600081116116bb5760405162461bcd60e51b815260206004820152602660248201527f53746162696c697479506f6f6c3a20416d6f756e74206d757374206265206e6f60448201527f6e2d7a65726f000000000000000000000000000000000000000000000000000060648201526084016107e0565b3360009081526003602052604090204290556116d56120d0565b6116de3361215e565b5060006116ea33611ae6565b90506116f533612350565b6040517fe75b3ae7000000000000000000000000000000000000000000000000000000008152336004820152602481018390527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03169063e75b3ae790604401600060405180830381600087803b15801561177657600080fd5b505af115801561178a573d6000803e3d6000fd5b5050505060008260025461179e9190613719565b60028190556040518181529091507fc348ac60fd6646a579769d005f3a080acc20db56a13b43b99f7de7d6bb1656f19060200160405180910390a160006117e58484613719565b33600081815260046020526040902082905590915061180490826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c99060200160405180910390a250505050565b600061184961192c565b6040517fe12f3a610000000000000000000000000000000000000000000000000000000081523060048201526001600160a01b03919091169063e12f3a6190602401602060405180830381865afa1580156118a8573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad6919061372c565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316638da5cb5b6040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663ad5c46486040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b6119946118cc565b6001600160a01b0316336001600160a01b0316146119f45760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b60006119fe61183f565b905060008111611a505760405162461bcd60e51b815260206004820152601360248201527f6e6f20636c61696d61626c6520616d6f756e740000000000000000000000000060448201526064016107e0565b611a5861192c565b6040517faad3ec960000000000000000000000000000000000000000000000000000000081526001600160a01b03848116600483015260248201849052919091169063aad3ec96906044016020604051808303816000875af1158015611ac2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610a06919061372c565b6001600160a01b038116600090815260046020526040812054808203611b0f5750600092915050565b6001600160a01b0383166000908152600560209081526040808320815160808101835281548152600182015493810193909352600201546001600160801b0380821692840192909252600160801b900416606082015290611b708383612824565b95945050505050565b600b602052826000526040600020602052816000526040600020816101008110611ba257600080fd5b0154925083915050565b610a06838383612911565b6002546001600160a01b038216600090815260046020526040812054909190811580611be1575080155b15611bf0575060009392505050565b6000600d54670de0b6b3a76400007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663137ee36e6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c5c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c80919061372c565b611c8a919061378e565b611c949190613719565b90506000611ca2848361376c565b9050600060095482611cb4919061378e565b6001600160a01b0388166000908152600560209081526040808320815160808101835281548152600182015493810193909352600201546001600160801b03808216928401839052600160801b909104811660608401819052600a549596509294929391928291168303611dc2576020808601516001600160801b038087166000908152600c84526040808220928816825291909352909120548791611d5991613706565b611d639190613719565b6001600160801b0385166000908152600c60205260408120919350633b9aca009190611d90866001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054611dbb919061376c565b9050611e5e565b6020808601516001600160801b038087166000908152600c8452604080822092881682529190935290912054611df89190613706565b6001600160801b0385166000908152600c60205260408120919350633b9aca00918891611e26876001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054611e519190613719565b611e5b919061376c565b90505b8451670de0b6b3a764000090611e748385613719565b611e7e908c61378e565b611e88919061376c565b611e92919061376c565b9c9b505050505050505050505050565b600e816101008110611eb357600080fd5b0154905081565b6001600160a01b03821660009081526020819052604090205415611f205760405162461bcd60e51b815260206004820152601960248201527f436f6c6c61746572616c206d7573742062652073756e7365740000000000000060448201526064016107e0565b600154808210611f725760405162461bcd60e51b815260206004820152600f60248201527f496e64657820746f6f206c61726765000000000000000000000000000000000060448201526064016107e0565b600a546001600160801b03600160801b82048116911660005b82816001600160801b031611611ffa5760005b82816001600160801b031611611ff1576001600160801b038083166000908152600b602090815260408083209385168352929052908120876101008110611fe757611fe7613664565b0155600101611f9e565b50600101611f8b565b50612006846001613719565b6001600160a01b038616600090815260208190526040902055600180547f9e147d339c63698deb55c3d0d44ed3eba29bac2a068a88c4bc5bde17d6331e1991908690811061205657612056613664565b60009182526020918290200154604080516001600160a01b039283168152918916928201929092520160405180910390a1846001858154811061209b5761209b613664565b9060005260206000200160006101000a8154816001600160a01b0302191690836001600160a01b031602179055505050505050565b61215c7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316632afd9f0b6040518163ffffffff1660e01b81526004016020604051808303816000875af1158015612133573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612157919061372c565b612a28565b565b6001600160a01b038116600090815260076020908152604080832060015460049093529083205490919080840361219757505050919050565b6001600160a01b0385166000908152600560209081526040808320600281015490546001600160801b03600160801b83048116808752600b808752858820929094168088528287529487208188529390955293949293909290816121fc866001613745565b6001600160801b03168152602080820192909252604090810160009081206001600160a01b038e16825260069093529081209192505b88811015612327578381610100811061224d5761224d613664565b0154156123155760019a5060008282610100811061226d5761226d613664565b01548583610100811061228257612282613664565b015461228e9190613706565b90506000633b9aca00858461010081106122aa576122aa613664565b01546122b6919061376c565b9050670de0b6b3a7640000876122cc8385613719565b6122d6908d61378e565b6122e0919061376c565b6122ea919061376c565b8c8461010081106122fd576122fd613664565b01600082825461230d9190613719565b909155505050505b8061231f81613690565b915050612232565b50505050505050505050919050565b60008183106123455781612347565b825b90505b92915050565b600061235b82612b24565b6001600160a01b038316600090815260086020526040902054909150612382908290613719565b6001600160a01b0390921660009081526008602052604090209190915550565b6000816002546123b29190613706565b60028190556040518181529091507fc348ac60fd6646a579769d005f3a080acc20db56a13b43b99f7de7d6bb1656f19060200160405180910390a15050565b6000816000036124ba57506001600160a01b03821660009081526005602052604081208181556001808201839055600290910182905554905b81811015612470576001600160a01b038416600090815260066020526040812082610100811061245c5761245c613664565b01558061246881613690565b91505061242a565b5060408051600080825260208201526001600160a01b038516917fc48943df4095f4f20d171fd2872eafdc0eed4d9014ac3672f3bde7fd425449d5910160405180910390a2505050565b50600a546009546001600160801b03600160801b80840482166000818152600b6020908152604080832095909716808352948152868220838352600c82528783208684528252878320546001600160a01b038b168452600590925296822086815560018082018390559484028617600290910155925495939491939192905b86811015612594578281610100811061255457612554613664565b01546001600160a01b038a16600090815260066020526040902082610100811061258057612580613664565b01558061258c81613690565b915050612539565b5060408051848152602081018390526001600160a01b038a16917fc48943df4095f4f20d171fd2872eafdc0eed4d9014ac3672f3bde7fd425449d5910160405180910390a25050505050505050565b6001600160a01b03811660009081526004602052604081205480156126855761260a6120d0565b60006126158461215e565b9050600061262285611ae6565b905060006126308285613706565b905061263b86612b24565b945060008111806126495750825b806126545750600085115b15612681576001600160a01b03861660009081526004602052604090208290558161267f87826123f1565b505b5050505b6001600160a01b03831660009081526008602052604090205480156126ca576126ae8184613719565b6001600160a01b03851660009081526008602052604081205592505b5050919050565b805160015460009067ffffffffffffffff8111156126f1576126f1613497565b60405190808252806020026020018201604052801561271a578160200160208202803683370190505b503360009081526007602052604081209192505b838110156127ea57600085828151811061274a5761274a613664565b6020026020010151905060008382610100811061276957612769613664565b0154905080156127e0578085838151811061278657612786613664565b6020026020010181815250506000848361010081106127a7576127a7613664565b01819055506127e08882600185815481106127c4576127c4613664565b6000918252602090912001546001600160a01b03169190612bb8565b505060010161272e565b50336001600160a01b03167faecf5c2e84838a7ed87234d73965fc51f96b87b4c957f03bf22cfeb618c9aae183604051610fd09190613453565b805160408201516060830151600a546000939291906001600160801b03600160801b90910481169082161015612860576000935050505061234a565b600a54600090819061287c9085906001600160801b03166137c7565b9050806001600160801b03166000036128af57846009548961289e919061378e565b6128a8919061376c565b91506128e3565b806001600160801b03166001036128de57633b9aca00856009548a6128d4919061378e565b61289e919061376c565b600091505b6128f1633b9aca008961376c565b8210156129065760009550505050505061234a565b509695505050505050565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146129af5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2043616c6c6572206973206e6f74204c697160448201527f7569646174696f6e204d616e616765720000000000000000000000000000000060648201526084016107e0565b6001600160a01b0383166000908152602081905260409020546129d3600182613706565b6002549091508015806129e4575083155b156129f0575050505050565b6129f86120d0565b600080612a0785878587612c38565b91509150612a16828286612d25565b612a1f866123a2565b50505050505050565b600254801580612a36575081155b15612a3f575050565b6000612a4b8383613090565b600a546009549192506001600160801b03600160801b8204811692911690600090612a76908561378e565b6001600160801b038085166000908152600c6020908152604080832093871683529290529081205491925090612aad908390613719565b6001600160801b038581166000818152600c60209081526040808320948916808452948252918290208590558151858152908101929092528101919091529091507f2d6127771b164a9cc8827d24b5955db2a77e7a81dac389107ebb8bce9fb649689060600160405180910390a150505050505050565b6001600160a01b038116600090815260046020526040812054808203612b4d5750600092915050565b6001600160a01b038316600090815260056020908152604091829020825160808101845281548152600182015492810192909252600201546001600160801b0380821693830193909352600160801b90049091166060820152612bb082826130e3565b949350505050565b604080516001600160a01b038416602482015260448082018490528251808303909101815260649091019091526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fa9059cbb00000000000000000000000000000000000000000000000000000000179052610a069084906131c7565b6000806000600e846101008110612c5157612c51613664565b0154612c65670de0b6b3a76400008961378e565b612c6f9190613719565b9050848603612c8e57600061010e55670de0b6b3a76400009150612ce5565b61010e54600090612ca7670de0b6b3a76400008961378e565b612cb19190613706565b9050612cbd868261376c565b612cc8906001613719565b925080612cd5878561378e565b612cdf9190613706565b61010e55505b612cef858261376c565b9250612cfb858461378e565b612d059082613706565b600e856101008110612d1957612d19613664565b01555094509492505050565b600954600080612d3d85670de0b6b3a7640000613706565b600a546001600160801b03600160801b820481166000818152600b60209081526040808320949095168083529390529283209394509092909190876101008110612d8957612d89613664565b015490506000612d99878b61378e565b90506000612da78284613719565b6001600160801b038086166000908152600b60209081526040808320938a1683529290522090915081908a6101008110612de357612de3613664565b0155604080518a8152602081018390526001600160801b03868116828401528716606082015290517fe150473acddd94d1c6add794bd840c8d3e297dc3e50d863b56c0fba04d0d02479181900360800190a185600003612f0957612e48846001613745565b600a80546001600160801b03908116600160801b93821684021791829055604051929091041681527fb50f0f59e7cb5b421dc77581c3a9919e3806e076e5fa78a874c3f120cb7d874d9060200160405180910390a1600a80547fffffffffffffffffffffffffffffffff00000000000000000000000000000000169055604051600081527f1f9dfc70cd666adb18a39d60a797518f7b4febf4b6e24ef37d44f6e1e7219fbe9060200160405180910390a1670de0b6b3a76400009650612ff9565b633b9aca00670de0b6b3a7640000612f21888b61378e565b612f2b919061376c565b1015612fd957670de0b6b3a7640000633b9aca00612f49888b61378e565b612f53919061378e565b612f5d919061376c565b9650612f6a856001613745565b600a80547fffffffffffffffffffffffffffffffff00000000000000000000000000000000166001600160801b039290921691821790556040519081527f1f9dfc70cd666adb18a39d60a797518f7b4febf4b6e24ef37d44f6e1e7219fbe9060200160405180910390a1612ff9565b670de0b6b3a7640000612fec878a61378e565b612ff6919061376c565b96505b6000871161304b5760405162461bcd60e51b81526004016107e09060208082526004908201527f4e65775000000000000000000000000000000000000000000000000000000000604082015260600190565b60098790556040518781527fc1a9618cb59ebca77cbdbc2949f126823c407ff13edb285fd0262519a9c18e8c9060200160405180910390a15050505050505050505050565b600080600d54670de0b6b3a7640000856130aa919061378e565b6130b49190613719565b905060006130c2848361376c565b90506130ce848261378e565b6130d89083613706565b600d55949350505050565b606081015160408083015160208085015185516001600160801b038087166000908152600c855286812091861681529352938220549194939091859061312a908490613706565b6001600160801b0386166000908152600c6020526040812091925090633b9aca009082613158886001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054613183919061376c565b90506000670de0b6b3a76400008461319b8486613719565b6131a5908d61378e565b6131af919061376c565b6131b9919061376c565b9a9950505050505050505050565b600061321c826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166132af9092919063ffffffff16565b905080516000148061323d57508080602001905181019061323d91906137a5565b610a065760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e60448201527f6f7420737563636565640000000000000000000000000000000000000000000060648201526084016107e0565b6060612bb0848460008585600080866001600160a01b031685876040516132d6919061380b565b60006040518083038185875af1925050503d8060008114613313576040519150601f19603f3d011682016040523d82523d6000602084013e613318565b606091505b509150915061332987838387613334565b979650505050505050565b606083156133a357825160000361339c576001600160a01b0385163b61339c5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e747261637400000060448201526064016107e0565b5081612bb0565b612bb083838151156133b85781518083602001fd5b8060405162461bcd60e51b81526004016107e09190613827565b6001600160a01b03811681146133e757600080fd5b50565b600080604083850312156133fd57600080fd5b8235613408816133d2565b946020939093013593505050565b60006020828403121561342857600080fd5b8135613433816133d2565b9392505050565b60006020828403121561344c57600080fd5b5035919050565b6020808252825182820181905260009190848201906040850190845b8181101561348b5783518352928401929184019160010161346f565b50909695505050505050565b634e487b7160e01b600052604160045260246000fd5b600080604083850312156134c057600080fd5b82356134cb816133d2565b915060208381013567ffffffffffffffff808211156134e957600080fd5b818601915086601f8301126134fd57600080fd5b81358181111561350f5761350f613497565b8060051b604051601f19603f8301168101818110858211171561353457613534613497565b60405291825284820192508381018501918983111561355257600080fd5b938501935b8285101561357057843584529385019392850192613557565b8096505050505050509250929050565b80356001600160801b038116811461359757600080fd5b919050565b600080604083850312156135af57600080fd5b6135b883613580565b91506135c660208401613580565b90509250929050565b6000806000606084860312156135e457600080fd5b6135ed84613580565b92506135fb60208501613580565b9150604084013590509250925092565b60006020828403121561361d57600080fd5b813561ffff8116811461343357600080fd5b60008060006060848603121561364457600080fd5b833561364f816133d2565b95602085013595506040909401359392505050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff82036136c1576136c161367a565b5060010190565b600061ffff8083168181036136df576136df61367a565b6001019392505050565b6000602082840312156136fb57600080fd5b8151613433816133d2565b8181038181111561234a5761234a61367a565b8082018082111561234a5761234a61367a565b60006020828403121561373e57600080fd5b5051919050565b6001600160801b038181168382160190808211156137655761376561367a565b5092915050565b60008261378957634e487b7160e01b600052601260045260246000fd5b500490565b808202811582820484141761234a5761234a61367a565b6000602082840312156137b757600080fd5b8151801515811461343357600080fd5b6001600160801b038281168282160390808211156137655761376561367a565b60005b838110156138025781810151838201526020016137ea565b50506000910152565b6000825161381d8184602087016137e7565b9190910192915050565b60208152600082518060208401526138468160408501602087016137e7565b601f01601f1916919091016040019291505056fea2646970667358221220e94292f1246a0a66f023ace5e0c887504535a4033df0240cad8dcc8c13a1f2e864736f6c63430008130033",
  "deployedBytecode": "0x608060405234801561001057600080fd5b50600436106102dd5760003560e01c806386ad29aa11610186578063c2d94aec116100e3578063dec8d97511610097578063e950342511610071578063e9503425146106f9578063eeb58d0b1461070c578063f2b6db511461071f57600080fd5b8063dec8d9751461065d578063e10d29ee146106b2578063e6666733146106e657600080fd5b8063cd7502fe116100c8578063cd7502fe1461062c578063ce4b5bbe1461063f578063db03fdaa1461064a57600080fd5b8063c2d94aec146105f2578063c45a01551461060557600080fd5b8063a20baee61161013a578063a4e59ac81161011f578063a4e59ac8146105cd578063a7528a03146105e0578063ad5c4648146105ea57600080fd5b8063a20baee61461059e578063a4beda63146105ad57600080fd5b80638b8fbd921161016b5780638b8fbd92146105665780638da5cb5b1461056f57806395fb16bb1461057757600080fd5b806386ad29aa146104ec57806386da0824146104f457600080fd5b80632e54bf951161023f5780635383dfcb116101f357806381bafb31116101cd57806381bafb311461049757806382e0a574146104a1578063835dada0146104cc57600080fd5b80635383dfcb14610432578063766718081461045257806378c77a241461048457600080fd5b806333a3d73f1161022457806333a3d73f1461040e578063452a932014610417578063457182781461041f57600080fd5b80632e54bf95146103db578063307d3612146103ee57600080fd5b8063172c48c71161029657806319f27b3b1161027b57806319f27b3b1461038e5780631ef3a04c146103a1578063272b1323146103c857600080fd5b8063172c48c714610373578063175e1a7d1461038657600080fd5b806309e2acb0116102c757806309e2acb01461033857806311be0de51461034b5780631500d2c31461036057600080fd5b80622dade9146102e2578063086ce520146102f9575b600080fd5b6002545b6040519081526020015b60405180910390f35b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020016102f0565b6102e66103463660046133ea565b610746565b61035e610359366004613416565b61076c565b005b6102e661036e3660046133ea565b610a0b565b61032061038136600461343a565b610a28565b610320610a52565b61035e61039c366004613416565b610adb565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b61035e6103d6366004613416565b610c8a565b61035e6103e936600461343a565b610d8b565b6104016103fc366004613416565b610fdf565b6040516102f09190613453565b6102e6600d5481565b610320611317565b61035e61042d3660046134ad565b611377565b6102e6610440366004613416565b60006020819052908152604090205481565b600a5461046c90600160801b90046001600160801b031681565b6040516001600160801b0390911681526020016102f0565b61035e61049236600461343a565b611576565b6102e661010e5481565b6102e66104af36600461359c565b600c60209081526000928352604080842090915290825290205481565b6102e66104da366004613416565b60046020526000908152604090205481565b6102e661183f565b610537610502366004613416565b6005602052600090815260409020805460018201546002909201549091906001600160801b0380821691600160801b90041684565b6040805194855260208501939093526001600160801b03918216928401929092521660608201526080016102f0565b6102e660095481565b6103206118cc565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6102e6670de0b6b3a764000081565b6102e66105bb366004613416565b60036020526000908152604090205481565b600a5461046c906001600160801b031681565b61046c62ed4e0081565b61032061192c565b61035e610600366004613416565b61198c565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b6102e661063a366004613416565b611ae6565b6102e6633b9aca0081565b6102e66106583660046135cf565b611b79565b61069261066b36600461360b565b61010f602052600090815260409020546001600160801b0380821691600160801b90041682565b604080516001600160801b039384168152929091166020830152016102f0565b610110546106cb9061ffff808216916201000090041682565b6040805161ffff9384168152929091166020830152016102f0565b61035e6106f436600461362f565b611bac565b6102e6610707366004613416565b611bb7565b6102e661071a36600461343a565b611ea2565b6103207f000000000000000000000000000000000000000000000000000000000000000081565b600660205281600052604060002081610100811061076357600080fd5b01549150829050565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146107e95760405162461bcd60e51b815260206004820152600b60248201527f4e6f7420666163746f727900000000000000000000000000000000000000000060448201526064015b60405180910390fd5b6001546000805b8281101561084a57836001600160a01b03166001828154811061081557610815613664565b6000918252602090912001546001600160a01b031603610838576001915061084a565b8061084281613690565b9150506107f0565b50806109a157604080518082019091526101105461ffff808216808452620100009092041660208301819052111561092a57805161ffff16600090815261010f60209081526040918290208251808401909352546001600160801b038082168452600160801b9091041690820181905242111561092857610110805461010f9160009161ffff1690826108dc836136c8565b82546101009290920a61ffff818102199093169183160217909155168152602081019190915260400160009081205580516109219086906001600160801b0316611eba565b5050505050565b505b506001805480820182557fb10e2d527612073b26eecdfd717e6a320cf44b4afac2b0732d9fcbe2b7fa0cf60180547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b038616908117909155905460009182526020829052604090912055505050565b6001600160a01b038316600090815260208190526040902054610a065760405162461bcd60e51b815260206004820152601860248201527f436f6c6c61746572616c2069732073756e73657474696e67000000000000000060448201526064016107e0565b505050565b600760205281600052604060002081610100811061076357600080fd5b60018181548110610a3857600080fd5b6000918252602090912001546001600160a01b0316905081565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663175e1a7d6040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad691906136e9565b905090565b610ae36118cc565b6001600160a01b0316336001600160a01b031614610b435760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b6001600160a01b038116600090815260208190526040902054610ba85760405162461bcd60e51b815260206004820152601d60248201527f436f6c6c61746572616c20616c72656164792073756e73657474696e6700000060448201526064016107e0565b6040805180820182526001600160a01b0383166000908152602081905291909120548190610bd890600190613706565b6001600160801b03168152602001610bf362ed4e0042613719565b6001600160801b03169052610110805461010f9160009162010000900461ffff16906002610c20836136c8565b825461ffff9182166101009390930a928302928202191691909117909155168152602080820192909252604090810160009081208451948401516001600160801b03908116600160801b029516949094179093556001600160a01b03909316825281905290812055565b610c926118cc565b6001600160a01b0316336001600160a01b031614610cf25760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b610cfa610a52565b6040517f954fa5ee0000000000000000000000000000000000000000000000000000000081523060048201526001600160a01b038381166024830152919091169063954fa5ee906044016020604051808303816000875af1158015610d63573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610d87919061372c565b5050565b3360009081526004602052604090205480610e0e5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2055736572206d757374206861766520612060448201527f6e6f6e2d7a65726f206465706f7369740000000000000000000000000000000060648201526084016107e0565b33600090815260036020526040902054429003610e935760405162461bcd60e51b815260206004820152602360248201527f53746162696c697479506f6f6c3a205769746864726177616c206973206c6f6360448201527f6b6564000000000000000000000000000000000000000000000000000000000060648201526084016107e0565b610e9b6120d0565b610ea43361215e565b506000610eb033611ae6565b90506000610ebe8483612336565b9050610ec933612350565b8015610f77576040517f20c582be000000000000000000000000000000000000000000000000000000008152306004820152336024820152604481018290527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316906320c582be90606401600060405180830381600087803b158015610f5657600080fd5b505af1158015610f6a573d6000803e3d6000fd5b50505050610f77816123a2565b6000610f838284613706565b336000818152600460205260409020829055909150610fa290826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c9906020015b60405180910390a25050505050565b60015460609067ffffffffffffffff811115610ffd57610ffd613497565b604051908082528060200260200182016040528015611026578160200160208202803683370190505b506001600160a01b0383166000908152600560205260408120549192508190036110505750919050565b6001600160a01b0383166000908152600760205260408082208151612000810192839052916101009082845b81548152602001906001019080831161107c57505050506001600160a01b03861660009081526004602090815260408083205460058352818420600201546001600160801b03600160801b82048116808752600b865284872091909216808752945282852083516120008101948590529798509196909550929392916101009082845b8154815260200190600101908083116110ff57505050506001600160801b0385166000908152600b6020526040812092935091905081611140856001613745565b6001600160801b03168152602081019190915260409081016000208151612000810192839052916101009082845b81548152602001906001019080831161116e57505050506001600160a01b038b166000908152600660205260408082208151612000810192839052949550919392506101009082845b8154815260200190600101908083116111b7575050505050905060005b895181101561130957878161010081106111f0576111f0613664565b60200201518a828151811061120757611207613664565b6020026020010181815250508381610100811061122657611226613664565b6020020151156112f75760008282610100811061124557611245613664565b60200201518583610100811061125d5761125d613664565b602002015161126c9190613706565b90506000633b9aca008584610100811061128857611288613664565b6020020151611297919061376c565b9050670de0b6b3a76400008b6112ad8385613719565b6112b7908c61378e565b6112c1919061376c565b6112cb919061376c565b8c84815181106112dd576112dd613664565b602002602001018181516112f19190613719565b90525050505b8061130181613690565b9150506111d4565b505050505050505050919050565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b33600090815260046020526040902054806113fa5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2055736572206d757374206861766520612060448201527f6e6f6e2d7a65726f206465706f7369740000000000000000000000000000000060648201526084016107e0565b6114026120d0565b61140b3361215e565b50600061141733611ae6565b905061142233612350565b336000818152600460205260409020829055819061144090826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c99060200160405180910390a26000611480336125e3565b90508015611524576040517f70ccf0240000000000000000000000000000000000000000000000000000000081526001600160a01b038781166004830152602482018390527f000000000000000000000000000000000000000000000000000000000000000016906370ccf02490604401600060405180830381600087803b15801561150b57600080fd5b505af115801561151f573d6000803e3d6000fd5b505050505b6040518181526001600160a01b0387169033907f0aa4d283470c904c551d18bb894d37e17674920f3261a7f854be501e25f421b79060200160405180910390a361156e86866126d1565b505050505050565b7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316635c975abb6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156115d4573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906115f891906137a5565b156116455760405162461bcd60e51b815260206004820152601360248201527f4465706f7369747320617265207061757365640000000000000000000000000060448201526064016107e0565b600081116116bb5760405162461bcd60e51b815260206004820152602660248201527f53746162696c697479506f6f6c3a20416d6f756e74206d757374206265206e6f60448201527f6e2d7a65726f000000000000000000000000000000000000000000000000000060648201526084016107e0565b3360009081526003602052604090204290556116d56120d0565b6116de3361215e565b5060006116ea33611ae6565b90506116f533612350565b6040517fe75b3ae7000000000000000000000000000000000000000000000000000000008152336004820152602481018390527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03169063e75b3ae790604401600060405180830381600087803b15801561177657600080fd5b505af115801561178a573d6000803e3d6000fd5b5050505060008260025461179e9190613719565b60028190556040518181529091507fc348ac60fd6646a579769d005f3a080acc20db56a13b43b99f7de7d6bb1656f19060200160405180910390a160006117e58484613719565b33600081815260046020526040902082905590915061180490826123f1565b60405181815233907fbce78369dccab09eec1986f4d409ab09ffbb47d65423e5148fcf98411c5111c99060200160405180910390a250505050565b600061184961192c565b6040517fe12f3a610000000000000000000000000000000000000000000000000000000081523060048201526001600160a01b03919091169063e12f3a6190602401602060405180830381865afa1580156118a8573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad6919061372c565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316638da5cb5b6040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663ad5c46486040518163ffffffff1660e01b8152600401602060405180830381865afa158015610ab2573d6000803e3d6000fd5b6119946118cc565b6001600160a01b0316336001600160a01b0316146119f45760405162461bcd60e51b815260206004820152600a60248201527f4f6e6c79206f776e65720000000000000000000000000000000000000000000060448201526064016107e0565b60006119fe61183f565b905060008111611a505760405162461bcd60e51b815260206004820152601360248201527f6e6f20636c61696d61626c6520616d6f756e740000000000000000000000000060448201526064016107e0565b611a5861192c565b6040517faad3ec960000000000000000000000000000000000000000000000000000000081526001600160a01b03848116600483015260248201849052919091169063aad3ec96906044016020604051808303816000875af1158015611ac2573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610a06919061372c565b6001600160a01b038116600090815260046020526040812054808203611b0f5750600092915050565b6001600160a01b0383166000908152600560209081526040808320815160808101835281548152600182015493810193909352600201546001600160801b0380821692840192909252600160801b900416606082015290611b708383612824565b95945050505050565b600b602052826000526040600020602052816000526040600020816101008110611ba257600080fd5b0154925083915050565b610a06838383612911565b6002546001600160a01b038216600090815260046020526040812054909190811580611be1575080155b15611bf0575060009392505050565b6000600d54670de0b6b3a76400007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663137ee36e6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611c5c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c80919061372c565b611c8a919061378e565b611c949190613719565b90506000611ca2848361376c565b9050600060095482611cb4919061378e565b6001600160a01b0388166000908152600560209081526040808320815160808101835281548152600182015493810193909352600201546001600160801b03808216928401839052600160801b909104811660608401819052600a549596509294929391928291168303611dc2576020808601516001600160801b038087166000908152600c84526040808220928816825291909352909120548791611d5991613706565b611d639190613719565b6001600160801b0385166000908152600c60205260408120919350633b9aca009190611d90866001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054611dbb919061376c565b9050611e5e565b6020808601516001600160801b038087166000908152600c8452604080822092881682529190935290912054611df89190613706565b6001600160801b0385166000908152600c60205260408120919350633b9aca00918891611e26876001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054611e519190613719565b611e5b919061376c565b90505b8451670de0b6b3a764000090611e748385613719565b611e7e908c61378e565b611e88919061376c565b611e92919061376c565b9c9b505050505050505050505050565b600e816101008110611eb357600080fd5b0154905081565b6001600160a01b03821660009081526020819052604090205415611f205760405162461bcd60e51b815260206004820152601960248201527f436f6c6c61746572616c206d7573742062652073756e7365740000000000000060448201526064016107e0565b600154808210611f725760405162461bcd60e51b815260206004820152600f60248201527f496e64657820746f6f206c61726765000000000000000000000000000000000060448201526064016107e0565b600a546001600160801b03600160801b82048116911660005b82816001600160801b031611611ffa5760005b82816001600160801b031611611ff1576001600160801b038083166000908152600b602090815260408083209385168352929052908120876101008110611fe757611fe7613664565b0155600101611f9e565b50600101611f8b565b50612006846001613719565b6001600160a01b038616600090815260208190526040902055600180547f9e147d339c63698deb55c3d0d44ed3eba29bac2a068a88c4bc5bde17d6331e1991908690811061205657612056613664565b60009182526020918290200154604080516001600160a01b039283168152918916928201929092520160405180910390a1846001858154811061209b5761209b613664565b9060005260206000200160006101000a8154816001600160a01b0302191690836001600160a01b031602179055505050505050565b61215c7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316632afd9f0b6040518163ffffffff1660e01b81526004016020604051808303816000875af1158015612133573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612157919061372c565b612a28565b565b6001600160a01b038116600090815260076020908152604080832060015460049093529083205490919080840361219757505050919050565b6001600160a01b0385166000908152600560209081526040808320600281015490546001600160801b03600160801b83048116808752600b808752858820929094168088528287529487208188529390955293949293909290816121fc866001613745565b6001600160801b03168152602080820192909252604090810160009081206001600160a01b038e16825260069093529081209192505b88811015612327578381610100811061224d5761224d613664565b0154156123155760019a5060008282610100811061226d5761226d613664565b01548583610100811061228257612282613664565b015461228e9190613706565b90506000633b9aca00858461010081106122aa576122aa613664565b01546122b6919061376c565b9050670de0b6b3a7640000876122cc8385613719565b6122d6908d61378e565b6122e0919061376c565b6122ea919061376c565b8c8461010081106122fd576122fd613664565b01600082825461230d9190613719565b909155505050505b8061231f81613690565b915050612232565b50505050505050505050919050565b60008183106123455781612347565b825b90505b92915050565b600061235b82612b24565b6001600160a01b038316600090815260086020526040902054909150612382908290613719565b6001600160a01b0390921660009081526008602052604090209190915550565b6000816002546123b29190613706565b60028190556040518181529091507fc348ac60fd6646a579769d005f3a080acc20db56a13b43b99f7de7d6bb1656f19060200160405180910390a15050565b6000816000036124ba57506001600160a01b03821660009081526005602052604081208181556001808201839055600290910182905554905b81811015612470576001600160a01b038416600090815260066020526040812082610100811061245c5761245c613664565b01558061246881613690565b91505061242a565b5060408051600080825260208201526001600160a01b038516917fc48943df4095f4f20d171fd2872eafdc0eed4d9014ac3672f3bde7fd425449d5910160405180910390a2505050565b50600a546009546001600160801b03600160801b80840482166000818152600b6020908152604080832095909716808352948152868220838352600c82528783208684528252878320546001600160a01b038b168452600590925296822086815560018082018390559484028617600290910155925495939491939192905b86811015612594578281610100811061255457612554613664565b01546001600160a01b038a16600090815260066020526040902082610100811061258057612580613664565b01558061258c81613690565b915050612539565b5060408051848152602081018390526001600160a01b038a16917fc48943df4095f4f20d171fd2872eafdc0eed4d9014ac3672f3bde7fd425449d5910160405180910390a25050505050505050565b6001600160a01b03811660009081526004602052604081205480156126855761260a6120d0565b60006126158461215e565b9050600061262285611ae6565b905060006126308285613706565b905061263b86612b24565b945060008111806126495750825b806126545750600085115b15612681576001600160a01b03861660009081526004602052604090208290558161267f87826123f1565b505b5050505b6001600160a01b03831660009081526008602052604090205480156126ca576126ae8184613719565b6001600160a01b03851660009081526008602052604081205592505b5050919050565b805160015460009067ffffffffffffffff8111156126f1576126f1613497565b60405190808252806020026020018201604052801561271a578160200160208202803683370190505b503360009081526007602052604081209192505b838110156127ea57600085828151811061274a5761274a613664565b6020026020010151905060008382610100811061276957612769613664565b0154905080156127e0578085838151811061278657612786613664565b6020026020010181815250506000848361010081106127a7576127a7613664565b01819055506127e08882600185815481106127c4576127c4613664565b6000918252602090912001546001600160a01b03169190612bb8565b505060010161272e565b50336001600160a01b03167faecf5c2e84838a7ed87234d73965fc51f96b87b4c957f03bf22cfeb618c9aae183604051610fd09190613453565b805160408201516060830151600a546000939291906001600160801b03600160801b90910481169082161015612860576000935050505061234a565b600a54600090819061287c9085906001600160801b03166137c7565b9050806001600160801b03166000036128af57846009548961289e919061378e565b6128a8919061376c565b91506128e3565b806001600160801b03166001036128de57633b9aca00856009548a6128d4919061378e565b61289e919061376c565b600091505b6128f1633b9aca008961376c565b8210156129065760009550505050505061234a565b509695505050505050565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146129af5760405162461bcd60e51b815260206004820152603060248201527f53746162696c697479506f6f6c3a2043616c6c6572206973206e6f74204c697160448201527f7569646174696f6e204d616e616765720000000000000000000000000000000060648201526084016107e0565b6001600160a01b0383166000908152602081905260409020546129d3600182613706565b6002549091508015806129e4575083155b156129f0575050505050565b6129f86120d0565b600080612a0785878587612c38565b91509150612a16828286612d25565b612a1f866123a2565b50505050505050565b600254801580612a36575081155b15612a3f575050565b6000612a4b8383613090565b600a546009549192506001600160801b03600160801b8204811692911690600090612a76908561378e565b6001600160801b038085166000908152600c6020908152604080832093871683529290529081205491925090612aad908390613719565b6001600160801b038581166000818152600c60209081526040808320948916808452948252918290208590558151858152908101929092528101919091529091507f2d6127771b164a9cc8827d24b5955db2a77e7a81dac389107ebb8bce9fb649689060600160405180910390a150505050505050565b6001600160a01b038116600090815260046020526040812054808203612b4d5750600092915050565b6001600160a01b038316600090815260056020908152604091829020825160808101845281548152600182015492810192909252600201546001600160801b0380821693830193909352600160801b90049091166060820152612bb082826130e3565b949350505050565b604080516001600160a01b038416602482015260448082018490528251808303909101815260649091019091526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fa9059cbb00000000000000000000000000000000000000000000000000000000179052610a069084906131c7565b6000806000600e846101008110612c5157612c51613664565b0154612c65670de0b6b3a76400008961378e565b612c6f9190613719565b9050848603612c8e57600061010e55670de0b6b3a76400009150612ce5565b61010e54600090612ca7670de0b6b3a76400008961378e565b612cb19190613706565b9050612cbd868261376c565b612cc8906001613719565b925080612cd5878561378e565b612cdf9190613706565b61010e55505b612cef858261376c565b9250612cfb858461378e565b612d059082613706565b600e856101008110612d1957612d19613664565b01555094509492505050565b600954600080612d3d85670de0b6b3a7640000613706565b600a546001600160801b03600160801b820481166000818152600b60209081526040808320949095168083529390529283209394509092909190876101008110612d8957612d89613664565b015490506000612d99878b61378e565b90506000612da78284613719565b6001600160801b038086166000908152600b60209081526040808320938a1683529290522090915081908a6101008110612de357612de3613664565b0155604080518a8152602081018390526001600160801b03868116828401528716606082015290517fe150473acddd94d1c6add794bd840c8d3e297dc3e50d863b56c0fba04d0d02479181900360800190a185600003612f0957612e48846001613745565b600a80546001600160801b03908116600160801b93821684021791829055604051929091041681527fb50f0f59e7cb5b421dc77581c3a9919e3806e076e5fa78a874c3f120cb7d874d9060200160405180910390a1600a80547fffffffffffffffffffffffffffffffff00000000000000000000000000000000169055604051600081527f1f9dfc70cd666adb18a39d60a797518f7b4febf4b6e24ef37d44f6e1e7219fbe9060200160405180910390a1670de0b6b3a76400009650612ff9565b633b9aca00670de0b6b3a7640000612f21888b61378e565b612f2b919061376c565b1015612fd957670de0b6b3a7640000633b9aca00612f49888b61378e565b612f53919061378e565b612f5d919061376c565b9650612f6a856001613745565b600a80547fffffffffffffffffffffffffffffffff00000000000000000000000000000000166001600160801b039290921691821790556040519081527f1f9dfc70cd666adb18a39d60a797518f7b4febf4b6e24ef37d44f6e1e7219fbe9060200160405180910390a1612ff9565b670de0b6b3a7640000612fec878a61378e565b612ff6919061376c565b96505b6000871161304b5760405162461bcd60e51b81526004016107e09060208082526004908201527f4e65775000000000000000000000000000000000000000000000000000000000604082015260600190565b60098790556040518781527fc1a9618cb59ebca77cbdbc2949f126823c407ff13edb285fd0262519a9c18e8c9060200160405180910390a15050505050505050505050565b600080600d54670de0b6b3a7640000856130aa919061378e565b6130b49190613719565b905060006130c2848361376c565b90506130ce848261378e565b6130d89083613706565b600d55949350505050565b606081015160408083015160208085015185516001600160801b038087166000908152600c855286812091861681529352938220549194939091859061312a908490613706565b6001600160801b0386166000908152600c6020526040812091925090633b9aca009082613158886001613745565b6001600160801b03166001600160801b0316815260200190815260200160002054613183919061376c565b90506000670de0b6b3a76400008461319b8486613719565b6131a5908d61378e565b6131af919061376c565b6131b9919061376c565b9a9950505050505050505050565b600061321c826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166132af9092919063ffffffff16565b905080516000148061323d57508080602001905181019061323d91906137a5565b610a065760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e60448201527f6f7420737563636565640000000000000000000000000000000000000000000060648201526084016107e0565b6060612bb0848460008585600080866001600160a01b031685876040516132d6919061380b565b60006040518083038185875af1925050503d8060008114613313576040519150601f19603f3d011682016040523d82523d6000602084013e613318565b606091505b509150915061332987838387613334565b979650505050505050565b606083156133a357825160000361339c576001600160a01b0385163b61339c5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e747261637400000060448201526064016107e0565b5081612bb0565b612bb083838151156133b85781518083602001fd5b8060405162461bcd60e51b81526004016107e09190613827565b6001600160a01b03811681146133e757600080fd5b50565b600080604083850312156133fd57600080fd5b8235613408816133d2565b946020939093013593505050565b60006020828403121561342857600080fd5b8135613433816133d2565b9392505050565b60006020828403121561344c57600080fd5b5035919050565b6020808252825182820181905260009190848201906040850190845b8181101561348b5783518352928401929184019160010161346f565b50909695505050505050565b634e487b7160e01b600052604160045260246000fd5b600080604083850312156134c057600080fd5b82356134cb816133d2565b915060208381013567ffffffffffffffff808211156134e957600080fd5b818601915086601f8301126134fd57600080fd5b81358181111561350f5761350f613497565b8060051b604051601f19603f8301168101818110858211171561353457613534613497565b60405291825284820192508381018501918983111561355257600080fd5b938501935b8285101561357057843584529385019392850192613557565b8096505050505050509250929050565b80356001600160801b038116811461359757600080fd5b919050565b600080604083850312156135af57600080fd5b6135b883613580565b91506135c660208401613580565b90509250929050565b6000806000606084860312156135e457600080fd5b6135ed84613580565b92506135fb60208501613580565b9150604084013590509250925092565b60006020828403121561361d57600080fd5b813561ffff8116811461343357600080fd5b60008060006060848603121561364457600080fd5b833561364f816133d2565b95602085013595506040909401359392505050565b634e487b7160e01b600052603260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff82036136c1576136c161367a565b5060010190565b600061ffff8083168181036136df576136df61367a565b6001019392505050565b6000602082840312156136fb57600080fd5b8151613433816133d2565b8181038181111561234a5761234a61367a565b8082018082111561234a5761234a61367a565b60006020828403121561373e57600080fd5b5051919050565b6001600160801b038181168382160190808211156137655761376561367a565b5092915050565b60008261378957634e487b7160e01b600052601260045260246000fd5b500490565b808202811582820484141761234a5761234a61367a565b6000602082840312156137b757600080fd5b8151801515811461343357600080fd5b6001600160801b038281168282160390808211156137655761376561367a565b60005b838110156138025781810151838201526020016137ea565b50506000910152565b6000825161381d8184602087016137e7565b9190910192915050565b60208152600082518060208401526138468160408501602087016137e7565b601f01601f1916919091016040019291505056fea2646970667358221220e94292f1246a0a66f023ace5e0c887504535a4033df0240cad8dcc8c13a1f2e864736f6c63430008130033",
  "devdoc": {
    "kind": "dev",
    "methods": {
      "startCollateralSunset(address)": {
        "details": "IMPORTANT: When sunsetting a collateral, `TroveManager.startSunset` should be called on all TM linked to that collateral",
        "params": {
          "collateral": "Collateral to sunset"
        }
      }
    },
    "title": "Propel Stability Pool",
    "version": 1
  },
  "userdoc": {
    "kind": "user",
    "methods": {
      "startCollateralSunset(address)": {
        "notice": "Starts sunsetting a collateral         During sunsetting liquidated collateral handoff to the SP will revert"
      }
    },
    "notice": "Based on Liquity's `StabilityPool` https://github.com/liquity/dev/blob/main/packages/contracts/contracts/StabilityPool.sol Propel's implementation is modified to support multiple collaterals. Deposits into the stability pool may be used to liquidate any supported collateral type.",
    "version": 1
  },
  "storageLayout": {
    "storage": [
      {
        "astId": 13119,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "indexByCollateral",
        "offset": 0,
        "slot": "0",
        "type": "t_mapping(t_contract(IERC20)1439,t_uint256)"
      },
      {
        "astId": 13123,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "collateralTokens",
        "offset": 0,
        "slot": "1",
        "type": "t_array(t_contract(IERC20)1439)dyn_storage"
      },
      {
        "astId": 13125,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "totalPropelUSDDeposits",
        "offset": 0,
        "slot": "2",
        "type": "t_uint256"
      },
      {
        "astId": 13129,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "lockTime",
        "offset": 0,
        "slot": "3",
        "type": "t_mapping(t_address,t_uint256)"
      },
      {
        "astId": 13133,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "accountDeposits",
        "offset": 0,
        "slot": "4",
        "type": "t_mapping(t_address,t_uint256)"
      },
      {
        "astId": 13138,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "depositSnapshots",
        "offset": 0,
        "slot": "5",
        "type": "t_mapping(t_address,t_struct(Snapshots)13203_storage)"
      },
      {
        "astId": 13144,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "depositSums",
        "offset": 0,
        "slot": "6",
        "type": "t_mapping(t_address,t_array(t_uint256)256_storage)"
      },
      {
        "astId": 13150,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "collateralGainsByDepositor",
        "offset": 0,
        "slot": "7",
        "type": "t_mapping(t_address,t_array(t_uint256)256_storage)"
      },
      {
        "astId": 13154,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "storedPendingReward",
        "offset": 0,
        "slot": "8",
        "type": "t_mapping(t_address,t_uint256)"
      },
      {
        "astId": 13157,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "P",
        "offset": 0,
        "slot": "9",
        "type": "t_uint256"
      },
      {
        "astId": 13162,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "currentScale",
        "offset": 0,
        "slot": "10",
        "type": "t_uint128"
      },
      {
        "astId": 13164,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "currentEpoch",
        "offset": 16,
        "slot": "10",
        "type": "t_uint128"
      },
      {
        "astId": 13172,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "epochToScaleToSums",
        "offset": 0,
        "slot": "11",
        "type": "t_mapping(t_uint128,t_mapping(t_uint128,t_array(t_uint256)256_storage))"
      },
      {
        "astId": 13178,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "epochToScaleToG",
        "offset": 0,
        "slot": "12",
        "type": "t_mapping(t_uint128,t_mapping(t_uint128,t_uint256))"
      },
      {
        "astId": 13180,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "lastEsPropelError",
        "offset": 0,
        "slot": "13",
        "type": "t_uint256"
      },
      {
        "astId": 13184,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "lastCollateralError_Offset",
        "offset": 0,
        "slot": "14",
        "type": "t_array(t_uint256)256_storage"
      },
      {
        "astId": 13186,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "lastDebtLossError_Offset",
        "offset": 0,
        "slot": "270",
        "type": "t_uint256"
      },
      {
        "astId": 13191,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "_sunsetIndexes",
        "offset": 0,
        "slot": "271",
        "type": "t_mapping(t_uint16,t_struct(SunsetIndex)13208_storage)"
      },
      {
        "astId": 13194,
        "contract": "contracts/core/StabilityPool.sol:StabilityPool",
        "label": "queue",
        "offset": 0,
        "slot": "272",
        "type": "t_struct(Queue)13213_storage"
      }
    ],
    "types": {
      "t_address": {
        "encoding": "inplace",
        "label": "address",
        "numberOfBytes": "20"
      },
      "t_array(t_contract(IERC20)1439)dyn_storage": {
        "base": "t_contract(IERC20)1439",
        "encoding": "dynamic_array",
        "label": "contract IERC20[]",
        "numberOfBytes": "32"
      },
      "t_array(t_uint256)256_storage": {
        "base": "t_uint256",
        "encoding": "inplace",
        "label": "uint256[256]",
        "numberOfBytes": "8192"
      },
      "t_contract(IERC20)1439": {
        "encoding": "inplace",
        "label": "contract IERC20",
        "numberOfBytes": "20"
      },
      "t_mapping(t_address,t_array(t_uint256)256_storage)": {
        "encoding": "mapping",
        "key": "t_address",
        "label": "mapping(address => uint256[256])",
        "numberOfBytes": "32",
        "value": "t_array(t_uint256)256_storage"
      },
      "t_mapping(t_address,t_struct(Snapshots)13203_storage)": {
        "encoding": "mapping",
        "key": "t_address",
        "label": "mapping(address => struct StabilityPool.Snapshots)",
        "numberOfBytes": "32",
        "value": "t_struct(Snapshots)13203_storage"
      },
      "t_mapping(t_address,t_uint256)": {
        "encoding": "mapping",
        "key": "t_address",
        "label": "mapping(address => uint256)",
        "numberOfBytes": "32",
        "value": "t_uint256"
      },
      "t_mapping(t_contract(IERC20)1439,t_uint256)": {
        "encoding": "mapping",
        "key": "t_contract(IERC20)1439",
        "label": "mapping(contract IERC20 => uint256)",
        "numberOfBytes": "32",
        "value": "t_uint256"
      },
      "t_mapping(t_uint128,t_array(t_uint256)256_storage)": {
        "encoding": "mapping",
        "key": "t_uint128",
        "label": "mapping(uint128 => uint256[256])",
        "numberOfBytes": "32",
        "value": "t_array(t_uint256)256_storage"
      },
      "t_mapping(t_uint128,t_mapping(t_uint128,t_array(t_uint256)256_storage))": {
        "encoding": "mapping",
        "key": "t_uint128",
        "label": "mapping(uint128 => mapping(uint128 => uint256[256]))",
        "numberOfBytes": "32",
        "value": "t_mapping(t_uint128,t_array(t_uint256)256_storage)"
      },
      "t_mapping(t_uint128,t_mapping(t_uint128,t_uint256))": {
        "encoding": "mapping",
        "key": "t_uint128",
        "label": "mapping(uint128 => mapping(uint128 => uint256))",
        "numberOfBytes": "32",
        "value": "t_mapping(t_uint128,t_uint256)"
      },
      "t_mapping(t_uint128,t_uint256)": {
        "encoding": "mapping",
        "key": "t_uint128",
        "label": "mapping(uint128 => uint256)",
        "numberOfBytes": "32",
        "value": "t_uint256"
      },
      "t_mapping(t_uint16,t_struct(SunsetIndex)13208_storage)": {
        "encoding": "mapping",
        "key": "t_uint16",
        "label": "mapping(uint16 => struct StabilityPool.SunsetIndex)",
        "numberOfBytes": "32",
        "value": "t_struct(SunsetIndex)13208_storage"
      },
      "t_struct(Queue)13213_storage": {
        "encoding": "inplace",
        "label": "struct StabilityPool.Queue",
        "members": [
          {
            "astId": 13210,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "firstSunsetIndexKey",
            "offset": 0,
            "slot": "0",
            "type": "t_uint16"
          },
          {
            "astId": 13212,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "nextSunsetIndexKey",
            "offset": 2,
            "slot": "0",
            "type": "t_uint16"
          }
        ],
        "numberOfBytes": "32"
      },
      "t_struct(Snapshots)13203_storage": {
        "encoding": "inplace",
        "label": "struct StabilityPool.Snapshots",
        "members": [
          {
            "astId": 13196,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "P",
            "offset": 0,
            "slot": "0",
            "type": "t_uint256"
          },
          {
            "astId": 13198,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "G",
            "offset": 0,
            "slot": "1",
            "type": "t_uint256"
          },
          {
            "astId": 13200,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "scale",
            "offset": 0,
            "slot": "2",
            "type": "t_uint128"
          },
          {
            "astId": 13202,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "epoch",
            "offset": 16,
            "slot": "2",
            "type": "t_uint128"
          }
        ],
        "numberOfBytes": "96"
      },
      "t_struct(SunsetIndex)13208_storage": {
        "encoding": "inplace",
        "label": "struct StabilityPool.SunsetIndex",
        "members": [
          {
            "astId": 13205,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "idx",
            "offset": 0,
            "slot": "0",
            "type": "t_uint128"
          },
          {
            "astId": 13207,
            "contract": "contracts/core/StabilityPool.sol:StabilityPool",
            "label": "expiry",
            "offset": 16,
            "slot": "0",
            "type": "t_uint128"
          }
        ],
        "numberOfBytes": "32"
      },
      "t_uint128": {
        "encoding": "inplace",
        "label": "uint128",
        "numberOfBytes": "16"
      },
      "t_uint16": {
        "encoding": "inplace",
        "label": "uint16",
        "numberOfBytes": "2"
      },
      "t_uint256": {
        "encoding": "inplace",
        "label": "uint256",
        "numberOfBytes": "32"
      }
    }
  }
}