Cancelling an auction doesn't repay the entire debt and doesn't unlock collateral
Summary
Cancelling an auction doesn't repay the entire debt and doesn't unlock collateral
Vulnerability Detail
When cancelling an auction, the reservePrice is expected to be paid (AuctionHouse.sol#L220). The price is the sum of outstanding debts of all liens (AuctionHouse.sol#L73-L77, LienToken.sol#L207-L213). However, when the repayment is made, an initiator fee is subtracted from the amount being repaid (AuctionHouse.sol#L265-L276). This reduces the total amount being repaid (AuctionHouse.sol#L276) and leaves at least one lien unrepaid (AuctionHouse.sol#L281-L298) (totalAmount won't be enough to repay all liens). The auction, however, will still be removed (AuctionHouse.sol#L223) and the owner won't be able to release their collateral due to the unrepaid lien.
Impact
After a borrower has cancelled an auction on their collateral and repaid the full amount of the debt, they won't be able to release the collateral since at least one lien won't be repaid. Anyone will be able to start a new auction, and since the total loan will be mostly repaid, the reserve price of the new auction will be low and it'll be cheap to create a bid that's higher than the reserve price, thus disallowing the borrower to cancel the auction (AuctionHouse.sol#L215). The borrower basically loses the amount the paid to cancel the auction.
function cancelAuction(uint256 auctionId, address canceledBy)
external
requiresAuth
{
require(
auctions[auctionId].currentBid < auctions[auctionId].reservePrice,
"cancelAuction: Auction is at or above reserve"
);
_handleIncomingPayment(
auctionId,
auctions[auctionId].reservePrice, // @audit borrower must pay this amount to cancel the auction
canceledBy
);
_cancelAuction(auctionId);
}
modifier releaseCheck(uint256 collateralId) {
require(
// @audit collateral can be released only when all liens were repaid
uint256(0) == LIEN_TOKEN.getLiens(collateralId).length &&
!AUCTION_HOUSE.auctionExists(collateralId),
"must be no liens or auctions to call this"
);
_;
}
function releaseToAddress(uint256 collateralId, address releaseTo)
public
releaseCheck(collateralId)
{
//check liens
require(
msg.sender == ownerOf(collateralId),
"You don't have permission to call this"
);
_releaseToAddress(collateralId, releaseTo);
}
Tool used
Manual Review
Recommendation
Consider including the initiator fee in the amount required to cancel an auction.
Jeiwan
high
Cancelling an auction doesn't repay the entire debt and doesn't unlock collateral
Summary
Cancelling an auction doesn't repay the entire debt and doesn't unlock collateral
Vulnerability Detail
When cancelling an auction, the
reservePrice
is expected to be paid (AuctionHouse.sol#L220). The price is the sum of outstanding debts of all liens (AuctionHouse.sol#L73-L77, LienToken.sol#L207-L213). However, when the repayment is made, an initiator fee is subtracted from the amount being repaid (AuctionHouse.sol#L265-L276). This reduces the total amount being repaid (AuctionHouse.sol#L276) and leaves at least one lien unrepaid (AuctionHouse.sol#L281-L298) (totalAmount
won't be enough to repay all liens). The auction, however, will still be removed (AuctionHouse.sol#L223) and the owner won't be able to release their collateral due to the unrepaid lien.Impact
After a borrower has cancelled an auction on their collateral and repaid the full amount of the debt, they won't be able to release the collateral since at least one lien won't be repaid. Anyone will be able to start a new auction, and since the total loan will be mostly repaid, the reserve price of the new auction will be low and it'll be cheap to create a bid that's higher than the reserve price, thus disallowing the borrower to cancel the auction (AuctionHouse.sol#L215). The borrower basically loses the amount the paid to cancel the auction.
Code Snippet
CollateralToken.sol#L331-L335:
AuctionHouse.sol#L210:
AuctionHouse.sol#L253:
CollateralToken.sol#L204-L214:
Tool used
Manual Review
Recommendation
Consider including the initiator fee in the amount required to cancel an auction.
Duplicate of #199