# Ineffective minimum order size check for ASK limit orders can lead to Denial of Service

Bug Deep Dive #15 · 11 December 2025

Bug Deep Dives · [The Contest Academy](https://0xsimao.com/the-contest-academy) · 0xSimao

---

| Title | Ineffective minimum order size check for ASK limit orders can lead to Denial of Service |
| Reward | $1493, 2 dups |
| Contest | Dango Dex - 15 Sep 2025 on Sherlock |
| Author | berndartmueller |
| Context | DoS |

The minimum order size check for ASK orders during order creation is ineffective, allowing the creation of a large number of economically insignificant ImmediateOrCancel (IOC) orders. During the cron-based auction these orders are cancelled and refunded, which can consume excessive execution time — and gas, though the cron uses an infinite gas meter, so there is no out-of-gas error — causing block timeouts, for instance when paired with Tendermint/CometBFT.

Additionally, the owner-callable `OwnerMsg::ForceCancelOrders` message can run out of gas when trying to force-cancel all orders, which is not limited to IOC orders.

In `order_creation.rs:103-110`, the pre-configured `pair.min_order_size` is checked against `amount_in_quote`. For an ASK order, `amount_in_quote` is $\text{base} \cdot \text{price}$. A malicious user bypasses the check by supplying a minimal amount of the base asset, say 1 wei, and an arbitrarily high limit price. That creates a valid order which is practically guaranteed never to fill.

```rust
103: ensure!(
104:     amount_in_quote >= pair.min_order_size,
105:     "order size ({} {}) is less than the minimum ({} {})",
106:     amount_in_quote,
107:     order.quote_denom,
108:     pair.min_order_size,
109:     order.quote_denom
110: );
```

When the cron_execute function runs, all unfilled IOC orders are [collected into memory and then processed for cancellation and refunds](https://github.com/left-curve/left-curve/blob/4dd70e17bae94997663c50fa1e0b09ef4fa2d358/dango/dex/src/cron.rs#L577-L596), potentially causing block timeouts due to the high execution time required to handle a large number of orders.

Additionally, a large number of such orders will cause the owner-callable [OwnerMsg::ForceCancelOrders](https://github.com/left-curve/left-curve/blob/4dd70e17bae94997663c50fa1e0b09ef4fa2d358/dango/dex/src/execute/order_cancellation.rs#L18-L31) message to consume a significant amount of gas, potentially exceeding the block/transaction gas limit and preventing the cancellation of all orders. Since this is not limited to IOC orders, the attacker is in no hurry: GTC orders stay open indefinitely.

**Alpha:** spam-based DoS findings are judged inconsistently, because they sit close to the line. Report them anyway when the risk is real. To find them, ask what happens with a very large number of orders, and whether there is any way to handle or cancel them a batch at a time.

**Conclusion**

This finding would earn you **\$1493**, and it comes down to there being no way to process the work in batches. Always check for that.

[**Full Report**](https://audits.sherlock.xyz/contests/1066/report)\
**Codebase**

---

Newer: [All taker collateral and collected fees can be stolen by re-entering via RFTLib.settle to manipulate uniswap spot price](https://0xsimao.com/the-contest-academy/bug-deep-dive-16) · Older: [XYK reflect_curve is incorrect and decreases K over time leading to loss of funds for LP providers](https://0xsimao.com/the-contest-academy/bug-deep-dive-14)
