AuctionHouse::forgive() helps the protocol in marking the debt as a total loss and maintaining the system updated if the auction is not completed.
File: AuctionHouse.sol
198: /// @notice forgive a loan, by marking the debt as a total loss
199: /// @dev this is meant to be used when an auction concludes without anyone bidding,
200: /// even if 0 CREDIT is asked in return. This situation could arise
201: /// if collateral assets are frozen within the lending term contract.
202: function forgive(bytes32 loanId) external {
203: // this view function will revert if the auction is not started,
204: // or if the auction is already ended.
205: (, uint256 creditAsked) = getBidDetail(loanId);
206: require(creditAsked == 0, "AuctionHouse: ongoing auction");
207:
208: // close the auction in state
209: auctions[loanId].endTime = block.timestamp;
210: nAuctionsInProgress--;
211:
212: // notify LendingTerm of auction result
213: address _lendingTerm = auctions[loanId].lendingTerm;
214: LendingTerm(_lendingTerm).onBid(
215: loanId,
216: msg.sender,
217: 0, // collateralToBorrower
218: 0, // collateralToBidder
219: 0 // creditFromBidder
220: );
221:
222: // emit event
223: emit AuctionEnd(
224: block.timestamp,
225: loanId,
226: LendingTerm(_lendingTerm).collateralToken(),
227: 0, // collateralSold
228: 0 // debtRecovered
229: );
230: }
According to the code comment, collateral can be obtained with zero credits if an auction ends without a bid:
// second phase fully elapsed, anyone can receive the full collateral and give 0 CREDIT
// in practice, somebody should have taken the arb before we reach this condition.
However, acquiring the collateral with zero credits is prevented by the bid function's validation:
and the AuctionHouse::forgive() function offers no incentive for the caller/bidder to call this function since the collateralToBidder is zero on code line 218:
Consequently, there is no incentive for the bidder to expend gas on the transaction, necessitating the protocol to regularly call the AuctionHouse::forgive() function in order to keep the system updated.
Tools used
Manual review
Recommended Mitigation Steps
When an auction ends without any bids, offer an incentive so that the forgive function can be invoked and the system can be updated.
Lines of code
https://github.com/code-423n4/2023-12-ethereumcreditguild/blob/2376d9af792584e3d15ec9c32578daa33bb56b43/src/loan/AuctionHouse.sol#L202
Vulnerability details
Impact
AuctionHouse::forgive() helps the protocol in marking the debt as a total loss and maintaining the system updated if the auction is not completed.
The
AuctionHouse::forgive()
function invokes the LendingTerm::onBid() function to close out the loan, report the loss to the ProfitManager, burn the principal credit and deduct the global variable issuance. The issue arises as there is no incentive for the caller to invoke theAuctionHouse::forgive()
function, necessitating the protocol itself to call this function to maintain system transparency.Proof of Concept
According to the code comment, collateral can be obtained with zero credits if an auction ends without a bid:
However, acquiring the collateral with zero credits is prevented by the bid function's validation:
and the
AuctionHouse::forgive()
function offersno incentive
for thecaller/bidder
to call this function since thecollateralToBidder
is zero on code line 218:Consequently, there is no incentive for the bidder to expend gas on the transaction, necessitating the protocol to regularly call the
AuctionHouse::forgive()
function in order to keep the system updated.Tools used
Manual review
Recommended Mitigation Steps
When an auction ends without any bids, offer an incentive so that the forgive function can be invoked and the system can be updated.
Assessed type
Context