Search Apps Documentation Source Content File Folder Download Copy Actions Download State String Boolean Number Struct Map Slice Pointer Function Closure Reference Nil Package Type Interface Unknown

factory_param.gno

3.06 Kb · 120 lines
  1package pool
  2
  3import (
  4	"strings"
  5
  6	"gno.land/p/gnoswap/consts"
  7	u256 "gno.land/p/gnoswap/uint256"
  8	ufmt "gno.land/p/nt/ufmt/v0"
  9	"gno.land/r/gnoswap/pool"
 10)
 11
 12const (
 13	FeeTier100   uint32 = 100
 14	FeeTier500   uint32 = 500
 15	FeeTier3000  uint32 = 3000
 16	FeeTier10000 uint32 = 10000
 17)
 18
 19const (
 20	MIN_SQRT_RATIO string = "4295128739"
 21	MAX_SQRT_RATIO string = "1461446703485210103287273052203988822378723970342"
 22)
 23
 24// poolCreateConfig holds the essential parameters for creating a new pool.
 25type poolCreateConfig struct {
 26	token0Path       string
 27	token1Path       string
 28	fee              uint32
 29	sqrtPriceX96     *u256.Uint
 30	tickSpacing      int32
 31	slot0FeeProtocol uint8
 32}
 33
 34// newPoolParams defines the essential parameters for creating a new pool.
 35func newPoolParams(
 36	token0Path string,
 37	token1Path string,
 38	fee uint32,
 39	sqrtPriceX96 string,
 40	tickSpacing int32,
 41	slot0FeeProtocol uint8,
 42) *poolCreateConfig {
 43	price := u256.MustFromDecimal(sqrtPriceX96)
 44	return &poolCreateConfig{
 45		token0Path:       token0Path,
 46		token1Path:       token1Path,
 47		fee:              fee,
 48		sqrtPriceX96:     price,
 49		tickSpacing:      tickSpacing,
 50		slot0FeeProtocol: slot0FeeProtocol,
 51	}
 52}
 53
 54func (p *poolCreateConfig) SqrtPriceX96() *u256.Uint { return p.sqrtPriceX96 }
 55func (p *poolCreateConfig) TickSpacing() int32       { return p.tickSpacing }
 56func (p *poolCreateConfig) Token0Path() string       { return p.token0Path }
 57func (p *poolCreateConfig) Token1Path() string       { return p.token1Path }
 58func (p *poolCreateConfig) Fee() uint32              { return p.fee }
 59
 60func (p *poolCreateConfig) update() error {
 61	token0Path := p.token0Path
 62	token1Path := p.token1Path
 63
 64	// Always validate that the price is within valid range
 65	if err := validateSqrtPriceX96(p.sqrtPriceX96); err != nil {
 66		return err
 67	}
 68
 69	if !p.isInOrder() {
 70		token0Path, token1Path = token1Path, token0Path
 71
 72		// newPrice = 2^192 / oldPrice
 73		newPrice := u256.Zero().Div(consts.Q192(), p.sqrtPriceX96)
 74
 75		// Check if calculated price is within valid range
 76		if err := validateSqrtPriceX96(newPrice); err != nil {
 77			return err
 78		}
 79
 80		p.sqrtPriceX96 = newPrice
 81	}
 82
 83	p.token0Path = token0Path
 84	p.token1Path = token1Path
 85
 86	return nil
 87}
 88
 89// isInOrder checks if token paths are in lexicographical (or, alphabetical) order
 90func (p *poolCreateConfig) isInOrder() bool {
 91	if strings.Compare(p.token0Path, p.token1Path) < 0 {
 92		return true
 93	}
 94	return false
 95}
 96
 97func (p *poolCreateConfig) poolPath() string {
 98	return pool.GetPoolPath(p.token0Path, p.token1Path, p.fee)
 99}
100
101// validateSqrtPriceX96 validates that the given sqrtPriceX96 is within valid range
102func validateSqrtPriceX96(sqrtPriceX96 *u256.Uint) error {
103	// Valid range is [minSqrtRatio, maxSqrtRatio) - same as TickMathGetTickAtSqrtRatio
104	if sqrtPriceX96.Lt(consts.MinSqrtRatio()) || sqrtPriceX96.Gte(consts.MaxSqrtRatio()) {
105		return makeErrorWithDetails(
106			errOutOfRange,
107			ufmt.Sprintf("sqrtPriceX96(%s) is out of range", sqrtPriceX96.ToString()),
108		)
109	}
110	return nil
111}
112
113func isValidFeeTier(feeTier uint32) bool {
114	switch feeTier {
115	case FeeTier100, FeeTier500, FeeTier3000, FeeTier10000:
116		return true
117	}
118
119	return false
120}