Pre-Liquidation

Complete API reference for Lotus pre-liquidation covering PreLiquidation contract, PreLiquidationFactory, interpolation formulas, and callback interface.

The pre-liquidation system allows partial liquidation of positions whose LTV is between PRE_LLTV and LLTV. Each pre-liquidation contract is deployed per-market, per-tranche via the PreLiquidationFactory.

PreLiquidation Contract

Immutable Parameters

Set at deployment and cannot be changed.

Parameter
Type
Description

LOTUS

address

Address of the Lotus core contract

ID

Id

Market identifier

TRANCHE_INDEX

uint256

Tranche this pre-liquidation applies to

PRE_LLTV

uint256

LTV threshold where pre-liquidation begins (WAD)

LLTV

uint256

Full liquidation loan-to-value (WAD, from the tranche config)

PRE_LCF_1

uint256

Close factor at PRE_LLTV — minimum (WAD)

PRE_LCF_2

uint256

Close factor at LLTV — maximum (WAD)

PRE_LIF_1

uint256

Liquidation incentive factor at PRE_LLTV — minimum (WAD)

PRE_LIF_2

uint256

Liquidation incentive factor at LLTV — maximum (WAD)

PRE_LIF_DELTA

uint256

Precomputed: PRE_LIF_2 - PRE_LIF_1

PRE_LCF_DELTA

uint256

Precomputed: PRE_LCF_2 - PRE_LCF_1

PRE_LIQUIDATION_ORACLE

address

Oracle used for pre-liquidation price checks

LOAN_TOKEN

address

Loan token address (cached from market parameters)

Constructor Validation

The constructor reverts if any of these conditions are violated:

Condition
Error

lotus == address(0)

ZeroAddress()

preLiquidationOracle == address(0)

ZeroAddress()

Market not created

MarketNotCreated()

trancheIndex >= numTranches

InvalidTrancheIndex()

preLltv >= LLTV

PreLltvTooHigh()

preLCF1 > preLCF2

InvalidCloseFactors()

preLCF1 > WAD

CloseFactorTooHigh()

preLIF1 < WAD

IncentiveFactorTooLow()

preLIF1 > preLIF2

InvalidIncentiveFactors()

preLIF2 > WAD.divWad(LLTV)

IncentiveFactor2TooHigh()

The constructor also approves LOAN_TOKEN to LOTUS with unlimited allowance for the repay flow.


preLiquidate

Parameter
Type
Description
Required

borrower

address

Address of the borrower to pre-liquidate

Yes

seizedAssets

uint256

Amount of collateral to seize (0 if using repaidShares)

Exactly one non-zero

repaidShares

uint256

Amount of borrow shares to repay (0 if using seizedAssets)

Exactly one non-zero

callbackData

bytes

Data forwarded to liquidator's onPreLiquidate callback

No (pass "")

Returns:

  • uint256 — actual collateral seized (in collateral token units)

  • uint256 — actual debt repaid (in loan token asset units)

Revert Conditions:

Error
Condition

InconsistentInput()

Both or neither of seizedAssets and repaidShares are zero

InvalidOraclePrice()

Oracle returned price of zero

NoDebt()

Borrower has no borrow shares in this tranche

NoCollateral()

Borrower has no collateral in this tranche

NotPreLiquidatable()

Borrower's LTV ≤ PRE_LLTV

FullyLiquidatable()

Borrower's LTV > LLTV (use regular liquidation)

ExceedsCloseFactor()

repaidShares exceeds the interpolated close factor limit

LiquidationAmountTooSmall()

Calculated amounts round to zero

Event:

Execution Flow

The preLiquidate function proceeds through the following steps:

  1. Validate inputs: exactly one of seizedAssets or repaidShares must be non-zero.

  2. Call accrueInterest on the Lotus market.

  3. Fetch borrower position, tranche state, and collateral price from the pre-liquidation oracle.

  4. Compute borrower's LTV: borrowed / (collateral * price / ORACLE_PRICE_SCALE).

  5. Verify LTV is in the pre-liquidation zone: PRE_LLTV < LTV < LLTV.

  6. Interpolate close factor and incentive factor based on position within the zone.

  7. Compute amounts based on input mode (see Amount Conversion below).

  8. Verify repaid shares do not exceed the close factor limit.

  9. Call Lotus.repay() on behalf of the borrower (triggers onLotusRepay callback).

  10. Emit PreLiquidate event.

