Vulnerability: If Base._updateInterest fails, the entire system will halt
Severity: medium

Description:
Before executing most methods, the `iETH` and `iToken` contracts update interest accumulated on borrows via the method `Base._updateInterest`. This method uses the contract's interest rate model to calculate the borrow interest rate. If the calculated value is above `maxBorrowRate` (0.001e18), the method will revert:\\n```\\nfunction \\_updateInterest() internal virtual override {\\n    InterestLocalVars memory \\_vars;\\n    \\_vars.currentCash = \\_getCurrentCash();\\n    \\_vars.totalBorrows = totalBorrows;\\n    \\_vars.totalReserves = totalReserves;\\n\\n    // Gets the current borrow interest rate.\\n    \\_vars.borrowRate = interestRateModel.getBorrowRate(\\n        \\_vars.currentCash,\\n        \\_vars.totalBorrows,\\n        \\_vars.totalReserves\\n    );\\n    require(\\n        \\_vars.borrowRate <= maxBorrowRate,\\n        "\\_updateInterest: Borrow rate is too high!"\\n    );\\n```\\n\\nIf this method reverts, the entire contract may halt and be unrecoverable. The only ways to change the values used to calculate this interest rate lie in methods that must first call `Base._updateInterest`. In this case, those methods would fail.\\nOne other potential avenue for recovery exists: the Owner role may update the interest rate calculation contract via TokenAdmin._setInterestRateModel:\\n```\\n/\\*\\*\\n \\* @dev Sets a new interest rate model.\\n \\* @param \\_newInterestRateModel The new interest rate model.\\n \\*/\\nfunction \\_setInterestRateModel(\\n    IInterestRateModelInterface \\_newInterestRateModel\\n) external virtual onlyOwner settleInterest {\\n    // Gets current interest rate model.\\n    IInterestRateModelInterface \\_oldInterestRateModel = interestRateModel;\\n\\n    // Ensures the input address is the interest model contract.\\n    require(\\n        \\_newInterestRateModel.isInterestRateModel(),\\n        "\\_setInterestRateModel: This is not the rate model contract!"\\n    );\\n\\n    // Set to the new interest rate model.\\n    interestRateModel = \\_newInterestRateModel;\\n```\\n\\nHowever, this method also calls `Base._updateInterest` before completing the upgrade, so it would fail as well.\\nWe used interest rate parameters taken from dForce's unit tests to determine whether any of the interest rate models could return a borrow rate that would cause this failure. The default `InterestRateModel` is deployed using these values:\\n```\\nbaseInterestPerBlock: 0\\ninterestPerBlock: 5.074e10\\nhighInterestPerBlock: 4.756e11\\nhigh: 0.75e18\\n```\\n\\nPlugging these values in to their borrow rate calculations, we determined that the utilization rate of the contract would need to be `2103e18` in order to reach the max borrow rate and trigger a failure. Plugging this in to the formula for utilization rate, we derived the following ratio:\\n`reserves >= (2102/2103)*borrows + cash`\\nWith the given interest rate parameters, if token reserves, total borrows, and underlying cash meet the above ratio, the interest rate model would return a borrow rate above the maximum, leading to the failure conditions described above.

Impact:

Recommended mitigation:
Note that the examples above depend on the specific interest rate parameters configured by dForce. In general, with reasonable interest rate parameters and a reasonable reserve ratio, it seems unlikely that the maximum borrow rate will be reached. Consider implementing the following changes as a precaution:\\nAs utilization rate should be between `0` and `1` (scaled by 1e18), prevent utilization rate calculations from returning anything above `1e18`. See issue 4.3 for a more thorough discussion of this topic.\\nRemove the `settleInterest` modifier from TokenAdmin._setInterestRateModel: In a worst case scenario, this will allow the Owner role to update the interest rate model without triggering the failure in `Base._updateInterest`.