@evvm/testnet-contracts 2.3.0 → 3.0.1
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.
- package/README.md +44 -24
- package/contracts/core/Core.sol +1392 -0
- package/contracts/core/lib/CoreStorage.sol +171 -0
- package/contracts/nameService/NameService.sol +613 -543
- package/contracts/nameService/lib/IdentityValidation.sol +15 -21
- package/contracts/p2pSwap/P2PSwap.sol +258 -145
- package/contracts/staking/Estimator.sol +25 -44
- package/contracts/staking/Staking.sol +284 -262
- package/contracts/treasury/Treasury.sol +40 -47
- package/contracts/treasuryTwoChains/TreasuryExternalChainStation.sol +585 -198
- package/contracts/treasuryTwoChains/TreasuryHostChainStation.sol +425 -174
- package/contracts/treasuryTwoChains/lib/PayloadUtils.sol +2 -4
- package/interfaces/{IEvvm.sol → ICore.sol} +58 -25
- package/interfaces/IEstimator.sol +1 -1
- package/interfaces/INameService.sol +46 -49
- package/interfaces/IP2PSwap.sol +16 -17
- package/interfaces/IStaking.sol +21 -17
- package/interfaces/ITreasury.sol +2 -1
- package/interfaces/ITreasuryExternalChainStation.sol +15 -9
- package/interfaces/ITreasuryHostChainStation.sol +14 -11
- package/interfaces/IUserValidator.sol +6 -0
- package/library/Erc191TestBuilder.sol +336 -471
- package/library/EvvmService.sol +27 -71
- package/library/errors/CoreError.sol +116 -0
- package/library/errors/CrossChainTreasuryError.sol +36 -0
- package/library/errors/NameServiceError.sol +79 -0
- package/library/errors/StakingError.sol +79 -0
- package/{contracts/treasury/lib/ErrorsLib.sol → library/errors/TreasuryError.sol} +9 -17
- package/library/structs/CoreStructs.sol +146 -0
- package/library/structs/ExternalChainStationStructs.sol +92 -0
- package/library/structs/HostChainStationStructs.sol +77 -0
- package/library/structs/NameServiceStructs.sol +47 -0
- package/library/structs/P2PSwapStructs.sol +127 -0
- package/library/structs/StakingStructs.sol +67 -0
- package/library/utils/AdvancedStrings.sol +62 -44
- package/library/utils/CAUtils.sol +29 -0
- package/library/utils/governance/Admin.sol +66 -0
- package/library/utils/governance/ProposalStructs.sol +49 -0
- package/library/utils/service/CoreExecution.sol +158 -0
- package/library/utils/service/StakingServiceUtils.sol +20 -37
- package/library/utils/signature/CoreHashUtils.sol +73 -0
- package/library/utils/signature/NameServiceHashUtils.sol +156 -0
- package/library/utils/signature/P2PSwapHashUtils.sol +65 -0
- package/library/utils/signature/StakingHashUtils.sol +41 -0
- package/library/utils/signature/TreasuryCrossChainHashUtils.sol +40 -0
- package/package.json +1 -1
- package/contracts/evvm/Evvm.sol +0 -1300
- package/contracts/evvm/lib/ErrorsLib.sol +0 -131
- package/contracts/evvm/lib/EvvmStorage.sol +0 -217
- package/contracts/evvm/lib/EvvmStructs.sol +0 -208
- package/contracts/evvm/lib/SignatureUtils.sol +0 -162
- package/contracts/nameService/lib/ErrorsLib.sol +0 -155
- package/contracts/nameService/lib/NameServiceStructs.sol +0 -125
- package/contracts/nameService/lib/SignatureUtils.sol +0 -420
- package/contracts/p2pSwap/lib/P2PSwapStructs.sol +0 -59
- package/contracts/p2pSwap/lib/SignatureUtils.sol +0 -98
- package/contracts/staking/lib/ErrorsLib.sol +0 -98
- package/contracts/staking/lib/SignatureUtils.sol +0 -105
- package/contracts/staking/lib/StakingStructs.sol +0 -106
- package/contracts/treasuryTwoChains/lib/ErrorsLib.sol +0 -48
- package/contracts/treasuryTwoChains/lib/ExternalChainStationStructs.sol +0 -80
- package/contracts/treasuryTwoChains/lib/HostChainStationStructs.sol +0 -87
- package/contracts/treasuryTwoChains/lib/SignatureUtils.sol +0 -79
- package/library/utils/GovernanceUtils.sol +0 -81
- package/library/utils/nonces/AsyncNonce.sol +0 -74
- package/library/utils/nonces/SyncNonce.sol +0 -71
- package/library/utils/service/EvvmPayments.sol +0 -144
|
@@ -2,33 +2,27 @@
|
|
|
2
2
|
// Full license terms available at: https://www.evvm.info/docs/EVVMNoncommercialLicense
|
|
3
3
|
|
|
4
4
|
pragma solidity ^0.8.0;
|
|
5
|
-
|
|
6
5
|
/**
|
|
7
|
-
* @title
|
|
6
|
+
* @title EVVM Identity Validation
|
|
8
7
|
* @author Mate labs
|
|
9
|
-
* @notice
|
|
10
|
-
* @dev
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
* Validation Types:
|
|
14
|
-
* - Username: Alphanumeric identifiers with specific length and format requirements
|
|
15
|
-
* - Email: Standard email format validation with prefix, domain, and TLD checks
|
|
16
|
-
* - Phone Number: Numeric phone numbers with length constraints
|
|
17
|
-
*
|
|
18
|
-
* Character Validation:
|
|
19
|
-
* - Uses ASCII byte ranges for precise character classification
|
|
20
|
-
* - Supports letters (A-Z, a-z), digits (0-9), and specific symbols
|
|
21
|
-
* - All checks performed without external dependencies for security
|
|
22
|
-
*
|
|
23
|
-
* @custom:scope Exclusive to NameService.sol contract
|
|
24
|
-
* @custom:security All functions are pure with no external calls
|
|
25
|
-
* @custom:gas-optimization Byte-level operations for maximum efficiency
|
|
8
|
+
* @notice Byte-level validation for usernames, phone numbers, and emails.
|
|
9
|
+
* @dev Optimized for gas efficiency. Rules: Usernames (4+ chars, start with letter),
|
|
10
|
+
* Phones (digit checks), Emails (structural structure).
|
|
26
11
|
*/
|
|
27
12
|
library IdentityValidation{
|
|
28
13
|
/**
|
|
29
|
-
* @notice Validates username format
|
|
30
|
-
* @dev Username must be
|
|
14
|
+
* @notice Validates username format per system rules
|
|
15
|
+
* @dev Username must be 4+ chars, start with letter,
|
|
16
|
+
* contain only letters/digits
|
|
17
|
+
*
|
|
18
|
+
* Validation Rules:
|
|
19
|
+
* - Minimum length: 4 characters
|
|
20
|
+
* - Must start with a letter (A-Z or a-z)
|
|
21
|
+
* - Can only contain letters and digits
|
|
22
|
+
* - No special characters or spaces allowed
|
|
23
|
+
*
|
|
31
24
|
* @param username The username string to validate
|
|
25
|
+
* @return True if valid username format, false otherwise
|
|
32
26
|
*/
|
|
33
27
|
function isValidUsername(string memory username) internal pure returns (bool) {
|
|
34
28
|
bytes memory usernameBytes = bytes(username);
|
|
@@ -2,6 +2,22 @@
|
|
|
2
2
|
// Full license terms available at: https://www.evvm.org/docs/EVVMNoncommercialLicense
|
|
3
3
|
|
|
4
4
|
pragma solidity ^0.8.0;
|
|
5
|
+
|
|
6
|
+
import {
|
|
7
|
+
P2PSwapHashUtils as Hash
|
|
8
|
+
} from "@evvm/testnet-contracts/library/utils/signature/P2PSwapHashUtils.sol";
|
|
9
|
+
import {
|
|
10
|
+
P2PSwapStructs as Structs
|
|
11
|
+
} from "@evvm/testnet-contracts/library/structs/P2PSwapStructs.sol";
|
|
12
|
+
|
|
13
|
+
import {Staking} from "@evvm/testnet-contracts/contracts/staking/Staking.sol";
|
|
14
|
+
import {EvvmService} from "@evvm/testnet-contracts/library/EvvmService.sol";
|
|
15
|
+
import {CoreStructs} from "@evvm/testnet-contracts/interfaces/ICore.sol";
|
|
16
|
+
|
|
17
|
+
import {
|
|
18
|
+
AdvancedStrings
|
|
19
|
+
} from "@evvm/testnet-contracts/library/utils/AdvancedStrings.sol";
|
|
20
|
+
|
|
5
21
|
/**
|
|
6
22
|
/$$$$$$$ /$$$$$$ /$$$$$$$ /$$$$$$
|
|
7
23
|
| $$__ $$/$$__ $| $$__ $$/$$__ $$
|
|
@@ -15,38 +31,14 @@ pragma solidity ^0.8.0;
|
|
|
15
31
|
| $$
|
|
16
32
|
|__/
|
|
17
33
|
|
|
18
|
-
* @title P2P Swap
|
|
34
|
+
* @title EVVM P2P Swap
|
|
19
35
|
* @author Mate labs
|
|
20
|
-
* @notice Peer-to-peer decentralized exchange for token trading within
|
|
21
|
-
* @dev
|
|
22
|
-
*
|
|
23
|
-
* and fixed fee models with time-delayed governance for parameter updates.
|
|
24
|
-
*
|
|
25
|
-
* Key Features:
|
|
26
|
-
* - Dynamic market creation for any token pair
|
|
27
|
-
* - Order management (create, cancel, execute)
|
|
28
|
-
* - Configurable fee structure with multi-party distribution
|
|
29
|
-
* - Service staking capabilities via StakingServiceHooks inheritance
|
|
30
|
-
* - ERC-191 signature verification for all operations
|
|
31
|
-
* - Time-delayed administrative governance
|
|
32
|
-
*
|
|
33
|
-
* Fee Distribution:
|
|
34
|
-
* - Seller: 50% (configurable)
|
|
35
|
-
* - Service: 40% (configurable)
|
|
36
|
-
* - Staker Rewards: 10% (configurable)
|
|
36
|
+
* @notice Peer-to-peer decentralized exchange for token trading within EVVM.
|
|
37
|
+
* @dev Supports order book-style trading with customizable fee models.
|
|
38
|
+
* Integrates with Core.sol for asset locking and settlements, and Staking.sol for validator rewards.
|
|
37
39
|
*/
|
|
38
40
|
|
|
39
|
-
|
|
40
|
-
import {SignatureUtils} from "@evvm/testnet-contracts/contracts/p2pSwap/lib/SignatureUtils.sol";
|
|
41
|
-
import {AdvancedStrings} from "@evvm/testnet-contracts/library/utils/AdvancedStrings.sol";
|
|
42
|
-
import {P2PSwapStructs} from "@evvm/testnet-contracts/contracts/p2pSwap/lib/P2PSwapStructs.sol";
|
|
43
|
-
import {EvvmStructs} from "@evvm/testnet-contracts/interfaces/IEvvm.sol";
|
|
44
|
-
import {EvvmService} from "@evvm/testnet-contracts/library/EvvmService.sol";
|
|
45
|
-
|
|
46
|
-
contract P2PSwap is
|
|
47
|
-
EvvmService,
|
|
48
|
-
P2PSwapStructs
|
|
49
|
-
{
|
|
41
|
+
contract P2PSwap is EvvmService, Structs {
|
|
50
42
|
address owner;
|
|
51
43
|
address owner_proposal;
|
|
52
44
|
uint256 owner_timeToAccept;
|
|
@@ -83,12 +75,10 @@ contract P2PSwap is
|
|
|
83
75
|
mapping(address => uint256) balancesOfContract;
|
|
84
76
|
|
|
85
77
|
constructor(
|
|
86
|
-
address
|
|
78
|
+
address _coreAddress,
|
|
87
79
|
address _stakingAddress,
|
|
88
80
|
address _owner
|
|
89
|
-
)
|
|
90
|
-
EvvmService(_evvmAddress, _stakingAddress)
|
|
91
|
-
{
|
|
81
|
+
) EvvmService(_coreAddress, _stakingAddress) {
|
|
92
82
|
owner = _owner;
|
|
93
83
|
maxLimitFillFixedFee = 0.001 ether;
|
|
94
84
|
percentageFee = 500;
|
|
@@ -99,40 +89,49 @@ contract P2PSwap is
|
|
|
99
89
|
});
|
|
100
90
|
}
|
|
101
91
|
|
|
92
|
+
/**
|
|
93
|
+
* @notice Creates a new limit order in a specific trading market.
|
|
94
|
+
* @dev Locks tokenA in Core.sol and opens an order slot.
|
|
95
|
+
* Markets are automatically created for new token pairs.
|
|
96
|
+
* @param user Seller address.
|
|
97
|
+
* @param metadata Order details (tokens, amounts, nonce).
|
|
98
|
+
* @param signature Seller's authorization signature.
|
|
99
|
+
* @param priorityFeePay Optional priority fee for the executor.
|
|
100
|
+
* @param noncePay Nonce for the Core payment (locks tokenA).
|
|
101
|
+
* @param signaturePay Signature for the Core payment.
|
|
102
|
+
* @return market The ID of the market.
|
|
103
|
+
* @return orderId The ID of the order within that market.
|
|
104
|
+
*/
|
|
102
105
|
function makeOrder(
|
|
103
106
|
address user,
|
|
104
107
|
MetadataMakeOrder memory metadata,
|
|
105
108
|
bytes memory signature,
|
|
106
|
-
uint256
|
|
107
|
-
uint256
|
|
108
|
-
|
|
109
|
-
bytes memory _signature_Evvm
|
|
109
|
+
uint256 priorityFeePay,
|
|
110
|
+
uint256 noncePay,
|
|
111
|
+
bytes memory signaturePay
|
|
110
112
|
) external returns (uint256 market, uint256 orderId) {
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
user,
|
|
115
|
-
metadata.nonce,
|
|
113
|
+
core.validateAndConsumeNonce(
|
|
114
|
+
user,
|
|
115
|
+
Hash.hashDataForMakeOrder(
|
|
116
116
|
metadata.tokenA,
|
|
117
117
|
metadata.tokenB,
|
|
118
118
|
metadata.amountA,
|
|
119
|
-
metadata.amountB
|
|
120
|
-
|
|
121
|
-
)
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
verifyAsyncNonce(user, metadata.nonce);
|
|
119
|
+
metadata.amountB
|
|
120
|
+
),
|
|
121
|
+
address(0),
|
|
122
|
+
metadata.nonce,
|
|
123
|
+
true,
|
|
124
|
+
signature
|
|
125
|
+
);
|
|
127
126
|
|
|
128
127
|
requestPay(
|
|
129
128
|
user,
|
|
130
129
|
metadata.tokenA,
|
|
131
130
|
metadata.amountA,
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
131
|
+
priorityFeePay,
|
|
132
|
+
noncePay,
|
|
133
|
+
true,
|
|
134
|
+
signaturePay
|
|
136
135
|
);
|
|
137
136
|
|
|
138
137
|
market = findMarket(metadata.tokenA, metadata.tokenB);
|
|
@@ -163,56 +162,85 @@ contract P2PSwap is
|
|
|
163
162
|
metadata.amountB
|
|
164
163
|
);
|
|
165
164
|
|
|
166
|
-
if (
|
|
167
|
-
if (
|
|
165
|
+
if (core.isAddressStaker(msg.sender)) {
|
|
166
|
+
if (priorityFeePay > 0) {
|
|
168
167
|
// send the executor the priorityFee
|
|
169
|
-
makeCaPay(msg.sender, metadata.tokenA,
|
|
168
|
+
makeCaPay(msg.sender, metadata.tokenA, priorityFeePay);
|
|
170
169
|
}
|
|
171
170
|
}
|
|
172
171
|
|
|
173
172
|
// send some mate token reward to the executor (independent of the priorityFee the user attached)
|
|
174
|
-
_rewardExecutor(msg.sender,
|
|
175
|
-
|
|
176
|
-
markAsyncNonceAsUsed(user, metadata.nonce);
|
|
173
|
+
_rewardExecutor(msg.sender, priorityFeePay > 0 ? 3 : 2);
|
|
177
174
|
}
|
|
178
175
|
|
|
176
|
+
/**
|
|
177
|
+
* @notice Cancels existing order and refunds locked tokens
|
|
178
|
+
* @dev Validates ownership, refunds tokenA, deletes order
|
|
179
|
+
*
|
|
180
|
+
* Cancellation Flow:
|
|
181
|
+
* 1. Validates signature via Core.sol
|
|
182
|
+
* 2. Validates user is order owner
|
|
183
|
+
* 3. Processes optional priority fee
|
|
184
|
+
* 4. Refunds locked tokenA to user
|
|
185
|
+
* 5. Deletes order (sets seller to address(0))
|
|
186
|
+
* 6. Rewards staker if applicable
|
|
187
|
+
*
|
|
188
|
+
* Core.sol Integration:
|
|
189
|
+
* - Validates signature with State.validateAndConsumeNonce
|
|
190
|
+
* - Uses async nonce (isAsyncExec = true)
|
|
191
|
+
* - Hash includes tokenA, tokenB, orderId
|
|
192
|
+
* - Prevents replay attacks and double cancellation
|
|
193
|
+
*
|
|
194
|
+
* Core.sol Integration:
|
|
195
|
+
* - Refunds tokenA via makeCaPay (order.amountA)
|
|
196
|
+
* - Priority fee via requestPay (if > 0)
|
|
197
|
+
* - Staker reward: 2-3x MATE via _rewardExecutor
|
|
198
|
+
* - makeCaPay handles staker priority fee distribution
|
|
199
|
+
*
|
|
200
|
+
* Security:
|
|
201
|
+
* - Only order owner can cancel
|
|
202
|
+
* - Atomic refund + deletion
|
|
203
|
+
* - Market slot becomes available for reuse
|
|
204
|
+
*
|
|
205
|
+
* @param user Address that owns the order
|
|
206
|
+
* @param metadata Cancel details (tokens, orderId, nonce)
|
|
207
|
+
* @param priorityFeePay Optional priority fee for staker
|
|
208
|
+
* @param noncePay Nonce for EVVM payment transaction
|
|
209
|
+
* @param signaturePay Signature for EVVM payment
|
|
210
|
+
*/
|
|
179
211
|
function cancelOrder(
|
|
180
212
|
address user,
|
|
181
213
|
MetadataCancelOrder memory metadata,
|
|
182
|
-
uint256
|
|
183
|
-
uint256
|
|
184
|
-
|
|
185
|
-
bytes memory _signature_Evvm
|
|
214
|
+
uint256 priorityFeePay,
|
|
215
|
+
uint256 noncePay,
|
|
216
|
+
bytes memory signaturePay
|
|
186
217
|
) external {
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
user,
|
|
191
|
-
metadata.nonce,
|
|
218
|
+
core.validateAndConsumeNonce(
|
|
219
|
+
user,
|
|
220
|
+
Hash.hashDataForCancelOrder(
|
|
192
221
|
metadata.tokenA,
|
|
193
222
|
metadata.tokenB,
|
|
194
|
-
metadata.orderId
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
223
|
+
metadata.orderId
|
|
224
|
+
),
|
|
225
|
+
metadata.originExecutor,
|
|
226
|
+
metadata.nonce,
|
|
227
|
+
true,
|
|
228
|
+
metadata.signature
|
|
229
|
+
);
|
|
200
230
|
|
|
201
231
|
uint256 market = findMarket(metadata.tokenA, metadata.tokenB);
|
|
202
232
|
|
|
203
|
-
verifyAsyncNonce(user, metadata.nonce);
|
|
204
|
-
|
|
205
233
|
_validateOrderOwnership(market, metadata.orderId, user);
|
|
206
234
|
|
|
207
|
-
if (
|
|
235
|
+
if (priorityFeePay > 0) {
|
|
208
236
|
requestPay(
|
|
209
237
|
user,
|
|
210
238
|
MATE_TOKEN_ADDRESS,
|
|
211
239
|
0,
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
240
|
+
priorityFeePay,
|
|
241
|
+
noncePay,
|
|
242
|
+
true,
|
|
243
|
+
signaturePay
|
|
216
244
|
);
|
|
217
245
|
}
|
|
218
246
|
|
|
@@ -224,40 +252,77 @@ contract P2PSwap is
|
|
|
224
252
|
|
|
225
253
|
_clearOrderAndUpdateMarket(market, metadata.orderId);
|
|
226
254
|
|
|
227
|
-
if (
|
|
228
|
-
makeCaPay(msg.sender, MATE_TOKEN_ADDRESS,
|
|
255
|
+
if (core.isAddressStaker(msg.sender) && priorityFeePay > 0) {
|
|
256
|
+
makeCaPay(msg.sender, MATE_TOKEN_ADDRESS, priorityFeePay);
|
|
229
257
|
}
|
|
230
|
-
_rewardExecutor(msg.sender,
|
|
231
|
-
|
|
232
|
-
markAsyncNonceAsUsed(user, metadata.nonce);
|
|
258
|
+
_rewardExecutor(msg.sender, priorityFeePay > 0 ? 3 : 2);
|
|
233
259
|
}
|
|
234
260
|
|
|
261
|
+
/**
|
|
262
|
+
* @notice Fills order using proportional fee model
|
|
263
|
+
* @dev Fee = amountB * percentageFee / 10,000
|
|
264
|
+
*
|
|
265
|
+
* Proportional Fee Execution Flow:
|
|
266
|
+
* 1. Validates signature via Core.sol
|
|
267
|
+
* 2. Validates market and order exist
|
|
268
|
+
* 3. Calculates fee: (amountB * percentageFee) / 10,000
|
|
269
|
+
* 4. Validates amountOfTokenBToFill >= amountB + fee
|
|
270
|
+
* 5. Collects tokenB + fee via Evvm.requestPay
|
|
271
|
+
* 6. Handles overpayment refund if any
|
|
272
|
+
* 7. Distributes payments (seller, service, staker)
|
|
273
|
+
* 8. Transfers tokenA to buyer via Evvm.makeCaPay
|
|
274
|
+
* 9. Rewards staker (4-5x MATE)
|
|
275
|
+
* 10. Deletes order
|
|
276
|
+
*
|
|
277
|
+
* Core.sol Integration:
|
|
278
|
+
* - Validates signature with State.validateAndConsumeNonce
|
|
279
|
+
* - Uses async nonce (isAsyncExec = true)
|
|
280
|
+
* - Hash includes tokenA, tokenB, orderId
|
|
281
|
+
* - Prevents double filling
|
|
282
|
+
*
|
|
283
|
+
* Core.sol Integration:
|
|
284
|
+
* - Collects tokenB via requestPay (amountB + fee)
|
|
285
|
+
* - Distributes via makeDisperseCaPay:
|
|
286
|
+
* * Seller: amountB + (fee * seller%)
|
|
287
|
+
* * Staker: priorityFee + (fee * staker%)
|
|
288
|
+
* * Service: fee * service% (accumulated)
|
|
289
|
+
* - Transfers tokenA to buyer via makeCaPay
|
|
290
|
+
* - Staker reward: 4-5x MATE via _rewardExecutor
|
|
291
|
+
*
|
|
292
|
+
* Fee Calculation:
|
|
293
|
+
* - Base: amountB (order requirement)
|
|
294
|
+
* - Fee: (amountB * percentageFee) / 10,000
|
|
295
|
+
* - Total: amountB + fee
|
|
296
|
+
* - Example: 5% fee = 500 / 10,000
|
|
297
|
+
*
|
|
298
|
+
* @param user Address filling the order (buyer)
|
|
299
|
+
* @param metadata Dispatch details (tokens, orderId, amount)
|
|
300
|
+
* @param priorityFeePay Optional priority fee for staker
|
|
301
|
+
* @param noncePay Nonce for EVVM payment transaction
|
|
302
|
+
* @param signaturePay Signature for EVVM payment
|
|
303
|
+
*/
|
|
235
304
|
function dispatchOrder_fillPropotionalFee(
|
|
236
305
|
address user,
|
|
237
306
|
MetadataDispatchOrder memory metadata,
|
|
238
|
-
uint256
|
|
239
|
-
uint256
|
|
240
|
-
|
|
241
|
-
bytes memory _signature_Evvm
|
|
307
|
+
uint256 priorityFeePay,
|
|
308
|
+
uint256 noncePay,
|
|
309
|
+
bytes memory signaturePay
|
|
242
310
|
) external {
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
user,
|
|
247
|
-
metadata.nonce,
|
|
311
|
+
core.validateAndConsumeNonce(
|
|
312
|
+
user,
|
|
313
|
+
Hash.hashDataForDispatchOrder(
|
|
248
314
|
metadata.tokenA,
|
|
249
315
|
metadata.tokenB,
|
|
250
|
-
metadata.orderId
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
316
|
+
metadata.orderId
|
|
317
|
+
),
|
|
318
|
+
metadata.originExecutor,
|
|
319
|
+
metadata.nonce,
|
|
320
|
+
true,
|
|
321
|
+
metadata.signature
|
|
322
|
+
);
|
|
256
323
|
|
|
257
324
|
uint256 market = findMarket(metadata.tokenA, metadata.tokenB);
|
|
258
325
|
|
|
259
|
-
verifyAsyncNonce(user, metadata.nonce);
|
|
260
|
-
|
|
261
326
|
Order storage order = _validateMarketAndOrder(market, metadata.orderId);
|
|
262
327
|
|
|
263
328
|
uint256 fee = calculateFillPropotionalFee(order.amountB);
|
|
@@ -271,10 +336,10 @@ contract P2PSwap is
|
|
|
271
336
|
user,
|
|
272
337
|
metadata.tokenB,
|
|
273
338
|
metadata.amountOfTokenBToFill,
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
339
|
+
priorityFeePay,
|
|
340
|
+
noncePay,
|
|
341
|
+
true,
|
|
342
|
+
signaturePay
|
|
278
343
|
);
|
|
279
344
|
|
|
280
345
|
// si es mas del fee + el monto de la orden hacemos caPay al usuario del sobranate
|
|
@@ -292,7 +357,7 @@ contract P2PSwap is
|
|
|
292
357
|
fee,
|
|
293
358
|
order.seller,
|
|
294
359
|
msg.sender,
|
|
295
|
-
|
|
360
|
+
priorityFeePay
|
|
296
361
|
);
|
|
297
362
|
|
|
298
363
|
// pay user with token A
|
|
@@ -301,36 +366,86 @@ contract P2PSwap is
|
|
|
301
366
|
_rewardExecutor(msg.sender, didRefund ? 5 : 4);
|
|
302
367
|
|
|
303
368
|
_clearOrderAndUpdateMarket(market, metadata.orderId);
|
|
304
|
-
markAsyncNonceAsUsed(user, metadata.nonce);
|
|
305
369
|
}
|
|
306
370
|
|
|
371
|
+
/**
|
|
372
|
+
* @notice Fills order using fixed/capped fee model
|
|
373
|
+
* @dev Fee = min(proportionalFee, maxLimitFillFixedFee)
|
|
374
|
+
* with -10% tolerance
|
|
375
|
+
*
|
|
376
|
+
* Fixed Fee Execution Flow:
|
|
377
|
+
* 1. Validates signature via Core.sol
|
|
378
|
+
* 2. Validates market and order exist
|
|
379
|
+
* 3. Calculates capped fee and 10% tolerance
|
|
380
|
+
* 4. Validates amountOfTokenBToFill >= amountB + fee - 10%
|
|
381
|
+
* 5. Collects tokenB + amount via Evvm.requestPay
|
|
382
|
+
* 6. Calculates final fee based on actual payment
|
|
383
|
+
* 7. Handles overpayment refund if any
|
|
384
|
+
* 8. Distributes payments (seller, service, staker)
|
|
385
|
+
* 9. Transfers tokenA to buyer via Evvm.makeCaPay
|
|
386
|
+
* 10. Rewards staker (4-5x MATE)
|
|
387
|
+
* 11. Deletes order
|
|
388
|
+
*
|
|
389
|
+
* Core.sol Integration:
|
|
390
|
+
* - Validates signature with State.validateAndConsumeNonce
|
|
391
|
+
* - Uses async nonce (isAsyncExec = true)
|
|
392
|
+
* - Hash includes tokenA, tokenB, orderId
|
|
393
|
+
* - Prevents double filling
|
|
394
|
+
*
|
|
395
|
+
* Core.sol Integration:
|
|
396
|
+
* - Collects tokenB via requestPay (variable amount)
|
|
397
|
+
* - Distributes via makeDisperseCaPay:
|
|
398
|
+
* * Seller: amountB + (finalFee * seller%)
|
|
399
|
+
* * Staker: priorityFee + (finalFee * staker%)
|
|
400
|
+
* * Service: finalFee * service% (accumulated)
|
|
401
|
+
* - Transfers tokenA to buyer via makeCaPay
|
|
402
|
+
* - Staker reward: 4-5x MATE via _rewardExecutor
|
|
403
|
+
*
|
|
404
|
+
* Fee Calculation:
|
|
405
|
+
* - Base: amountB (order requirement)
|
|
406
|
+
* - ProportionalFee: (amountB * percentageFee) / 10,000
|
|
407
|
+
* - Fee: min(proportionalFee, maxLimitFillFixedFee)
|
|
408
|
+
* - Tolerance: fee * 10% (fee10)
|
|
409
|
+
* - MinRequired: amountB + fee - fee10
|
|
410
|
+
* - FullRequired: amountB + fee
|
|
411
|
+
* - FinalFee: Based on actual payment amount
|
|
412
|
+
*
|
|
413
|
+
* Tolerance Range:
|
|
414
|
+
* - Accepts payment between [amountB + 90% fee] and
|
|
415
|
+
* [amountB + 100% fee]
|
|
416
|
+
* - Calculates actual fee from payment received
|
|
417
|
+
* - Enables flexible fee payment for users
|
|
418
|
+
*
|
|
419
|
+
* @param user Address filling the order (buyer)
|
|
420
|
+
* @param metadata Dispatch details (tokens, orderId, amount)
|
|
421
|
+
* @param priorityFeePay Optional priority fee for staker
|
|
422
|
+
* @param noncePay Nonce for EVVM payment transaction
|
|
423
|
+
* @param signaturePay Signature for EVVM payment
|
|
424
|
+
* @param maxFillFixedFee Max fee cap (for testing)
|
|
425
|
+
*/
|
|
307
426
|
function dispatchOrder_fillFixedFee(
|
|
308
427
|
address user,
|
|
309
428
|
MetadataDispatchOrder memory metadata,
|
|
310
|
-
uint256
|
|
311
|
-
uint256
|
|
312
|
-
|
|
313
|
-
bytes memory _signature_Evvm,
|
|
429
|
+
uint256 priorityFeePay,
|
|
430
|
+
uint256 noncePay,
|
|
431
|
+
bytes memory signaturePay,
|
|
314
432
|
uint256 maxFillFixedFee ///@dev for testing purposes
|
|
315
433
|
) external {
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
user,
|
|
320
|
-
metadata.nonce,
|
|
434
|
+
core.validateAndConsumeNonce(
|
|
435
|
+
user,
|
|
436
|
+
Hash.hashDataForDispatchOrder(
|
|
321
437
|
metadata.tokenA,
|
|
322
438
|
metadata.tokenB,
|
|
323
|
-
metadata.orderId
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
439
|
+
metadata.orderId
|
|
440
|
+
),
|
|
441
|
+
metadata.originExecutor,
|
|
442
|
+
metadata.nonce,
|
|
443
|
+
true,
|
|
444
|
+
metadata.signature
|
|
445
|
+
);
|
|
329
446
|
|
|
330
447
|
uint256 market = findMarket(metadata.tokenA, metadata.tokenB);
|
|
331
448
|
|
|
332
|
-
verifyAsyncNonce(user, metadata.nonce);
|
|
333
|
-
|
|
334
449
|
Order storage order = _validateMarketAndOrder(market, metadata.orderId);
|
|
335
450
|
|
|
336
451
|
(uint256 fee, uint256 fee10) = calculateFillFixedFee(
|
|
@@ -349,10 +464,10 @@ contract P2PSwap is
|
|
|
349
464
|
user,
|
|
350
465
|
metadata.tokenB,
|
|
351
466
|
metadata.amountOfTokenBToFill,
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
467
|
+
priorityFeePay,
|
|
468
|
+
noncePay,
|
|
469
|
+
true,
|
|
470
|
+
signaturePay
|
|
356
471
|
);
|
|
357
472
|
|
|
358
473
|
uint256 finalFee = _calculateFinalFee(
|
|
@@ -377,7 +492,7 @@ contract P2PSwap is
|
|
|
377
492
|
finalFee,
|
|
378
493
|
order.seller,
|
|
379
494
|
msg.sender,
|
|
380
|
-
|
|
495
|
+
priorityFeePay
|
|
381
496
|
);
|
|
382
497
|
|
|
383
498
|
makeCaPay(user, metadata.tokenA, order.amountA);
|
|
@@ -385,7 +500,6 @@ contract P2PSwap is
|
|
|
385
500
|
_rewardExecutor(msg.sender, didRefund ? 5 : 4);
|
|
386
501
|
|
|
387
502
|
_clearOrderAndUpdateMarket(market, metadata.orderId);
|
|
388
|
-
markAsyncNonceAsUsed(user, metadata.nonce);
|
|
389
503
|
}
|
|
390
504
|
|
|
391
505
|
function calculateFillPropotionalFee(
|
|
@@ -465,10 +579,7 @@ contract P2PSwap is
|
|
|
465
579
|
uint256 orderId,
|
|
466
580
|
address user
|
|
467
581
|
) internal view {
|
|
468
|
-
if (
|
|
469
|
-
market == 0 ||
|
|
470
|
-
ordersInsideMarket[market][orderId].seller != user
|
|
471
|
-
) {
|
|
582
|
+
if (market == 0 || ordersInsideMarket[market][orderId].seller != user) {
|
|
472
583
|
revert("Invalid order");
|
|
473
584
|
}
|
|
474
585
|
}
|
|
@@ -479,11 +590,11 @@ contract P2PSwap is
|
|
|
479
590
|
* @param multiplier The reward multiplier (2, 3, 4, or 5)
|
|
480
591
|
*/
|
|
481
592
|
function _rewardExecutor(address executor, uint256 multiplier) internal {
|
|
482
|
-
if (
|
|
593
|
+
if (core.isAddressStaker(executor)) {
|
|
483
594
|
makeCaPay(
|
|
484
595
|
executor,
|
|
485
596
|
MATE_TOKEN_ADDRESS,
|
|
486
|
-
|
|
597
|
+
core.getRewardAmount() * multiplier
|
|
487
598
|
);
|
|
488
599
|
}
|
|
489
600
|
}
|
|
@@ -539,14 +650,16 @@ contract P2PSwap is
|
|
|
539
650
|
address executor,
|
|
540
651
|
uint256 priorityFee
|
|
541
652
|
) internal {
|
|
542
|
-
uint256 sellerAmount = orderAmount +
|
|
543
|
-
|
|
653
|
+
uint256 sellerAmount = orderAmount +
|
|
654
|
+
((fee * rewardPercentage.seller) / 10_000);
|
|
655
|
+
uint256 executorAmount = priorityFee +
|
|
656
|
+
((fee * rewardPercentage.mateStaker) / 10_000);
|
|
544
657
|
|
|
545
|
-
|
|
546
|
-
memory toData = new
|
|
658
|
+
CoreStructs.DisperseCaPayMetadata[]
|
|
659
|
+
memory toData = new CoreStructs.DisperseCaPayMetadata[](2);
|
|
547
660
|
|
|
548
|
-
toData[0] =
|
|
549
|
-
toData[1] =
|
|
661
|
+
toData[0] = CoreStructs.DisperseCaPayMetadata(sellerAmount, seller);
|
|
662
|
+
toData[1] = CoreStructs.DisperseCaPayMetadata(executorAmount, executor);
|
|
550
663
|
|
|
551
664
|
balancesOfContract[token] += (fee * rewardPercentage.service) / 10_000;
|
|
552
665
|
|