Real-World DeFi Scenarios

Practical monitoring patterns for common DeFi operations and attack vectors

Learning Objective

Apply FailSafe expressions to detect real DeFi security threats and operational anomalies

Wash Trading Detection

watchRule:

{
  "expressions": [
    "system.uintCompare(tx1.UniswapV2Router.F.swapExactETHForTokens.amountOutMin, <, ${lowSlippage}) && system.uintCompare(tx2.UniswapV2Router.F.swapExactTokensForETH.amountOutMin, <, ${lowSlippage}) && system.uintCompare(tx3.UniswapV2Router.F.swapExactETHForTokens.amountOutMin, <, ${lowSlippage})"
  ]
}

options:

{
  "literalDefs": {
    "lowSlippage": 100000000000000000
  }
}
Concept: Wash trading detection

Detects rapid back-and-forth trading by same address (ETH→Token→ETH→Token) with low slippage tolerance - indicates potential wash trading to artificially inflate volume or manipulate prices

Suspicious Large Withdrawal

watchRule:

{
  "expressions": [
    "system.uintCompare(tx1.LendingPool.F.withdraw.amount, >, ${largeWithdrawal}) && system.uintCompare(tx1.LendingPool.riskscore, >, ${highRisk})"
  ]
}

options:

{
  "literalDefs": {
    "largeWithdrawal": 1e+24,
    "highRisk": 75
  }
}
Concept: Suspicious large withdrawal

Monitors large withdrawals from high-risk addresses

Reentrancy Attack Detection

watchRule:

{
  "expressions": [
    "system.reentrant(tx1.WETH.F.withdraw) && system.invoked(tx1.itx1.MaliciousContract.F.fallback)"
  ]
}
Concept: Reentrancy attack detection

Detects reentrancy in WETH withdraw where the withdraw function triggers an internal call to a malicious contract's fallback function - classic reentrancy attack pattern where the callback re-enters the vulnerable contract

Unauthorized Large Transfer

watchRule:

{
  "expressions": [
    "system.uintCompare(tx2.DAI.F.transferFrom.amount, >, ${significantAmount}) && system.noMatches(system.invoked(tx1.DAI.F.approve))"
  ]
}

options:

{
  "literalDefs": {
    "significantAmount": 1e+24
  }
}
Concept: Unauthorized large transfer

Large DAI transferFrom in tx2 without prior approval in tx1 - potential exploit or compromised approval

Excessive Borrowing Detection

watchRule:

{
  "expressions": [
    "system.emitted(tx1.CompoundComptroller.E.MarketEntered) && system.uintCompare(tx1.itx1.CompoundCToken.F.borrow.borrowAmount, >, ${maxBorrow})"
  ]
}

options:

{
  "literalDefs": {
    "maxBorrow": 1e+24
  }
}
Concept: Excessive borrowing detection

Monitors large borrows immediately after entering Compound markets where MarketEntered event triggers internal calls to cToken borrow functions - detects potential over-leveraging attacks

Flash Loan via DEX Detection

watchRule:

{
  "expressions": [
    "system.invoked(tx1.UniswapV2Pair.F.swap) && system.uintCompare(tx1.UniswapV2Pair.E.Swap.amount0Out, >, ${flashLoanThreshold}) && system.uintCompare(tx1.UniswapV2Pair.E.Swap.amount1In, ==, 0)"
  ]
}

options:

{
  "literalDefs": {
    "flashLoanThreshold": 1e+24
  }
}
Concept: Flash loan via DEX detection

Detects large swaps with zero input (flash loan pattern)

Liquidation Without Oracle Update

watchRule:

{
  "expressions": [
    "system.uintCompare(tx1.CompoundCToken.F.liquidateBorrow.repayAmount, >, ${largeLiquidation}) && system.noMatches(system.invoked(tx2.ChainlinkOracle.F.updatePrice))"
  ]
}

options:

{
  "literalDefs": {
    "largeLiquidation": 1e+24
  }
}
Concept: Liquidation without oracle update

Large liquidation executed but price oracle not updated in subsequent transaction - indicates potential stale price exploitation with tight block window