Interpolation Formulas

At PRE_LLTV the factors equal their minimums (PRE_LIF_1, PRE_LCF_1). At LLTV they equal their maximums (PRE_LIF_2, PRE_LCF_2).

Amount Conversion

When repaidShares is provided:

When seizedAssets is provided:

Close Factor Constraint


onLotusRepay

Internal callback invoked by Lotus during the repay() step. Not intended for external callers.

Reverts: OnlyLotus() if msg.sender is not the Lotus contract.

Flow within the callback:

  1. Decode callback data: (borrower, seizedAssets, liquidator, callbackData).

  2. Call Lotus.withdrawCollateral() with onBehalf = borrower and receiver = liquidator. This requires the borrower to have authorized the pre-liquidation contract.

  3. If callbackData is non-empty, invoke IPreLiquidationCallback(liquidator).onPreLiquidate(repaidAssets, callbackData).

  4. Transfer repaidAssets of loan tokens from the liquidator to the pre-liquidation contract (which has pre-approved Lotus to pull them).


marketParams

Returns the market parameters this contract is configured for.


PreLiquidationFactory

createPreLiquidation

Parameter
Type
Description
Required

id

Id

Market identifier

Yes

trancheIndex

uint256

Tranche index

Yes

params

PreLiquidationParams

Configuration parameters

Yes

salt

bytes32

CREATE2 salt for deterministic address

Yes

Returns: IPreLiquidation — the deployed pre-liquidation contract.

Event:

Side effects: Sets isPreLiquidation[address(preLiquidation)] = true in the factory's registry.

computePreLiquidationAddress

Returns the deterministic address where the pre-liquidation contract will be deployed with the given parameters and salt. Useful for computing the address before deployment so borrowers can pre-authorize it.

PreLiquidationParams

Field
Type
Description

preLltv

uint256

LTV threshold where pre-liquidation begins (WAD)

preLCF1

uint256

Close factor at PRE_LLTV (WAD)

preLCF2

uint256

Close factor at LLTV (WAD)

preLIF1

uint256

Incentive factor at PRE_LLTV (WAD, must be ≥ 1e18)

preLIF2

uint256

Incentive factor at LLTV (WAD, must be ≤ WAD.divWad(LLTV))

preLiquidationOracle

address

Oracle for pre-liquidation price checks


IPreLiquidationCallback

Optional callback invoked on the liquidator after collateral has been seized and before loan tokens are pulled. Allows the liquidator to execute custom logic such as swapping seized collateral into loan tokens for repayment.

Parameter
Type
Description

repaidAssets

uint256

Amount of loan tokens the liquidator must have available

data

bytes

Custom data passed through from preLiquidate


Errors

All errors are defined in PreLiquidationErrorsLib.sol.

Error
Condition

ZeroAddress()

Zero address where non-zero required

MarketNotCreated()

Market does not exist

InvalidTrancheIndex()

Tranche index out of bounds

PreLltvTooHigh()

preLltv >= LLTV

InvalidCloseFactors()

preLCF1 > preLCF2

CloseFactorTooHigh()

preLCF1 > WAD

IncentiveFactorTooLow()

preLIF1 < WAD

InvalidIncentiveFactors()

preLIF1 > preLIF2

IncentiveFactor2TooHigh()

preLIF2 > WAD.divWad(LLTV)

InconsistentInput()

Both or neither seizedAssets/repaidShares are zero

NotPreLiquidatable()

Borrower's LTV ≤ PRE_LLTV

FullyLiquidatable()

Borrower's LTV > LLTV

ExceedsCloseFactor()

Repaid shares exceed close factor limit

OnlyLotus()

Callback caller is not the Lotus contract

NoDebt()

Borrower has no debt

NoCollateral()

Borrower has no collateral

InvalidOraclePrice()

Oracle returned zero price

LiquidationAmountTooSmall()

Calculated amounts round to zero


See Also

Last updated