Skip to content

Latest commit

 

History

History
127 lines (90 loc) · 3.93 KB

074.md

File metadata and controls

127 lines (90 loc) · 3.93 KB

Tiny Gingerbread Tarantula

High

Borrower Exploitation via APR Front-Running in matchOfferV3

Summary

The matchOffersV3 function in the DebitaV3Aggregator.sol contract is vulnerable to front-running attacks, where a lender can increase the APR (Annual Percentage Rate) to any value after seeing a borrower's transaction in the mempool. This can lead to higher interest rates for the borrower than initially intended apr

Root Cause

The root cause of the issue is that In the updateLendOrder function, the lender can update critical parameters such as APR, as the APR param has no max bound limit, after the borrower's transaction is visible in the mempool but before it is mined. This allows the lender to increase the APR, resulting in higher interest payments for the borrower

Internal pre-conditions

No response

External pre-conditions

No response

Attack Path

No response

Impact

Borrowers are forced to pay higher interest than initially anticipated, leading to unfair loan terms and potential financial losses.

PoC

•	Bob wants to borrow `100,000` USD from Alice.
•	Alice initially sets an APR of `2,000 bps (20%)`, which is acceptable to Bob.
•	Jack matches the borrow and lend orders (matchOffersV3).
•	Alice sees Jack’s pending transaction in the mempool and updates her APR to 100,000 bps (1,000%) before the transaction is executed.
•	Interest is calculated for a 7-day loan on the borrowed amount (100,000 USD).

Calculations

The formula for interest based on APR is:

•	Initial APR (20%) Calculation:
•	Borrowed Amount: 100,000 USD
•	APR: 2,000 bps = 20%
•	Loan Duration: 7 days





•	Initial APR (20%) Calculation:
•	Borrowed Amount: 100,000 USD
•	APR: 2,000 bps = 20%
•	Loan Duration: 7 days

As shown:

uint anualInterest = (offer.principleAmount * offer.apr) / 10000;

initial interest = ((100,000 USD * 2,000) / 10,000)

7 days interest:

uint interest = (anualInterest * activeTime) / 31536000;

interest = (20000 * 604800) / 31536000 Expected 7 days interest = 383.56 USD

Front-Run APR (1,000%) Calculation: • Borrowed Amount: 100,000 USD • APR: 100,000 bps = 1,000% • Loan Duration: 7 days

interest = ((100,000 USD * 100,000) / 10,000) interest = (1,000,000 * 604800) / 31536000

Interest after front-run in 7 days = 19,178.08 USD

Lender still has the tendency to increase the APR

From the above: • Before Front-Running: Bob pays $383.56 interest for 7 days. • After Front-Running: Bob pays $19,178.08 interest for the same 7 days, which is 50x higher.

Mitigation

To mitigate this issue, borrowers should be able to set acceptable APR bounds that they are willing to pay. Here is the corrected code:

function createBorrowOrder(
    ...,
    uint _maxAcceptableAPR,
    ...
) external returns (address) {
    require(_maxAcceptableAPR > 0, "Invalid APR bound");
    ...
    borrowOffer.initialize(
        ...,
        _maxAcceptableAPR,
        ...
    );
    ...
}

In matchOffersV3

function matchOffersV3(
    ...
) public returns (address) {
    ...
    for (uint i = 0; i < lendOrders.length; i++) {
        require(
            lendInfo.apr <= borrowOrder.maxAcceptableAPR,
            "APR exceeds acceptable limit"
        );
    }
    ...
}

The protocol can decide to add a cap in updateLendOrder

require(newApr <= 10000, "APR Capp reached")