Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Some changes to exec (bit simplication and check vat.Line) #40

Merged
merged 6 commits into from
Apr 25, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
59 changes: 34 additions & 25 deletions src/DssDirectDepositHub.sol
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,10 @@
pragma solidity 0.6.12;

interface VatLike {
function Line() external returns (uint256);
function debt() external view returns (uint256);
function hope(address) external;
function ilks(bytes32) external view returns (uint256, uint256, uint256, uint256, uint256);
function Line() external view returns (uint256);
function urns(bytes32, address) external view returns (uint256, uint256);
function gem(bytes32, address) external view returns (uint256);
function live() external view returns (uint256);
Expand Down Expand Up @@ -135,6 +136,12 @@ contract DssDirectDepositHub {
function _min(uint256 x, uint256 y) internal pure returns (uint256 z) {
z = x <= y ? x : y;
}
function _max(uint256 x, uint256 y) internal pure returns (uint256 z) {
z = x >= y ? x : y;
}
function _divup(uint256 x, uint256 y) internal pure returns (uint256 z) {
z = _add(x, _sub(y, 1)) / y;
}

// --- Administration ---
function file(bytes32 what, address data) external auth {
Expand Down Expand Up @@ -298,39 +305,41 @@ contract DssDirectDepositHub {
);
} else {
// Normal path

// Determine if it needs to unwind due to debt ceilings
(uint256 Art,,, uint256 line,) = vat.ilks(ilk_);
uint256 lineWad = line / RAY; // Round down to always be under the actual limit
uint256 Line = vat.Line();
uint256 debt = vat.debt();
uint256 toUnwind;
if (Art > lineWad) {
toUnwind = Art - lineWad;
}
if (debt > Line) {
toUnwind = _max(toUnwind, _divup(debt - Line, RAY));
}

// Determine if it needs to unwind due plan
uint256 targetAssets = ilks[ilk_].plan.getTargetAssets(currentAssets);
if (targetAssets < currentAssets) {
toUnwind = _max(toUnwind, currentAssets - targetAssets);
}

if (targetAssets > currentAssets) {
// Amount is limited by the debt ceiling
uint256 Line = vat.Line();
(uint256 Art,,, uint256 line,) = vat.ilks(ilk_);
uint256 lineWad = _min(line, Line) / RAY; // Take min of ilk line and global like, the round down to always be under the actual limit

if(Art > lineWad) { // Our debt is greater than our debt ceiling, we need to unwind
_unwind(
ilk_,
pool,
Art - lineWad,
availableAssets,
Mode.NORMAL,
currentAssets
);
} else {
uint256 amount = targetAssets - currentAssets;
if (_add(Art, amount) > lineWad) { // we do not have enough room in the debt ceiling to fully wind
amount = lineWad - Art;
}
_wind(ilk_, pool, amount);
}
} else if (targetAssets < currentAssets) {
if (toUnwind > 0) {
_unwind(
ilk_,
pool,
currentAssets - targetAssets,
toUnwind,
availableAssets,
Mode.NORMAL,
currentAssets
);
} else {
// All the substractions are safe as otherwise toUnwind is > 0
uint256 toWind = targetAssets - currentAssets;
toWind = _min(toWind, lineWad - Art);
toWind = _min(toWind, (Line - debt) / RAY);
_wind(ilk_, pool, toWind);
}
}
}
Expand Down
34 changes: 29 additions & 5 deletions src/DssDirectDepositHub.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -335,6 +335,30 @@ contract DssDirectDepositHubTest is DSTest {
directDepositHub.file(ilk, "pool", address(123));
}

function test_wind_limited_ilk_line() public {
d3mTestPlan.file("bar", 10);
d3mTestPlan.file("targetAssets", 50 * WAD);
vat.file(ilk, "line", 40 * RAD);
directDepositHub.exec(ilk);

(uint256 ink, uint256 art) = vat.urns(ilk, address(d3mTestPool));
assertEq(ink, 40 * WAD);
assertEq(art, 40 * WAD);
assertTrue(d3mTestPool.accrued());
}

function test_wind_limited_Line() public {
d3mTestPlan.file("bar", 10);
d3mTestPlan.file("targetAssets", 50 * WAD);
vat.file("Line", vat.debt() + 40 * RAD);
directDepositHub.exec(ilk);

(uint256 ink, uint256 art) = vat.urns(ilk, address(d3mTestPool));
assertEq(ink, 40 * WAD);
assertEq(art, 40 * WAD);
assertTrue(d3mTestPool.accrued());
}

function test_unwind_bar_zero() public {
_windSystem();

Expand All @@ -354,13 +378,13 @@ contract DssDirectDepositHubTest is DSTest {
_windSystem();

// Set ilk line below current debt
d3mTestPlan.file("targetAssets", 55 * WAD);
d3mTestPlan.file("targetAssets", 55 * WAD); // Increasing target in 5 WAD
vat.file(ilk, "line", 45 * RAD);
directDepositHub.exec(ilk);

// Ensure we unwound our position to debt ceiling
(uint256 ink, uint256 art) = vat.urns(ilk, address(d3mTestPool));
assertEq(ink, 45 * WAD);
assertEq(ink, 45 * WAD); // Instead of 5 WAD more results in 5 WAD less due debt ceiling
assertEq(art, 45 * WAD);
// Make sure unwind calls accrued
assertTrue(d3mTestPool.accrued());
Expand All @@ -370,13 +394,13 @@ contract DssDirectDepositHubTest is DSTest {
_windSystem();

// Set ilk line below current debt
d3mTestPlan.file("targetAssets", 55 * WAD);
vat.file("Line", 45 * RAD);
d3mTestPlan.file("targetAssets", 55 * WAD); // Increasing target in 5 WAD
vat.file("Line", vat.debt() - 5 * RAD);
directDepositHub.exec(ilk);

// Ensure we unwound our position to debt ceiling
(uint256 ink, uint256 art) = vat.urns(ilk, address(d3mTestPool));
assertEq(ink, 45 * WAD);
assertEq(ink, 45 * WAD); // Instead of 5 WAD more results in 5 WAD less due debt ceiling
talbaneth marked this conversation as resolved.
Show resolved Hide resolved
assertEq(art, 45 * WAD);
// Make sure unwind calls accrued
assertTrue(d3mTestPool.accrued());
Expand Down
1 change: 1 addition & 0 deletions src/tests/interfaces/interfaces.sol
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ interface SpotLike {
}

interface VatLike {
function debt() external view returns (uint256);
function rely(address) external;
function hope(address) external;
function urns(bytes32, address) external view returns (uint256, uint256);
Expand Down