@rev-net/core-v6 0.0.18 → 0.0.19
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/ADMINISTRATION.md +14 -4
- package/ARCHITECTURE.md +13 -10
- package/AUDIT_INSTRUCTIONS.md +39 -18
- package/CHANGE_LOG.md +79 -1
- package/README.md +10 -5
- package/RISKS.md +12 -11
- package/SKILLS.md +27 -12
- package/USER_JOURNEYS.md +15 -14
- package/foundry.toml +1 -1
- package/package.json +1 -1
- package/script/Deploy.s.sol +42 -4
- package/src/REVDeployer.sol +20 -305
- package/src/REVLoans.sol +24 -29
- package/src/REVOwner.sol +430 -0
- package/src/interfaces/IREVDeployer.sol +4 -10
- package/src/interfaces/IREVOwner.sol +10 -0
- package/test/REV.integrations.t.sol +14 -1
- package/test/REVAutoIssuanceFuzz.t.sol +14 -1
- package/test/REVDeployerRegressions.t.sol +17 -2
- package/test/REVInvincibility.t.sol +31 -3
- package/test/REVLifecycle.t.sol +16 -1
- package/test/REVLoans.invariants.t.sol +16 -1
- package/test/REVLoansAttacks.t.sol +16 -1
- package/test/REVLoansFeeRecovery.t.sol +16 -1
- package/test/REVLoansFindings.t.sol +16 -1
- package/test/REVLoansRegressions.t.sol +16 -1
- package/test/REVLoansSourceFeeRecovery.t.sol +16 -1
- package/test/REVLoansSourced.t.sol +16 -1
- package/test/REVLoansUnSourced.t.sol +16 -1
- package/test/TestBurnHeldTokens.t.sol +16 -1
- package/test/TestCEIPattern.t.sol +16 -1
- package/test/TestCashOutCallerValidation.t.sol +19 -4
- package/test/TestConversionDocumentation.t.sol +16 -1
- package/test/TestCrossCurrencyReclaim.t.sol +16 -1
- package/test/TestCrossSourceReallocation.t.sol +16 -1
- package/test/TestERC2771MetaTx.t.sol +16 -1
- package/test/TestEmptyBuybackSpecs.t.sol +18 -3
- package/test/TestFlashLoanSurplus.t.sol +16 -1
- package/test/TestHookArrayOOB.t.sol +17 -2
- package/test/TestLiquidationBehavior.t.sol +16 -1
- package/test/TestLoanSourceRotation.t.sol +16 -1
- package/test/TestLoansCashOutDelay.t.sol +21 -6
- package/test/TestLongTailEconomics.t.sol +16 -1
- package/test/TestLowFindings.t.sol +16 -1
- package/test/TestMixedFixes.t.sol +16 -1
- package/test/TestPermit2Signatures.t.sol +16 -1
- package/test/TestReallocationSandwich.t.sol +16 -1
- package/test/TestRevnetRegressions.t.sol +16 -1
- package/test/TestSplitWeightAdjustment.t.sol +43 -19
- package/test/TestSplitWeightE2E.t.sol +26 -2
- package/test/TestSplitWeightFork.t.sol +16 -1
- package/test/TestStageTransitionBorrowable.t.sol +16 -1
- package/test/TestSwapTerminalPermission.t.sol +16 -1
- package/test/TestUint112Overflow.t.sol +16 -1
- package/test/TestZeroRepayment.t.sol +16 -1
- package/test/audit/LoanIdOverflowGuard.t.sol +16 -1
- package/test/fork/ForkTestBase.sol +16 -1
- package/test/fork/TestPermit2PaymentFork.t.sol +4 -3
- package/test/regression/TestBurnPermissionRequired.t.sol +16 -1
- package/test/regression/TestCashOutBuybackFeeLeak.t.sol +15 -1
- package/test/regression/TestCrossRevnetLiquidation.t.sol +16 -1
- package/test/regression/TestCumulativeLoanCounter.t.sol +16 -1
- package/test/regression/TestLiquidateGapHandling.t.sol +16 -1
- package/test/regression/TestZeroPriceFeed.t.sol +16 -1
|
@@ -40,6 +40,8 @@ import {JB721TiersHook} from "@bananapus/721-hook-v6/src/JB721TiersHook.sol";
|
|
|
40
40
|
import {JB721TiersHookStore} from "@bananapus/721-hook-v6/src/JB721TiersHookStore.sol";
|
|
41
41
|
import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressRegistry.sol";
|
|
42
42
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
43
|
+
import {REVOwner} from "../src/REVOwner.sol";
|
|
44
|
+
import {IREVDeployer} from "../src/interfaces/IREVDeployer.sol";
|
|
43
45
|
|
|
44
46
|
/// @notice Tests for PR #16: zero repayment prevention.
|
|
45
47
|
contract TestZeroRepayment is TestBaseWorkflow {
|
|
@@ -49,6 +51,8 @@ contract TestZeroRepayment is TestBaseWorkflow {
|
|
|
49
51
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
50
52
|
REVDeployer REV_DEPLOYER;
|
|
51
53
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
|
+
REVOwner REV_OWNER;
|
|
55
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
52
56
|
JB721TiersHook EXAMPLE_HOOK;
|
|
53
57
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
58
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -102,6 +106,14 @@ contract TestZeroRepayment is TestBaseWorkflow {
|
|
|
102
106
|
permit2: permit2(),
|
|
103
107
|
trustedForwarder: TRUSTED_FORWARDER
|
|
104
108
|
});
|
|
109
|
+
REV_OWNER = new REVOwner(
|
|
110
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
111
|
+
jbDirectory(),
|
|
112
|
+
FEE_PROJECT_ID,
|
|
113
|
+
SUCKER_REGISTRY,
|
|
114
|
+
address(LOANS_CONTRACT)
|
|
115
|
+
);
|
|
116
|
+
|
|
105
117
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
106
118
|
jbController(),
|
|
107
119
|
SUCKER_REGISTRY,
|
|
@@ -110,8 +122,11 @@ contract TestZeroRepayment is TestBaseWorkflow {
|
|
|
110
122
|
PUBLISHER,
|
|
111
123
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
112
124
|
address(LOANS_CONTRACT),
|
|
113
|
-
TRUSTED_FORWARDER
|
|
125
|
+
TRUSTED_FORWARDER,
|
|
126
|
+
address(REV_OWNER)
|
|
114
127
|
);
|
|
128
|
+
|
|
129
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
115
130
|
vm.prank(multisig());
|
|
116
131
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
117
132
|
_deployFeeProject();
|
|
@@ -42,6 +42,8 @@ import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressReg
|
|
|
42
42
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
43
43
|
// Helper that provides empty 721 tier configs for revnet deployment.
|
|
44
44
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
45
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
46
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
45
47
|
|
|
46
48
|
/// @notice Regression tests for the loan ID overflow guard in REVLoans.
|
|
47
49
|
/// @dev The totalLoansBorrowedFor counter must never exceed _ONE_TRILLION (1e12).
|
|
@@ -74,6 +76,8 @@ contract LoanIdOverflowGuard is TestBaseWorkflow {
|
|
|
74
76
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
75
77
|
REVDeployer REV_DEPLOYER;
|
|
76
78
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
79
|
+
REVOwner REV_OWNER;
|
|
80
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
77
81
|
JB721TiersHook EXAMPLE_HOOK;
|
|
78
82
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
79
83
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -159,6 +163,14 @@ contract LoanIdOverflowGuard is TestBaseWorkflow {
|
|
|
159
163
|
});
|
|
160
164
|
|
|
161
165
|
// Deploy the REVDeployer with a deterministic salt.
|
|
166
|
+
REV_OWNER = new REVOwner(
|
|
167
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
168
|
+
jbDirectory(),
|
|
169
|
+
FEE_PROJECT_ID,
|
|
170
|
+
SUCKER_REGISTRY,
|
|
171
|
+
address(LOANS_CONTRACT)
|
|
172
|
+
);
|
|
173
|
+
|
|
162
174
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
163
175
|
jbController(),
|
|
164
176
|
SUCKER_REGISTRY,
|
|
@@ -167,9 +179,12 @@ contract LoanIdOverflowGuard is TestBaseWorkflow {
|
|
|
167
179
|
PUBLISHER,
|
|
168
180
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
169
181
|
address(LOANS_CONTRACT),
|
|
170
|
-
TRUSTED_FORWARDER
|
|
182
|
+
TRUSTED_FORWARDER,
|
|
183
|
+
address(REV_OWNER)
|
|
171
184
|
);
|
|
172
185
|
|
|
186
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
187
|
+
|
|
173
188
|
// Approve the deployer to configure the fee project.
|
|
174
189
|
vm.prank(multisig());
|
|
175
190
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
@@ -71,6 +71,8 @@ import {TickMath} from "@uniswap/v4-core/src/libraries/TickMath.sol";
|
|
|
71
71
|
import {StateLibrary} from "@uniswap/v4-core/src/libraries/StateLibrary.sol";
|
|
72
72
|
|
|
73
73
|
import {IERC20} from "@openzeppelin/contracts/interfaces/IERC20.sol";
|
|
74
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
75
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
74
76
|
|
|
75
77
|
/// @notice Helper that adds liquidity to a V4 pool via the unlock/callback pattern.
|
|
76
78
|
contract LiquidityHelper is IUnlockCallback {
|
|
@@ -237,6 +239,8 @@ abstract contract ForkTestBase is TestBaseWorkflow {
|
|
|
237
239
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
238
240
|
REVDeployer REV_DEPLOYER;
|
|
239
241
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
242
|
+
REVOwner REV_OWNER;
|
|
243
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
240
244
|
JBBuybackHook BUYBACK_HOOK;
|
|
241
245
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
242
246
|
JBBuybackHookRegistry BUYBACK_REGISTRY;
|
|
@@ -330,6 +334,14 @@ abstract contract ForkTestBase is TestBaseWorkflow {
|
|
|
330
334
|
trustedForwarder: TRUSTED_FORWARDER
|
|
331
335
|
});
|
|
332
336
|
|
|
337
|
+
REV_OWNER = new REVOwner(
|
|
338
|
+
IJBBuybackHookRegistry(address(BUYBACK_REGISTRY)),
|
|
339
|
+
jbDirectory(),
|
|
340
|
+
FEE_PROJECT_ID,
|
|
341
|
+
SUCKER_REGISTRY,
|
|
342
|
+
address(LOANS_CONTRACT)
|
|
343
|
+
);
|
|
344
|
+
|
|
333
345
|
REV_DEPLOYER = new REVDeployer{salt: "REVDeployer_Fork"}(
|
|
334
346
|
jbController(),
|
|
335
347
|
SUCKER_REGISTRY,
|
|
@@ -338,9 +350,12 @@ abstract contract ForkTestBase is TestBaseWorkflow {
|
|
|
338
350
|
PUBLISHER,
|
|
339
351
|
IJBBuybackHookRegistry(address(BUYBACK_REGISTRY)),
|
|
340
352
|
address(LOANS_CONTRACT),
|
|
341
|
-
TRUSTED_FORWARDER
|
|
353
|
+
TRUSTED_FORWARDER,
|
|
354
|
+
address(REV_OWNER)
|
|
342
355
|
);
|
|
343
356
|
|
|
357
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
358
|
+
|
|
344
359
|
vm.prank(multisig());
|
|
345
360
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
346
361
|
|
|
@@ -149,14 +149,15 @@ contract TestPermit2PaymentFork is ForkTestBase {
|
|
|
149
149
|
sigDeadline: sigDeadline, amount: amount, expiration: expiration, nonce: nonce, signature: sig
|
|
150
150
|
});
|
|
151
151
|
|
|
152
|
-
// Encode as metadata with the "permit2" key targeting the terminal, plus a
|
|
153
|
-
//
|
|
152
|
+
// Encode as metadata with the "permit2" key targeting the terminal, plus a "quote" entry
|
|
153
|
+
// targeting the buyback hook with minimumSwapAmountOut=1 so the buyback hook skips the
|
|
154
|
+
// TWAP oracle and falls through to normal minting (no V4 pool has liquidity for testToken).
|
|
154
155
|
bytes4[] memory ids = new bytes4[](2);
|
|
155
156
|
bytes[] memory datas = new bytes[](2);
|
|
156
157
|
ids[0] = JBMetadataResolver.getId("permit2", address(jbMultiTerminal()));
|
|
157
158
|
datas[0] = abi.encode(allowance);
|
|
158
159
|
ids[1] = JBMetadataResolver.getId("quote", address(BUYBACK_HOOK));
|
|
159
|
-
datas[1] = abi.encode(uint256(0), uint256(
|
|
160
|
+
datas[1] = abi.encode(uint256(0), uint256(1));
|
|
160
161
|
metadata = JBMetadataResolver.createMetadata(ids, datas);
|
|
161
162
|
}
|
|
162
163
|
|
|
@@ -40,6 +40,8 @@ import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/
|
|
|
40
40
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
41
41
|
import {JBPermissionIds} from "@bananapus/permission-ids-v6/src/JBPermissionIds.sol";
|
|
42
42
|
import {JBPermissioned} from "@bananapus/core-v6/src/abstract/JBPermissioned.sol";
|
|
43
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
44
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
43
45
|
|
|
44
46
|
/// @notice Validates that borrowFrom() reverts with a clear error when the caller hasn't granted BURN_TOKENS
|
|
45
47
|
/// permission to the REVLoans contract.
|
|
@@ -52,6 +54,8 @@ contract TestBurnPermissionRequired is TestBaseWorkflow {
|
|
|
52
54
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
53
55
|
REVDeployer REV_DEPLOYER;
|
|
54
56
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
57
|
+
REVOwner REV_OWNER;
|
|
58
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
55
59
|
JB721TiersHook EXAMPLE_HOOK;
|
|
56
60
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
57
61
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -104,6 +108,14 @@ contract TestBurnPermissionRequired is TestBaseWorkflow {
|
|
|
104
108
|
permit2: permit2(),
|
|
105
109
|
trustedForwarder: TRUSTED_FORWARDER
|
|
106
110
|
});
|
|
111
|
+
REV_OWNER = new REVOwner(
|
|
112
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
113
|
+
jbDirectory(),
|
|
114
|
+
FEE_PROJECT_ID,
|
|
115
|
+
SUCKER_REGISTRY,
|
|
116
|
+
address(LOANS_CONTRACT)
|
|
117
|
+
);
|
|
118
|
+
|
|
107
119
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
108
120
|
jbController(),
|
|
109
121
|
SUCKER_REGISTRY,
|
|
@@ -112,8 +124,11 @@ contract TestBurnPermissionRequired is TestBaseWorkflow {
|
|
|
112
124
|
PUBLISHER,
|
|
113
125
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
114
126
|
address(LOANS_CONTRACT),
|
|
115
|
-
TRUSTED_FORWARDER
|
|
127
|
+
TRUSTED_FORWARDER,
|
|
128
|
+
address(REV_OWNER)
|
|
116
129
|
);
|
|
130
|
+
|
|
131
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
117
132
|
vm.prank(multisig());
|
|
118
133
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
119
134
|
_deployFeeProject();
|
|
@@ -35,6 +35,8 @@ import {REVSuckerDeploymentConfig} from "../../src/structs/REVSuckerDeploymentCo
|
|
|
35
35
|
import {REVLoans} from "../../src/REVLoans.sol";
|
|
36
36
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
37
37
|
import {MockBuybackCashOutRecorder} from "../mock/MockBuybackCashOutRecorder.sol";
|
|
38
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
39
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
38
40
|
|
|
39
41
|
/// @title TestCashOutBuybackFeeLeak
|
|
40
42
|
/// @notice Proves the buyback hook callback receives only the non-fee cashOutCount (not the full count).
|
|
@@ -46,6 +48,7 @@ contract TestCashOutBuybackFeeLeak is TestBaseWorkflow {
|
|
|
46
48
|
address private constant TRUSTED_FORWARDER = 0xB2b5841DBeF766d4b521221732F9B618fCf34A87;
|
|
47
49
|
|
|
48
50
|
REVDeployer internal revDeployer;
|
|
51
|
+
REVOwner internal revOwner;
|
|
49
52
|
MockBuybackCashOutRecorder internal mockBuyback;
|
|
50
53
|
JB721TiersHook internal exampleHook;
|
|
51
54
|
IJB721TiersHookDeployer internal hookDeployer;
|
|
@@ -81,6 +84,14 @@ contract TestCashOutBuybackFeeLeak is TestBaseWorkflow {
|
|
|
81
84
|
trustedForwarder: TRUSTED_FORWARDER
|
|
82
85
|
});
|
|
83
86
|
|
|
87
|
+
revOwner = new REVOwner(
|
|
88
|
+
IJBBuybackHookRegistry(address(mockBuyback)),
|
|
89
|
+
jbDirectory(),
|
|
90
|
+
feeProjectId,
|
|
91
|
+
IJBSuckerRegistry(address(suckerRegistry)),
|
|
92
|
+
address(loans)
|
|
93
|
+
);
|
|
94
|
+
|
|
84
95
|
revDeployer = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
85
96
|
jbController(),
|
|
86
97
|
suckerRegistry,
|
|
@@ -89,9 +100,12 @@ contract TestCashOutBuybackFeeLeak is TestBaseWorkflow {
|
|
|
89
100
|
publisher,
|
|
90
101
|
IJBBuybackHookRegistry(address(mockBuyback)),
|
|
91
102
|
address(loans),
|
|
92
|
-
TRUSTED_FORWARDER
|
|
103
|
+
TRUSTED_FORWARDER,
|
|
104
|
+
address(revOwner)
|
|
93
105
|
);
|
|
94
106
|
|
|
107
|
+
revOwner.initialize(IREVDeployer(address(revDeployer)));
|
|
108
|
+
|
|
95
109
|
vm.prank(multisig());
|
|
96
110
|
jbProjects().approve(address(revDeployer), feeProjectId);
|
|
97
111
|
|
|
@@ -37,6 +37,8 @@ import {JB721TiersHookStore} from "@bananapus/721-hook-v6/src/JB721TiersHookStor
|
|
|
37
37
|
import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressRegistry.sol";
|
|
38
38
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
39
39
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
40
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
41
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
40
42
|
|
|
41
43
|
/// @notice Validates that liquidateExpiredLoansFrom rejects loan number ranges that would overflow into another
|
|
42
44
|
/// revnet's namespace.
|
|
@@ -49,6 +51,8 @@ contract TestCrossRevnetLiquidation is TestBaseWorkflow {
|
|
|
49
51
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
50
52
|
REVDeployer REV_DEPLOYER;
|
|
51
53
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
|
+
REVOwner REV_OWNER;
|
|
55
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
52
56
|
JB721TiersHook EXAMPLE_HOOK;
|
|
53
57
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
58
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -102,6 +106,14 @@ contract TestCrossRevnetLiquidation is TestBaseWorkflow {
|
|
|
102
106
|
permit2: permit2(),
|
|
103
107
|
trustedForwarder: TRUSTED_FORWARDER
|
|
104
108
|
});
|
|
109
|
+
REV_OWNER = new REVOwner(
|
|
110
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
111
|
+
jbDirectory(),
|
|
112
|
+
FEE_PROJECT_ID,
|
|
113
|
+
SUCKER_REGISTRY,
|
|
114
|
+
address(LOANS_CONTRACT)
|
|
115
|
+
);
|
|
116
|
+
|
|
105
117
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
106
118
|
jbController(),
|
|
107
119
|
SUCKER_REGISTRY,
|
|
@@ -110,8 +122,11 @@ contract TestCrossRevnetLiquidation is TestBaseWorkflow {
|
|
|
110
122
|
PUBLISHER,
|
|
111
123
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
112
124
|
address(LOANS_CONTRACT),
|
|
113
|
-
TRUSTED_FORWARDER
|
|
125
|
+
TRUSTED_FORWARDER,
|
|
126
|
+
address(REV_OWNER)
|
|
114
127
|
);
|
|
128
|
+
|
|
129
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
115
130
|
vm.prank(multisig());
|
|
116
131
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
117
132
|
_deployFeeProject();
|
|
@@ -38,6 +38,8 @@ import {JB721TiersHookStore} from "@bananapus/721-hook-v6/src/JB721TiersHookStor
|
|
|
38
38
|
import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressRegistry.sol";
|
|
39
39
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
40
40
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
41
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
42
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
41
43
|
|
|
42
44
|
/// @notice totalLoansBorrowedFor is a cumulative counter, not an active loan count.
|
|
43
45
|
/// @dev The rename from numberOfLoansFor to totalLoansBorrowedFor clarifies that the counter only increments
|
|
@@ -50,6 +52,8 @@ contract TestCumulativeLoanCounter is TestBaseWorkflow {
|
|
|
50
52
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
51
53
|
REVDeployer REV_DEPLOYER;
|
|
52
54
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
55
|
+
REVOwner REV_OWNER;
|
|
56
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
53
57
|
JB721TiersHook EXAMPLE_HOOK;
|
|
54
58
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
55
59
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -106,6 +110,14 @@ contract TestCumulativeLoanCounter is TestBaseWorkflow {
|
|
|
106
110
|
permit2: permit2(),
|
|
107
111
|
trustedForwarder: TRUSTED_FORWARDER
|
|
108
112
|
});
|
|
113
|
+
REV_OWNER = new REVOwner(
|
|
114
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
115
|
+
jbDirectory(),
|
|
116
|
+
FEE_PROJECT_ID,
|
|
117
|
+
SUCKER_REGISTRY,
|
|
118
|
+
address(LOANS_CONTRACT)
|
|
119
|
+
);
|
|
120
|
+
|
|
109
121
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
110
122
|
jbController(),
|
|
111
123
|
SUCKER_REGISTRY,
|
|
@@ -114,8 +126,11 @@ contract TestCumulativeLoanCounter is TestBaseWorkflow {
|
|
|
114
126
|
PUBLISHER,
|
|
115
127
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
116
128
|
address(LOANS_CONTRACT),
|
|
117
|
-
TRUSTED_FORWARDER
|
|
129
|
+
TRUSTED_FORWARDER,
|
|
130
|
+
address(REV_OWNER)
|
|
118
131
|
);
|
|
132
|
+
|
|
133
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
119
134
|
vm.prank(multisig());
|
|
120
135
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
121
136
|
_deployFeeProject();
|
|
@@ -39,6 +39,8 @@ import {JB721TiersHookStore} from "@bananapus/721-hook-v6/src/JB721TiersHookStor
|
|
|
39
39
|
import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressRegistry.sol";
|
|
40
40
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
41
41
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
42
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
43
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
42
44
|
|
|
43
45
|
/// @notice liquidateExpiredLoansFrom halts on deleted loan gaps.
|
|
44
46
|
/// @dev Before the fix, the function used `break` when encountering a deleted loan (createdAt == 0),
|
|
@@ -51,6 +53,8 @@ contract TestLiquidateGapHandling is TestBaseWorkflow {
|
|
|
51
53
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
52
54
|
REVDeployer REV_DEPLOYER;
|
|
53
55
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
56
|
+
REVOwner REV_OWNER;
|
|
57
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
58
|
JB721TiersHook EXAMPLE_HOOK;
|
|
55
59
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
56
60
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -108,6 +112,14 @@ contract TestLiquidateGapHandling is TestBaseWorkflow {
|
|
|
108
112
|
permit2: permit2(),
|
|
109
113
|
trustedForwarder: TRUSTED_FORWARDER
|
|
110
114
|
});
|
|
115
|
+
REV_OWNER = new REVOwner(
|
|
116
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
117
|
+
jbDirectory(),
|
|
118
|
+
FEE_PROJECT_ID,
|
|
119
|
+
SUCKER_REGISTRY,
|
|
120
|
+
address(LOANS_CONTRACT)
|
|
121
|
+
);
|
|
122
|
+
|
|
111
123
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
112
124
|
jbController(),
|
|
113
125
|
SUCKER_REGISTRY,
|
|
@@ -116,8 +128,11 @@ contract TestLiquidateGapHandling is TestBaseWorkflow {
|
|
|
116
128
|
PUBLISHER,
|
|
117
129
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
118
130
|
address(LOANS_CONTRACT),
|
|
119
|
-
TRUSTED_FORWARDER
|
|
131
|
+
TRUSTED_FORWARDER,
|
|
132
|
+
address(REV_OWNER)
|
|
120
133
|
);
|
|
134
|
+
|
|
135
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
121
136
|
vm.prank(multisig());
|
|
122
137
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
123
138
|
_deployFeeProject();
|
|
@@ -40,6 +40,8 @@ import {JBAddressRegistry} from "@bananapus/address-registry-v6/src/JBAddressReg
|
|
|
40
40
|
import {IJBAddressRegistry} from "@bananapus/address-registry-v6/src/interfaces/IJBAddressRegistry.sol";
|
|
41
41
|
import {REVEmpty721Config} from "../helpers/REVEmpty721Config.sol";
|
|
42
42
|
import {IJBPrices} from "@bananapus/core-v6/src/interfaces/IJBPrices.sol";
|
|
43
|
+
import {REVOwner} from "../../src/REVOwner.sol";
|
|
44
|
+
import {IREVDeployer} from "../../src/interfaces/IREVDeployer.sol";
|
|
43
45
|
|
|
44
46
|
/// @notice Verifies that `_totalBorrowedFrom` gracefully handles zero-price feeds.
|
|
45
47
|
/// @dev When a cross-currency price feed returns 0 (e.g., inverse truncation at low decimals), the affected source
|
|
@@ -53,6 +55,8 @@ contract TestZeroPriceFeed is TestBaseWorkflow {
|
|
|
53
55
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
54
56
|
REVDeployer REV_DEPLOYER;
|
|
55
57
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
58
|
+
REVOwner REV_OWNER;
|
|
59
|
+
// forge-lint: disable-next-line(mixed-case-variable)
|
|
56
60
|
JB721TiersHook EXAMPLE_HOOK;
|
|
57
61
|
// forge-lint: disable-next-line(mixed-case-variable)
|
|
58
62
|
IJB721TiersHookDeployer HOOK_DEPLOYER;
|
|
@@ -117,6 +121,14 @@ contract TestZeroPriceFeed is TestBaseWorkflow {
|
|
|
117
121
|
trustedForwarder: TRUSTED_FORWARDER
|
|
118
122
|
});
|
|
119
123
|
|
|
124
|
+
REV_OWNER = new REVOwner(
|
|
125
|
+
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
126
|
+
jbDirectory(),
|
|
127
|
+
FEE_PROJECT_ID,
|
|
128
|
+
SUCKER_REGISTRY,
|
|
129
|
+
address(LOANS_CONTRACT)
|
|
130
|
+
);
|
|
131
|
+
|
|
120
132
|
REV_DEPLOYER = new REVDeployer{salt: REV_DEPLOYER_SALT}(
|
|
121
133
|
jbController(),
|
|
122
134
|
SUCKER_REGISTRY,
|
|
@@ -125,9 +137,12 @@ contract TestZeroPriceFeed is TestBaseWorkflow {
|
|
|
125
137
|
PUBLISHER,
|
|
126
138
|
IJBBuybackHookRegistry(address(MOCK_BUYBACK)),
|
|
127
139
|
address(LOANS_CONTRACT),
|
|
128
|
-
TRUSTED_FORWARDER
|
|
140
|
+
TRUSTED_FORWARDER,
|
|
141
|
+
address(REV_OWNER)
|
|
129
142
|
);
|
|
130
143
|
|
|
144
|
+
REV_OWNER.initialize(IREVDeployer(address(REV_DEPLOYER)));
|
|
145
|
+
|
|
131
146
|
vm.prank(multisig());
|
|
132
147
|
jbProjects().approve(address(REV_DEPLOYER), FEE_PROJECT_ID);
|
|
133
148
|
|