Skip to content

Eliminate reentrancy / re-entrancy-ordering risk in the Risk Pool payout path #570

Description

@grantfox-oss

Module: meridian-contracts/contracts/risk_pool/src/lib.rs

Problem
payout_claim (lib.rs:132) and withdraw_liquidity (lib.rs:99) both transfer
tokens to a recipient before updating on-chain accounting. The token
transfer (client.transfer, lib.rs:145) is a cross-contract call into an
arbitrary Stellar asset contract. A malicious or re-entrant token contract can
re-enter payout_claim/withdraw_liquidity (or another entry that mutates the
same AvailableCapital/ProviderStake storage) before balances are finalized,
double-spending pool capital. Stellar asset contracts are user-deployable, so
this is a real attack surface, not theoretical.

Deliverables

  • Apply the checks-effects-interactions pattern: update all AvailableCapital,
    TotalCapital, ClaimsPaid and ProviderStake storage before the
    token::Client::transfer call in payout_claim, withdraw_liquidity, and
    deposit_liquidity.
  • Add an explicit re-entrancy guard (a transient Instance/Persistent bool
    flag set at entry, cleared at exit) mirroring the require_not_paused pattern
    used in the escrow contract (meridian-contracts/contracts/escrow/src/validation.rs).
  • Write an integration test using a malicious mock token contract that attempts
    to re-enter during the transfer and assert capital is conserved.
  • Document the invariant in a short comment on each affected function.

Acceptance criteria

  • All three functions update storage before external calls.
  • A re-entrancy test fails before the fix and passes after.

Metadata

Metadata

Assignees

Labels

GrantFox OSSIssue tracked in GrantFox OSSMaybe RewardedIssue may be eligible for a GrantFox rewardOfficial Campaign | FWC26Campaign: Official Campaign | FWC26

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions