@paraswap/dex-lib 2.42.28 → 2.42.29

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (130) hide show
  1. package/build/abi/{algebra/AlgebraPool.abi.json → solidly-v3/SolidlyV3Pool.abi.json} +293 -282
  2. package/build/abi/solidly-v3/SolidlyV3StateMulticall.abi.json +375 -0
  3. package/build/config.js +2 -2
  4. package/build/dex/index.js +2 -0
  5. package/build/dex/index.js.map +1 -1
  6. package/build/dex/solidly-v3/config.d.ts +9 -0
  7. package/build/dex/solidly-v3/config.js +58 -0
  8. package/build/dex/solidly-v3/config.js.map +1 -0
  9. package/build/dex/solidly-v3/constants.d.ts +27 -0
  10. package/build/dex/solidly-v3/constants.js +34 -0
  11. package/build/dex/solidly-v3/constants.js.map +1 -0
  12. package/build/dex/solidly-v3/contract-math/BitMath.d.ts +4 -0
  13. package/build/dex/solidly-v3/contract-math/BitMath.js +93 -0
  14. package/build/dex/solidly-v3/contract-math/BitMath.js.map +1 -0
  15. package/build/dex/solidly-v3/contract-math/FixedPoint128.d.ts +3 -0
  16. package/build/dex/solidly-v3/contract-math/FixedPoint128.js +8 -0
  17. package/build/dex/solidly-v3/contract-math/FixedPoint128.js.map +1 -0
  18. package/build/dex/solidly-v3/contract-math/FixedPoint96.d.ts +4 -0
  19. package/build/dex/solidly-v3/contract-math/FixedPoint96.js +9 -0
  20. package/build/dex/solidly-v3/contract-math/FixedPoint96.js.map +1 -0
  21. package/build/dex/solidly-v3/contract-math/FullMath.d.ts +4 -0
  22. package/build/dex/solidly-v3/contract-math/FullMath.js +19 -0
  23. package/build/dex/solidly-v3/contract-math/FullMath.js.map +1 -0
  24. package/build/dex/solidly-v3/contract-math/LiquidityMath.d.ts +3 -0
  25. package/build/dex/solidly-v3/contract-math/LiquidityMath.js +22 -0
  26. package/build/dex/solidly-v3/contract-math/LiquidityMath.js.map +1 -0
  27. package/build/dex/solidly-v3/contract-math/SqrtPriceMath.d.ts +10 -0
  28. package/build/dex/solidly-v3/contract-math/SqrtPriceMath.js +91 -0
  29. package/build/dex/solidly-v3/contract-math/SqrtPriceMath.js.map +1 -0
  30. package/build/dex/solidly-v3/contract-math/SwapMath.d.ts +8 -0
  31. package/build/dex/solidly-v3/contract-math/SwapMath.js +70 -0
  32. package/build/dex/solidly-v3/contract-math/SwapMath.js.map +1 -0
  33. package/build/dex/solidly-v3/contract-math/Tick.d.ts +7 -0
  34. package/build/dex/solidly-v3/contract-math/Tick.js +36 -0
  35. package/build/dex/solidly-v3/contract-math/Tick.js.map +1 -0
  36. package/build/dex/solidly-v3/contract-math/TickBitMap.d.ts +7 -0
  37. package/build/dex/solidly-v3/contract-math/TickBitMap.js +84 -0
  38. package/build/dex/solidly-v3/contract-math/TickBitMap.js.map +1 -0
  39. package/build/dex/solidly-v3/contract-math/TickMath.d.ts +8 -0
  40. package/build/dex/solidly-v3/contract-math/TickMath.js +162 -0
  41. package/build/dex/solidly-v3/contract-math/TickMath.js.map +1 -0
  42. package/build/dex/solidly-v3/contract-math/UnsafeMath.d.ts +3 -0
  43. package/build/dex/solidly-v3/contract-math/UnsafeMath.js +10 -0
  44. package/build/dex/solidly-v3/contract-math/UnsafeMath.js.map +1 -0
  45. package/build/dex/solidly-v3/contract-math/uniswap-v3-math.d.ts +31 -0
  46. package/build/dex/solidly-v3/contract-math/uniswap-v3-math.js +363 -0
  47. package/build/dex/solidly-v3/contract-math/uniswap-v3-math.js.map +1 -0
  48. package/build/dex/solidly-v3/contract-math/utils.d.ts +7 -0
  49. package/build/dex/solidly-v3/contract-math/utils.js +39 -0
  50. package/build/dex/solidly-v3/contract-math/utils.js.map +1 -0
  51. package/build/dex/solidly-v3/solidly-v3-factory.d.ts +26 -0
  52. package/build/dex/solidly-v3/solidly-v3-factory.js +44 -0
  53. package/build/dex/solidly-v3/solidly-v3-factory.js.map +1 -0
  54. package/build/dex/{algebra/algebra-pool.d.ts → solidly-v3/solidly-v3-pool.d.ts} +14 -16
  55. package/build/dex/{algebra/algebra-pool.js → solidly-v3/solidly-v3-pool.js} +127 -165
  56. package/build/dex/solidly-v3/solidly-v3-pool.js.map +1 -0
  57. package/build/dex/solidly-v3/solidly-v3.d.ts +67 -0
  58. package/build/dex/solidly-v3/solidly-v3.js +590 -0
  59. package/build/dex/solidly-v3/solidly-v3.js.map +1 -0
  60. package/build/dex/solidly-v3/types.d.ts +132 -0
  61. package/build/dex/solidly-v3/types.js +9 -0
  62. package/build/dex/solidly-v3/types.js.map +1 -0
  63. package/build/dex/solidly-v3/utils.d.ts +6 -0
  64. package/build/dex/solidly-v3/utils.js +53 -0
  65. package/build/dex/solidly-v3/utils.js.map +1 -0
  66. package/build/dex/trader-joe-v2-1-2/config.d.ts +4 -0
  67. package/build/dex/trader-joe-v2-1-2/config.js +15 -0
  68. package/build/dex/trader-joe-v2-1-2/config.js.map +1 -0
  69. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2-pool.d.ts +39 -0
  70. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2-pool.js +64 -0
  71. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2-pool.js.map +1 -0
  72. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2.d.ts +37 -0
  73. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2.js +126 -0
  74. package/build/dex/trader-joe-v2-1-2/trader-joe-v2-1-2.js.map +1 -0
  75. package/build/dex/trader-joe-v2-1-2/types.d.ts +6 -0
  76. package/build/dex/trader-joe-v2-1-2/types.js +3 -0
  77. package/build/dex/trader-joe-v2-1-2/types.js.map +1 -0
  78. package/build/dex/trader-joe-v2_1/config.d.ts +4 -0
  79. package/build/dex/trader-joe-v2_1/config.js +48 -0
  80. package/build/dex/trader-joe-v2_1/config.js.map +1 -0
  81. package/build/dex/trader-joe-v2_1/constants.d.ts +15 -0
  82. package/build/dex/trader-joe-v2_1/constants.js +17 -0
  83. package/build/dex/trader-joe-v2_1/constants.js.map +1 -0
  84. package/build/dex/trader-joe-v2_1/trader-joe-v2.1.d.ts +0 -0
  85. package/build/dex/trader-joe-v2_1/trader-joe-v2.1.js +183 -0
  86. package/build/dex/trader-joe-v2_1/trader-joe-v2.1.js.map +1 -0
  87. package/build/dex/trader-joe-v2_1/types.d.ts +39 -0
  88. package/build/dex/trader-joe-v2_1/types.js +3 -0
  89. package/build/dex/trader-joe-v2_1/types.js.map +1 -0
  90. package/build/dex/wombat/wombat-pool-poller.d.ts +22 -0
  91. package/build/dex/wombat/wombat-pool-poller.js +164 -0
  92. package/build/dex/wombat/wombat-pool-poller.js.map +1 -0
  93. package/package.json +1 -1
  94. package/src/abi/solidly-v3/SolidlyV3Pool.abi.json +738 -0
  95. package/src/abi/solidly-v3/SolidlyV3StateMulticall.abi.json +375 -0
  96. package/src/config.ts +2 -2
  97. package/src/dex/index.ts +2 -0
  98. package/src/dex/solidly-v3/config.ts +64 -0
  99. package/src/dex/solidly-v3/constants.ts +42 -0
  100. package/src/dex/solidly-v3/contract-math/BitMath.ts +90 -0
  101. package/src/dex/solidly-v3/contract-math/FixedPoint128.ts +3 -0
  102. package/src/dex/solidly-v3/contract-math/FixedPoint96.ts +4 -0
  103. package/src/dex/solidly-v3/contract-math/FullMath.ts +30 -0
  104. package/src/dex/solidly-v3/contract-math/LiquidityMath.ts +17 -0
  105. package/src/dex/solidly-v3/contract-math/SqrtPriceMath.ts +226 -0
  106. package/src/dex/solidly-v3/contract-math/SwapMath.ts +139 -0
  107. package/src/dex/solidly-v3/contract-math/Tick.ts +66 -0
  108. package/src/dex/solidly-v3/contract-math/TickBitMap.ts +123 -0
  109. package/src/dex/solidly-v3/contract-math/TickMath.ts +211 -0
  110. package/src/dex/solidly-v3/contract-math/UnsafeMath.ts +5 -0
  111. package/src/dex/solidly-v3/contract-math/uniswap-v3-math.ts +570 -0
  112. package/src/dex/solidly-v3/contract-math/utils.ts +50 -0
  113. package/src/dex/solidly-v3/solidly-v3-e2e.test.ts +124 -0
  114. package/src/dex/solidly-v3/solidly-v3-events.test.ts +144 -0
  115. package/src/dex/solidly-v3/solidly-v3-factory.ts +73 -0
  116. package/src/dex/solidly-v3/solidly-v3-integration.test.ts +358 -0
  117. package/src/dex/solidly-v3/solidly-v3-pool.ts +494 -0
  118. package/src/dex/solidly-v3/solidly-v3.ts +988 -0
  119. package/src/dex/solidly-v3/types.ts +158 -0
  120. package/src/dex/solidly-v3/utils.ts +71 -0
  121. package/src/dex/uniswap-v3/uniswap-v3-events.test.ts +3 -0
  122. package/build/abi/uniswap-v3/UniswapV3Quoter.abi.json +0 -193
  123. package/build/dex/algebra/algebra-pool.js.map +0 -1
  124. package/build/dex/quickswap/camelot-v3.d.ts +0 -6
  125. package/build/dex/quickswap/camelot-v3.js +0 -19
  126. package/build/dex/quickswap/camelot-v3.js.map +0 -1
  127. package/build/dex/quickswap/zyberswap-v3.d.ts +0 -6
  128. package/build/dex/quickswap/zyberswap-v3.js +0 -19
  129. package/build/dex/quickswap/zyberswap-v3.js.map +0 -1
  130. package/build/dex/uniswap-v2/rebase-tokens.json +0 -7
@@ -0,0 +1,226 @@
1
+ import { BI_MAX_UINT160 } from '../../../bigint-constants';
2
+ import { FixedPoint96 } from './FixedPoint96';
3
+ import { FullMath } from './FullMath';
4
+ import { UnsafeMath } from './UnsafeMath';
5
+ import { _require } from '../../../utils';
6
+
7
+ export class SqrtPriceMath {
8
+ static getNextSqrtPriceFromAmount0RoundingUp(
9
+ sqrtPX96: bigint,
10
+ liquidity: bigint,
11
+ amount: bigint,
12
+ add: boolean,
13
+ ): bigint {
14
+ if (amount === 0n) return sqrtPX96;
15
+ const numerator1 =
16
+ BigInt.asUintN(256, liquidity) << FixedPoint96.RESOLUTION;
17
+
18
+ const product = amount * sqrtPX96;
19
+ if (add) {
20
+ if (product / amount === sqrtPX96) {
21
+ const denominator = numerator1 + product;
22
+ if (denominator >= numerator1) {
23
+ return BigInt.asUintN(
24
+ 160,
25
+ FullMath.mulDivRoundingUp(numerator1, sqrtPX96, denominator),
26
+ );
27
+ }
28
+ }
29
+ return BigInt.asUintN(
30
+ 160,
31
+ UnsafeMath.divRoundingUp(numerator1, numerator1 / sqrtPX96 + amount),
32
+ );
33
+ } else {
34
+ _require(
35
+ product / amount === sqrtPX96 && numerator1 > product,
36
+ '',
37
+ { product, amount, sqrtPX96, numerator1 },
38
+ 'product / amount === sqrtPX96 && numerator1 > product',
39
+ );
40
+ const denominator = numerator1 - product;
41
+ return BigInt.asUintN(
42
+ 160,
43
+ FullMath.mulDivRoundingUp(numerator1, sqrtPX96, denominator),
44
+ );
45
+ }
46
+ }
47
+
48
+ static getNextSqrtPriceFromAmount1RoundingDown(
49
+ sqrtPX96: bigint,
50
+ liquidity: bigint,
51
+ amount: bigint,
52
+ add: boolean,
53
+ ): bigint {
54
+ if (add) {
55
+ const quotient =
56
+ amount <= BI_MAX_UINT160
57
+ ? (amount << FixedPoint96.RESOLUTION) / liquidity
58
+ : FullMath.mulDiv(amount, FixedPoint96.Q96, liquidity);
59
+ return BigInt.asUintN(160, BigInt.asUintN(256, sqrtPX96) + quotient);
60
+ } else {
61
+ const quotient =
62
+ amount <= BI_MAX_UINT160
63
+ ? UnsafeMath.divRoundingUp(
64
+ amount << FixedPoint96.RESOLUTION,
65
+ liquidity,
66
+ )
67
+ : FullMath.mulDivRoundingUp(amount, FixedPoint96.Q96, liquidity);
68
+
69
+ _require(
70
+ sqrtPX96 > quotient,
71
+ '',
72
+ { sqrtPX96, quotient },
73
+ 'sqrtPX96 > quotient',
74
+ );
75
+ return BigInt.asUintN(160, sqrtPX96 - quotient);
76
+ }
77
+ }
78
+
79
+ static getNextSqrtPriceFromInput(
80
+ sqrtPX96: bigint,
81
+ liquidity: bigint,
82
+ amountIn: bigint,
83
+ zeroForOne: boolean,
84
+ ): bigint {
85
+ _require(sqrtPX96 > 0n, '', { sqrtPX96 }, 'sqrtPX96 > 0n');
86
+ _require(liquidity > 0n, '', { liquidity }, 'liquidity > 0n');
87
+
88
+ return zeroForOne
89
+ ? SqrtPriceMath.getNextSqrtPriceFromAmount0RoundingUp(
90
+ sqrtPX96,
91
+ liquidity,
92
+ amountIn,
93
+ true,
94
+ )
95
+ : SqrtPriceMath.getNextSqrtPriceFromAmount1RoundingDown(
96
+ sqrtPX96,
97
+ liquidity,
98
+ amountIn,
99
+ true,
100
+ );
101
+ }
102
+
103
+ static getNextSqrtPriceFromOutput(
104
+ sqrtPX96: bigint,
105
+ liquidity: bigint,
106
+ amountOut: bigint,
107
+ zeroForOne: boolean,
108
+ ): bigint {
109
+ _require(sqrtPX96 > 0n, '', { sqrtPX96 }, 'sqrtPX96 > 0n');
110
+ _require(liquidity > 0n, '', { liquidity }, 'liquidity > 0n');
111
+
112
+ return zeroForOne
113
+ ? SqrtPriceMath.getNextSqrtPriceFromAmount1RoundingDown(
114
+ sqrtPX96,
115
+ liquidity,
116
+ amountOut,
117
+ false,
118
+ )
119
+ : SqrtPriceMath.getNextSqrtPriceFromAmount0RoundingUp(
120
+ sqrtPX96,
121
+ liquidity,
122
+ amountOut,
123
+ false,
124
+ );
125
+ }
126
+
127
+ static getAmount0Delta(
128
+ sqrtRatioAX96: bigint,
129
+ sqrtRatioBX96: bigint,
130
+ liquidity: bigint,
131
+ roundUp: boolean,
132
+ ) {
133
+ if (sqrtRatioAX96 > sqrtRatioBX96) {
134
+ [sqrtRatioAX96, sqrtRatioBX96] = [sqrtRatioBX96, sqrtRatioAX96];
135
+ }
136
+
137
+ const numerator1 =
138
+ BigInt.asUintN(256, liquidity) << FixedPoint96.RESOLUTION;
139
+ const numerator2 = sqrtRatioBX96 - sqrtRatioAX96;
140
+
141
+ _require(sqrtRatioAX96 > 0, '', { sqrtRatioAX96 }, 'sqrtRatioAX96 > 0');
142
+
143
+ return roundUp
144
+ ? UnsafeMath.divRoundingUp(
145
+ FullMath.mulDivRoundingUp(numerator1, numerator2, sqrtRatioBX96),
146
+ sqrtRatioAX96,
147
+ )
148
+ : FullMath.mulDiv(numerator1, numerator2, sqrtRatioBX96) / sqrtRatioAX96;
149
+ }
150
+
151
+ static getAmount1Delta(
152
+ sqrtRatioAX96: bigint,
153
+ sqrtRatioBX96: bigint,
154
+ liquidity: bigint,
155
+ roundUp: boolean,
156
+ ) {
157
+ if (sqrtRatioAX96 > sqrtRatioBX96)
158
+ [sqrtRatioAX96, sqrtRatioBX96] = [sqrtRatioBX96, sqrtRatioAX96];
159
+
160
+ return roundUp
161
+ ? FullMath.mulDivRoundingUp(
162
+ liquidity,
163
+ sqrtRatioBX96 - sqrtRatioAX96,
164
+ FixedPoint96.Q96,
165
+ )
166
+ : FullMath.mulDiv(
167
+ liquidity,
168
+ sqrtRatioBX96 - sqrtRatioAX96,
169
+ FixedPoint96.Q96,
170
+ );
171
+ }
172
+
173
+ // Overloaded with different argument numbers
174
+ static _getAmount0DeltaO(
175
+ sqrtRatioAX96: bigint,
176
+ sqrtRatioBX96: bigint,
177
+ liquidity: bigint,
178
+ ) {
179
+ return liquidity < 0
180
+ ? -BigInt.asIntN(
181
+ 256,
182
+ SqrtPriceMath.getAmount0Delta(
183
+ sqrtRatioAX96,
184
+ sqrtRatioBX96,
185
+ BigInt.asUintN(128, -liquidity),
186
+ false,
187
+ ),
188
+ )
189
+ : BigInt.asIntN(
190
+ 256,
191
+ SqrtPriceMath.getAmount0Delta(
192
+ sqrtRatioAX96,
193
+ sqrtRatioBX96,
194
+ BigInt.asUintN(128, liquidity),
195
+ true,
196
+ ),
197
+ );
198
+ }
199
+
200
+ // Overloaded with different argument numbers
201
+ static _getAmount1DeltaO(
202
+ sqrtRatioAX96: bigint,
203
+ sqrtRatioBX96: bigint,
204
+ liquidity: bigint,
205
+ ) {
206
+ return liquidity < 0
207
+ ? -BigInt.asIntN(
208
+ 256,
209
+ SqrtPriceMath.getAmount1Delta(
210
+ sqrtRatioAX96,
211
+ sqrtRatioBX96,
212
+ BigInt.asUintN(128, -liquidity),
213
+ false,
214
+ ),
215
+ )
216
+ : BigInt.asIntN(
217
+ 256,
218
+ SqrtPriceMath.getAmount1Delta(
219
+ sqrtRatioAX96,
220
+ sqrtRatioBX96,
221
+ BigInt.asUintN(128, liquidity),
222
+ true,
223
+ ),
224
+ );
225
+ }
226
+ }
@@ -0,0 +1,139 @@
1
+ import { BI_POWS } from '../../../bigint-constants';
2
+ import { FullMath } from './FullMath';
3
+ import { SqrtPriceMath } from './SqrtPriceMath';
4
+
5
+ export class SwapMath {
6
+ static computeSwapStep(
7
+ sqrtRatioCurrentX96: bigint,
8
+ sqrtRatioTargetX96: bigint,
9
+ liquidity: bigint,
10
+ amountRemaining: bigint,
11
+ feePips: bigint,
12
+ ): {
13
+ sqrtRatioNextX96: bigint;
14
+ amountIn: bigint;
15
+ amountOut: bigint;
16
+ feeAmount: bigint;
17
+ } {
18
+ const zeroForOne = sqrtRatioCurrentX96 >= sqrtRatioTargetX96;
19
+ const exactIn = amountRemaining >= 0n;
20
+
21
+ let sqrtRatioNextX96 = 0n;
22
+ let amountIn = 0n;
23
+ let amountOut = 0n;
24
+ let feeAmount = 0n;
25
+
26
+ if (exactIn) {
27
+ const amountRemainingLessFee = FullMath.mulDiv(
28
+ BigInt.asUintN(256, amountRemaining),
29
+ BI_POWS[6] - feePips,
30
+ BI_POWS[6],
31
+ );
32
+ amountIn = zeroForOne
33
+ ? SqrtPriceMath.getAmount0Delta(
34
+ sqrtRatioTargetX96,
35
+ sqrtRatioCurrentX96,
36
+ liquidity,
37
+ true,
38
+ )
39
+ : SqrtPriceMath.getAmount1Delta(
40
+ sqrtRatioCurrentX96,
41
+ sqrtRatioTargetX96,
42
+ liquidity,
43
+ true,
44
+ );
45
+ if (amountRemainingLessFee >= amountIn)
46
+ sqrtRatioNextX96 = sqrtRatioTargetX96;
47
+ else
48
+ sqrtRatioNextX96 = SqrtPriceMath.getNextSqrtPriceFromInput(
49
+ sqrtRatioCurrentX96,
50
+ liquidity,
51
+ amountRemainingLessFee,
52
+ zeroForOne,
53
+ );
54
+ } else {
55
+ amountOut = zeroForOne
56
+ ? SqrtPriceMath.getAmount1Delta(
57
+ sqrtRatioTargetX96,
58
+ sqrtRatioCurrentX96,
59
+ liquidity,
60
+ false,
61
+ )
62
+ : SqrtPriceMath.getAmount0Delta(
63
+ sqrtRatioCurrentX96,
64
+ sqrtRatioTargetX96,
65
+ liquidity,
66
+ false,
67
+ );
68
+ if (BigInt.asUintN(256, -amountRemaining) >= amountOut)
69
+ sqrtRatioNextX96 = sqrtRatioTargetX96;
70
+ else
71
+ sqrtRatioNextX96 = SqrtPriceMath.getNextSqrtPriceFromOutput(
72
+ sqrtRatioCurrentX96,
73
+ liquidity,
74
+ BigInt.asUintN(256, -amountRemaining),
75
+ zeroForOne,
76
+ );
77
+ }
78
+
79
+ const max = sqrtRatioTargetX96 == sqrtRatioNextX96;
80
+
81
+ if (zeroForOne) {
82
+ amountIn =
83
+ max && exactIn
84
+ ? amountIn
85
+ : SqrtPriceMath.getAmount0Delta(
86
+ sqrtRatioNextX96,
87
+ sqrtRatioCurrentX96,
88
+ liquidity,
89
+ true,
90
+ );
91
+ amountOut =
92
+ max && !exactIn
93
+ ? amountOut
94
+ : SqrtPriceMath.getAmount1Delta(
95
+ sqrtRatioNextX96,
96
+ sqrtRatioCurrentX96,
97
+ liquidity,
98
+ false,
99
+ );
100
+ } else {
101
+ amountIn =
102
+ max && exactIn
103
+ ? amountIn
104
+ : SqrtPriceMath.getAmount1Delta(
105
+ sqrtRatioCurrentX96,
106
+ sqrtRatioNextX96,
107
+ liquidity,
108
+ true,
109
+ );
110
+ amountOut =
111
+ max && !exactIn
112
+ ? amountOut
113
+ : SqrtPriceMath.getAmount0Delta(
114
+ sqrtRatioCurrentX96,
115
+ sqrtRatioNextX96,
116
+ liquidity,
117
+ false,
118
+ );
119
+ }
120
+
121
+ // cap the output amount to not exceed the remaining output amount
122
+ if (!exactIn && amountOut > BigInt.asUintN(256, -amountRemaining)) {
123
+ amountOut = BigInt.asUintN(256, -amountRemaining);
124
+ }
125
+
126
+ if (exactIn && sqrtRatioNextX96 != sqrtRatioTargetX96) {
127
+ // we didn't reach the target, so take the remainder of the maximum input as fee
128
+ feeAmount = BigInt.asUintN(256, amountRemaining) - amountIn;
129
+ } else {
130
+ feeAmount = FullMath.mulDivRoundingUp(
131
+ amountIn,
132
+ feePips,
133
+ BI_POWS[6] - feePips,
134
+ );
135
+ }
136
+
137
+ return { sqrtRatioNextX96, amountIn, amountOut, feeAmount };
138
+ }
139
+ }
@@ -0,0 +1,66 @@
1
+ import { PoolState, TickInfo } from '../types';
2
+ import { LiquidityMath } from './LiquidityMath';
3
+ import { _require } from '../../../utils';
4
+ import { NumberAsString } from '@paraswap/core';
5
+ import { ZERO_TICK_INFO } from '../constants';
6
+
7
+ export class Tick {
8
+ static update(
9
+ state: Pick<PoolState, 'ticks'>,
10
+ tick: bigint,
11
+ liquidityDelta: bigint,
12
+ upper: boolean,
13
+ maxLiquidity: bigint,
14
+ ): boolean {
15
+ let info = state.ticks[Number(tick)];
16
+
17
+ if (info === undefined) {
18
+ info = { ...ZERO_TICK_INFO };
19
+ state.ticks[Number(tick)] = info;
20
+ }
21
+
22
+ const liquidityGrossBefore = info.liquidityGross;
23
+ const liquidityGrossAfter = LiquidityMath.addDelta(
24
+ liquidityGrossBefore,
25
+ liquidityDelta,
26
+ );
27
+
28
+ _require(
29
+ liquidityGrossAfter <= maxLiquidity,
30
+ 'LO',
31
+ { liquidityGrossAfter, maxLiquidity },
32
+ 'liquidityGrossAfter <= maxLiquidity',
33
+ );
34
+
35
+ const flipped = (liquidityGrossAfter == 0n) != (liquidityGrossBefore == 0n);
36
+
37
+ if (liquidityGrossBefore == 0n) {
38
+ info.initialized = true;
39
+ }
40
+
41
+ info.liquidityGross = liquidityGrossAfter;
42
+
43
+ info.liquidityNet = upper
44
+ ? BigInt.asIntN(
45
+ 128,
46
+ BigInt.asIntN(256, info.liquidityNet) - liquidityDelta,
47
+ )
48
+ : BigInt.asIntN(
49
+ 128,
50
+ BigInt.asIntN(256, info.liquidityNet) + liquidityDelta,
51
+ );
52
+ return flipped;
53
+ }
54
+
55
+ static clear(state: Pick<PoolState, 'ticks'>, tick: bigint) {
56
+ delete state.ticks[Number(tick)];
57
+ }
58
+
59
+ static cross(
60
+ ticks: Record<NumberAsString, TickInfo>,
61
+ tick: bigint,
62
+ ): bigint {
63
+ const info = ticks[Number(tick)];
64
+ return info.liquidityNet;
65
+ }
66
+ }
@@ -0,0 +1,123 @@
1
+ import { BI_MAX_UINT8 } from '../../../bigint-constants';
2
+ import { PoolState } from '../types';
3
+ import { BitMath } from './BitMath';
4
+ import { _require } from '../../../utils';
5
+ import { DeepReadonly } from 'ts-essentials';
6
+ import {
7
+ OUT_OF_RANGE_ERROR_POSTFIX,
8
+ TICK_BITMAP_BUFFER,
9
+ TICK_BITMAP_TO_USE,
10
+ } from '../constants';
11
+
12
+ function isWordPosOut(
13
+ wordPos: bigint,
14
+ startTickBitmap: bigint,
15
+ // For pricing we use wider range to check price impact. If function called from event
16
+ // it must always be within buffer
17
+ isPriceQuery: boolean,
18
+ ) {
19
+ let lowerTickBitmapLimit;
20
+ let upperTickBitmapLimit;
21
+
22
+ if (isPriceQuery) {
23
+ lowerTickBitmapLimit =
24
+ startTickBitmap - (TICK_BITMAP_BUFFER + TICK_BITMAP_TO_USE);
25
+ upperTickBitmapLimit =
26
+ startTickBitmap + (TICK_BITMAP_BUFFER + TICK_BITMAP_TO_USE);
27
+ } else {
28
+ lowerTickBitmapLimit = startTickBitmap - TICK_BITMAP_BUFFER;
29
+ upperTickBitmapLimit = startTickBitmap + TICK_BITMAP_BUFFER;
30
+ }
31
+
32
+ _require(
33
+ wordPos >= lowerTickBitmapLimit && wordPos <= upperTickBitmapLimit,
34
+ `wordPos is out of safe state tickBitmap request range: ${OUT_OF_RANGE_ERROR_POSTFIX}`,
35
+ { wordPos },
36
+ `wordPos >= LOWER_TICK_REQUEST_LIMIT && wordPos <= UPPER_TICK_REQUEST_LIMIT`,
37
+ );
38
+ }
39
+
40
+ export class TickBitMap {
41
+ static position(tick: bigint): [bigint, bigint] {
42
+ return [BigInt.asIntN(16, tick >> 8n), BigInt.asUintN(8, tick % 256n)];
43
+ }
44
+
45
+ static flipTick(
46
+ state: Pick<PoolState, 'startTickBitmap' | 'tickBitmap'>,
47
+ tick: bigint,
48
+ tickSpacing: bigint,
49
+ ) {
50
+ _require(
51
+ tick % tickSpacing === 0n,
52
+ '',
53
+ { tick, tickSpacing },
54
+ 'tick % tickSpacing == 0n,',
55
+ );
56
+ const [wordPos, bitPos] = TickBitMap.position(tick / tickSpacing);
57
+ const mask = 1n << bitPos;
58
+
59
+ // flipTick is used only in _updatePosition which is always state changing event
60
+ // Therefore it is never used in price query
61
+ isWordPosOut(wordPos, state.startTickBitmap, false);
62
+
63
+ const stringWordPos = wordPos.toString();
64
+ if (state.tickBitmap[stringWordPos] === undefined) {
65
+ state.tickBitmap[stringWordPos] = 0n;
66
+ }
67
+
68
+ state.tickBitmap[stringWordPos] ^= mask;
69
+ }
70
+
71
+ static nextInitializedTickWithinOneWord(
72
+ state: DeepReadonly<Pick<PoolState, 'startTickBitmap' | 'tickBitmap'>>,
73
+ tick: bigint,
74
+ tickSpacing: bigint,
75
+ lte: boolean,
76
+ isPriceQuery: boolean,
77
+ ): [bigint, boolean] {
78
+ let compressed = tick / tickSpacing;
79
+ if (tick < 0n && tick % tickSpacing != 0n) compressed--;
80
+
81
+ let next = 0n;
82
+ let initialized = false;
83
+
84
+ if (lte) {
85
+ const [wordPos, bitPos] = TickBitMap.position(compressed);
86
+ const mask = (1n << bitPos) - 1n + (1n << bitPos);
87
+
88
+ isWordPosOut(wordPos, state.startTickBitmap, isPriceQuery);
89
+ let tickBitmapValue = state.tickBitmap[wordPos.toString()];
90
+ tickBitmapValue = tickBitmapValue === undefined ? 0n : tickBitmapValue;
91
+
92
+ const masked = tickBitmapValue & mask;
93
+
94
+ initialized = masked != 0n;
95
+ next = initialized
96
+ ? (compressed -
97
+ BigInt.asIntN(24, bitPos - BitMath.mostSignificantBit(masked))) *
98
+ tickSpacing
99
+ : (compressed - BigInt.asIntN(24, bitPos)) * tickSpacing;
100
+ } else {
101
+ // start from the word of the next tick, since the current tick state doesn't matter
102
+ const [wordPos, bitPos] = TickBitMap.position(compressed + 1n);
103
+ const mask = ~((1n << bitPos) - 1n);
104
+
105
+ isWordPosOut(wordPos, state.startTickBitmap, isPriceQuery);
106
+ let tickBitmapValue = state.tickBitmap[wordPos.toString()];
107
+ tickBitmapValue = tickBitmapValue === undefined ? 0n : tickBitmapValue;
108
+
109
+ const masked = tickBitmapValue & mask;
110
+
111
+ initialized = masked != 0n;
112
+ next = initialized
113
+ ? (compressed +
114
+ 1n +
115
+ BigInt.asIntN(24, BitMath.leastSignificantBit(masked) - bitPos)) *
116
+ tickSpacing
117
+ : (compressed + 1n + BigInt.asIntN(24, BI_MAX_UINT8 - bitPos)) *
118
+ tickSpacing;
119
+ }
120
+
121
+ return [next, initialized];
122
+ }
123
+ }