> For the complete documentation index, see [llms.txt](https://docs.curvance.com/app/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.curvance.com/app/developer-docs/dynamic-liquidation-engine-dle.md).

# Dynamic Liquidation Engine (DLE)

### Overview

The Dynamic Liquidation Engine (DLE) is Curvance's liquidation framework for isolated markets. It combines position-health-based liquidation math in the Market Manager, public liquidation entrypoints on borrowable cTokens, bad-debt recognition in the debt cToken, and an optional Atlas-based auction path for OEV capture.

### Technical Architecture

#### MEV Integration with Atlas

The contract integrates MEV (Maximal Extractable Value) capture:

* **ME Auction Mechanism:** Auction-based liquidations can run after an oracle update or after a non-oracle state change, such as interest accrual, makes liquidation available. Off-chain auction and solver ordering are handled outside the core lending contracts.
* **Atomic Execution:** In the oracle-update path, the auction flow can update the oracle price and execute the liquidation in the same transaction. The auction manager also supports an auction path that intentionally skips oracle updates.
* **Bid Distribution:** Auction revenue is accumulated by the auction manager and distributed according to its configured revenue split, including the Curvance Protocol destination.
* **Collateral Targeting:** Each auction targets a specific cToken, both the market and the target cToken must be unlocked via the transient storage during the transaction, otherwise liquidation reverts.

#### Auction Buffer System

The contract implements a liquidation buffer that gives auction transactions priority access to liquidations:

* **Buffer Mechanism:** A buffer that gives auction transactions priority for liquidations by applying this discount when pricing collateral.
  * Correlated: 10 bps `(AUCTION_BUFFER = 9990)`
  * Uncorrelated: 50 bps `(AUCTION_BUFFER = 9950)`
* **Implementation:** The Market Manager applies `AUCTION_BUFFER` only when the market is unlocked for the current auction transaction and the requested collateral token matches the transiently unlocked cToken. If only one side is unlocked, the attempted auction liquidation reverts.
* **Benefits:**
  * Captures liquidation opportunities from oracle updates and from non-oracle state changes, such as debt growth through interest accrual.
  * Compensates for execution latency.

#### Transient Storage Risk Parameters

Auction-specific liquidation overrides are managed through transient storage:

* **Liquidation Incentive:** An auction flow can supply a liquidation incentive within the selected collateral token's configured min/max bounds. Passing zero tells the Market Manager to derive the incentive from `lFactor`.
* **Close Factor:** An auction flow can supply a close factor within the selected collateral token's configured min/max bounds. Passing zero tells the Market Manager to derive the close factor from `lFactor`.
* **Transient Nature:** The selected collateral token, incentive, and close factor exist only for the transaction.
* **Validation:** The Market Manager validates the caller, token listing, collateral eligibility, and configured min/max bounds before storing the transient values.

#### Liquidation Types

The contract supports token-specific liquidations:

* **Token-Specific Liquidations:**
  * Target a selected collateral cToken and debt cToken pair.
  * In an auction flow, `unlockAuctionForMarket()` and `setTransientLiquidationConfig()` identify the market and collateral cToken that can receive the auction buffer and any auction-specific close-factor or incentive override.
  * The same liquidation path can produce no liquidation, soft liquidation, hard liquidation, or bad-debt realization depending on the account's `lFactor`, selected debt amount, and available posted collateral.

#### Multi-Liquidation Support

The system is designed to efficiently process liquidations:

* **Batch Processing:** Can handle multiple liquidations in a single transaction.
* **Cached Pricing:** Retrieves asset prices once per transaction rather than per liquidation.
* **Gas Optimization:** Significantly reduces gas costs during liquidation cascades.
* **Debt Repayment Rollup:** Combines debt repayment and bad debt recognition into a single action (1,000 liquidations requires 1 debt token transfer, not 1,000 transfers).

### lFactor (Liquidation Factor)

**Definition:** A continuous score showing how close a position is to hard liquidation.

{% hint style="info" %}
lFactor is denominated in WAD aka 1e18.
{% endhint %}

**Calculation:**&#x20;

1. **Soft Requirement Debt Limit:** for each collateral asset, take its USD value and divide by that asset’s soft collateral requirement; add across assets. If an auction liquidation is active, apply the auction buffer discount to this total.
2. **Hard Requirement Debt Limit:** same as above but using each asset’s hard requirement; apply the same auction buffer if applicable.

* If Debt ≤ **Soft Requirement Debt Limit**: lFactor = 0
* If Debt ≥ **Hard Requirement Debt Limit**: lFactor = 1e18
* Otherwise, lFactor = (debt - soft requirement debt limit) / (hard requirement debt limit- soft requirement debt limit), using rounding up.

**Why it matters:**

* When no auction override is supplied, close factor and liquidation incentive scale linearly with `lFactor`. The Market Manager computes `closeFactor = closeFactorBase + closeFactorCurve * lFactor / WAD` and `liqInc = liqIncBase + liqIncCurve * lFactor / WAD`. Nonzero auction-supplied values bypass that derived curve for the supplied field.

#### Validation Process

Liquidation attempts undergo multiple validation checks.

For example, we check if collateral is unlocked for auction transactions:

```solidity
// Will revert if this liquidation is an attempted auction liquidator
// and liquidator has chosen incorrect collateral or market.
// Pulls any relevant offchain liquidation configuration.
(tData.auctionBuffer, aData.liqInc, aData.closeFactor) =
    _checkLiquidationConfig(collateralToken);
```

### Dual-Oracle Architecture

For each supported asset, Curvance can simultaneously integrate with two independent oracle providers. This creates redundancy and provides additional verification of asset prices, with the following benefits:

* **Enhanced security:** Mitigates risk from oracle failures or manipulation.
* **Continuous operation:** Ensures liquidations can proceed even in volatile markets.
* **Safety Buffer:** Creates a safety buffer when valuing collateral during distressed situations.

#### Price Selection Logic

{% hint style="warning" %}
**The dual-oracle architecture exists in the codebase, but it is not used in the current live implementation.** Live deployments use a single configured oracle source per asset, with heartbeat checks and price guards where applicable, especially for pegged or reference-priced assets.
{% endhint %}

When determining an asset's price, Curvance employs the "most safe" selection algorithm:

1. Each oracle reports its price for the asset.
2. The system applies sanity checks to both reported prices:
   1. Deviation from previous price must not exceed configured limits.
   2. Price must be above minimum threshold (non-zero).
   3. Oracle must have reported within the maximum allowable reporting window.
3. **For borrowable assets, the system selects the higher of the two valid prices.**
4. **For collateral assets, the system selects the lower of the two valid prices.**

```solidity
// inside of _getLiquidationConfig()

(tData.collateralSharesPrice, tData.debtUnderlyingPrice) =
    CommonLib._oracleManager(centralRegistry)
    .getPriceIsolatedPair(collateralToken, debtToken, 2);
```

This approach ensures that in liquidation scenarios, the protocol always errors on the side of protecting itself from bad debt, while giving borrowers the benefit of the most favorable valid price.

### Oracle Pricing During Liquidation

Curvance prices liquidation pairs through the Oracle Manager. The liquidation path calls `getPriceIsolatedPair(collateralToken, debtToken, BAD_SOURCE)`, which prices the collateral cToken shares with the lower-side price and the debt token underlying with the higher-side price.

If the oracle path reports a `BAD_SOURCE` level error, the liquidation reverts. Live deployments rely on configured single-source oracle feeds with heartbeat and price-guard defenses.

#### Risk Mitigation

The system incorporates several safeguards:

* **Transient Storage:** Ensures parameters reset after each transaction.
* **Permission Checks:** Restricts access to orderflow auction functions to authorized addresses.
* **Collateral Locking:** Prevents liquidation of unauthorized collateral during Atlas transactions.

### Protocol Benefits

* **Value Capture:** Extracts MEV from liquidations that would otherwise go to third parties.
* **Liquidation Efficiency:** Ensures timely liquidations even during high volatility.
* **Gas Optimization:** Uses efficient code combined with transient storage for parameter management.
* **Graceful Degradation:** Protocol remains secure even if OEV auctions fail.

By implementing this sophisticated liquidation system, Curvance balances the needs of protocol security, liquidator incentives, and value capture, creating a powerful framework for position management across diverse market conditions.

***


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.curvance.com/app/developer-docs/dynamic-liquidation-engine-dle.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
