The contract goes back to being in a Delinquent state 1 seconds after repaying all DelinquentDebt because of a wrong repayment flow #59
Labels
bug
Something isn't working
downgraded by judge
Judge downgraded the risk level of this issue
edited-by-warden
grade-b
primary issue
Highest quality submission among a set of duplicates
QA (Quality Assurance)
Assets are not at risk. State handling, function incorrect as to spec, issues with clarity, syntax
🤖_68_group
AI based duplicate group recommendation
sponsor disputed
Sponsor cannot duplicate the issue, or otherwise disagrees this is an issue
sufficient quality report
This report is of sufficient quality
Lines of code
https://github.com/code-423n4/2024-08-wildcat/blob/fe746cc0fbedc4447a981a50e6ba4c95f98b9fe1/src/market/WildcatMarket.sol#L186-L191
https://github.com/code-423n4/2024-08-wildcat/blob/fe746cc0fbedc4447a981a50e6ba4c95f98b9fe1/src/market/WildcatMarket.sol#L202-L214
https://github.com/code-423n4/2024-08-wildcat/blob/fe746cc0fbedc4447a981a50e6ba4c95f98b9fe1/src/market/WildcatMarket.sol#L226-L287
Vulnerability details
Impact
In the current implementation of the contract's
repayOutstandingDebt()
function, when a borrower repays their delinquent debt, the contract enters a delinquent state again just seconds after repayment due to improper handling of batched withdrawals. The repayment logic does not process pending withdrawals, resulting in the borrower incurring more debt despite having repaid their outstanding balance. This is due to batched and expired withdrawals not being accounted for during repayment, leading to the accumulation of additional debt.The
closeMarket()
function, on the other hand, correctly handles pending withdrawals by updating the market state and processing withdrawals before marking the market as closed. This behavior should be replicated in the debt repayment function.Proof of Concept
The contract does not account for batched withdrawals during debt repayment, as seen in this test:
The issue arises because pending withdrawals and fees are pay immediately the borrower repaid. After calling
_repay()
, the system continues to accumulate debt from these unprocessed batches. This is handled correctly in thecloseMarket()
function, where the contract processes all pending and expired withdrawals before finalizing the market closure.Tool Used
Manual Code analysis
Mitigation Steps
Suggested Fix
The repayment function should follow the same flow as the
closeMarket()
function to ensure that all batched withdrawals are processed before marking the debt as cleared. This prevents the borrower from incurring more debt after repayment.Fix: Refactor
repayOutstandingDebt()
to process pending withdrawalsKey Changes:
By processing pending withdrawals in the
repayOutstandingDebt()
function, the contract ensures that the borrower does not incur additional debt after repayment. This follows the correct logic already present in thecloseMarket()
function, thereby aligning the two processes and preventing any inconsistency in the debt repayment flow.Assessed type
Error
The text was updated successfully, but these errors were encountered: