docs: pause freezes user escrow retrieval with no governance force-refund path [SEC-I03] (F-03) #457

Closed
opened 2026-06-30 17:39:15 +00:00 by totdking · 7 comments
totdking commented 2026-06-30 17:39:15 +00:00 (Migrated from gitlab.com)
No description provided.
totdking commented 2026-06-30 17:52:12 +00:00 (Migrated from gitlab.com)

Summary

By design, pausing a pair also blocks CancelLimitOrder, CancelLimitOrders, ClaimExpiredLimitOrder, and ClaimExpiredLimitOrders. Users with resting or expiry-parked limit orders cannot retrieve escrowed funds for the duration of the pause. Governance has SweepPair for excess balances but no mechanism to force-refund outstanding limit order escrow to individual depositors. This is a documented design choice but creates a user protection concern during prolonged pauses that is not currently surfaced in operator runbooks.


What Was Checked

  • smartcontracts/contracts/pair/src/contract.rs lines 593-594: assert_not_paused called before Receive dispatch.
  • smartcontracts/contracts/pair/src/contract.rs lines 640-678: CancelLimitOrder, CancelLimitOrders, ClaimExpiredLimitOrder, ClaimExpiredLimitOrders all guarded by assert_not_paused.
  • Docstring at line 1962: design choice referenced with GitLab #120.
  • docs/runbooks/emergency-commands.md: pause runbook does not mention the escrow retrieval freeze or the absence of a force-refund path.

Expected (per checklist)

Operator runbooks document that pausing a pair also locks all user limit order escrow, state how long a pause is expected to last, and describe what options governance has (none currently for per-user escrow refund). If prolonged pauses are anticipated, consider whether a governance-callable emergency force-refund path is warranted.


Actual

The escrow freeze consequence of pair pause is not mentioned in docs/runbooks/emergency-commands.md or any other operator-facing runbook. An operator pausing a pair under time pressure may not be aware that users with limit orders lose access to their funds for the duration.


Suggested Fix

Add a note to the "Pause a pair" section of docs/runbooks/emergency-commands.md stating: pausing a pair also blocks all limit order cancel and claim operations for the duration. Users with resting or expired limit orders cannot retrieve escrowed funds while the pair is paused. Governance has no force-refund path for individual limit order escrow; SweepPair only affects excess balances. If the team decides to add a governance-callable emergency force-refund path, open a separate implementation issue.


Verification Checklist

  • docs/runbooks/emergency-commands.md "Pause a pair" section notes that limit order cancel and claim are also blocked during pause
  • Runbook notes the absence of a governance force-refund path for limit order escrow
  • If a force-refund path is added, a separate implementation issue is opened and linked

Cc: @PlasticDigits

### Summary By design, pausing a pair also blocks `CancelLimitOrder`, `CancelLimitOrders`, `ClaimExpiredLimitOrder`, and `ClaimExpiredLimitOrders`. Users with resting or expiry-parked limit orders cannot retrieve escrowed funds for the duration of the pause. Governance has `SweepPair` for excess balances but no mechanism to force-refund outstanding limit order escrow to individual depositors. This is a documented design choice but creates a user protection concern during prolonged pauses that is not currently surfaced in operator runbooks. --- ### What Was Checked - `smartcontracts/contracts/pair/src/contract.rs` lines 593-594: `assert_not_paused` called before `Receive` dispatch. - `smartcontracts/contracts/pair/src/contract.rs` lines 640-678: `CancelLimitOrder`, `CancelLimitOrders`, `ClaimExpiredLimitOrder`, `ClaimExpiredLimitOrders` all guarded by `assert_not_paused`. - Docstring at line 1962: design choice referenced with GitLab #120. - `docs/runbooks/emergency-commands.md`: pause runbook does not mention the escrow retrieval freeze or the absence of a force-refund path. --- ### Expected (per checklist) Operator runbooks document that pausing a pair also locks all user limit order escrow, state how long a pause is expected to last, and describe what options governance has (none currently for per-user escrow refund). If prolonged pauses are anticipated, consider whether a governance-callable emergency force-refund path is warranted. --- ### Actual The escrow freeze consequence of pair pause is not mentioned in `docs/runbooks/emergency-commands.md` or any other operator-facing runbook. An operator pausing a pair under time pressure may not be aware that users with limit orders lose access to their funds for the duration. --- ### Suggested Fix Add a note to the "Pause a pair" section of `docs/runbooks/emergency-commands.md` stating: pausing a pair also blocks all limit order cancel and claim operations for the duration. Users with resting or expired limit orders cannot retrieve escrowed funds while the pair is paused. Governance has no force-refund path for individual limit order escrow; `SweepPair` only affects excess balances. If the team decides to add a governance-callable emergency force-refund path, open a separate implementation issue. --- ### Verification Checklist - [ ] `docs/runbooks/emergency-commands.md` "Pause a pair" section notes that limit order cancel and claim are also blocked during pause - [ ] Runbook notes the absence of a governance force-refund path for limit order escrow - [ ] If a force-refund path is added, a separate implementation issue is opened and linked Cc: @PlasticDigits
totdking commented 2026-06-30 17:52:59 +00:00 (Migrated from gitlab.com)

mentioned in issue #452

mentioned in issue #452
totdking commented 2026-06-30 18:37:55 +00:00 (Migrated from gitlab.com)

mentioned in issue #381

mentioned in issue #381
Brouie commented 2026-06-30 19:07:42 +00:00 (Migrated from gitlab.com)

mentioned in merge request !986

mentioned in merge request !986
Brouie commented 2026-06-30 19:08:58 +00:00 (Migrated from gitlab.com)

Added the runbook note. The "Pause a pair" section in emergency-commands.md already listed that cancel/claim are blocked, but didn't surface the user-protection consequence: pausing freezes all resting/expiry-parked limit-order escrow for the duration, and there's no governance force-refund path (SweepPair only moves excess balance, not a depositor's locked order).

New callout in that section:

  • keep pauses as short as the incident allows — a prolonged pause freezes user escrow, not just trading
  • state in incident comms that open limit orders are locked (funds safe but not withdrawable) until unpause
  • pointer that a governance-callable emergency force-refund would be a separate implementation issue if the team wants one

check_emergency_commands_docs.py passes. Covers checklist items 1 and 2; item 3 (the force-refund path itself) stays a separate decision/implementation issue if you want it.

MR !986, branch qa/457-pause-escrow-docs, commit 62209b1f. Needs review/merge @PlasticDigits — leaving open for verification.

Added the runbook note. The "Pause a pair" section in `emergency-commands.md` already listed that cancel/claim are blocked, but didn't surface the user-protection consequence: pausing freezes all resting/expiry-parked limit-order escrow for the duration, and there's no governance force-refund path (SweepPair only moves excess balance, not a depositor's locked order). New callout in that section: - keep pauses as short as the incident allows — a prolonged pause freezes user escrow, not just trading - state in incident comms that open limit orders are locked (funds safe but not withdrawable) until unpause - pointer that a governance-callable emergency force-refund would be a separate implementation issue if the team wants one `check_emergency_commands_docs.py` passes. Covers checklist items 1 and 2; item 3 (the force-refund path itself) stays a separate decision/implementation issue if you want it. MR !986, branch `qa/457-pause-escrow-docs`, commit `62209b1f`. Needs review/merge @PlasticDigits — leaving open for verification.
PlasticDigits commented 2026-06-30 22:02:08 +00:00 (Migrated from gitlab.com)

mentioned in commit a1d92b622a

mentioned in commit a1d92b622a9188cafa68a9c1c881b215e6a74f9d
PlasticDigits commented 2026-06-30 22:16:12 +00:00 (Migrated from gitlab.com)

Verification — #457 (SEC-I03 F-03)

Result: PASS — all acceptance criteria satisfied on main via merged MR !986 (62209b1f).

Checklist

Item Result Evidence
"Pause a pair" runbook notes cancel/claim blocked during pause PASS docs/runbooks/emergency-commands.md §1 callout (lines 136–141): blocks CancelLimitOrder(s) and ClaimExpiredLimitOrder(s); section intro lists "limit placement/cancel/claim"
Runbook notes absence of governance force-refund for limit-order escrow PASS Same callout: "Governance has no force-refund path"; SweepPair only moves excess balance, not locked order escrow
Force-refund path (if added) → separate implementation issue PASS Callout directs operators to open a separate implementation issue and link it; no force-refund execute path exists in contracts (by design)

How verified

  1. Docs (no chain): make check-emergency-commands-docs → OK: emergency-commands cookbook covers SEC-B11 operations, SEC-G07 unpause prerequisite checklist, and is cross-linked
  2. Runbook content: Read docs/runbooks/emergency-commands.md §1 — user-escrow consequence callout links #457 and user incident FAQ
  3. On-chain behavior (code review): smartcontracts/contracts/pair/src/contract.rs — assert_not_paused before Receive (L593), CancelLimitOrder / CancelLimitOrders (L640, L650), ClaimExpiredLimitOrder / ClaimExpiredLimitOrders (L660, L670); execute_set_paused docstring (L1962–L1965) documents resting escrow freeze until unpause
  4. Delivery: MR !986 merged to main; no additional repo changes required

Follow-ups (optional)

If prolonged pauses become an operational pattern, consider a dedicated implementation issue for a governance-callable emergency per-order escrow refund (as noted in the runbook callout).

## Verification — #457 (SEC-I03 F-03) **Result: PASS** — all acceptance criteria satisfied on `main` via merged MR !986 (`62209b1f`). ### Checklist | Item | Result | Evidence | |------|--------|----------| | "Pause a pair" runbook notes cancel/claim blocked during pause | **PASS** | `docs/runbooks/emergency-commands.md` §1 callout (lines 136–141): blocks `CancelLimitOrder(s)` and `ClaimExpiredLimitOrder(s)`; section intro lists "limit placement/cancel/claim" | | Runbook notes absence of governance force-refund for limit-order escrow | **PASS** | Same callout: "Governance has **no force-refund path**"; `SweepPair` only moves excess balance, not locked order escrow | | Force-refund path (if added) → separate implementation issue | **PASS** | Callout directs operators to open a separate implementation issue and link it; no force-refund execute path exists in contracts (by design) | ### How verified 1. **Docs (no chain):** `make check-emergency-commands-docs` → `OK: emergency-commands cookbook covers SEC-B11 operations, SEC-G07 unpause prerequisite checklist, and is cross-linked` 2. **Runbook content:** Read `docs/runbooks/emergency-commands.md` §1 — user-escrow consequence callout links [#457](https://gitlab.com/PlasticDigits/cl8y-dex-terraclassic/-/issues/457) and [user incident FAQ](../user-incident-faq.md) 3. **On-chain behavior (code review):** `smartcontracts/contracts/pair/src/contract.rs` — `assert_not_paused` before `Receive` (L593), `CancelLimitOrder` / `CancelLimitOrders` (L640, L650), `ClaimExpiredLimitOrder` / `ClaimExpiredLimitOrders` (L660, L670); `execute_set_paused` docstring (L1962–L1965) documents resting escrow freeze until unpause 4. **Delivery:** MR !986 merged to `main`; no additional repo changes required ### Follow-ups (optional) If prolonged pauses become an operational pattern, consider a dedicated implementation issue for a governance-callable emergency per-order escrow refund (as noted in the runbook callout).
PlasticDigits (Migrated from gitlab.com) closed this issue 2026-06-30 22:16:14 +00:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
code/cl8y-dex-terraclassic#457
No description provided.