RWf(x): RAAC Stablecoin Minting System¶
Overview¶
The RAAC Stablecoin Minting System is a fork of the f(x) protocol designed to use RWA-backed tokens as collateral to mint stablecoins and leverage tokens. This system enables the creation of stablecoins backed by real-world assets like fractionalized gold (fGOLD) and RWA NFTs.
First Stablecoin Launch
The first stablecoins to be launched will be pmUSD and xpmUSD, backed by tokenized gold.
f(x) Protocol Reference
You can read the original f(x) documentation at: https://fxprotocol.gitbook.io/fx-docs/
Purpose¶
- Use RWA-backed tokens as collaterals (fGOLD, fRWA NFTs) to mint stablecoins (fToken) and leverage tokens (xToken)
- Enable fractionalized gold as collateral to mint pmUSD (stablecoin) and xPM (leverage token)
- Maintain stability through collateral ratio management and automated rebalancing
- Provide a permissioned system for authorized managers to maintain system stability
Core Components¶
Using f(x) Components¶
- f(x)/v1/* - Core f(x) protocol contracts
- f(x)/math/FxLowVolatilityMath.sol - Mathematical calculations for low volatility scenarios
Key Contracts¶
| Contract | Purpose |
|---|---|
| \(\text{Treasury}\) | Core treasury management with RWA oracle integration |
| \(\text{Market}\) | Market operations (manager-only access) |
| \(\text{MintManager}\) | Asset management for authorized keepers |
| \(\text{FractionalToken}\) | fToken implementation with under-collateralized handling |
Use Case Example¶
fGOLD Integration:
- fGOLD represents fractionalized gold
- Instruxi provides oracle function \(\text{RWACoordinator::getSharePrice}\) and \(\text{BaseToken}\) address
- System mints: pmUSD (fToken) and xPM (xToken)
- xPM absorbs volatility while pmUSD maintains stability
Price Source and Minting Process:
- Price Source: Instruxi, the tokenization partner of RAAC, uses the Chainlink price feed for gold. This price is accessed by interacting with Instruxi's contract.
- Minting Process: Gold share tokens are deposited into the system, and stablecoins are minted in return.
Example Scenario:
- fGOLD NAV: $3000
- pmUSD NAV: $1
- xPM NAV: $1
- Minted: $150 worth of gold → $100 pmUSD + $50 xPM
- Collateral Ratio = 1.5 = Stability Ratio
When gold value increases to $200:
- Collateral ratio becomes 2.0
- Manager mints more pmUSD without adding fGOLD to restore stability ratio
System Restrictions¶
Upgradeability¶
- All contracts must be upgradeable
Access Control¶
- All \(\text{Market}\) actions are manager-only
- Authorized Silo managers can interact with the system
- Managers are multi-sig with RAAC as necessary signatory
- Prevents unauthorized minting, especially \(\text{mintFTokenWithoutCollateral}\)
Fee Structure¶
- No fees and incentives (all related parameters disabled)
- No \(\text{reservePool}\) and \(\text{registry}\)
- No liquidations or self-liquidation mechanisms
Beta Configuration¶
- \(\text{Treasury.beta}\): 1 (stablecoin)
- \(\text{Treasury.(constructor)}\): 0.9 (initialRatio - $0.9 for each $1 collateral)
- Since beta = 0, fToken multiple is 0, ensuring fNAV = \(10^{18}\) always
System Parameters¶
Enabled Parameters¶
| Parameter | Value | Description |
|---|---|---|
| \(\text{Treasury.beta}\) | 1 | Stablecoin configuration |
| \(\text{Treasury.initialRatio}\) | 0.9 (not final) | Initial collateral ratio |
| \(\text{Market.MarketConfig.stabilityRatio}\) | Variable | Target stability ratio |
| \(\text{fTokenMintInSystemStabilityModePaused}\) | true | Pauses fToken minting in stability mode |
| \(\text{xTokenRedeemInSystemStabilityModePaused}\) | true | Pauses xToken redemption in stability mode |
| \(\text{mintBothInSystemStabilityModePaused}\) | true | Pauses both token operations in stability mode |
Constructor Parameters
For detailed constructor parameters, refer to \(\text{scripts/raac/stablecoin/stablecoin_config.ts}\)
Under-Collateralized System Handling¶
When the system becomes under-collateralized, the following mechanisms activate:
System State Changes¶
- xNAV = 0 - Negative xNAV is not allowed
- Equality \(n \cdot v = n_f \cdot v_f + n_x \cdot v_x\) no longer holds
- Blocked operations: \(\text{mint}\), \(\text{addBaseToken}\), \(\text{liquidation}\)
- Allowed operations: \(\text{redeem}\) for fToken (pro-rata redemption)
Pro-rata Redemption¶
If there are 100 baseToken and you have 200 fToken out of 1000 fToken supply:
- You are entitled to 20% of the baseToken (20 baseToken)
RAAC-Specific Actions¶
- \(\text{donateBaseToken}\) - Allows silos to provide collateral to stabilize the system
- Amount calculation: \(CR = \frac{(n + dn) \cdot v}{n_f \cdot v_f}\) to find required \(dn\)
fNAV Calculation¶
- Collateralized state: Returns 1 (if beta=0)
- Under-collateralized state: Returns \(\frac{n \cdot v}{n_f}\)
- Example: $20,000 collateral with 40,000 fToken → fNAV = $0.5
Key Modifications from f(x)¶
New Functions Added¶
| Function | Purpose |
|---|---|
| \(\text{FxLowVolatilityMath::maxMintableFTokenWithoutBaseToken}\) | Calculate max fToken mintable without collateral |
| \(\text{FxLowVolatilityMath:maxBaseDonationForCollateralRatio}\) | Compute the amount of base token needed to reach the new collateral ratio. |
| \(\text{Treasury::mintFTokenWithoutBaseToken}\) | Mint fToken without base token |
| \(\text{Treasury::maxMintableFTokenWithoutBaseToken}\) | Get maximum mintable amount |
| \(\text{Treasury::maxBaseForCollateralRatio}\) | Get maximum base amount for target collateral ratio |
| \(\text{Market::mintFTokenWithoutBaseToken}\) | Market-level minting function |
| \(\text{Market::donateBaseToken}\) | Supply base token to the system to increase collateral |
Oracle Integration¶
- Uses \(\text{Treasury::_fetchRWAOraclePrice}\) instead of \(\text{TWAPOracle}\)
- Simplified \(\text{_loadSwapState}\) without min/max parameters
Access Control¶
- Added \(\text{AccessControl}\) to all \(\text{Market}\) methods
- Ensured system works without \(\text{reservePool}\) and \(\text{registry}\)
- Disabled fee collection mechanisms
MintManager Contract¶
- Asset owners deposit assets (e.g., fGOLD)
- Authorized keepers can run market methods
- Automated rebalancing through bot operators
Mathematical Foundation (Optional)¶
Core Invariant¶
Where:
- \(n\) = number of base tokens (fGOLD)
- \(v\) = NAV of base asset (gold price)
- \(n_f\) = number of stable assets (pmUSD)
- \(v_f\) = NAV of stable asset
- \(n_x\) = number of leveraged assets (xPM)
- \(v_x\) = NAV of leveraged asset
Collateral Ratio¶
Example:
- $150 fGOLD → $100 pmUSD + $50 xPM
- Collateral Ratio = \(\frac{150}{100} = 1.5\)
Price Impact Scenarios¶
Gold Price Increase:
- fGOLD NAV: $6000
- Position: $300 fGOLD → $100 pmUSD + $200 xPM
- Collateral Ratio = \(\frac{300}{100} = 3.0\) (safer)
Gold Price Decrease:
- fGOLD NAV: $1500
- Position: $75 fGOLD → $100 pmUSD - $25 xPM
- Collateral Ratio = \(\frac{75}{100} = 0.75\) (undercollateralized)
MaxMintableFToken Formula¶
The formula calculates how much fToken can be minted to reduce collateral ratio:
Solving for \(df\) (fToken to mint):
Leverage Ratio Formula¶
function leverageRatio(
SwapState memory state,
uint256 beta,
int256 earningRatio
) internal pure returns (uint256 ratio) {
uint256 rho = state.fSupply.mul(state.fNav).mul(PRECISION).div(state.baseSupply.mul(state.baseNav));
uint256 x = rho.mul(beta).mul(uint256(PRECISION_I256 + earningRatio)).div(PRECISION * PRECISION);
ratio = PRECISION.sub(x).mul(PRECISION).div(PRECISION - rho);
if (ratio > MAX_LEVERAGE_RATIO) ratio = MAX_LEVERAGE_RATIO;
}
Formula Breakdown¶
- \(\rho\) = fAsset value / base asset value
- \(\beta\) = fAsset sensitivity to base asset price changes
- \(r\) = earning ratio (percentage price change)
Beta = 0 Scenario (Stablecoin)¶
When \(\beta = 0\) (pmUSD has no sensitivity to fGOLD price):
- fAssets don't absorb base asset movements
- All volatility flows to xAssets
- Leverage ratio = \(\frac{1}{1 - \rho}\)
Known Issues¶
Treasury.mintFTokenWithoutBaseToken Issue¶
Problem: The function calculates max mintable fToken for the entire treasury, not individual positions.
Example:
- User 1: 500 fGOLD → 400 pmUSD + 100 xPM
- User 2: 300 fGOLD → 240 pmUSD + 60 xPM
- Treasury: 800 fGOLD × $10 = $8000 base value, 640 pmUSD × $1 = $640 fAsset value
- Collateral ratio: \(\frac{8000}{640} = 12.5\)
If User 2 calls \(\text{mintFTokenWithoutBaseToken}\) with target ratio = 5:
- Max mintable = \(\frac{8000}{5} = 1600\)
- Available to mint = \(1600 - 640 = 960\) pmUSD
- User 2 gets 960 pmUSD but only supplied $300 fGOLD
Mitigation: Multi-sig managers with RAAC oversight monitor all operations to prevent lopsided positions.
System Invariants¶
- Access Control: All external state-changing functions in \(\text{Market.sol}\) must be gated to \(\text{onlyManager}\)
- Total Balance: \(\text{totalBaseToken}\) must always equal the amount of base assets in the system
- Stability: fToken value never changes unless user mints more fTokens (assuming stable asset)