@percolatorct/sdk 1.0.0-beta.9 → 2.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/dist/index.js CHANGED
@@ -1,13 +1,16 @@
1
1
  // src/abi/encode.ts
2
2
  import { PublicKey } from "@solana/web3.js";
3
+ var U8_MAX = 255;
4
+ var U16_MAX = 65535;
5
+ var U32_MAX = 4294967295;
3
6
  function encU8(val) {
4
- if (!Number.isInteger(val) || val < 0 || val > 255) {
7
+ if (!Number.isInteger(val) || val < 0 || val > U8_MAX) {
5
8
  throw new Error(`encU8: value out of range (0..255), got ${val}`);
6
9
  }
7
10
  return new Uint8Array([val]);
8
11
  }
9
12
  function encU16(val) {
10
- if (!Number.isInteger(val) || val < 0 || val > 65535) {
13
+ if (!Number.isInteger(val) || val < 0 || val > U16_MAX) {
11
14
  throw new Error(`encU16: value out of range (0..65535), got ${val}`);
12
15
  }
13
16
  const buf = new Uint8Array(2);
@@ -15,7 +18,7 @@ function encU16(val) {
15
18
  return buf;
16
19
  }
17
20
  function encU32(val) {
18
- if (!Number.isInteger(val) || val < 0 || val > 4294967295) {
21
+ if (!Number.isInteger(val) || val < 0 || val > U32_MAX) {
19
22
  throw new Error(`encU32: value out of range (0..4294967295), got ${val}`);
20
23
  }
21
24
  const buf = new Uint8Array(4);
@@ -93,7 +96,6 @@ function concatBytes(...arrays) {
93
96
  }
94
97
 
95
98
  // src/abi/instructions.ts
96
- var MAX_ORACLE_PRICE = 1000000000000n;
97
99
  var IX_TAG = {
98
100
  InitMarket: 0,
99
101
  InitUser: 1,
@@ -111,8 +113,7 @@ var IX_TAG = {
111
113
  CloseSlab: 13,
112
114
  UpdateConfig: 14,
113
115
  SetMaintenanceFee: 15,
114
- SetOracleAuthority: 16,
115
- PushOraclePrice: 17,
116
+ // 16, 17 — removed in v1.0.0-beta.29 (Phase G admin-push oracle removal)
116
117
  SetOraclePriceCap: 18,
117
118
  ResolveMarket: 19,
118
119
  WithdrawInsurance: 20,
@@ -131,17 +132,12 @@ var IX_TAG = {
131
132
  ReclaimEmptyAccount: 25,
132
133
  SettleAccount: 26,
133
134
  // Tags 27-28: on-chain = DepositFeeCredits/ConvertReleasedPnl.
134
- // Legacy aliases (PauseMarket/UnpauseMarket) kept — those instructions don't exist on-chain.
135
135
  DepositFeeCredits: 27,
136
- /** @deprecated No on-chain PauseMarket instruction */
137
- PauseMarket: 27,
138
136
  ConvertReleasedPnl: 28,
139
- /** @deprecated No on-chain UnpauseMarket instruction */
140
- UnpauseMarket: 28,
141
137
  // Tags 29-30: on-chain = ResolvePermissionless/ForceCloseResolved.
142
138
  ResolvePermissionless: 29,
143
- /** @deprecated Use ResolvePermissionless */
144
- AcceptAdmin: 29,
139
+ // Note: `AcceptAdmin` used to be a @deprecated alias for tag 29; removed in
140
+ // beta.27 because AcceptAdmin is now a real instruction at tag 82 (Phase E).
145
141
  ForceCloseResolved: 30,
146
142
  // Tag 31: gap (no decode arm on-chain)
147
143
  SetPythOracle: 32,
@@ -188,8 +184,7 @@ var IX_TAG = {
188
184
  AttestCrossMargin: 55,
189
185
  /** PERC-622: Advance oracle phase (permissionless crank) */
190
186
  AdvanceOraclePhase: 56,
191
- /** PERC-623: Top up a market's keeper fund (permissionless) */
192
- TopUpKeeperFund: 57,
187
+ // 57: removed (keeper fund)
193
188
  /** PERC-629: Slash a market creator's deposit (permissionless) */
194
189
  SlashCreationDeposit: 58,
195
190
  /** PERC-628: Initialize the global shared vault (admin) */
@@ -225,9 +220,36 @@ var IX_TAG = {
225
220
  /** PERC-SetDexPool: Pin admin-approved DEX pool address for a HYPERP market (admin). */
226
221
  SetDexPool: 74,
227
222
  /** CPI to the matcher program to initialize a matcher context account for an LP slot. Admin-only. */
228
- InitMatcherCtx: 75
223
+ InitMatcherCtx: 75,
224
+ /** PauseMarket (tag 76): admin emergency pause. Blocks Trade/Deposit/Withdraw/InitUser. */
225
+ PauseMarket: 76,
226
+ /** UnpauseMarket (tag 77): admin unpause. Re-enables all operations. */
227
+ UnpauseMarket: 77,
228
+ /** PERC-305 / SECURITY(H-4): Set PnL cap for ADL pre-check (admin only). */
229
+ SetMaxPnlCap: 78,
230
+ /** PERC-309: Set OI cap multiplier for LP withdrawal limits (admin only). Packed u64. */
231
+ SetOiCapMultiplier: 79,
232
+ /** PERC-314: Set dispute params (window_slots + bond_amount, admin only). */
233
+ SetDisputeParams: 80,
234
+ /** PERC-315: Set LP collateral params (enabled + ltv_bps, admin only). */
235
+ SetLpCollateralParams: 81,
236
+ /** Phase E (2026-04-17): Accept a pending admin transfer. Signer must match pending_admin. */
237
+ AcceptAdmin: 82,
238
+ /**
239
+ * v12.18.x 4-way authority split (added 2026-04-22, wrapper 86ea41f).
240
+ * Unified mutator for admin/hyperp_mark/insurance/insurance_operator.
241
+ * Wrapper handler: src/percolator.rs:6876.
242
+ */
243
+ UpdateAuthority: 83
244
+ // 78: removed (keeper fund)
229
245
  };
230
246
  Object.freeze(IX_TAG);
247
+ function removedInstruction(name, tag, replacement) {
248
+ const suffix = replacement ? ` Use ${replacement} instead.` : "";
249
+ throw new Error(
250
+ `${name} (tag ${tag}) is not accepted by the deployed wrapper program.${suffix}`
251
+ );
252
+ }
231
253
  var HEX_RE = /^[0-9a-fA-F]{64}$/;
232
254
  function encodeFeedId(feedId) {
233
255
  const hex = feedId.startsWith("0x") ? feedId.slice(2) : feedId;
@@ -248,9 +270,29 @@ function encodeFeedId(feedId) {
248
270
  }
249
271
  return bytes;
250
272
  }
251
- var INIT_MARKET_DATA_LEN = 352;
273
+ var INIT_MARKET_BASE_LEN = 304;
274
+ var INIT_MARKET_EXTENDED_TAIL_LEN = 66;
275
+ function extendedTailHasNonZero(t) {
276
+ const toBigInt = (v) => typeof v === "string" ? BigInt(v) : v;
277
+ return t.insuranceWithdrawMaxBps !== 0 || toBigInt(t.insuranceWithdrawCooldownSlots) !== 0n || toBigInt(t.permissionlessResolveStaleSlots) !== 0n || toBigInt(t.fundingHorizonSlots) !== 0n || toBigInt(t.fundingKBps) !== 0n || toBigInt(t.fundingMaxPremiumBps) !== 0n || toBigInt(t.fundingMaxBpsPerSlot) !== 0n || toBigInt(t.markMinFee) !== 0n || toBigInt(t.forceCloseDelaySlots) !== 0n;
278
+ }
279
+ function encodeExtendedTail(t) {
280
+ return concatBytes(
281
+ encU16(t.insuranceWithdrawMaxBps),
282
+ encU64(t.insuranceWithdrawCooldownSlots),
283
+ encU64(t.permissionlessResolveStaleSlots),
284
+ encU64(t.fundingHorizonSlots),
285
+ encU64(t.fundingKBps),
286
+ encI64(t.fundingMaxPremiumBps),
287
+ encI64(t.fundingMaxBpsPerSlot),
288
+ encU64(t.markMinFee),
289
+ encU64(t.forceCloseDelaySlots)
290
+ );
291
+ }
252
292
  function encodeInitMarket(args) {
253
- const data = concatBytes(
293
+ const hMin = args.hMin ?? args.warmupPeriodSlots ?? 0n;
294
+ const hMax = args.hMax ?? args.warmupPeriodSlots ?? 0n;
295
+ const header = concatBytes(
254
296
  encU8(IX_TAG.InitMarket),
255
297
  encPubkey(args.admin),
256
298
  encPubkey(args.collateralMint),
@@ -260,34 +302,43 @@ function encodeInitMarket(args) {
260
302
  encU8(args.invert),
261
303
  encU32(args.unitScale),
262
304
  encU64(args.initialMarkPriceE6),
263
- // 3 fields between header and RiskParams (immutable after init)
264
- encU128(args.maxMaintenanceFeePerSlot ?? 0n),
265
- encU128(args.maxInsuranceFloor ?? 0n),
266
- encU64(args.minOraclePriceCap ?? 0n),
267
- // RiskParams block (15 fields)
268
- encU64(args.warmupPeriodSlots),
305
+ encU128(args.maxMaintenanceFeePerSlot ?? 0n)
306
+ );
307
+ const riskParamsCommon = concatBytes(
308
+ encU64(hMin),
269
309
  encU64(args.maintenanceMarginBps),
270
310
  encU64(args.initialMarginBps),
271
311
  encU64(args.tradingFeeBps),
272
312
  encU64(args.maxAccounts),
273
313
  encU128(args.newAccountFee),
274
- encU128(args.riskReductionThreshold),
275
- encU128(args.maintenanceFeePerSlot),
314
+ encU128(args.insuranceFloor ?? 0n),
315
+ encU64(hMax),
276
316
  encU64(args.maxCrankStalenessSlots),
277
317
  encU64(args.liquidationFeeBps),
278
318
  encU128(args.liquidationFeeCap),
279
- encU64(args.liquidationBufferBps),
280
- encU128(args.minLiquidationAbs),
281
- encU128(args.minInitialDeposit),
319
+ encU64(args.liquidationBufferBps ?? 0n),
320
+ encU128(args.minLiquidationAbs)
321
+ );
322
+ const riskParamsTail = concatBytes(
282
323
  encU128(args.minNonzeroMmReq),
283
324
  encU128(args.minNonzeroImReq)
284
325
  );
285
- if (data.length !== INIT_MARKET_DATA_LEN) {
326
+ const base = concatBytes(header, riskParamsCommon, riskParamsTail);
327
+ if (base.length !== INIT_MARKET_BASE_LEN) {
286
328
  throw new Error(
287
- `encodeInitMarket: expected ${INIT_MARKET_DATA_LEN} bytes, got ${data.length}`
329
+ `encodeInitMarket: base payload expected ${INIT_MARKET_BASE_LEN} bytes, got ${base.length}`
288
330
  );
289
331
  }
290
- return data;
332
+ if (args.extendedTail && extendedTailHasNonZero(args.extendedTail)) {
333
+ const tail = encodeExtendedTail(args.extendedTail);
334
+ if (tail.length !== INIT_MARKET_EXTENDED_TAIL_LEN) {
335
+ throw new Error(
336
+ `encodeInitMarket: extended tail expected ${INIT_MARKET_EXTENDED_TAIL_LEN} bytes, got ${tail.length}`
337
+ );
338
+ }
339
+ return concatBytes(base, tail);
340
+ }
341
+ return base;
291
342
  }
292
343
  function encodeInitUser(args) {
293
344
  return concatBytes(encU8(IX_TAG.InitUser), encU64(args.feePayment));
@@ -314,12 +365,28 @@ function encodeWithdrawCollateral(args) {
314
365
  encU64(args.amount)
315
366
  );
316
367
  }
368
+ var LiquidationPolicyTag = {
369
+ FullClose: 0,
370
+ ExactPartial: 1,
371
+ TouchOnly: 255
372
+ };
317
373
  function encodeKeeperCrank(args) {
318
- return concatBytes(
374
+ const parts = [
319
375
  encU8(IX_TAG.KeeperCrank),
320
376
  encU16(args.callerIdx),
321
- encU8(args.allowPanic ? 1 : 0)
322
- );
377
+ encU8(1)
378
+ // format_version = 1 (REQUIRED by v12.17)
379
+ ];
380
+ if (args.candidates) {
381
+ for (const c of args.candidates) {
382
+ parts.push(encU16(c.idx));
383
+ parts.push(encU8(c.policy));
384
+ if (c.policy === LiquidationPolicyTag.ExactPartial) {
385
+ parts.push(encU128(c.quantity));
386
+ }
387
+ }
388
+ }
389
+ return concatBytes(...parts);
323
390
  }
324
391
  function encodeTradeNoCpi(args) {
325
392
  return concatBytes(
@@ -346,23 +413,18 @@ function encodeTradeCpi(args) {
346
413
  encU8(IX_TAG.TradeCpi),
347
414
  encU16(args.lpIdx),
348
415
  encU16(args.userIdx),
349
- encI128(args.size)
350
- );
351
- }
352
- function encodeTradeCpiV2(args) {
353
- return concatBytes(
354
- encU8(IX_TAG.TradeCpiV2),
355
- encU16(args.lpIdx),
356
- encU16(args.userIdx),
357
416
  encI128(args.size),
358
- encU8(args.bump)
417
+ encU64(args.limitPriceE6)
359
418
  );
360
419
  }
361
- function encodeSetRiskThreshold(args) {
362
- return concatBytes(
363
- encU8(IX_TAG.SetRiskThreshold),
364
- encU128(args.newThreshold)
365
- );
420
+ function encodeTradeCpiV2(_args) {
421
+ return removedInstruction("TradeCpiV2", IX_TAG.TradeCpiV2, "encodeTradeCpi()");
422
+ }
423
+ function encodeUnresolveMarket(_args) {
424
+ return removedInstruction("UnresolveMarket", IX_TAG.UnresolveMarket, "encodeResolveMarket()");
425
+ }
426
+ function encodeSetRiskThreshold(_args) {
427
+ return removedInstruction("SetRiskThreshold", IX_TAG.SetRiskThreshold, "encodeInitMarket()");
366
428
  }
367
429
  function encodeUpdateAdmin(args) {
368
430
  return concatBytes(encU8(IX_TAG.UpdateAdmin), encPubkey(args.newAdmin));
@@ -375,46 +437,13 @@ function encodeUpdateConfig(args) {
375
437
  encU8(IX_TAG.UpdateConfig),
376
438
  encU64(args.fundingHorizonSlots),
377
439
  encU64(args.fundingKBps),
378
- encU128(args.fundingInvScaleNotionalE6),
379
440
  encI64(args.fundingMaxPremiumBps),
380
- // Rust: i64 (can be negative)
381
441
  encI64(args.fundingMaxBpsPerSlot),
382
- // Rust: i64 (can be negative)
383
- encU128(args.threshFloor),
384
- encU64(args.threshRiskBps),
385
- encU64(args.threshUpdateIntervalSlots),
386
- encU64(args.threshStepBps),
387
- encU64(args.threshAlphaBps),
388
- encU128(args.threshMin),
389
- encU128(args.threshMax),
390
- encU128(args.threshMinStep)
442
+ encU16(args.tvlInsuranceCapMult ?? 0)
391
443
  );
392
444
  }
393
- function encodeSetMaintenanceFee(args) {
394
- return concatBytes(
395
- encU8(IX_TAG.SetMaintenanceFee),
396
- encU128(args.newFee)
397
- );
398
- }
399
- function encodeSetOracleAuthority(args) {
400
- return concatBytes(
401
- encU8(IX_TAG.SetOracleAuthority),
402
- encPubkey(args.newAuthority)
403
- );
404
- }
405
- function encodePushOraclePrice(args) {
406
- const price = typeof args.priceE6 === "string" ? BigInt(args.priceE6) : args.priceE6;
407
- if (price === 0n) {
408
- throw new Error("encodePushOraclePrice: price cannot be zero (division by zero in engine)");
409
- }
410
- if (price > MAX_ORACLE_PRICE) {
411
- throw new Error(`encodePushOraclePrice: price exceeds maximum (${MAX_ORACLE_PRICE}), got ${price}`);
412
- }
413
- return concatBytes(
414
- encU8(IX_TAG.PushOraclePrice),
415
- encU64(price),
416
- encI64(args.timestamp)
417
- );
445
+ function encodeSetMaintenanceFee(_args) {
446
+ return removedInstruction("SetMaintenanceFee", IX_TAG.SetMaintenanceFee, "encodeInitMarket()");
418
447
  }
419
448
  function encodeSetOraclePriceCap(args) {
420
449
  return concatBytes(
@@ -434,23 +463,20 @@ function encodeAdminForceClose(args) {
434
463
  encU16(args.targetIdx)
435
464
  );
436
465
  }
437
- function encodeUpdateRiskParams(args) {
438
- const parts = [
439
- encU8(IX_TAG.UpdateRiskParams),
440
- encU64(args.initialMarginBps),
441
- encU64(args.maintenanceMarginBps)
442
- ];
443
- if (args.tradingFeeBps !== void 0) {
444
- parts.push(encU64(args.tradingFeeBps));
445
- }
446
- return concatBytes(...parts);
466
+ function encodeUpdateRiskParams(_args) {
467
+ return removedInstruction(
468
+ "UpdateRiskParams",
469
+ IX_TAG.UpdateRiskParams,
470
+ "encodeSetInsuranceWithdrawPolicy()"
471
+ );
447
472
  }
448
473
  var RENOUNCE_ADMIN_CONFIRMATION = 0x52454E4F554E4345n;
449
474
  var UNRESOLVE_CONFIRMATION = 0xDEADBEEFCAFE1234n;
450
475
  function encodeRenounceAdmin() {
451
- return concatBytes(
452
- encU8(IX_TAG.RenounceAdmin),
453
- encU64(RENOUNCE_ADMIN_CONFIRMATION)
476
+ return removedInstruction(
477
+ "RenounceAdmin",
478
+ IX_TAG.RenounceAdmin,
479
+ "encodeWithdrawInsuranceLimited()"
454
480
  );
455
481
  }
456
482
  function encodeLpVaultWithdraw(args) {
@@ -463,34 +489,22 @@ function encodeUnpauseMarket() {
463
489
  return encU8(IX_TAG.UnpauseMarket);
464
490
  }
465
491
  function encodeSetPythOracle(args) {
466
- if (args.feedId.length !== 32) throw new Error("feedId must be 32 bytes");
467
- if (args.maxStalenessSecs <= 0n) throw new Error("maxStalenessSecs must be > 0");
468
- const buf = new Uint8Array(43);
469
- const dv3 = new DataView(buf.buffer);
470
- buf[0] = 32;
471
- buf.set(args.feedId, 1);
472
- dv3.setBigUint64(
473
- 33,
474
- args.maxStalenessSecs,
475
- /* little-endian */
476
- true
477
- );
478
- dv3.setUint16(41, args.confFilterBps, true);
479
- return buf;
492
+ void args;
493
+ return removedInstruction("SetPythOracle", IX_TAG.SetPythOracle, "encodeInitMarket()");
480
494
  }
481
495
  var PYTH_RECEIVER_PROGRAM_ID = "rec5EKMGg6MxZYaMdyBfgwp4d5rB9T1VQH5pJv5LtFJ";
482
496
  async function derivePythPriceUpdateAccount(feedId, shardId = 0) {
483
- const { PublicKey: PublicKey15 } = await import("@solana/web3.js");
497
+ const { PublicKey: PublicKey16 } = await import("@solana/web3.js");
484
498
  const shardBuf = new Uint8Array(2);
485
499
  new DataView(shardBuf.buffer).setUint16(0, shardId, true);
486
- const [pda] = PublicKey15.findProgramAddressSync(
500
+ const [pda] = PublicKey16.findProgramAddressSync(
487
501
  [shardBuf, feedId],
488
- new PublicKey15(PYTH_RECEIVER_PROGRAM_ID)
502
+ new PublicKey16(PYTH_RECEIVER_PROGRAM_ID)
489
503
  );
490
504
  return pda.toBase58();
491
505
  }
492
506
  function encodeUpdateMarkPrice() {
493
- return new Uint8Array([33]);
507
+ return removedInstruction("UpdateMarkPrice", IX_TAG.UpdateMarkPrice, "encodeUpdateHyperpMark()");
494
508
  }
495
509
  var MARK_PRICE_EMA_WINDOW_SLOTS = 72000n;
496
510
  var MARK_PRICE_EMA_ALPHA_E6 = 2000000n / (MARK_PRICE_EMA_WINDOW_SLOTS + 1n);
@@ -516,7 +530,12 @@ function encodeFundMarketInsurance(args) {
516
530
  return concatBytes(encU8(IX_TAG.FundMarketInsurance), encU64(args.amount));
517
531
  }
518
532
  function encodeSetInsuranceIsolation(args) {
519
- return concatBytes(encU8(IX_TAG.SetInsuranceIsolation), encU16(args.bps));
533
+ void args;
534
+ return removedInstruction(
535
+ "SetInsuranceIsolation",
536
+ IX_TAG.SetInsuranceIsolation,
537
+ "encodeFundMarketInsurance()"
538
+ );
520
539
  }
521
540
  function encodeQueueWithdrawal(args) {
522
541
  return concatBytes(encU8(IX_TAG.QueueWithdrawal), encU64(args.lpAmount));
@@ -540,7 +559,14 @@ function encodeAuditCrank() {
540
559
  return encU8(IX_TAG.AuditCrank);
541
560
  }
542
561
  var VAMM_MAGIC = 0x504552434d415443n;
562
+ var MATCHER_MAGIC = VAMM_MAGIC;
563
+ var CTX_RETURN_OFFSET = 0;
564
+ var MATCHER_RETURN_LEN = 64;
543
565
  var CTX_VAMM_OFFSET = 64;
566
+ var CTX_VAMM_LEN = 256;
567
+ var MATCHER_CONTEXT_LEN = 320;
568
+ var MATCHER_CALL_LEN = 67;
569
+ var INIT_CTX_LEN = 78;
544
570
  var BPS_DENOM = 10000n;
545
571
  function computeVammQuote(params, oraclePriceE6, tradeSize, isLong) {
546
572
  const absSize = tradeSize < 0n ? -tradeSize : tradeSize;
@@ -596,11 +622,8 @@ function checkPhaseTransition(currentSlot, marketCreatedSlot, oraclePhase, cumul
596
622
  return [ORACLE_PHASE_MATURE, false];
597
623
  }
598
624
  }
599
- function encodeTopUpKeeperFund(args) {
600
- return concatBytes(encU8(IX_TAG.TopUpKeeperFund), encU64(args.amount));
601
- }
602
625
  function encodeSlashCreationDeposit() {
603
- return encU8(IX_TAG.SlashCreationDeposit);
626
+ return removedInstruction("SlashCreationDeposit", IX_TAG.SlashCreationDeposit);
604
627
  }
605
628
  function encodeInitSharedVault(args) {
606
629
  return concatBytes(
@@ -720,6 +743,87 @@ function encodeCloseOrphanSlab() {
720
743
  function encodeSetDexPool(args) {
721
744
  return concatBytes(encU8(IX_TAG.SetDexPool), encPubkey(args.pool));
722
745
  }
746
+ function encodeCreateInsuranceMint() {
747
+ return encodeCreateLpVault({ feeShareBps: 0n });
748
+ }
749
+ function encodeDepositInsuranceLP(args) {
750
+ return encodeLpVaultDeposit({ amount: args.amount });
751
+ }
752
+ function encodeWithdrawInsuranceLP(args) {
753
+ return encodeLpVaultWithdraw({ lpAmount: args.lpAmount });
754
+ }
755
+ function encodeSetMaxPnlCap(args) {
756
+ return concatBytes(encU8(IX_TAG.SetMaxPnlCap), encU64(args.cap));
757
+ }
758
+ function encodeSetOiCapMultiplier(args) {
759
+ return concatBytes(encU8(IX_TAG.SetOiCapMultiplier), encU64(args.packed));
760
+ }
761
+ function packOiCap(multiplierBps, softCapBps) {
762
+ if (multiplierBps < 0 || multiplierBps > 4294967295) {
763
+ throw new Error(`packOiCap: multiplier_bps out of u32 range: ${multiplierBps}`);
764
+ }
765
+ if (softCapBps < 0 || softCapBps > 4294967295) {
766
+ throw new Error(`packOiCap: soft_cap_bps out of u32 range: ${softCapBps}`);
767
+ }
768
+ return BigInt(multiplierBps) | BigInt(softCapBps) << 32n;
769
+ }
770
+ function encodeSetDisputeParams(args) {
771
+ return concatBytes(
772
+ encU8(IX_TAG.SetDisputeParams),
773
+ encU64(args.windowSlots),
774
+ encU64(args.bondAmount)
775
+ );
776
+ }
777
+ function encodeSetLpCollateralParams(args) {
778
+ if (args.enabled !== 0 && args.enabled !== 1) {
779
+ throw new Error(`encodeSetLpCollateralParams: enabled must be 0 or 1, got ${args.enabled}`);
780
+ }
781
+ if (args.ltvBps < 0 || args.ltvBps > 1e4) {
782
+ throw new Error(`encodeSetLpCollateralParams: ltvBps ${args.ltvBps} out of range [0, 10000]`);
783
+ }
784
+ return concatBytes(
785
+ encU8(IX_TAG.SetLpCollateralParams),
786
+ encU8(args.enabled),
787
+ encU16(args.ltvBps)
788
+ );
789
+ }
790
+ function encodeAcceptAdmin() {
791
+ return encU8(IX_TAG.AcceptAdmin);
792
+ }
793
+ function encodeReclaimEmptyAccount(args) {
794
+ return concatBytes(encU8(IX_TAG.ReclaimEmptyAccount), encU16(args.userIdx));
795
+ }
796
+ function encodeSettleAccount(args) {
797
+ return concatBytes(encU8(IX_TAG.SettleAccount), encU16(args.userIdx));
798
+ }
799
+ function encodeDepositFeeCredits(args) {
800
+ return concatBytes(
801
+ encU8(IX_TAG.DepositFeeCredits),
802
+ encU16(args.userIdx),
803
+ encU64(args.amount)
804
+ );
805
+ }
806
+ function encodeConvertReleasedPnl(args) {
807
+ return concatBytes(
808
+ encU8(IX_TAG.ConvertReleasedPnl),
809
+ encU16(args.userIdx),
810
+ encU64(args.amount)
811
+ );
812
+ }
813
+ var AUTHORITY_KIND = {
814
+ Admin: 0,
815
+ HyperpMark: 1,
816
+ Insurance: 2,
817
+ InsuranceOperator: 4
818
+ };
819
+ Object.freeze(AUTHORITY_KIND);
820
+ function encodeUpdateAuthority(args) {
821
+ return concatBytes(
822
+ encU8(IX_TAG.UpdateAuthority),
823
+ encU8(args.kind),
824
+ encPubkey(args.newPubkey)
825
+ );
826
+ }
723
827
 
724
828
  // src/abi/accounts.ts
725
829
  import {
@@ -744,14 +848,16 @@ var ACCOUNTS_INIT_USER = [
744
848
  { name: "slab", signer: false, writable: true },
745
849
  { name: "userAta", signer: false, writable: true },
746
850
  { name: "vault", signer: false, writable: true },
747
- { name: "tokenProgram", signer: false, writable: false }
851
+ { name: "tokenProgram", signer: false, writable: false },
852
+ { name: "clock", signer: false, writable: false }
748
853
  ];
749
854
  var ACCOUNTS_INIT_LP = [
750
855
  { name: "user", signer: true, writable: true },
751
856
  { name: "slab", signer: false, writable: true },
752
857
  { name: "userAta", signer: false, writable: true },
753
858
  { name: "vault", signer: false, writable: true },
754
- { name: "tokenProgram", signer: false, writable: false }
859
+ { name: "tokenProgram", signer: false, writable: false },
860
+ { name: "clock", signer: false, writable: false }
755
861
  ];
756
862
  var ACCOUNTS_DEPOSIT_COLLATERAL = [
757
863
  { name: "user", signer: true, writable: true },
@@ -781,6 +887,7 @@ var ACCOUNTS_TRADE_NOCPI = [
781
887
  { name: "user", signer: true, writable: true },
782
888
  { name: "lp", signer: true, writable: true },
783
889
  { name: "slab", signer: false, writable: true },
890
+ { name: "clock", signer: false, writable: false },
784
891
  { name: "oracle", signer: false, writable: false }
785
892
  ];
786
893
  var ACCOUNTS_LIQUIDATE_AT_ORACLE = [
@@ -804,13 +911,15 @@ var ACCOUNTS_TOPUP_INSURANCE = [
804
911
  { name: "slab", signer: false, writable: true },
805
912
  { name: "userAta", signer: false, writable: true },
806
913
  { name: "vault", signer: false, writable: true },
807
- { name: "tokenProgram", signer: false, writable: false }
914
+ { name: "tokenProgram", signer: false, writable: false },
915
+ { name: "clock", signer: false, writable: false }
808
916
  ];
809
917
  var ACCOUNTS_TRADE_CPI = [
810
918
  { name: "user", signer: true, writable: true },
811
919
  { name: "lpOwner", signer: false, writable: false },
812
920
  // LP delegated to matcher - no signature needed
813
921
  { name: "slab", signer: false, writable: true },
922
+ { name: "clock", signer: false, writable: false },
814
923
  { name: "oracle", signer: false, writable: false },
815
924
  { name: "matcherProg", signer: false, writable: false },
816
925
  { name: "matcherCtx", signer: false, writable: true },
@@ -824,33 +933,37 @@ var ACCOUNTS_UPDATE_ADMIN = [
824
933
  { name: "admin", signer: true, writable: true },
825
934
  { name: "slab", signer: false, writable: true }
826
935
  ];
827
- var ACCOUNTS_CLOSE_SLAB = [
828
- { name: "admin", signer: true, writable: true },
936
+ var ACCOUNTS_ACCEPT_ADMIN = [
937
+ { name: "pendingAdmin", signer: true, writable: true },
829
938
  { name: "slab", signer: false, writable: true }
830
939
  ];
940
+ var ACCOUNTS_CLOSE_SLAB = [
941
+ { name: "dest", signer: true, writable: true },
942
+ { name: "slab", signer: false, writable: true },
943
+ { name: "vault", signer: false, writable: true },
944
+ { name: "vaultAuthority", signer: false, writable: false },
945
+ { name: "destAta", signer: false, writable: true },
946
+ { name: "tokenProgram", signer: false, writable: false }
947
+ ];
831
948
  var ACCOUNTS_UPDATE_CONFIG = [
832
949
  { name: "admin", signer: true, writable: true },
833
- { name: "slab", signer: false, writable: true }
950
+ { name: "slab", signer: false, writable: true },
951
+ { name: "clock", signer: false, writable: false }
834
952
  ];
835
953
  var ACCOUNTS_SET_MAINTENANCE_FEE = [
836
954
  { name: "admin", signer: true, writable: true },
837
955
  { name: "slab", signer: false, writable: true }
838
956
  ];
839
- var ACCOUNTS_SET_ORACLE_AUTHORITY = [
840
- { name: "admin", signer: true, writable: true },
841
- { name: "slab", signer: false, writable: true }
842
- ];
843
957
  var ACCOUNTS_SET_ORACLE_PRICE_CAP = [
844
958
  { name: "admin", signer: true, writable: true },
845
- { name: "slab", signer: false, writable: true }
846
- ];
847
- var ACCOUNTS_PUSH_ORACLE_PRICE = [
848
- { name: "authority", signer: true, writable: true },
849
- { name: "slab", signer: false, writable: true }
959
+ { name: "slab", signer: false, writable: true },
960
+ { name: "clock", signer: false, writable: false }
850
961
  ];
851
962
  var ACCOUNTS_RESOLVE_MARKET = [
852
963
  { name: "admin", signer: true, writable: true },
853
- { name: "slab", signer: false, writable: true }
964
+ { name: "slab", signer: false, writable: true },
965
+ { name: "clock", signer: false, writable: false },
966
+ { name: "oracle", signer: false, writable: false }
854
967
  ];
855
968
  var ACCOUNTS_WITHDRAW_INSURANCE = [
856
969
  { name: "admin", signer: true, writable: true },
@@ -860,6 +973,19 @@ var ACCOUNTS_WITHDRAW_INSURANCE = [
860
973
  { name: "tokenProgram", signer: false, writable: false },
861
974
  { name: "vaultPda", signer: false, writable: false }
862
975
  ];
976
+ var ACCOUNTS_WITHDRAW_INSURANCE_LIMITED_RESOLVED = [
977
+ { name: "authority", signer: true, writable: true },
978
+ { name: "slab", signer: false, writable: true },
979
+ { name: "authorityAta", signer: false, writable: true },
980
+ { name: "vault", signer: false, writable: true },
981
+ { name: "tokenProgram", signer: false, writable: false },
982
+ { name: "vaultPda", signer: false, writable: false },
983
+ { name: "clock", signer: false, writable: false }
984
+ ];
985
+ var ACCOUNTS_WITHDRAW_INSURANCE_LIMITED_LIVE = [
986
+ ...ACCOUNTS_WITHDRAW_INSURANCE_LIMITED_RESOLVED,
987
+ { name: "oracle", signer: false, writable: false }
988
+ ];
863
989
  var ACCOUNTS_PAUSE_MARKET = [
864
990
  { name: "admin", signer: true, writable: true },
865
991
  { name: "slab", signer: false, writable: true }
@@ -868,6 +994,38 @@ var ACCOUNTS_UNPAUSE_MARKET = [
868
994
  { name: "admin", signer: true, writable: true },
869
995
  { name: "slab", signer: false, writable: true }
870
996
  ];
997
+ var ACCOUNTS_RECLAIM_EMPTY_ACCOUNT = [
998
+ { name: "slab", signer: false, writable: true },
999
+ { name: "clock", signer: false, writable: false }
1000
+ ];
1001
+ var ACCOUNTS_SETTLE_ACCOUNT = [
1002
+ { name: "slab", signer: false, writable: true },
1003
+ { name: "clock", signer: false, writable: false },
1004
+ { name: "oracle", signer: false, writable: false }
1005
+ ];
1006
+ var ACCOUNTS_DEPOSIT_FEE_CREDITS = [
1007
+ { name: "user", signer: true, writable: true },
1008
+ { name: "slab", signer: false, writable: true },
1009
+ { name: "userAta", signer: false, writable: true },
1010
+ { name: "vault", signer: false, writable: true },
1011
+ { name: "tokenProgram", signer: false, writable: false },
1012
+ { name: "clock", signer: false, writable: false }
1013
+ ];
1014
+ var ACCOUNTS_CONVERT_RELEASED_PNL = [
1015
+ { name: "user", signer: true, writable: true },
1016
+ { name: "slab", signer: false, writable: true },
1017
+ { name: "clock", signer: false, writable: false },
1018
+ { name: "oracle", signer: false, writable: false }
1019
+ ];
1020
+ var ACCOUNTS_SET_INSURANCE_WITHDRAW_POLICY = [
1021
+ { name: "admin", signer: true, writable: true },
1022
+ { name: "slab", signer: false, writable: true }
1023
+ ];
1024
+ var ACCOUNTS_UPDATE_AUTHORITY = [
1025
+ { name: "currentAuthority", signer: true, writable: false },
1026
+ { name: "newAuthority", signer: true, writable: false },
1027
+ { name: "slab", signer: false, writable: true }
1028
+ ];
871
1029
  function buildAccountMetas(spec, keys) {
872
1030
  let keysArray;
873
1031
  if (Array.isArray(keys)) {
@@ -894,6 +1052,37 @@ function buildAccountMetas(spec, keys) {
894
1052
  isWritable: s.writable
895
1053
  }));
896
1054
  }
1055
+ var ACCOUNTS_CREATE_INSURANCE_MINT = [
1056
+ { name: "admin", signer: true, writable: false },
1057
+ { name: "slab", signer: false, writable: false },
1058
+ { name: "insLpMint", signer: false, writable: true },
1059
+ { name: "vaultAuthority", signer: false, writable: false },
1060
+ { name: "collateralMint", signer: false, writable: false },
1061
+ { name: "systemProgram", signer: false, writable: false },
1062
+ { name: "tokenProgram", signer: false, writable: false },
1063
+ { name: "rent", signer: false, writable: false },
1064
+ { name: "payer", signer: true, writable: true }
1065
+ ];
1066
+ var ACCOUNTS_DEPOSIT_INSURANCE_LP = [
1067
+ { name: "depositor", signer: true, writable: false },
1068
+ { name: "slab", signer: false, writable: true },
1069
+ { name: "depositorAta", signer: false, writable: true },
1070
+ { name: "vault", signer: false, writable: true },
1071
+ { name: "tokenProgram", signer: false, writable: false },
1072
+ { name: "insLpMint", signer: false, writable: true },
1073
+ { name: "depositorLpAta", signer: false, writable: true },
1074
+ { name: "vaultAuthority", signer: false, writable: false }
1075
+ ];
1076
+ var ACCOUNTS_WITHDRAW_INSURANCE_LP = [
1077
+ { name: "withdrawer", signer: true, writable: false },
1078
+ { name: "slab", signer: false, writable: true },
1079
+ { name: "withdrawerAta", signer: false, writable: true },
1080
+ { name: "vault", signer: false, writable: true },
1081
+ { name: "tokenProgram", signer: false, writable: false },
1082
+ { name: "insLpMint", signer: false, writable: true },
1083
+ { name: "withdrawerLpAta", signer: false, writable: true },
1084
+ { name: "vaultAuthority", signer: false, writable: false }
1085
+ ];
897
1086
  var ACCOUNTS_LP_VAULT_WITHDRAW = [
898
1087
  { name: "withdrawer", signer: true, writable: false },
899
1088
  { name: "slab", signer: false, writable: true },
@@ -947,6 +1136,30 @@ var ACCOUNTS_EXECUTE_ADL = [
947
1136
  { name: "clock", signer: false, writable: false },
948
1137
  { name: "oracle", signer: false, writable: false }
949
1138
  ];
1139
+ var ACCOUNTS_RESOLVE_PERMISSIONLESS = [
1140
+ { name: "slab", signer: false, writable: true },
1141
+ { name: "clock", signer: false, writable: false },
1142
+ { name: "oracle", signer: false, writable: false }
1143
+ ];
1144
+ var ACCOUNTS_FORCE_CLOSE_RESOLVED = [
1145
+ { name: "slab", signer: false, writable: true },
1146
+ { name: "vault", signer: false, writable: true },
1147
+ { name: "ownerAta", signer: false, writable: true },
1148
+ { name: "vaultAuthority", signer: false, writable: false },
1149
+ { name: "tokenProgram", signer: false, writable: false },
1150
+ { name: "clock", signer: false, writable: false },
1151
+ { name: "oracle", signer: false, writable: false }
1152
+ ];
1153
+ var ACCOUNTS_ADMIN_FORCE_CLOSE = [
1154
+ { name: "admin", signer: true, writable: true },
1155
+ { name: "slab", signer: false, writable: true },
1156
+ { name: "vault", signer: false, writable: true },
1157
+ { name: "ownerAta", signer: false, writable: true },
1158
+ { name: "vaultAuthority", signer: false, writable: false },
1159
+ { name: "tokenProgram", signer: false, writable: false },
1160
+ { name: "clock", signer: false, writable: false },
1161
+ { name: "oracle", signer: false, writable: false }
1162
+ ];
950
1163
  var ACCOUNTS_CLOSE_STALE_SLABS = [
951
1164
  { name: "dest", signer: true, writable: true },
952
1165
  { name: "slab", signer: false, writable: true }
@@ -961,15 +1174,108 @@ var ACCOUNTS_AUDIT_CRANK = [
961
1174
  var ACCOUNTS_ADVANCE_ORACLE_PHASE = [
962
1175
  { name: "slab", signer: false, writable: true }
963
1176
  ];
964
- var ACCOUNTS_TOPUP_KEEPER_FUND = [
965
- { name: "funder", signer: true, writable: true },
1177
+ var ACCOUNTS_UPDATE_HYPERP_MARK = [
1178
+ { name: "slab", signer: false, writable: true },
1179
+ { name: "dexPool", signer: false, writable: false },
1180
+ { name: "clock", signer: false, writable: false }
1181
+ ];
1182
+ var ACCOUNTS_CREATE_LP_VAULT = [
1183
+ { name: "admin", signer: true, writable: true },
1184
+ { name: "slab", signer: false, writable: true },
1185
+ { name: "lpVaultState", signer: false, writable: true },
1186
+ { name: "lpVaultMint", signer: false, writable: true },
1187
+ { name: "vaultAuthority", signer: false, writable: false },
1188
+ { name: "systemProgram", signer: false, writable: false },
1189
+ { name: "tokenProgram", signer: false, writable: false },
1190
+ { name: "rent", signer: false, writable: false }
1191
+ ];
1192
+ var ACCOUNTS_LP_VAULT_DEPOSIT = [
1193
+ { name: "depositor", signer: true, writable: true },
1194
+ { name: "slab", signer: false, writable: true },
1195
+ { name: "depositorAta", signer: false, writable: true },
1196
+ { name: "vault", signer: false, writable: true },
1197
+ { name: "tokenProgram", signer: false, writable: false },
1198
+ { name: "lpVaultMint", signer: false, writable: true },
1199
+ { name: "depositorLpAta", signer: false, writable: true },
1200
+ { name: "vaultAuthority", signer: false, writable: false },
1201
+ { name: "lpVaultState", signer: false, writable: true }
1202
+ ];
1203
+ var ACCOUNTS_LP_VAULT_CRANK_FEES = [
1204
+ { name: "slab", signer: false, writable: true },
1205
+ { name: "lpVaultState", signer: false, writable: true }
1206
+ ];
1207
+ var ACCOUNTS_CHALLENGE_SETTLEMENT = [
1208
+ { name: "challenger", signer: true, writable: true },
1209
+ { name: "slab", signer: false, writable: true },
1210
+ { name: "dispute", signer: false, writable: true },
1211
+ { name: "challengerAta", signer: false, writable: true },
1212
+ { name: "vault", signer: false, writable: true },
1213
+ { name: "tokenProgram", signer: false, writable: false },
1214
+ { name: "systemProgram", signer: false, writable: false }
1215
+ ];
1216
+ var ACCOUNTS_RESOLVE_DISPUTE = [
1217
+ { name: "admin", signer: true, writable: true },
1218
+ { name: "slab", signer: false, writable: true },
1219
+ { name: "dispute", signer: false, writable: true },
1220
+ { name: "challengerAta", signer: false, writable: true },
1221
+ { name: "vault", signer: false, writable: true },
1222
+ { name: "vaultAuthority", signer: false, writable: false },
1223
+ { name: "tokenProgram", signer: false, writable: false }
1224
+ ];
1225
+ var ACCOUNTS_DEPOSIT_LP_COLLATERAL = [
1226
+ { name: "user", signer: true, writable: true },
966
1227
  { name: "slab", signer: false, writable: true },
967
- { name: "keeperFund", signer: false, writable: true }
1228
+ { name: "userLpAta", signer: false, writable: true },
1229
+ { name: "lpVaultMint", signer: false, writable: false },
1230
+ { name: "lpVaultState", signer: false, writable: true },
1231
+ { name: "tokenProgram", signer: false, writable: false },
1232
+ { name: "lpEscrow", signer: false, writable: true }
1233
+ ];
1234
+ var ACCOUNTS_WITHDRAW_LP_COLLATERAL = [
1235
+ { name: "user", signer: true, writable: true },
1236
+ { name: "slab", signer: false, writable: true },
1237
+ { name: "userLpAta", signer: false, writable: true },
1238
+ { name: "lpVaultMint", signer: false, writable: false },
1239
+ { name: "lpVaultState", signer: false, writable: true },
1240
+ { name: "tokenProgram", signer: false, writable: false },
1241
+ { name: "lpEscrow", signer: false, writable: true },
1242
+ { name: "vaultAuthority", signer: false, writable: false }
1243
+ ];
1244
+ var ACCOUNTS_SET_OFFSET_PAIR = [
1245
+ { name: "admin", signer: true, writable: true },
1246
+ { name: "slabA", signer: false, writable: true },
1247
+ { name: "slabB", signer: false, writable: true },
1248
+ { name: "pairPda", signer: false, writable: true },
1249
+ { name: "systemProgram", signer: false, writable: false }
1250
+ ];
1251
+ var ACCOUNTS_ATTEST_CROSS_MARGIN = [
1252
+ { name: "payer", signer: true, writable: true },
1253
+ { name: "slabA", signer: false, writable: true },
1254
+ { name: "slabB", signer: false, writable: true },
1255
+ { name: "attestation", signer: false, writable: true },
1256
+ { name: "pairPda", signer: false, writable: false },
1257
+ { name: "systemProgram", signer: false, writable: false }
968
1258
  ];
969
1259
  var ACCOUNTS_SET_OI_IMBALANCE_HARD_BLOCK = [
970
1260
  { name: "admin", signer: true, writable: false },
971
1261
  { name: "slab", signer: false, writable: true }
972
1262
  ];
1263
+ var ACCOUNTS_SET_MAX_PNL_CAP = [
1264
+ { name: "admin", signer: true, writable: false },
1265
+ { name: "slab", signer: false, writable: true }
1266
+ ];
1267
+ var ACCOUNTS_SET_OI_CAP_MULTIPLIER = [
1268
+ { name: "admin", signer: true, writable: false },
1269
+ { name: "slab", signer: false, writable: true }
1270
+ ];
1271
+ var ACCOUNTS_SET_DISPUTE_PARAMS = [
1272
+ { name: "admin", signer: true, writable: false },
1273
+ { name: "slab", signer: false, writable: true }
1274
+ ];
1275
+ var ACCOUNTS_SET_LP_COLLATERAL_PARAMS = [
1276
+ { name: "admin", signer: true, writable: false },
1277
+ { name: "slab", signer: false, writable: true }
1278
+ ];
973
1279
  var ACCOUNTS_MINT_POSITION_NFT = [
974
1280
  { name: "payer", signer: true, writable: true },
975
1281
  { name: "slab", signer: false, writable: true },
@@ -1011,10 +1317,33 @@ var ACCOUNTS_CLEAR_PENDING_SETTLEMENT = [
1011
1317
  { name: "slab", signer: false, writable: false },
1012
1318
  { name: "positionNftPda", signer: false, writable: true }
1013
1319
  ];
1320
+ var ACCOUNTS_TRANSFER_OWNERSHIP_CPI = [
1321
+ { name: "caller", signer: true, writable: false },
1322
+ { name: "slab", signer: false, writable: true },
1323
+ { name: "nftProgram", signer: false, writable: false }
1324
+ ];
1014
1325
  var ACCOUNTS_SET_WALLET_CAP = [
1015
1326
  { name: "admin", signer: true, writable: false },
1016
1327
  { name: "slab", signer: false, writable: true }
1017
1328
  ];
1329
+ var ACCOUNTS_RESCUE_ORPHAN_VAULT = [
1330
+ { name: "admin", signer: true, writable: true },
1331
+ { name: "slab", signer: false, writable: true },
1332
+ { name: "adminAta", signer: false, writable: true },
1333
+ { name: "vault", signer: false, writable: true },
1334
+ { name: "tokenProgram", signer: false, writable: false },
1335
+ { name: "vaultPda", signer: false, writable: false }
1336
+ ];
1337
+ var ACCOUNTS_CLOSE_ORPHAN_SLAB = [
1338
+ { name: "admin", signer: true, writable: true },
1339
+ { name: "slab", signer: false, writable: true },
1340
+ { name: "vault", signer: false, writable: true }
1341
+ ];
1342
+ var ACCOUNTS_SET_DEX_POOL = [
1343
+ { name: "admin", signer: true, writable: false },
1344
+ { name: "slab", signer: false, writable: true },
1345
+ { name: "poolAccount", signer: false, writable: false }
1346
+ ];
1018
1347
  var ACCOUNTS_INIT_MATCHER_CTX = [
1019
1348
  { name: "admin", signer: true, writable: false },
1020
1349
  { name: "slab", signer: false, writable: false },
@@ -1306,24 +1635,11 @@ function getErrorName(code) {
1306
1635
  function getErrorHint(code) {
1307
1636
  return PERCOLATOR_ERRORS[code]?.hint;
1308
1637
  }
1309
- var LIGHTHOUSE_PROGRAM_ID_STR = "L2TExMFKdjpN9kozasaurPirfHy9P8sbXoAN1qA3S95";
1310
- var ANCHOR_ERROR_RANGE_START = 6e3;
1311
- var ANCHOR_ERROR_RANGE_END = 8191;
1312
- var ANCHOR_ERROR_NAMES = {
1313
- 6032: "ConstraintMut",
1314
- 6036: "ConstraintOwner",
1315
- 6038: "ConstraintSeeds",
1316
- 6400: "ConstraintAddress"
1317
- };
1318
- function isAnchorErrorCode(code) {
1319
- return code >= ANCHOR_ERROR_RANGE_START && code <= ANCHOR_ERROR_RANGE_END;
1320
- }
1321
1638
  var CUSTOM_ERROR_HEX_MAX_LEN = 8;
1322
1639
  function parseErrorFromLogs(logs) {
1323
1640
  if (!Array.isArray(logs)) {
1324
1641
  return null;
1325
1642
  }
1326
- let insideLighthouse = false;
1327
1643
  const re = new RegExp(
1328
1644
  `custom program error: 0x([0-9a-fA-F]{1,${CUSTOM_ERROR_HEX_MAX_LEN}})(?![0-9a-fA-F])`,
1329
1645
  "i"
@@ -1332,44 +1648,212 @@ function parseErrorFromLogs(logs) {
1332
1648
  if (typeof log !== "string") {
1333
1649
  continue;
1334
1650
  }
1335
- if (log.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR} invoke`)) {
1336
- insideLighthouse = true;
1337
- } else if (log.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR} success`)) {
1338
- insideLighthouse = false;
1339
- }
1340
1651
  const match = log.match(re);
1341
1652
  if (match) {
1342
1653
  const code = parseInt(match[1], 16);
1343
1654
  if (!Number.isFinite(code) || code < 0 || code > 4294967295) {
1344
1655
  continue;
1345
1656
  }
1346
- if (isAnchorErrorCode(code) || insideLighthouse) {
1347
- const anchorName = ANCHOR_ERROR_NAMES[code] ?? `AnchorError(0x${code.toString(16)})`;
1348
- return {
1349
- code,
1350
- name: `Lighthouse:${anchorName}`,
1351
- hint: "This error comes from the Lighthouse/Blowfish wallet guard, not from Percolator. The transaction itself is valid. Disable transaction simulation in your wallet settings, or use a wallet without Blowfish protection (e.g., Backpack, Solflare).",
1352
- source: "lighthouse"
1353
- };
1354
- }
1355
1657
  const info = decodeError(code);
1356
1658
  return {
1357
1659
  code,
1358
1660
  name: info?.name ?? `Unknown(${code})`,
1359
- hint: info?.hint,
1360
- source: info ? "percolator" : "unknown"
1661
+ hint: info?.hint
1361
1662
  };
1362
1663
  }
1363
1664
  }
1364
1665
  return null;
1365
1666
  }
1366
1667
 
1367
- // src/solana/slab.ts
1668
+ // src/abi/nft.ts
1669
+ import { PublicKey as PublicKey4 } from "@solana/web3.js";
1670
+
1671
+ // src/config/program-ids.ts
1368
1672
  import { PublicKey as PublicKey3 } from "@solana/web3.js";
1673
+ function safeEnv(key) {
1674
+ try {
1675
+ return typeof process !== "undefined" && process?.env ? process.env[key] : void 0;
1676
+ } catch {
1677
+ return void 0;
1678
+ }
1679
+ }
1680
+ var PROGRAM_IDS = {
1681
+ devnet: {
1682
+ percolator: "FxfD37s1AZTeWfFQps9Zpebi2dNQ9QSSDtfMKdbsfKrD",
1683
+ matcher: "GTRgyTDfrMvBubALAqtHuQwT8tbGyXid7svXZKtWfC9k"
1684
+ },
1685
+ mainnet: {
1686
+ percolator: "ESa89R5Es3rJ5mnwGybVRG1GrNt9etP11Z5V2QWD4edv",
1687
+ matcher: "GDK8wx38kpiSVSfGTVNiSdptX3Z5R4kQyqh6Q3QX6wmi"
1688
+ }
1689
+ };
1690
+ function getProgramId(network) {
1691
+ const override = safeEnv("PROGRAM_ID");
1692
+ if (override) {
1693
+ console.warn(
1694
+ `[percolator-sdk] PROGRAM_ID env override active: ${override} \u2014 ensure this points to a trusted program`
1695
+ );
1696
+ return new PublicKey3(override);
1697
+ }
1698
+ const detectedNetwork = getCurrentNetwork();
1699
+ const targetNetwork = network ?? detectedNetwork;
1700
+ const programId = PROGRAM_IDS[targetNetwork].percolator;
1701
+ return new PublicKey3(programId);
1702
+ }
1703
+ function getMatcherProgramId(network) {
1704
+ const override = safeEnv("MATCHER_PROGRAM_ID");
1705
+ if (override) {
1706
+ console.warn(
1707
+ `[percolator-sdk] MATCHER_PROGRAM_ID env override active: ${override} \u2014 ensure this points to a trusted program`
1708
+ );
1709
+ return new PublicKey3(override);
1710
+ }
1711
+ const detectedNetwork = getCurrentNetwork();
1712
+ const targetNetwork = network ?? detectedNetwork;
1713
+ const programId = PROGRAM_IDS[targetNetwork].matcher;
1714
+ if (!programId) {
1715
+ throw new Error(`Matcher program not deployed on ${targetNetwork}`);
1716
+ }
1717
+ return new PublicKey3(programId);
1718
+ }
1719
+ function getCurrentNetwork() {
1720
+ const network = safeEnv("NETWORK")?.toLowerCase();
1721
+ if (network === "mainnet" || network === "mainnet-beta") {
1722
+ return "mainnet";
1723
+ }
1724
+ return "devnet";
1725
+ }
1726
+
1727
+ // src/abi/nft.ts
1728
+ var NFT_PROGRAM_OVERRIDE = safeEnv("NFT_PROGRAM_ID");
1729
+ var NFT_PROGRAM_ID = new PublicKey4(
1730
+ NFT_PROGRAM_OVERRIDE ?? "FqhKJT9gtScjrmfUuRMjeg7cXNpif1fqsy5Jh65tJmTS"
1731
+ );
1732
+ function getNftProgramId() {
1733
+ return NFT_PROGRAM_ID;
1734
+ }
1735
+ var NFT_IX_TAG = {
1736
+ MintPositionNft: 0,
1737
+ BurnPositionNft: 1,
1738
+ SettleFunding: 2,
1739
+ GetPositionValue: 3,
1740
+ ExecuteTransferHook: 4,
1741
+ EmergencyBurn: 5
1742
+ };
1743
+ function encodeNftMint(userIdx) {
1744
+ const buf = new Uint8Array(3);
1745
+ buf[0] = NFT_IX_TAG.MintPositionNft;
1746
+ buf[1] = userIdx & 255;
1747
+ buf[2] = userIdx >> 8 & 255;
1748
+ return buf;
1749
+ }
1750
+ function encodeNftBurn() {
1751
+ return new Uint8Array([NFT_IX_TAG.BurnPositionNft]);
1752
+ }
1753
+ function encodeNftSettleFunding() {
1754
+ return new Uint8Array([NFT_IX_TAG.SettleFunding]);
1755
+ }
1756
+ function encodeNftEmergencyBurn() {
1757
+ return new Uint8Array([NFT_IX_TAG.EmergencyBurn]);
1758
+ }
1759
+ var ACCOUNTS_NFT_MINT = [
1760
+ "sw",
1761
+ "w",
1762
+ "sw",
1763
+ "w",
1764
+ "r",
1765
+ "r",
1766
+ "r",
1767
+ "r",
1768
+ "r",
1769
+ "w"
1770
+ ];
1771
+ var ACCOUNTS_NFT_BURN = [
1772
+ "s",
1773
+ "w",
1774
+ "w",
1775
+ "w",
1776
+ "r",
1777
+ "r",
1778
+ "r"
1779
+ ];
1780
+ var ACCOUNTS_NFT_EMERGENCY_BURN = [
1781
+ "s",
1782
+ "w",
1783
+ "w",
1784
+ "w",
1785
+ "r",
1786
+ "r",
1787
+ "r"
1788
+ ];
1789
+ var TEXT = new TextEncoder();
1790
+ function idxBuf(userIdx) {
1791
+ const buf = new Uint8Array(2);
1792
+ new DataView(buf.buffer).setUint16(0, userIdx, true);
1793
+ return buf;
1794
+ }
1795
+ function deriveNftPda(slab, userIdx, programId = NFT_PROGRAM_ID) {
1796
+ return PublicKey4.findProgramAddressSync(
1797
+ [TEXT.encode("position_nft"), slab.toBytes(), idxBuf(userIdx)],
1798
+ programId
1799
+ );
1800
+ }
1801
+ function deriveNftMint(slab, userIdx, programId = NFT_PROGRAM_ID) {
1802
+ return PublicKey4.findProgramAddressSync(
1803
+ [TEXT.encode("position_nft_mint"), slab.toBytes(), idxBuf(userIdx)],
1804
+ programId
1805
+ );
1806
+ }
1807
+ function deriveMintAuthority(programId = NFT_PROGRAM_ID) {
1808
+ return PublicKey4.findProgramAddressSync(
1809
+ [TEXT.encode("mint_authority")],
1810
+ programId
1811
+ );
1812
+ }
1813
+ var POSITION_NFT_STATE_LEN = 208;
1814
+ function readI128FromView(view, offset) {
1815
+ const lo = view.getBigUint64(offset, true);
1816
+ const hi = view.getBigUint64(offset + 8, true);
1817
+ const unsigned = hi << 64n | lo;
1818
+ const SIGN_BIT = 1n << 127n;
1819
+ if (unsigned >= SIGN_BIT) {
1820
+ return unsigned - (1n << 128n);
1821
+ }
1822
+ return unsigned;
1823
+ }
1824
+ function parsePositionNftAccount(data) {
1825
+ if (data.length < POSITION_NFT_STATE_LEN) {
1826
+ throw new Error(
1827
+ `PositionNft account too small: ${data.length} < ${POSITION_NFT_STATE_LEN}`
1828
+ );
1829
+ }
1830
+ const view = new DataView(data.buffer, data.byteOffset, data.byteLength);
1831
+ return {
1832
+ version: data[8],
1833
+ bump: data[9],
1834
+ slab: new PublicKey4(data.subarray(16, 48)),
1835
+ userIdx: view.getUint16(48, true),
1836
+ nftMint: new PublicKey4(data.subarray(56, 88)),
1837
+ positionOwner: new PublicKey4(data.subarray(160, 192)),
1838
+ entryPriceE6: view.getBigUint64(88, true),
1839
+ positionSize: view.getBigUint64(96, true),
1840
+ isLong: data[104] === 1,
1841
+ positionBasisQ: readI128FromView(view, 112),
1842
+ lastFundingIndexE18: readI128FromView(view, 128),
1843
+ mintedAt: view.getBigInt64(144, true),
1844
+ accountId: view.getBigUint64(152, true)
1845
+ };
1846
+ }
1847
+
1848
+ // src/solana/slab.ts
1849
+ import { PublicKey as PublicKey5 } from "@solana/web3.js";
1369
1850
  function dv(data) {
1370
1851
  return new DataView(data.buffer, data.byteOffset, data.byteLength);
1371
1852
  }
1372
1853
  function readU8(data, off) {
1854
+ if (off >= data.length) {
1855
+ throw new RangeError(`readU8: offset ${off} out of bounds (length ${data.length})`);
1856
+ }
1373
1857
  return data[off];
1374
1858
  }
1375
1859
  function readU16LE(data, off) {
@@ -1400,6 +1884,7 @@ function readU128LE(buf, offset) {
1400
1884
  return hi << 64n | lo;
1401
1885
  }
1402
1886
  var MAGIC = 0x504552434f4c4154n;
1887
+ var SLAB_MAGIC = MAGIC;
1403
1888
  var FLAG_RESOLVED = 1 << 0;
1404
1889
  var V0_HEADER_LEN = 72;
1405
1890
  var V0_CONFIG_LEN = 408;
@@ -1571,8 +2056,27 @@ var V12_1_ENGINE_OFF = 648;
1571
2056
  var V12_1_ACCOUNT_SIZE = 320;
1572
2057
  var V12_1_ACCOUNT_SIZE_SBF = 280;
1573
2058
  var V12_1_ENGINE_BITMAP_OFF = 1016;
1574
- var V12_1_ENGINE_PARAMS_OFF = 96;
2059
+ var V12_1_ENGINE_PARAMS_OFF_SBF = 32;
2060
+ var V12_1_ENGINE_PARAMS_OFF_HOST = 96;
2061
+ var V12_1_PARAMS_SIZE_SBF = 184;
1575
2062
  var V12_1_PARAMS_SIZE = 352;
2063
+ var V12_1_SBF_OFF_CURRENT_SLOT = 216;
2064
+ var V12_1_SBF_OFF_FUNDING_RATE = 224;
2065
+ var V12_1_SBF_OFF_LAST_CRANK_SLOT = 232;
2066
+ var V12_1_SBF_OFF_MAX_CRANK_STALENESS = 240;
2067
+ var V12_1_SBF_OFF_C_TOT = 248;
2068
+ var V12_1_SBF_OFF_PNL_POS_TOT = 264;
2069
+ var V12_1_SBF_OFF_LIQ_CURSOR = 296;
2070
+ var V12_1_SBF_OFF_GC_CURSOR = 298;
2071
+ var V12_1_SBF_OFF_LAST_SWEEP_START = 304;
2072
+ var V12_1_SBF_OFF_LAST_SWEEP_COMPLETE = 312;
2073
+ var V12_1_SBF_OFF_CRANK_CURSOR = 320;
2074
+ var V12_1_SBF_OFF_SWEEP_START_IDX = 322;
2075
+ var V12_1_SBF_OFF_LIFETIME_LIQUIDATIONS = 328;
2076
+ var V12_1_SBF_OFF_TOTAL_OI = 448;
2077
+ var V12_1_SBF_OFF_LONG_OI = 464;
2078
+ var V12_1_SBF_OFF_SHORT_OI = 480;
2079
+ var V12_1_SBF_OFF_MARK_PRICE_E6 = 560;
1576
2080
  var V12_1_ENGINE_CURRENT_SLOT_OFF = 448;
1577
2081
  var V12_1_ENGINE_FUNDING_RATE_BPS_OFF = 456;
1578
2082
  var V12_1_ENGINE_LAST_CRANK_SLOT_OFF = 464;
@@ -1607,7 +2111,112 @@ var V12_1_ACCT_FEE_CREDITS_OFF = 240;
1607
2111
  var V12_1_ACCT_LAST_FEE_SLOT_OFF = 256;
1608
2112
  var V12_1_ACCT_POSITION_SIZE_OFF = 88;
1609
2113
  var V12_1_ACCT_ENTRY_PRICE_OFF = -1;
1610
- var V12_1_ACCT_FUNDING_INDEX_OFF = 288;
2114
+ var V12_1_EP_SBF_ACCOUNT_SIZE = 288;
2115
+ var V12_1_EP_ACCT_ENTRY_PRICE_OFF = 144;
2116
+ var V12_1_EP_ACCT_MATCHER_PROGRAM_OFF = 152;
2117
+ var V12_1_EP_ACCT_MATCHER_CONTEXT_OFF = 184;
2118
+ var V12_1_EP_ACCT_OWNER_OFF = 216;
2119
+ var V12_1_EP_ACCT_FEE_CREDITS_OFF = 248;
2120
+ var V12_1_EP_ACCT_LAST_FEE_SLOT_OFF = 264;
2121
+ var V12_15_ENGINE_OFF = 624;
2122
+ var V12_15_ENGINE_OFF_SBF = 616;
2123
+ var V12_15_ACCOUNT_SIZE = 4400;
2124
+ var V12_15_ACCOUNT_SIZE_SMALL = 920;
2125
+ var V12_15_ACCT_ACCOUNT_ID_OFF = 0;
2126
+ var V12_15_ACCT_CAPITAL_OFF = 8;
2127
+ var V12_15_ACCT_KIND_OFF = 24;
2128
+ var V12_15_ACCT_PNL_OFF = 32;
2129
+ var V12_15_ACCT_RESERVED_PNL_OFF = 48;
2130
+ var V12_15_ACCT_POSITION_BASIS_Q_OFF = 64;
2131
+ var V12_15_ACCT_ENTRY_PRICE_OFF = 120;
2132
+ var V12_15_ACCT_MATCHER_PROGRAM_OFF = 128;
2133
+ var V12_15_ACCT_MATCHER_CONTEXT_OFF = 160;
2134
+ var V12_15_ACCT_OWNER_OFF = 192;
2135
+ var V12_15_ACCT_FEE_CREDITS_OFF = 224;
2136
+ var V12_15_ACCT_FEES_EARNED_TOTAL_OFF = 240;
2137
+ var V12_15_ACCT_EXACT_RESERVE_COHORTS_OFF = 256;
2138
+ var V12_15_ACCT_EXACT_COHORT_COUNT_OFF = 4224;
2139
+ var V12_15_ACCT_OVERFLOW_OLDER_OFF = 4240;
2140
+ var V12_15_ACCT_OVERFLOW_OLDER_PRESENT_OFF = 4304;
2141
+ var V12_15_ACCT_OVERFLOW_NEWEST_OFF = 4320;
2142
+ var V12_15_ACCT_OVERFLOW_NEWEST_PRESENT_OFF = 4384;
2143
+ var V12_15_PARAMS_SIZE = 192;
2144
+ var V12_15_PARAMS_MAX_ACCOUNTS_OFF = 24;
2145
+ var V12_15_PARAMS_INSURANCE_FLOOR_OFF = 144;
2146
+ var V12_15_PARAMS_H_MIN_OFF = 160;
2147
+ var V12_15_PARAMS_H_MAX_OFF = 168;
2148
+ var V12_15_ENGINE_PARAMS_OFF = 32;
2149
+ var V12_15_ENGINE_CURRENT_SLOT_OFF = 224;
2150
+ var V12_15_ENGINE_FUNDING_RATE_E9_OFF = 240;
2151
+ var V12_15_ENGINE_C_TOT_OFF = 344;
2152
+ var V12_15_ENGINE_PNL_POS_TOT_OFF = 368;
2153
+ var V12_15_ENGINE_PNL_MATURED_POS_TOT_OFF = 384;
2154
+ var V12_15_ENGINE_BITMAP_OFF = 862;
2155
+ var V12_15_SIZES = /* @__PURE__ */ new Map();
2156
+ var V12_17_ENGINE_OFF = 592;
2157
+ var V12_17_ACCOUNT_SIZE = 368;
2158
+ var V12_17_ENGINE_BITMAP_OFF = 752;
2159
+ var V12_17_RISK_BUF_LEN = 160;
2160
+ var V12_17_GEN_TABLE_ENTRY = 8;
2161
+ var V12_17_ENGINE_OFF_SBF = 584;
2162
+ var V12_17_ACCOUNT_SIZE_SBF = 352;
2163
+ var V12_17_ENGINE_BITMAP_OFF_SBF = 712;
2164
+ var V12_17_ACCT_CAPITAL_OFF = 0;
2165
+ var V12_17_ACCT_KIND_OFF = 16;
2166
+ var V12_17_ACCT_PNL_OFF = 32;
2167
+ var V12_17_ACCT_RESERVED_PNL_OFF = 48;
2168
+ var V12_17_ACCT_POSITION_BASIS_Q_OFF = 64;
2169
+ var V12_17_ACCT_ADL_A_BASIS_OFF = 80;
2170
+ var V12_17_ACCT_ADL_K_SNAP_OFF = 96;
2171
+ var V12_17_ACCT_F_SNAP_OFF = 112;
2172
+ var V12_17_ACCT_ADL_EPOCH_SNAP_OFF = 128;
2173
+ var V12_17_ACCT_MATCHER_PROGRAM_OFF = 136;
2174
+ var V12_17_ACCT_MATCHER_CONTEXT_OFF = 168;
2175
+ var V12_17_ACCT_OWNER_OFF = 200;
2176
+ var V12_17_ACCT_FEE_CREDITS_OFF = 232;
2177
+ var V12_17_ACCT_SCHED_PRESENT_OFF = 248;
2178
+ var V12_17_ACCT_SCHED_REMAINING_Q_OFF = 256;
2179
+ var V12_17_ACCT_SCHED_ANCHOR_Q_OFF = 272;
2180
+ var V12_17_ACCT_SCHED_START_SLOT_OFF = 288;
2181
+ var V12_17_ACCT_SCHED_HORIZON_OFF = 296;
2182
+ var V12_17_ACCT_SCHED_RELEASE_Q_OFF = 304;
2183
+ var V12_17_ACCT_PENDING_PRESENT_OFF = 320;
2184
+ var V12_17_ACCT_PENDING_REMAINING_Q_OFF = 336;
2185
+ var V12_17_ACCT_PENDING_HORIZON_OFF = 352;
2186
+ var V12_17_ACCT_PENDING_CREATED_SLOT_OFF = 360;
2187
+ var V12_17_ENGINE_PARAMS_OFF = 32;
2188
+ var V12_17_ENGINE_CURRENT_SLOT_OFF = 224;
2189
+ var V12_17_ENGINE_MARKET_MODE_OFF = 232;
2190
+ var V12_17_ENGINE_RESOLVED_K_LONG_OFF = 304;
2191
+ var V12_17_ENGINE_RESOLVED_K_SHORT_OFF = 320;
2192
+ var V12_17_ENGINE_RESOLVED_LIVE_PRICE_OFF = 336;
2193
+ var V12_17_ENGINE_LAST_CRANK_SLOT_OFF = 344;
2194
+ var V12_17_ENGINE_C_TOT_OFF = 352;
2195
+ var V12_17_ENGINE_PNL_POS_TOT_OFF = 368;
2196
+ var V12_17_ENGINE_PNL_MATURED_POS_TOT_OFF = 384;
2197
+ var V12_17_ENGINE_GC_CURSOR_OFF = 400;
2198
+ var V12_17_ENGINE_OI_EFF_LONG_OFF = 528;
2199
+ var V12_17_ENGINE_OI_EFF_SHORT_OFF = 544;
2200
+ var V12_17_ENGINE_NEG_PNL_COUNT_OFF = 648;
2201
+ var V12_17_ENGINE_LAST_ORACLE_PRICE_OFF = 656;
2202
+ var V12_17_ENGINE_FUND_PX_LAST_OFF = 664;
2203
+ var V12_17_ENGINE_F_LONG_NUM_OFF = 688;
2204
+ var V12_17_ENGINE_F_SHORT_NUM_OFF = 704;
2205
+ var V12_17_SBF_ENGINE_CURRENT_SLOT_OFF = 216;
2206
+ var V12_17_SBF_ENGINE_MARKET_MODE_OFF = 224;
2207
+ var V12_17_SBF_ENGINE_LAST_CRANK_SLOT_OFF = 328;
2208
+ var V12_17_SBF_ENGINE_C_TOT_OFF = 336;
2209
+ var V12_17_SBF_ENGINE_PNL_POS_TOT_OFF = 352;
2210
+ var V12_17_SBF_ENGINE_PNL_MATURED_POS_TOT_OFF = 368;
2211
+ var V12_17_SBF_ENGINE_GC_CURSOR_OFF = 384;
2212
+ var V12_17_SBF_ENGINE_OI_EFF_LONG_OFF = 504;
2213
+ var V12_17_SBF_ENGINE_OI_EFF_SHORT_OFF = 520;
2214
+ var V12_17_SBF_ENGINE_NEG_PNL_COUNT_OFF = 616;
2215
+ var V12_17_SBF_ENGINE_LAST_ORACLE_PRICE_OFF = 624;
2216
+ var V12_17_SBF_ENGINE_FUND_PX_LAST_OFF = 632;
2217
+ var V12_17_SBF_ENGINE_F_LONG_NUM_OFF = 648;
2218
+ var V12_17_SBF_ENGINE_F_SHORT_NUM_OFF = 664;
2219
+ var V12_17_SIZES = /* @__PURE__ */ new Map();
1611
2220
  var V1M_ENGINE_OFF = 640;
1612
2221
  var V1M_CONFIG_LEN = 536;
1613
2222
  var V1M_ACCOUNT_SIZE = 248;
@@ -1680,16 +2289,92 @@ for (const n of TIERS) {
1680
2289
  V1M2_SIZES.set(computeSlabSize(V1M2_ENGINE_OFF, V1M2_ENGINE_BITMAP_OFF, V1M2_ACCOUNT_SIZE, n, 18), n);
1681
2290
  V_SETDEXPOOL_SIZES.set(computeSlabSize(V_SETDEXPOOL_ENGINE_OFF, V_ADL_ENGINE_BITMAP_OFF, V_ADL_ACCOUNT_SIZE, n, 18), n);
1682
2291
  V12_1_SIZES.set(computeSlabSize(V12_1_ENGINE_OFF, V12_1_ENGINE_BITMAP_OFF, V12_1_ACCOUNT_SIZE, n, 18), n);
2292
+ V12_15_SIZES.set(computeSlabSize(V12_15_ENGINE_OFF, V12_15_ENGINE_BITMAP_OFF, V12_15_ACCOUNT_SIZE, n, 18), n);
2293
+ }
2294
+ V12_15_SIZES.set(computeSlabSize(V12_15_ENGINE_OFF, V12_15_ENGINE_BITMAP_OFF, V12_15_ACCOUNT_SIZE, 2048, 18), 2048);
2295
+ V12_15_SIZES.set(237512, 256);
2296
+ var V12_17_TIERS = [256, 1024, 4096];
2297
+ for (const n of V12_17_TIERS) {
2298
+ const bitmapWords = Math.ceil(n / 64);
2299
+ const bitmapBytes = bitmapWords * 8;
2300
+ const postBitmap = 4;
2301
+ const nextFreeBytes = n * 2;
2302
+ const preAccNative = V12_17_ENGINE_BITMAP_OFF + bitmapBytes + postBitmap + nextFreeBytes;
2303
+ const accountsOffNative = Math.ceil(preAccNative / 16) * 16;
2304
+ const nativeSize = V12_17_ENGINE_OFF + accountsOffNative + n * V12_17_ACCOUNT_SIZE + V12_17_RISK_BUF_LEN + n * V12_17_GEN_TABLE_ENTRY;
2305
+ V12_17_SIZES.set(nativeSize, n);
2306
+ const preAccSbf = V12_17_ENGINE_BITMAP_OFF_SBF + bitmapBytes + postBitmap + nextFreeBytes;
2307
+ const accountsOffSbf = Math.ceil(preAccSbf / 8) * 8;
2308
+ const sbfSize = V12_17_ENGINE_OFF_SBF + accountsOffSbf + n * V12_17_ACCOUNT_SIZE_SBF + V12_17_RISK_BUF_LEN + n * V12_17_GEN_TABLE_ENTRY;
2309
+ V12_17_SIZES.set(sbfSize, n);
2310
+ }
2311
+ var V12_19_CONFIG_LEN = 528;
2312
+ var V12_19_ENGINE_OFF_SBF = 600;
2313
+ var V12_19_SBF_ENGINE_CURRENT_SLOT_OFF = 216;
2314
+ var V12_19_SBF_ENGINE_MARKET_MODE_OFF = 224;
2315
+ var V12_19_SBF_ENGINE_RESOLVED_LIVE_PRICE_OFF = 320;
2316
+ var V12_19_SBF_ENGINE_C_TOT_OFF = 328;
2317
+ var V12_19_SBF_ENGINE_PNL_POS_TOT_OFF = 344;
2318
+ var V12_19_SBF_ENGINE_PNL_MATURED_POS_TOT_OFF = 360;
2319
+ var V12_19_SBF_ENGINE_OI_EFF_LONG_OFF = 488;
2320
+ var V12_19_SBF_ENGINE_OI_EFF_SHORT_OFF = 504;
2321
+ var V12_19_SBF_ENGINE_NEG_PNL_COUNT_OFF = 608;
2322
+ var V12_19_SBF_ENGINE_RR_CURSOR_OFF = 616;
2323
+ var V12_19_SBF_ENGINE_LAST_ORACLE_PRICE_OFF = 640;
2324
+ var V12_19_SBF_ENGINE_FUND_PX_LAST_OFF = 648;
2325
+ var V12_19_SBF_ENGINE_LAST_MARKET_SLOT_OFF = 656;
2326
+ var V12_19_SBF_ENGINE_F_LONG_NUM_OFF = 664;
2327
+ var V12_19_SBF_ENGINE_F_SHORT_NUM_OFF = 680;
2328
+ var V12_19_SIZES = /* @__PURE__ */ new Map([
2329
+ [19640, 64],
2330
+ // --features micro
2331
+ [94168, 256],
2332
+ // --features small (deployed mainnet ESa89R5...)
2333
+ [372280, 1024],
2334
+ // --features medium
2335
+ [1484728, 4096]
2336
+ // default features (large)
2337
+ ]);
2338
+ function buildLayoutV12_19(maxAccounts, dataLen) {
2339
+ const base = buildLayoutV12_17(maxAccounts, dataLen);
2340
+ return {
2341
+ ...base,
2342
+ configLen: V12_19_CONFIG_LEN,
2343
+ engineOff: V12_19_ENGINE_OFF_SBF,
2344
+ accountsOff: V12_19_ENGINE_OFF_SBF + (base.accountsOff - base.engineOff),
2345
+ // V12_19 engine field offsets (only the fields exposed in SlabLayout).
2346
+ // Other engine fields (negPnlCount, fundPxLast, fLongNum, fShortNum,
2347
+ // lastOraclePrice, marketMode, pnlMaturedPosTot) are read by parseEngine
2348
+ // via its own version-aware switch keyed on engineOff === 600.
2349
+ engineCurrentSlotOff: V12_19_SBF_ENGINE_CURRENT_SLOT_OFF,
2350
+ engineCTotOff: V12_19_SBF_ENGINE_C_TOT_OFF,
2351
+ enginePnlPosTotOff: V12_19_SBF_ENGINE_PNL_POS_TOT_OFF,
2352
+ engineLongOiOff: V12_19_SBF_ENGINE_OI_EFF_LONG_OFF,
2353
+ engineShortOiOff: V12_19_SBF_ENGINE_OI_EFF_SHORT_OFF,
2354
+ // V12_19 last_market_slot replaces V12_17 last_crank_slot semantics.
2355
+ engineLastCrankSlotOff: V12_19_SBF_ENGINE_LAST_MARKET_SLOT_OFF,
2356
+ // V12_19 rr_cursor_position replaces V12_17 gc_cursor semantics.
2357
+ engineGcCursorOff: V12_19_SBF_ENGINE_RR_CURSOR_OFF
2358
+ };
1683
2359
  }
1684
2360
  var V12_1_SBF_ACCOUNT_SIZE = 280;
1685
- var V12_1_SBF_ENGINE_PREAMBLE = 558;
2361
+ var V12_1_SBF_ENGINE_OFF = 616;
2362
+ var V12_1_SBF_BITMAP_OFF = 584;
1686
2363
  for (const [, n] of [["Micro", 64], ["Small", 256], ["Medium", 1024], ["Large", 4096]]) {
1687
2364
  const bitmapBytes = Math.ceil(n / 64) * 8;
1688
- const preAccLen = V12_1_SBF_ENGINE_PREAMBLE + bitmapBytes + 18 + n * 2;
2365
+ const preAccLen = V12_1_SBF_BITMAP_OFF + bitmapBytes + 18 + n * 2;
1689
2366
  const accountsOff = Math.ceil(preAccLen / 8) * 8;
1690
- const total = V12_1_ENGINE_OFF + accountsOff + n * V12_1_SBF_ACCOUNT_SIZE;
2367
+ const total = V12_1_SBF_ENGINE_OFF + accountsOff + n * V12_1_SBF_ACCOUNT_SIZE;
1691
2368
  V12_1_SIZES.set(total, n);
1692
2369
  }
2370
+ var V12_1_EP_SIZES = /* @__PURE__ */ new Map();
2371
+ for (const [, n] of [["Micro", 64], ["Small", 256], ["Medium", 1024], ["Large", 4096]]) {
2372
+ const bitmapBytes = Math.ceil(n / 64) * 8;
2373
+ const preAccLen = V12_1_SBF_BITMAP_OFF + bitmapBytes + 18 + n * 2;
2374
+ const accountsOff = Math.ceil(preAccLen / 8) * 8;
2375
+ const total = V12_1_SBF_ENGINE_OFF + accountsOff + n * V12_1_EP_SBF_ACCOUNT_SIZE;
2376
+ V12_1_EP_SIZES.set(total, n);
2377
+ }
1693
2378
  var SLAB_TIERS_V2 = {
1694
2379
  small: { maxAccounts: 256, dataSize: 65088, label: "Small", description: "256 slots (V2 BPF intermediate)" },
1695
2380
  large: { maxAccounts: 4096, dataSize: 1025568, label: "Large", description: "4,096 slots (V2 BPF intermediate)" }
@@ -2154,6 +2839,19 @@ for (const [label, n] of [["Micro", 64], ["Small", 256], ["Medium", 1024], ["Lar
2154
2839
  const size = computeSlabSize(V12_1_ENGINE_OFF, V12_1_ENGINE_BITMAP_OFF, V12_1_ACCOUNT_SIZE, n, 18);
2155
2840
  SLAB_TIERS_V12_1[label.toLowerCase()] = { maxAccounts: n, dataSize: size, label, description: `${n} slots (v12.1)` };
2156
2841
  }
2842
+ var SLAB_TIERS_V12_15 = {};
2843
+ for (const [label, n] of [["Micro", 64], ["Small", 256], ["Medium", 1024], ["Medium2048", 2048], ["Large", 4096]]) {
2844
+ const size = computeSlabSize(V12_15_ENGINE_OFF, V12_15_ENGINE_BITMAP_OFF, V12_15_ACCOUNT_SIZE, n, 18);
2845
+ SLAB_TIERS_V12_15[label.toLowerCase()] = { maxAccounts: n, dataSize: size, label, description: `${n} slots (v12.15)` };
2846
+ }
2847
+ var SLAB_TIERS_V12_17 = {};
2848
+ for (const [label, n] of [["Small", 256], ["Medium", 1024], ["Large", 4096]]) {
2849
+ const bitmapBytes = Math.ceil(n / 64) * 8;
2850
+ const preAcc = V12_17_ENGINE_BITMAP_OFF_SBF + bitmapBytes + 4 + n * 2;
2851
+ const accountsOff = Math.ceil(preAcc / 8) * 8;
2852
+ const size = V12_17_ENGINE_OFF_SBF + accountsOff + n * V12_17_ACCOUNT_SIZE_SBF + V12_17_RISK_BUF_LEN + n * V12_17_GEN_TABLE_ENTRY;
2853
+ SLAB_TIERS_V12_17[label.toLowerCase()] = { maxAccounts: n, dataSize: size, label, description: `${n} slots (v12.17)` };
2854
+ }
2157
2855
  function buildLayoutVSetDexPool(maxAccounts) {
2158
2856
  const engineOff = V_SETDEXPOOL_ENGINE_OFF;
2159
2857
  const bitmapOff = V_ADL_ENGINE_BITMAP_OFF;
@@ -2214,73 +2912,341 @@ function buildLayoutVSetDexPool(maxAccounts) {
2214
2912
  engineInsuranceIsolationBpsOff: 64
2215
2913
  };
2216
2914
  }
2217
- function buildLayoutV12_1(maxAccounts, dataLen) {
2218
- const engineOff = V12_1_ENGINE_OFF;
2219
- const bitmapOff = V12_1_ENGINE_BITMAP_OFF;
2220
- const hostSize = computeSlabSize(engineOff, bitmapOff, V12_1_ACCOUNT_SIZE, maxAccounts, 18);
2221
- const isSbf = dataLen !== void 0 && dataLen !== hostSize;
2222
- const accountSize = isSbf ? V12_1_ACCOUNT_SIZE_SBF : V12_1_ACCOUNT_SIZE;
2915
+ function buildLayoutV12_1(maxAccounts, dataLen) {
2916
+ const hostSize = computeSlabSize(V12_1_ENGINE_OFF, V12_1_ENGINE_BITMAP_OFF, V12_1_ACCOUNT_SIZE, maxAccounts, 18);
2917
+ const isSbf = dataLen !== void 0 && dataLen !== hostSize;
2918
+ const engineOff = isSbf ? V12_1_SBF_ENGINE_OFF : V12_1_ENGINE_OFF;
2919
+ const bitmapOff = isSbf ? V12_1_SBF_BITMAP_OFF : V12_1_ENGINE_BITMAP_OFF - V12_1_ENGINE_OFF;
2920
+ const accountSize = isSbf ? V12_1_ACCOUNT_SIZE_SBF : V12_1_ACCOUNT_SIZE;
2921
+ const bitmapWords = Math.ceil(maxAccounts / 64);
2922
+ const bitmapBytes = bitmapWords * 8;
2923
+ const postBitmap = 18;
2924
+ const nextFreeBytes = maxAccounts * 2;
2925
+ const preAccountsLen = bitmapOff + bitmapBytes + postBitmap + nextFreeBytes;
2926
+ const accountsOffRel = Math.ceil(preAccountsLen / 8) * 8;
2927
+ return {
2928
+ version: 1,
2929
+ headerLen: V0_HEADER_LEN,
2930
+ // 72
2931
+ configOffset: V0_HEADER_LEN,
2932
+ // 72
2933
+ configLen: isSbf ? 544 : 576,
2934
+ reservedOff: V1_RESERVED_OFF,
2935
+ engineOff,
2936
+ accountSize,
2937
+ maxAccounts,
2938
+ bitmapWords,
2939
+ accountsOff: engineOff + accountsOffRel,
2940
+ engineInsuranceOff: 16,
2941
+ engineParamsOff: isSbf ? V12_1_ENGINE_PARAMS_OFF_SBF : V12_1_ENGINE_PARAMS_OFF_HOST,
2942
+ paramsSize: isSbf ? V12_1_PARAMS_SIZE_SBF : V12_1_PARAMS_SIZE,
2943
+ // SBF engine offsets — all verified by cargo build-sbf offset_of! assertions.
2944
+ // Fields that don't exist in the deployed program are set to -1 on SBF.
2945
+ engineCurrentSlotOff: isSbf ? V12_1_SBF_OFF_CURRENT_SLOT : V12_1_ENGINE_CURRENT_SLOT_OFF,
2946
+ engineFundingIndexOff: isSbf ? -1 : V12_1_ENGINE_FUNDING_INDEX_OFF,
2947
+ // not in deployed struct
2948
+ engineLastFundingSlotOff: isSbf ? -1 : V12_1_ENGINE_LAST_FUNDING_SLOT_OFF,
2949
+ // not in deployed struct
2950
+ engineFundingRateBpsOff: isSbf ? V12_1_SBF_OFF_FUNDING_RATE : V12_1_ENGINE_FUNDING_RATE_BPS_OFF,
2951
+ engineMarkPriceOff: isSbf ? V12_1_SBF_OFF_MARK_PRICE_E6 : V12_1_ENGINE_MARK_PRICE_OFF,
2952
+ engineLastCrankSlotOff: isSbf ? V12_1_SBF_OFF_LAST_CRANK_SLOT : V12_1_ENGINE_LAST_CRANK_SLOT_OFF,
2953
+ engineMaxCrankStalenessOff: isSbf ? V12_1_SBF_OFF_MAX_CRANK_STALENESS : V12_1_ENGINE_MAX_CRANK_STALENESS_OFF,
2954
+ engineTotalOiOff: isSbf ? V12_1_SBF_OFF_TOTAL_OI : V12_1_ENGINE_TOTAL_OI_OFF,
2955
+ engineLongOiOff: isSbf ? V12_1_SBF_OFF_LONG_OI : V12_1_ENGINE_LONG_OI_OFF,
2956
+ engineShortOiOff: isSbf ? V12_1_SBF_OFF_SHORT_OI : V12_1_ENGINE_SHORT_OI_OFF,
2957
+ engineCTotOff: isSbf ? V12_1_SBF_OFF_C_TOT : V12_1_ENGINE_C_TOT_OFF,
2958
+ enginePnlPosTotOff: isSbf ? V12_1_SBF_OFF_PNL_POS_TOT : V12_1_ENGINE_PNL_POS_TOT_OFF,
2959
+ engineLiqCursorOff: isSbf ? V12_1_SBF_OFF_LIQ_CURSOR : V12_1_ENGINE_LIQ_CURSOR_OFF,
2960
+ engineGcCursorOff: isSbf ? V12_1_SBF_OFF_GC_CURSOR : V12_1_ENGINE_GC_CURSOR_OFF,
2961
+ engineLastSweepStartOff: isSbf ? V12_1_SBF_OFF_LAST_SWEEP_START : V12_1_ENGINE_LAST_SWEEP_START_OFF,
2962
+ engineLastSweepCompleteOff: isSbf ? V12_1_SBF_OFF_LAST_SWEEP_COMPLETE : V12_1_ENGINE_LAST_SWEEP_COMPLETE_OFF,
2963
+ engineCrankCursorOff: isSbf ? V12_1_SBF_OFF_CRANK_CURSOR : V12_1_ENGINE_CRANK_CURSOR_OFF,
2964
+ engineSweepStartIdxOff: isSbf ? V12_1_SBF_OFF_SWEEP_START_IDX : V12_1_ENGINE_SWEEP_START_IDX_OFF,
2965
+ engineLifetimeLiquidationsOff: isSbf ? V12_1_SBF_OFF_LIFETIME_LIQUIDATIONS : V12_1_ENGINE_LIFETIME_LIQUIDATIONS_OFF,
2966
+ engineLifetimeForceClosesOff: isSbf ? -1 : V12_1_ENGINE_LIFETIME_FORCE_CLOSES_OFF,
2967
+ // not in deployed struct
2968
+ engineNetLpPosOff: isSbf ? -1 : V12_1_ENGINE_NET_LP_POS_OFF,
2969
+ // not in deployed struct
2970
+ engineLpSumAbsOff: isSbf ? -1 : V12_1_ENGINE_LP_SUM_ABS_OFF,
2971
+ // not in deployed struct
2972
+ engineLpMaxAbsOff: isSbf ? -1 : V12_1_ENGINE_LP_MAX_ABS_OFF,
2973
+ // not in deployed struct
2974
+ engineLpMaxAbsSweepOff: isSbf ? -1 : V12_1_ENGINE_LP_MAX_ABS_SWEEP_OFF,
2975
+ // not in deployed struct
2976
+ engineEmergencyOiModeOff: isSbf ? -1 : V12_1_ENGINE_EMERGENCY_OI_MODE_OFF,
2977
+ // not in deployed struct
2978
+ engineEmergencyStartSlotOff: isSbf ? -1 : V12_1_ENGINE_EMERGENCY_START_SLOT_OFF,
2979
+ // not in deployed struct
2980
+ engineLastBreakerSlotOff: isSbf ? -1 : V12_1_ENGINE_LAST_BREAKER_SLOT_OFF,
2981
+ // not in deployed struct
2982
+ engineBitmapOff: bitmapOff,
2983
+ postBitmap: 18,
2984
+ acctOwnerOff: V12_1_ACCT_OWNER_OFF,
2985
+ // InsuranceFund on deployed program is just {balance: U128} = 16 bytes.
2986
+ // No isolated_balance or insurance_isolation_bps fields.
2987
+ hasInsuranceIsolation: !isSbf,
2988
+ engineInsuranceIsolatedOff: isSbf ? -1 : 48,
2989
+ engineInsuranceIsolationBpsOff: isSbf ? -1 : 64
2990
+ };
2991
+ }
2992
+ function buildLayoutV12_1EP(maxAccounts) {
2993
+ const engineOff = V12_1_SBF_ENGINE_OFF;
2994
+ const bitmapOff = V12_1_SBF_BITMAP_OFF;
2995
+ const accountSize = V12_1_EP_SBF_ACCOUNT_SIZE;
2996
+ const bitmapWords = Math.ceil(maxAccounts / 64);
2997
+ const bitmapBytes = bitmapWords * 8;
2998
+ const postBitmap = 18;
2999
+ const nextFreeBytes = maxAccounts * 2;
3000
+ const preAccountsLen = bitmapOff + bitmapBytes + postBitmap + nextFreeBytes;
3001
+ const accountsOffRel = Math.ceil(preAccountsLen / 8) * 8;
3002
+ return {
3003
+ version: 1,
3004
+ headerLen: 72,
3005
+ configOffset: 72,
3006
+ configLen: 544,
3007
+ reservedOff: 80,
3008
+ // V1_RESERVED_OFF
3009
+ engineOff,
3010
+ accountSize,
3011
+ maxAccounts,
3012
+ bitmapWords,
3013
+ accountsOff: engineOff + accountsOffRel,
3014
+ engineInsuranceOff: 16,
3015
+ engineParamsOff: 32,
3016
+ // V12_1_ENGINE_PARAMS_OFF_SBF
3017
+ paramsSize: 184,
3018
+ // V12_1_PARAMS_SIZE_SBF
3019
+ // Engine offsets identical to V12_1 SBF
3020
+ engineCurrentSlotOff: V12_1_SBF_OFF_CURRENT_SLOT,
3021
+ engineFundingIndexOff: -1,
3022
+ engineLastFundingSlotOff: -1,
3023
+ engineFundingRateBpsOff: V12_1_SBF_OFF_FUNDING_RATE,
3024
+ engineMarkPriceOff: V12_1_SBF_OFF_MARK_PRICE_E6,
3025
+ engineLastCrankSlotOff: V12_1_SBF_OFF_LAST_CRANK_SLOT,
3026
+ engineMaxCrankStalenessOff: V12_1_SBF_OFF_MAX_CRANK_STALENESS,
3027
+ engineTotalOiOff: V12_1_SBF_OFF_TOTAL_OI,
3028
+ engineLongOiOff: V12_1_SBF_OFF_LONG_OI,
3029
+ engineShortOiOff: V12_1_SBF_OFF_SHORT_OI,
3030
+ engineCTotOff: V12_1_SBF_OFF_C_TOT,
3031
+ enginePnlPosTotOff: V12_1_SBF_OFF_PNL_POS_TOT,
3032
+ engineLiqCursorOff: V12_1_SBF_OFF_LIQ_CURSOR,
3033
+ engineGcCursorOff: V12_1_SBF_OFF_GC_CURSOR,
3034
+ engineLastSweepStartOff: V12_1_SBF_OFF_LAST_SWEEP_START,
3035
+ engineLastSweepCompleteOff: V12_1_SBF_OFF_LAST_SWEEP_COMPLETE,
3036
+ engineCrankCursorOff: V12_1_SBF_OFF_CRANK_CURSOR,
3037
+ engineSweepStartIdxOff: V12_1_SBF_OFF_SWEEP_START_IDX,
3038
+ engineLifetimeLiquidationsOff: V12_1_SBF_OFF_LIFETIME_LIQUIDATIONS,
3039
+ engineLifetimeForceClosesOff: -1,
3040
+ engineNetLpPosOff: -1,
3041
+ engineLpSumAbsOff: -1,
3042
+ engineLpMaxAbsOff: -1,
3043
+ engineLpMaxAbsSweepOff: -1,
3044
+ engineEmergencyOiModeOff: -1,
3045
+ engineEmergencyStartSlotOff: -1,
3046
+ engineLastBreakerSlotOff: -1,
3047
+ engineBitmapOff: bitmapOff,
3048
+ postBitmap: 18,
3049
+ // Account offsets — shifted +8 from V12_1 due to entry_price insertion
3050
+ acctOwnerOff: V12_1_EP_ACCT_OWNER_OFF,
3051
+ // 216 (was 208)
3052
+ hasInsuranceIsolation: false,
3053
+ engineInsuranceIsolatedOff: -1,
3054
+ engineInsuranceIsolationBpsOff: -1
3055
+ };
3056
+ }
3057
+ function buildLayoutV12_15(maxAccounts, dataLen) {
3058
+ const isSbf = dataLen === 237512;
3059
+ const accountSize = isSbf ? V12_15_ACCOUNT_SIZE_SMALL : V12_15_ACCOUNT_SIZE;
3060
+ const engineOff = isSbf ? V12_15_ENGINE_OFF_SBF : V12_15_ENGINE_OFF;
3061
+ const bitmapOff = V12_15_ENGINE_BITMAP_OFF;
3062
+ const effectiveBitmapOff = isSbf ? 648 : bitmapOff;
3063
+ const bitmapWords = Math.ceil(maxAccounts / 64);
3064
+ const bitmapBytes = bitmapWords * 8;
3065
+ const postBitmap = 18;
3066
+ const nextFreeBytes = maxAccounts * 2;
3067
+ const preAccountsLen = effectiveBitmapOff + bitmapBytes + postBitmap + nextFreeBytes;
3068
+ const accountsOffRel = Math.ceil(preAccountsLen / 8) * 8;
3069
+ return {
3070
+ version: 2,
3071
+ headerLen: V0_HEADER_LEN,
3072
+ // 72
3073
+ configOffset: V0_HEADER_LEN,
3074
+ // 72
3075
+ configLen: 552,
3076
+ // SBF CONFIG_LEN for v12.15
3077
+ reservedOff: V1_RESERVED_OFF,
3078
+ // 80
3079
+ engineOff,
3080
+ accountSize,
3081
+ maxAccounts,
3082
+ bitmapWords,
3083
+ accountsOff: engineOff + accountsOffRel,
3084
+ engineInsuranceOff: 16,
3085
+ engineParamsOff: V12_15_ENGINE_PARAMS_OFF,
3086
+ // 32
3087
+ paramsSize: isSbf ? 184 : V12_15_PARAMS_SIZE,
3088
+ // SBF=184 (no trailing pad), native=192
3089
+ engineCurrentSlotOff: isSbf ? 216 : V12_15_ENGINE_CURRENT_SLOT_OFF,
3090
+ // SBF=216, native=224
3091
+ engineFundingIndexOff: -1,
3092
+ // not present in v12.15 engine struct
3093
+ engineLastFundingSlotOff: -1,
3094
+ // not present in v12.15 engine struct
3095
+ engineFundingRateBpsOff: isSbf ? 224 : V12_15_ENGINE_FUNDING_RATE_E9_OFF,
3096
+ // SBF=224, native=240
3097
+ engineMarkPriceOff: -1,
3098
+ // not present in v12.15
3099
+ engineLastCrankSlotOff: -1,
3100
+ // not yet mapped
3101
+ engineMaxCrankStalenessOff: -1,
3102
+ // not yet mapped
3103
+ engineTotalOiOff: -1,
3104
+ // not present in v12.15 engine
3105
+ engineLongOiOff: -1,
3106
+ // not present in v12.15 engine
3107
+ engineShortOiOff: -1,
3108
+ // not present in v12.15 engine
3109
+ engineCTotOff: isSbf ? 320 : V12_15_ENGINE_C_TOT_OFF,
3110
+ // SBF=320 (verified on-chain), native=344
3111
+ enginePnlPosTotOff: isSbf ? 336 : V12_15_ENGINE_PNL_POS_TOT_OFF,
3112
+ // SBF=336 (verified), native=368
3113
+ engineLiqCursorOff: -1,
3114
+ // not yet mapped
3115
+ engineGcCursorOff: -1,
3116
+ // not yet mapped
3117
+ engineLastSweepStartOff: -1,
3118
+ // not yet mapped
3119
+ engineLastSweepCompleteOff: -1,
3120
+ // not yet mapped
3121
+ engineCrankCursorOff: -1,
3122
+ // not yet mapped
3123
+ engineSweepStartIdxOff: -1,
3124
+ // not yet mapped
3125
+ engineLifetimeLiquidationsOff: -1,
3126
+ // not yet mapped
3127
+ engineLifetimeForceClosesOff: -1,
3128
+ // not present in v12.15
3129
+ engineNetLpPosOff: -1,
3130
+ // not present in v12.15
3131
+ engineLpSumAbsOff: -1,
3132
+ // not present in v12.15
3133
+ engineLpMaxAbsOff: -1,
3134
+ // not present in v12.15
3135
+ engineLpMaxAbsSweepOff: -1,
3136
+ // not present in v12.15
3137
+ engineEmergencyOiModeOff: -1,
3138
+ // not present in v12.15
3139
+ engineEmergencyStartSlotOff: -1,
3140
+ // not present in v12.15
3141
+ engineLastBreakerSlotOff: -1,
3142
+ // not present in v12.15
3143
+ engineBitmapOff: effectiveBitmapOff,
3144
+ // SBF=640, native=862
3145
+ postBitmap,
3146
+ acctOwnerOff: V12_15_ACCT_OWNER_OFF,
3147
+ // 192
3148
+ hasInsuranceIsolation: false,
3149
+ engineInsuranceIsolatedOff: -1,
3150
+ engineInsuranceIsolationBpsOff: -1
3151
+ };
3152
+ }
3153
+ function buildLayoutV12_17(maxAccounts, dataLen) {
3154
+ const isSbf = (() => {
3155
+ const bitmapBytes2 = Math.ceil(maxAccounts / 64) * 8;
3156
+ const preAccNative = V12_17_ENGINE_BITMAP_OFF + bitmapBytes2 + 4 + maxAccounts * 2;
3157
+ const accountsOffNative = Math.ceil(preAccNative / 16) * 16;
3158
+ const nativeSize = V12_17_ENGINE_OFF + accountsOffNative + maxAccounts * V12_17_ACCOUNT_SIZE + V12_17_RISK_BUF_LEN + maxAccounts * V12_17_GEN_TABLE_ENTRY;
3159
+ return dataLen !== nativeSize;
3160
+ })();
3161
+ const engineOff = isSbf ? V12_17_ENGINE_OFF_SBF : V12_17_ENGINE_OFF;
3162
+ const accountSize = isSbf ? V12_17_ACCOUNT_SIZE_SBF : V12_17_ACCOUNT_SIZE;
3163
+ const bitmapOff = isSbf ? V12_17_ENGINE_BITMAP_OFF_SBF : V12_17_ENGINE_BITMAP_OFF;
2223
3164
  const bitmapWords = Math.ceil(maxAccounts / 64);
2224
3165
  const bitmapBytes = bitmapWords * 8;
2225
- const postBitmap = 18;
3166
+ const postBitmap = 4;
2226
3167
  const nextFreeBytes = maxAccounts * 2;
2227
3168
  const preAccountsLen = bitmapOff + bitmapBytes + postBitmap + nextFreeBytes;
2228
- const accountsOffRel = Math.ceil(preAccountsLen / 8) * 8;
3169
+ const acctAlign = isSbf ? 8 : 16;
3170
+ const accountsOffRel = Math.ceil(preAccountsLen / acctAlign) * acctAlign;
2229
3171
  return {
2230
- version: 1,
2231
- // V12_1 upstream rebase uses 72-byte header (SlabHeader only, no V1 extension).
2232
- // Empirically verified: USDC mint found at offset 72 on mainnet slab BVjPc6rd.
3172
+ version: 2,
2233
3173
  headerLen: V0_HEADER_LEN,
2234
- // 72 (not 104 — V12_1 removed the 32-byte header extension)
3174
+ // 72
2235
3175
  configOffset: V0_HEADER_LEN,
2236
3176
  // 72
2237
- configLen: 576,
2238
- // 544 + 32 (dex_pool: [u8;32] added in V12_1)
3177
+ // configLen = 512 (SBF-aligned MarketConfig size after Phase A/B/E).
3178
+ // Verified field-by-field against percolator-prog/src/percolator.rs MarketConfig struct.
3179
+ // Missing 80 bytes from prior value 432: max_pnl_cap, last_audit_pause_slot,
3180
+ // oi_cap_multiplier_bps, dispute_window_slots, dispute_bond_amount,
3181
+ // lp_collateral_enabled, lp_collateral_ltv_bps, _new_fields_pad, pending_admin.
3182
+ configLen: 512,
2239
3183
  reservedOff: V1_RESERVED_OFF,
3184
+ // 80
2240
3185
  engineOff,
2241
3186
  accountSize,
2242
3187
  maxAccounts,
2243
3188
  bitmapWords,
2244
3189
  accountsOff: engineOff + accountsOffRel,
2245
3190
  engineInsuranceOff: 16,
2246
- engineParamsOff: V12_1_ENGINE_PARAMS_OFF,
2247
- paramsSize: V12_1_PARAMS_SIZE,
2248
- engineCurrentSlotOff: V12_1_ENGINE_CURRENT_SLOT_OFF,
2249
- engineFundingIndexOff: V12_1_ENGINE_FUNDING_INDEX_OFF,
2250
- engineLastFundingSlotOff: V12_1_ENGINE_LAST_FUNDING_SLOT_OFF,
2251
- engineFundingRateBpsOff: V12_1_ENGINE_FUNDING_RATE_BPS_OFF,
2252
- engineMarkPriceOff: V12_1_ENGINE_MARK_PRICE_OFF,
2253
- engineLastCrankSlotOff: V12_1_ENGINE_LAST_CRANK_SLOT_OFF,
2254
- engineMaxCrankStalenessOff: V12_1_ENGINE_MAX_CRANK_STALENESS_OFF,
2255
- engineTotalOiOff: V12_1_ENGINE_TOTAL_OI_OFF,
2256
- engineLongOiOff: V12_1_ENGINE_LONG_OI_OFF,
2257
- engineShortOiOff: V12_1_ENGINE_SHORT_OI_OFF,
2258
- engineCTotOff: V12_1_ENGINE_C_TOT_OFF,
2259
- enginePnlPosTotOff: V12_1_ENGINE_PNL_POS_TOT_OFF,
2260
- engineLiqCursorOff: V12_1_ENGINE_LIQ_CURSOR_OFF,
2261
- engineGcCursorOff: V12_1_ENGINE_GC_CURSOR_OFF,
2262
- engineLastSweepStartOff: V12_1_ENGINE_LAST_SWEEP_START_OFF,
2263
- engineLastSweepCompleteOff: V12_1_ENGINE_LAST_SWEEP_COMPLETE_OFF,
2264
- engineCrankCursorOff: V12_1_ENGINE_CRANK_CURSOR_OFF,
2265
- engineSweepStartIdxOff: V12_1_ENGINE_SWEEP_START_IDX_OFF,
2266
- engineLifetimeLiquidationsOff: V12_1_ENGINE_LIFETIME_LIQUIDATIONS_OFF,
2267
- engineLifetimeForceClosesOff: V12_1_ENGINE_LIFETIME_FORCE_CLOSES_OFF,
2268
- engineNetLpPosOff: V12_1_ENGINE_NET_LP_POS_OFF,
2269
- engineLpSumAbsOff: V12_1_ENGINE_LP_SUM_ABS_OFF,
2270
- engineLpMaxAbsOff: V12_1_ENGINE_LP_MAX_ABS_OFF,
2271
- engineLpMaxAbsSweepOff: V12_1_ENGINE_LP_MAX_ABS_SWEEP_OFF,
2272
- engineEmergencyOiModeOff: V12_1_ENGINE_EMERGENCY_OI_MODE_OFF,
2273
- engineEmergencyStartSlotOff: V12_1_ENGINE_EMERGENCY_START_SLOT_OFF,
2274
- engineLastBreakerSlotOff: V12_1_ENGINE_LAST_BREAKER_SLOT_OFF,
2275
- engineBitmapOff: V12_1_ENGINE_BITMAP_OFF,
2276
- postBitmap: 18,
2277
- acctOwnerOff: V12_1_ACCT_OWNER_OFF,
2278
- hasInsuranceIsolation: true,
2279
- engineInsuranceIsolatedOff: 48,
2280
- engineInsuranceIsolationBpsOff: 64
3191
+ engineParamsOff: V12_17_ENGINE_PARAMS_OFF,
3192
+ // 32
3193
+ paramsSize: isSbf ? 184 : 192,
3194
+ engineCurrentSlotOff: isSbf ? V12_17_SBF_ENGINE_CURRENT_SLOT_OFF : V12_17_ENGINE_CURRENT_SLOT_OFF,
3195
+ engineFundingIndexOff: -1,
3196
+ // replaced by per-side f_long_num/f_short_num
3197
+ engineLastFundingSlotOff: -1,
3198
+ engineFundingRateBpsOff: -1,
3199
+ // no stored funding rate in v12.17
3200
+ engineMarkPriceOff: -1,
3201
+ // v12.17 computes mark from state; no stored field
3202
+ engineLastCrankSlotOff: isSbf ? V12_17_SBF_ENGINE_LAST_CRANK_SLOT_OFF : V12_17_ENGINE_LAST_CRANK_SLOT_OFF,
3203
+ engineMaxCrankStalenessOff: -1,
3204
+ engineTotalOiOff: -1,
3205
+ // parseEngine sums long + short when total offset is -1
3206
+ engineLongOiOff: isSbf ? V12_17_SBF_ENGINE_OI_EFF_LONG_OFF : V12_17_ENGINE_OI_EFF_LONG_OFF,
3207
+ engineShortOiOff: isSbf ? V12_17_SBF_ENGINE_OI_EFF_SHORT_OFF : V12_17_ENGINE_OI_EFF_SHORT_OFF,
3208
+ engineCTotOff: isSbf ? V12_17_SBF_ENGINE_C_TOT_OFF : V12_17_ENGINE_C_TOT_OFF,
3209
+ enginePnlPosTotOff: isSbf ? V12_17_SBF_ENGINE_PNL_POS_TOT_OFF : V12_17_ENGINE_PNL_POS_TOT_OFF,
3210
+ engineLiqCursorOff: -1,
3211
+ // removed in v12.17
3212
+ engineGcCursorOff: isSbf ? V12_17_SBF_ENGINE_GC_CURSOR_OFF : V12_17_ENGINE_GC_CURSOR_OFF,
3213
+ engineLastSweepStartOff: -1,
3214
+ engineLastSweepCompleteOff: -1,
3215
+ engineCrankCursorOff: -1,
3216
+ engineSweepStartIdxOff: -1,
3217
+ engineLifetimeLiquidationsOff: -1,
3218
+ engineLifetimeForceClosesOff: -1,
3219
+ engineNetLpPosOff: -1,
3220
+ engineLpSumAbsOff: -1,
3221
+ engineLpMaxAbsOff: -1,
3222
+ engineLpMaxAbsSweepOff: -1,
3223
+ engineEmergencyOiModeOff: -1,
3224
+ engineEmergencyStartSlotOff: -1,
3225
+ engineLastBreakerSlotOff: -1,
3226
+ engineBitmapOff: bitmapOff,
3227
+ postBitmap,
3228
+ acctOwnerOff: isSbf ? 192 : V12_17_ACCT_OWNER_OFF,
3229
+ // SBF=192, native=200
3230
+ hasInsuranceIsolation: false,
3231
+ engineInsuranceIsolatedOff: -1,
3232
+ engineInsuranceIsolationBpsOff: -1,
3233
+ // v12.17 dropped the engine.mark_price field (see engineMarkPriceOff above).
3234
+ // The EWMA-smoothed mark that the matcher actually quotes against lives in
3235
+ // MarketConfig.mark_ewma_e6 at offset 304 within the config struct.
3236
+ // Layout is identical on SBF and native. configOffset is V0_HEADER_LEN = 72,
3237
+ // so absolute offset in the slab is 72 + 304 = 376.
3238
+ configMarkEwmaOff: V0_HEADER_LEN + 304
2281
3239
  };
2282
3240
  }
2283
3241
  function detectSlabLayout(dataLen, data) {
3242
+ const v1219n = V12_19_SIZES.get(dataLen);
3243
+ if (v1219n !== void 0) return buildLayoutV12_19(v1219n, dataLen);
3244
+ const v1217n = V12_17_SIZES.get(dataLen);
3245
+ if (v1217n !== void 0) return buildLayoutV12_17(v1217n, dataLen);
3246
+ const v1215n = V12_15_SIZES.get(dataLen);
3247
+ if (v1215n !== void 0) return buildLayoutV12_15(v1215n, dataLen);
3248
+ const v121epn = V12_1_EP_SIZES.get(dataLen);
3249
+ if (v121epn !== void 0) return buildLayoutV12_1EP(v121epn);
2284
3250
  const v121n = V12_1_SIZES.get(dataLen);
2285
3251
  if (v121n !== void 0) return buildLayoutV12_1(v121n, dataLen);
2286
3252
  const vsdpn = V_SETDEXPOOL_SIZES.get(dataLen);
@@ -2327,6 +3293,15 @@ var PARAMS_LIQUIDATION_FEE_BPS_OFF = 96;
2327
3293
  var PARAMS_LIQUIDATION_FEE_CAP_OFF = 104;
2328
3294
  var PARAMS_LIQUIDATION_BUFFER_OFF = 120;
2329
3295
  var PARAMS_MIN_LIQUIDATION_OFF = 128;
3296
+ var V12_1_PARAMS_MAINT_FEE_OFF = 56;
3297
+ var V12_1_PARAMS_MAX_CRANK_OFF = 72;
3298
+ var V12_1_PARAMS_LIQ_FEE_BPS_OFF = 80;
3299
+ var V12_1_PARAMS_LIQ_FEE_CAP_OFF = 88;
3300
+ var V12_1_PARAMS_MIN_LIQ_OFF = 104;
3301
+ var V12_1_PARAMS_MIN_INITIAL_DEP_OFF = 120;
3302
+ var V12_1_PARAMS_MIN_NZ_MM_OFF = 136;
3303
+ var V12_1_PARAMS_MIN_NZ_IM_OFF = 152;
3304
+ var V12_1_PARAMS_INS_FLOOR_OFF = 168;
2330
3305
  var ACCT_ACCOUNT_ID_OFF = 0;
2331
3306
  var ACCT_CAPITAL_OFF = 8;
2332
3307
  var ACCT_KIND_OFF = 24;
@@ -2397,7 +3372,7 @@ function parseHeader(data) {
2397
3372
  const version = readU32LE(data, 8);
2398
3373
  const bump = readU8(data, 12);
2399
3374
  const flags = readU8(data, 13);
2400
- const admin = new PublicKey3(data.subarray(16, 48));
3375
+ const admin = new PublicKey5(data.subarray(16, 48));
2401
3376
  const layout = detectSlabLayout(data.length, data);
2402
3377
  const roff = layout ? layout.reservedOff : V0_RESERVED_OFF;
2403
3378
  const nonce = readU64LE(data, roff);
@@ -2414,20 +3389,99 @@ function parseHeader(data) {
2414
3389
  lastThrUpdateSlot
2415
3390
  };
2416
3391
  }
3392
+ function parseConfigV12_17(data, configOff) {
3393
+ const MIN_V12_17_BYTES = 512;
3394
+ if (data.length < configOff + MIN_V12_17_BYTES) {
3395
+ throw new Error(`Slab data too short for V12_17 config: ${data.length} < ${configOff + MIN_V12_17_BYTES}`);
3396
+ }
3397
+ const b = configOff;
3398
+ const collateralMint = new PublicKey5(data.subarray(b + 0, b + 32));
3399
+ const vaultPubkey = new PublicKey5(data.subarray(b + 32, b + 64));
3400
+ const indexFeedId = new PublicKey5(data.subarray(b + 64, b + 96));
3401
+ const maxStalenessSlots = readU64LE(data, b + 96);
3402
+ const confFilterBps = readU16LE(data, b + 104);
3403
+ const vaultAuthorityBump = readU8(data, b + 106);
3404
+ const invert = readU8(data, b + 107);
3405
+ const unitScale = readU32LE(data, b + 108);
3406
+ const fundingHorizonSlots = readU64LE(data, b + 112);
3407
+ const fundingKBps = readU64LE(data, b + 120);
3408
+ const fundingMaxPremiumBps = readI64LE(data, b + 128);
3409
+ const fundingMaxBpsPerSlot = readI64LE(data, b + 136);
3410
+ const oracleAuthority = new PublicKey5(data.subarray(b + 144, b + 176));
3411
+ const authorityPriceE6 = readU64LE(data, b + 176);
3412
+ const authorityTimestamp = readI64LE(data, b + 184);
3413
+ const oraclePriceCapE2bps = readU64LE(data, b + 192);
3414
+ const lastEffectivePriceE6 = readU64LE(data, b + 200);
3415
+ const dexPoolBytes = data.subarray(b + 400, b + 432);
3416
+ const dexPool = dexPoolBytes.some((x) => x !== 0) ? new PublicKey5(dexPoolBytes) : null;
3417
+ return {
3418
+ collateralMint,
3419
+ vaultPubkey,
3420
+ indexFeedId,
3421
+ maxStalenessSlots,
3422
+ confFilterBps,
3423
+ vaultAuthorityBump,
3424
+ invert,
3425
+ unitScale,
3426
+ fundingHorizonSlots,
3427
+ fundingKBps,
3428
+ fundingInvScaleNotionalE6: 0n,
3429
+ // removed in v12.17
3430
+ fundingMaxPremiumBps,
3431
+ fundingMaxBpsPerSlot,
3432
+ fundingPremiumWeightBps: 0n,
3433
+ fundingSettlementIntervalSlots: 0n,
3434
+ fundingPremiumDampeningE6: 0n,
3435
+ fundingPremiumMaxBpsPerSlot: 0n,
3436
+ threshFloor: 0n,
3437
+ // removed in v12.17
3438
+ threshRiskBps: 0n,
3439
+ threshUpdateIntervalSlots: 0n,
3440
+ threshStepBps: 0n,
3441
+ threshAlphaBps: 0n,
3442
+ threshMin: 0n,
3443
+ threshMax: 0n,
3444
+ threshMinStep: 0n,
3445
+ oracleAuthority,
3446
+ authorityPriceE6,
3447
+ authorityTimestamp,
3448
+ oraclePriceCapE2bps,
3449
+ lastEffectivePriceE6,
3450
+ oiCapMultiplierBps: readU64LE(data, b + 448),
3451
+ maxPnlCap: readU64LE(data, b + 432),
3452
+ adaptiveFundingEnabled: false,
3453
+ // removed in v12.17
3454
+ adaptiveScaleBps: 0,
3455
+ adaptiveMaxFundingBps: 0n,
3456
+ marketCreatedSlot: 0n,
3457
+ oiRampSlots: 0n,
3458
+ resolvedSlot: 0n,
3459
+ insuranceIsolationBps: 0,
3460
+ oraclePhase: 0,
3461
+ cumulativeVolumeE6: 0n,
3462
+ phase2DeltaSlots: 0,
3463
+ dexPool
3464
+ };
3465
+ }
2417
3466
  function parseConfig(data, layoutHint) {
2418
3467
  const layout = layoutHint !== void 0 ? layoutHint : detectSlabLayout(data.length, data);
2419
3468
  const configOff = layout ? layout.configOffset : V0_HEADER_LEN;
2420
3469
  const configLen = layout ? layout.configLen : V0_CONFIG_LEN;
2421
- const minLen = configOff + Math.min(configLen, 120);
3470
+ const isV12_17 = layout && (layout.accountSize === V12_17_ACCOUNT_SIZE || layout.accountSize === V12_17_ACCOUNT_SIZE_SBF);
3471
+ if (isV12_17) {
3472
+ return parseConfigV12_17(data, configOff);
3473
+ }
3474
+ const MIN_CONFIG_BYTES = 376;
3475
+ const minLen = configOff + Math.min(configLen, MIN_CONFIG_BYTES);
2422
3476
  if (data.length < minLen) {
2423
3477
  throw new Error(`Slab data too short for config: ${data.length} < ${minLen}`);
2424
3478
  }
2425
3479
  let off = configOff;
2426
- const collateralMint = new PublicKey3(data.subarray(off, off + 32));
3480
+ const collateralMint = new PublicKey5(data.subarray(off, off + 32));
2427
3481
  off += 32;
2428
- const vaultPubkey = new PublicKey3(data.subarray(off, off + 32));
3482
+ const vaultPubkey = new PublicKey5(data.subarray(off, off + 32));
2429
3483
  off += 32;
2430
- const indexFeedId = new PublicKey3(data.subarray(off, off + 32));
3484
+ const indexFeedId = new PublicKey5(data.subarray(off, off + 32));
2431
3485
  off += 32;
2432
3486
  const maxStalenessSlots = readU64LE(data, off);
2433
3487
  off += 8;
@@ -2465,7 +3519,7 @@ function parseConfig(data, layoutHint) {
2465
3519
  off += 16;
2466
3520
  const threshMinStep = readU128LE(data, off);
2467
3521
  off += 16;
2468
- const oracleAuthority = new PublicKey3(data.subarray(off, off + 32));
3522
+ const oracleAuthority = new PublicKey5(data.subarray(off, off + 32));
2469
3523
  off += 32;
2470
3524
  const authorityPriceE6 = readU64LE(data, off);
2471
3525
  off += 8;
@@ -2518,7 +3572,7 @@ function parseConfig(data, layoutHint) {
2518
3572
  if (configLen >= DEX_POOL_REL_OFF + 32 && data.length >= configOff + DEX_POOL_REL_OFF + 32) {
2519
3573
  const dexPoolBytes = data.subarray(configOff + DEX_POOL_REL_OFF, configOff + DEX_POOL_REL_OFF + 32);
2520
3574
  if (dexPoolBytes.some((b) => b !== 0)) {
2521
- dexPool = new PublicKey3(dexPoolBytes);
3575
+ dexPool = new PublicKey5(dexPoolBytes);
2522
3576
  }
2523
3577
  }
2524
3578
  return {
@@ -2573,26 +3627,61 @@ function parseParams(data, layoutHint) {
2573
3627
  const paramsOff = layout ? layout.engineParamsOff : V0_ENGINE_PARAMS_OFF;
2574
3628
  const paramsSize = layout ? layout.paramsSize : V0_PARAMS_SIZE;
2575
3629
  const base = engineOff + paramsOff;
2576
- if (data.length < base + Math.min(paramsSize, 56)) {
2577
- throw new Error("Slab data too short for RiskParams");
3630
+ const MIN_PARAMS_BYTES = paramsSize >= 144 ? 144 : 56;
3631
+ if (data.length < base + MIN_PARAMS_BYTES) {
3632
+ throw new Error(`Slab data too short for RiskParams: ${data.length} < ${base + MIN_PARAMS_BYTES}`);
2578
3633
  }
3634
+ const isV12_15Params = paramsSize === V12_15_PARAMS_SIZE || paramsSize === 184;
3635
+ const isV12_1Sbf = !isV12_15Params && layout !== null && layout !== void 0 && layout.engineOff === V12_1_SBF_ENGINE_OFF && paramsSize === 184;
2579
3636
  const result = {
2580
- warmupPeriodSlots: readU64LE(data, base + PARAMS_WARMUP_PERIOD_OFF),
2581
- maintenanceMarginBps: readU64LE(data, base + PARAMS_MAINTENANCE_MARGIN_OFF),
2582
- initialMarginBps: readU64LE(data, base + PARAMS_INITIAL_MARGIN_OFF),
2583
- tradingFeeBps: readU64LE(data, base + PARAMS_TRADING_FEE_OFF),
2584
- maxAccounts: readU64LE(data, base + PARAMS_MAX_ACCOUNTS_OFF),
2585
- newAccountFee: readU128LE(data, base + PARAMS_NEW_ACCOUNT_FEE_OFF),
2586
- // Extended params: only read if V1 (paramsSize >= 144)
3637
+ warmupPeriodSlots: isV12_15Params ? readU64LE(data, base + V12_15_PARAMS_H_MIN_OFF) : readU64LE(data, base + PARAMS_WARMUP_PERIOD_OFF),
3638
+ maintenanceMarginBps: isV12_15Params ? readU64LE(data, base + 0) : readU64LE(data, base + PARAMS_MAINTENANCE_MARGIN_OFF),
3639
+ initialMarginBps: isV12_15Params ? readU64LE(data, base + 8) : readU64LE(data, base + PARAMS_INITIAL_MARGIN_OFF),
3640
+ tradingFeeBps: isV12_15Params ? readU64LE(data, base + 16) : readU64LE(data, base + PARAMS_TRADING_FEE_OFF),
3641
+ maxAccounts: isV12_15Params ? readU64LE(data, base + V12_15_PARAMS_MAX_ACCOUNTS_OFF) : readU64LE(data, base + PARAMS_MAX_ACCOUNTS_OFF),
3642
+ newAccountFee: isV12_15Params ? readU128LE(data, base + 32) : readU128LE(data, base + PARAMS_NEW_ACCOUNT_FEE_OFF),
3643
+ // Extended params: defaults; overwritten below if layout supports them
2587
3644
  riskReductionThreshold: 0n,
2588
3645
  maintenanceFeePerSlot: 0n,
2589
3646
  maxCrankStalenessSlots: 0n,
2590
3647
  liquidationFeeBps: 0n,
2591
3648
  liquidationFeeCap: 0n,
2592
3649
  liquidationBufferBps: 0n,
2593
- minLiquidationAbs: 0n
3650
+ minLiquidationAbs: 0n,
3651
+ minInitialDeposit: 0n,
3652
+ minNonzeroMmReq: 0n,
3653
+ minNonzeroImReq: 0n,
3654
+ insuranceFloor: 0n,
3655
+ hMin: 0n,
3656
+ hMax: 0n
2594
3657
  };
2595
- if (paramsSize >= 144) {
3658
+ if (isV12_15Params) {
3659
+ result.hMin = readU64LE(data, base + V12_15_PARAMS_H_MIN_OFF);
3660
+ result.hMax = readU64LE(data, base + V12_15_PARAMS_H_MAX_OFF);
3661
+ result.insuranceFloor = readU128LE(data, base + V12_15_PARAMS_INSURANCE_FLOOR_OFF);
3662
+ result.riskReductionThreshold = 0n;
3663
+ result.maintenanceFeePerSlot = 0n;
3664
+ result.maxCrankStalenessSlots = readU64LE(data, base + 48);
3665
+ result.liquidationFeeBps = readU64LE(data, base + 56);
3666
+ result.liquidationFeeCap = readU128LE(data, base + 64);
3667
+ result.liquidationBufferBps = 0n;
3668
+ result.minLiquidationAbs = readU128LE(data, base + 80);
3669
+ result.minInitialDeposit = readU128LE(data, base + 96);
3670
+ result.minNonzeroMmReq = readU128LE(data, base + 112);
3671
+ result.minNonzeroImReq = readU128LE(data, base + 128);
3672
+ } else if (isV12_1Sbf) {
3673
+ result.maintenanceFeePerSlot = readU128LE(data, base + V12_1_PARAMS_MAINT_FEE_OFF);
3674
+ result.maxCrankStalenessSlots = readU64LE(data, base + V12_1_PARAMS_MAX_CRANK_OFF);
3675
+ result.liquidationFeeBps = readU64LE(data, base + V12_1_PARAMS_LIQ_FEE_BPS_OFF);
3676
+ result.liquidationFeeCap = readU128LE(data, base + V12_1_PARAMS_LIQ_FEE_CAP_OFF);
3677
+ result.minLiquidationAbs = readU128LE(data, base + V12_1_PARAMS_MIN_LIQ_OFF);
3678
+ result.minInitialDeposit = readU128LE(data, base + V12_1_PARAMS_MIN_INITIAL_DEP_OFF);
3679
+ result.minNonzeroMmReq = readU128LE(data, base + V12_1_PARAMS_MIN_NZ_MM_OFF);
3680
+ result.minNonzeroImReq = readU128LE(data, base + V12_1_PARAMS_MIN_NZ_IM_OFF);
3681
+ result.insuranceFloor = readU128LE(data, base + V12_1_PARAMS_INS_FLOOR_OFF);
3682
+ result.hMin = result.warmupPeriodSlots;
3683
+ result.hMax = result.warmupPeriodSlots;
3684
+ } else if (paramsSize >= 144) {
2596
3685
  result.riskReductionThreshold = readU128LE(data, base + PARAMS_RISK_THRESHOLD_OFF);
2597
3686
  result.maintenanceFeePerSlot = readU128LE(data, base + PARAMS_MAINTENANCE_FEE_OFF);
2598
3687
  result.maxCrankStalenessSlots = readU64LE(data, base + PARAMS_MAX_CRANK_STALENESS_OFF);
@@ -2600,6 +3689,8 @@ function parseParams(data, layoutHint) {
2600
3689
  result.liquidationFeeCap = readU128LE(data, base + PARAMS_LIQUIDATION_FEE_CAP_OFF);
2601
3690
  result.liquidationBufferBps = readU64LE(data, base + PARAMS_LIQUIDATION_BUFFER_OFF);
2602
3691
  result.minLiquidationAbs = readU128LE(data, base + PARAMS_MIN_LIQUIDATION_OFF);
3692
+ result.hMin = result.warmupPeriodSlots;
3693
+ result.hMax = result.warmupPeriodSlots;
2603
3694
  }
2604
3695
  return result;
2605
3696
  }
@@ -2609,41 +3700,129 @@ function parseEngine(data) {
2609
3700
  throw new Error(`Unrecognized slab data length: ${data.length}. Cannot determine layout version.`);
2610
3701
  }
2611
3702
  const base = layout.engineOff;
3703
+ const isV12_17 = layout.accountSize === V12_17_ACCOUNT_SIZE || layout.accountSize === V12_17_ACCOUNT_SIZE_SBF;
3704
+ const isV12_15 = !isV12_17 && (layout.accountSize === V12_15_ACCOUNT_SIZE || layout.accountSize === V12_15_ACCOUNT_SIZE_SMALL) && (layout.engineOff === V12_15_ENGINE_OFF || layout.engineOff === V12_15_ENGINE_OFF_SBF);
3705
+ if (isV12_17) {
3706
+ const isV12_19 = layout.engineOff === V12_19_ENGINE_OFF_SBF;
3707
+ const isSbf = layout.engineOff === V12_17_ENGINE_OFF_SBF || isV12_19;
3708
+ const currentSlotOff = isV12_19 ? V12_19_SBF_ENGINE_CURRENT_SLOT_OFF : isSbf ? V12_17_SBF_ENGINE_CURRENT_SLOT_OFF : V12_17_ENGINE_CURRENT_SLOT_OFF;
3709
+ const marketModeOff = isV12_19 ? V12_19_SBF_ENGINE_MARKET_MODE_OFF : isSbf ? V12_17_SBF_ENGINE_MARKET_MODE_OFF : V12_17_ENGINE_MARKET_MODE_OFF;
3710
+ const cTotOff = isV12_19 ? V12_19_SBF_ENGINE_C_TOT_OFF : isSbf ? V12_17_SBF_ENGINE_C_TOT_OFF : V12_17_ENGINE_C_TOT_OFF;
3711
+ const pnlPosTotOff = isV12_19 ? V12_19_SBF_ENGINE_PNL_POS_TOT_OFF : isSbf ? V12_17_SBF_ENGINE_PNL_POS_TOT_OFF : V12_17_ENGINE_PNL_POS_TOT_OFF;
3712
+ const pnlMaturedOff = isV12_19 ? V12_19_SBF_ENGINE_PNL_MATURED_POS_TOT_OFF : isSbf ? V12_17_SBF_ENGINE_PNL_MATURED_POS_TOT_OFF : V12_17_ENGINE_PNL_MATURED_POS_TOT_OFF;
3713
+ const negPnlOff = isV12_19 ? V12_19_SBF_ENGINE_NEG_PNL_COUNT_OFF : isSbf ? V12_17_SBF_ENGINE_NEG_PNL_COUNT_OFF : V12_17_ENGINE_NEG_PNL_COUNT_OFF;
3714
+ const oraclePriceOff = isV12_19 ? V12_19_SBF_ENGINE_LAST_ORACLE_PRICE_OFF : isSbf ? V12_17_SBF_ENGINE_LAST_ORACLE_PRICE_OFF : V12_17_ENGINE_LAST_ORACLE_PRICE_OFF;
3715
+ const fundPxLastOff = isV12_19 ? V12_19_SBF_ENGINE_FUND_PX_LAST_OFF : isSbf ? V12_17_SBF_ENGINE_FUND_PX_LAST_OFF : V12_17_ENGINE_FUND_PX_LAST_OFF;
3716
+ const fLongNumOff = isV12_19 ? V12_19_SBF_ENGINE_F_LONG_NUM_OFF : isSbf ? V12_17_SBF_ENGINE_F_LONG_NUM_OFF : V12_17_ENGINE_F_LONG_NUM_OFF;
3717
+ const fShortNumOff = isV12_19 ? V12_19_SBF_ENGINE_F_SHORT_NUM_OFF : isSbf ? V12_17_SBF_ENGINE_F_SHORT_NUM_OFF : V12_17_ENGINE_F_SHORT_NUM_OFF;
3718
+ const resolvedKLongOff = isV12_19 ? 288 : isSbf ? 288 : V12_17_ENGINE_RESOLVED_K_LONG_OFF;
3719
+ const resolvedKShortOff = isV12_19 ? 304 : isSbf ? 304 : V12_17_ENGINE_RESOLVED_K_SHORT_OFF;
3720
+ const resolvedLivePriceOff = isV12_19 ? V12_19_SBF_ENGINE_RESOLVED_LIVE_PRICE_OFF : isSbf ? 320 : V12_17_ENGINE_RESOLVED_LIVE_PRICE_OFF;
3721
+ const lastCrankSlotOff = isV12_19 ? V12_19_SBF_ENGINE_LAST_MARKET_SLOT_OFF : isSbf ? V12_17_SBF_ENGINE_LAST_CRANK_SLOT_OFF : V12_17_ENGINE_LAST_CRANK_SLOT_OFF;
3722
+ const gcCursorOff = isV12_19 ? V12_19_SBF_ENGINE_RR_CURSOR_OFF : isSbf ? V12_17_SBF_ENGINE_GC_CURSOR_OFF : V12_17_ENGINE_GC_CURSOR_OFF;
3723
+ const oiEffLongOff = isV12_19 ? V12_19_SBF_ENGINE_OI_EFF_LONG_OFF : isSbf ? V12_17_SBF_ENGINE_OI_EFF_LONG_OFF : V12_17_ENGINE_OI_EFF_LONG_OFF;
3724
+ const oiEffShortOff = isV12_19 ? V12_19_SBF_ENGINE_OI_EFF_SHORT_OFF : isSbf ? V12_17_SBF_ENGINE_OI_EFF_SHORT_OFF : V12_17_ENGINE_OI_EFF_SHORT_OFF;
3725
+ const longOi = readU128LE(data, base + oiEffLongOff);
3726
+ const shortOi = readU128LE(data, base + oiEffShortOff);
3727
+ const bitmapEnd = layout.engineBitmapOff + layout.bitmapWords * 8;
3728
+ return {
3729
+ vault: readU128LE(data, base),
3730
+ insuranceFund: {
3731
+ balance: readU128LE(data, base + 16),
3732
+ feeRevenue: 0n,
3733
+ isolatedBalance: 0n,
3734
+ isolationBps: 0
3735
+ },
3736
+ currentSlot: readU64LE(data, base + currentSlotOff),
3737
+ fundingIndexQpbE6: 0n,
3738
+ // replaced by per-side funding
3739
+ lastFundingSlot: 0n,
3740
+ fundingRateBpsPerSlotLast: 0n,
3741
+ // no stored funding rate in v12.17
3742
+ fundingRateE9: 0n,
3743
+ // no stored funding rate in v12.17
3744
+ marketMode: readU8(data, base + marketModeOff) === 1 ? 1 : 0,
3745
+ lastCrankSlot: readU64LE(data, base + lastCrankSlotOff),
3746
+ maxCrankStalenessSlots: 0n,
3747
+ totalOpenInterest: longOi + shortOi,
3748
+ longOi,
3749
+ shortOi,
3750
+ cTot: readU128LE(data, base + cTotOff),
3751
+ pnlPosTot: readU128LE(data, base + pnlPosTotOff),
3752
+ pnlMaturedPosTot: readU128LE(data, base + pnlMaturedOff),
3753
+ liqCursor: 0,
3754
+ gcCursor: readU16LE(data, base + gcCursorOff),
3755
+ lastSweepStartSlot: 0n,
3756
+ lastSweepCompleteSlot: 0n,
3757
+ crankCursor: 0,
3758
+ sweepStartIdx: 0,
3759
+ lifetimeLiquidations: 0n,
3760
+ lifetimeForceCloses: 0n,
3761
+ netLpPos: 0n,
3762
+ lpSumAbs: 0n,
3763
+ lpMaxAbs: 0n,
3764
+ lpMaxAbsSweep: 0n,
3765
+ emergencyOiMode: false,
3766
+ emergencyStartSlot: 0n,
3767
+ lastBreakerSlot: 0n,
3768
+ markPriceE6: 0n,
3769
+ oraclePriceE6: readU64LE(data, base + oraclePriceOff),
3770
+ numUsedAccounts: readU16LE(data, base + bitmapEnd),
3771
+ nextAccountId: 0n,
3772
+ // removed in v12.17 (replaced by mat_counter in header)
3773
+ // V12_17 fields
3774
+ fLongNum: readI128LE(data, base + fLongNumOff),
3775
+ fShortNum: readI128LE(data, base + fShortNumOff),
3776
+ negPnlAccountCount: readU64LE(data, base + negPnlOff),
3777
+ fundPxLast: readU64LE(data, base + fundPxLastOff),
3778
+ resolvedKLongTerminalDelta: readI128LE(data, base + resolvedKLongOff),
3779
+ resolvedKShortTerminalDelta: readI128LE(data, base + resolvedKShortOff),
3780
+ resolvedLivePrice: readU64LE(data, base + resolvedLivePriceOff)
3781
+ };
3782
+ }
3783
+ const fundingRateBpsPerSlotLast = isV12_15 ? readI128LE(data, base + layout.engineFundingRateBpsOff) : readI64LE(data, base + layout.engineFundingRateBpsOff);
2612
3784
  return {
2613
3785
  vault: readU128LE(data, base),
2614
3786
  insuranceFund: {
2615
3787
  balance: readU128LE(data, base + layout.engineInsuranceOff),
2616
- feeRevenue: readU128LE(data, base + layout.engineInsuranceOff + 16),
3788
+ // feeRevenue: only exists in percolator-core (80-byte InsuranceFund), not deployed (16-byte)
3789
+ feeRevenue: layout.hasInsuranceIsolation ? readU128LE(data, base + layout.engineInsuranceOff + 16) : 0n,
2617
3790
  isolatedBalance: layout.hasInsuranceIsolation ? readU128LE(data, base + layout.engineInsuranceIsolatedOff) : 0n,
2618
3791
  isolationBps: layout.hasInsuranceIsolation ? readU16LE(data, base + layout.engineInsuranceIsolationBpsOff) : 0
2619
3792
  },
2620
3793
  currentSlot: readU64LE(data, base + layout.engineCurrentSlotOff),
2621
- fundingIndexQpbE6: readI128LE(data, base + layout.engineFundingIndexOff),
2622
- lastFundingSlot: readU64LE(data, base + layout.engineLastFundingSlotOff),
2623
- fundingRateBpsPerSlotLast: readI64LE(data, base + layout.engineFundingRateBpsOff),
2624
- lastCrankSlot: readU64LE(data, base + layout.engineLastCrankSlotOff),
2625
- maxCrankStalenessSlots: readU64LE(data, base + layout.engineMaxCrankStalenessOff),
2626
- totalOpenInterest: readU128LE(data, base + layout.engineTotalOiOff),
3794
+ fundingIndexQpbE6: layout.engineFundingIndexOff >= 0 ? readI128LE(data, base + layout.engineFundingIndexOff) : 0n,
3795
+ lastFundingSlot: layout.engineLastFundingSlotOff >= 0 ? readU64LE(data, base + layout.engineLastFundingSlotOff) : 0n,
3796
+ fundingRateBpsPerSlotLast,
3797
+ fundingRateE9: isV12_15 ? readI128LE(data, base + layout.engineFundingRateBpsOff) : 0n,
3798
+ marketMode: isV12_15 ? readU8(data, base + layout.engineFundingRateBpsOff + 16) === 1 ? 1 : 0 : null,
3799
+ lastCrankSlot: layout.engineLastCrankSlotOff >= 0 ? readU64LE(data, base + layout.engineLastCrankSlotOff) : 0n,
3800
+ maxCrankStalenessSlots: layout.engineMaxCrankStalenessOff >= 0 ? readU64LE(data, base + layout.engineMaxCrankStalenessOff) : 0n,
3801
+ totalOpenInterest: layout.engineTotalOiOff >= 0 ? readU128LE(data, base + layout.engineTotalOiOff) : 0n,
2627
3802
  longOi: layout.engineLongOiOff >= 0 ? readU128LE(data, base + layout.engineLongOiOff) : 0n,
2628
3803
  shortOi: layout.engineShortOiOff >= 0 ? readU128LE(data, base + layout.engineShortOiOff) : 0n,
2629
3804
  cTot: readU128LE(data, base + layout.engineCTotOff),
2630
3805
  pnlPosTot: readU128LE(data, base + layout.enginePnlPosTotOff),
2631
- liqCursor: readU16LE(data, base + layout.engineLiqCursorOff),
2632
- gcCursor: readU16LE(data, base + layout.engineGcCursorOff),
2633
- lastSweepStartSlot: readU64LE(data, base + layout.engineLastSweepStartOff),
2634
- lastSweepCompleteSlot: readU64LE(data, base + layout.engineLastSweepCompleteOff),
2635
- crankCursor: readU16LE(data, base + layout.engineCrankCursorOff),
2636
- sweepStartIdx: readU16LE(data, base + layout.engineSweepStartIdxOff),
2637
- lifetimeLiquidations: readU64LE(data, base + layout.engineLifetimeLiquidationsOff),
2638
- lifetimeForceCloses: readU64LE(data, base + layout.engineLifetimeForceClosesOff),
2639
- netLpPos: readI128LE(data, base + layout.engineNetLpPosOff),
2640
- lpSumAbs: readU128LE(data, base + layout.engineLpSumAbsOff),
3806
+ pnlMaturedPosTot: isV12_15 ? readU128LE(data, base + V12_15_ENGINE_PNL_MATURED_POS_TOT_OFF) : 0n,
3807
+ liqCursor: layout.engineLiqCursorOff >= 0 ? readU16LE(data, base + layout.engineLiqCursorOff) : 0,
3808
+ gcCursor: layout.engineGcCursorOff >= 0 ? readU16LE(data, base + layout.engineGcCursorOff) : 0,
3809
+ lastSweepStartSlot: layout.engineLastSweepStartOff >= 0 ? readU64LE(data, base + layout.engineLastSweepStartOff) : 0n,
3810
+ lastSweepCompleteSlot: layout.engineLastSweepCompleteOff >= 0 ? readU64LE(data, base + layout.engineLastSweepCompleteOff) : 0n,
3811
+ crankCursor: layout.engineCrankCursorOff >= 0 ? readU16LE(data, base + layout.engineCrankCursorOff) : 0,
3812
+ sweepStartIdx: layout.engineSweepStartIdxOff >= 0 ? readU16LE(data, base + layout.engineSweepStartIdxOff) : 0,
3813
+ lifetimeLiquidations: layout.engineLifetimeLiquidationsOff >= 0 ? readU64LE(data, base + layout.engineLifetimeLiquidationsOff) : 0n,
3814
+ lifetimeForceCloses: layout.engineLifetimeForceClosesOff >= 0 ? readU64LE(data, base + layout.engineLifetimeForceClosesOff) : 0n,
3815
+ netLpPos: layout.engineNetLpPosOff >= 0 ? readI128LE(data, base + layout.engineNetLpPosOff) : 0n,
3816
+ lpSumAbs: layout.engineLpSumAbsOff >= 0 ? readU128LE(data, base + layout.engineLpSumAbsOff) : 0n,
2641
3817
  lpMaxAbs: layout.engineLpMaxAbsOff >= 0 ? readU128LE(data, base + layout.engineLpMaxAbsOff) : 0n,
2642
3818
  lpMaxAbsSweep: layout.engineLpMaxAbsSweepOff >= 0 ? readU128LE(data, base + layout.engineLpMaxAbsSweepOff) : 0n,
2643
3819
  emergencyOiMode: layout.engineEmergencyOiModeOff >= 0 ? data[base + layout.engineEmergencyOiModeOff] !== 0 : false,
2644
3820
  emergencyStartSlot: layout.engineEmergencyStartSlotOff >= 0 ? readU64LE(data, base + layout.engineEmergencyStartSlotOff) : 0n,
2645
3821
  lastBreakerSlot: layout.engineLastBreakerSlotOff >= 0 ? readU64LE(data, base + layout.engineLastBreakerSlotOff) : 0n,
2646
3822
  markPriceE6: layout.engineMarkPriceOff >= 0 ? readU64LE(data, base + layout.engineMarkPriceOff) : 0n,
3823
+ // V12_15: last_oracle_price at engine+608 (SBF) / engine+... (native).
3824
+ // Located at bitmapOff - 40 on SBF (648-40=608, verified on-chain).
3825
+ oraclePriceE6: isV12_15 ? readU64LE(data, base + layout.engineBitmapOff - 40) : 0n,
2647
3826
  numUsedAccounts: (() => {
2648
3827
  if (layout.postBitmap < 18) return 0;
2649
3828
  const bw = layout.bitmapWords;
@@ -2654,7 +3833,15 @@ function parseEngine(data) {
2654
3833
  const bw = layout.bitmapWords;
2655
3834
  const numUsedOff = layout.engineBitmapOff + bw * 8;
2656
3835
  return readU64LE(data, base + Math.ceil((numUsedOff + 2) / 8) * 8);
2657
- })()
3836
+ })(),
3837
+ // V12_17 fields (not present in pre-v12.17)
3838
+ fLongNum: 0n,
3839
+ fShortNum: 0n,
3840
+ negPnlAccountCount: 0n,
3841
+ fundPxLast: 0n,
3842
+ resolvedKLongTerminalDelta: 0n,
3843
+ resolvedKShortTerminalDelta: 0n,
3844
+ resolvedLivePrice: 0n
2658
3845
  };
2659
3846
  }
2660
3847
  function parseUsedIndices(data) {
@@ -2704,17 +3891,129 @@ function parseAccount(data, idx) {
2704
3891
  if (data.length < base + layout.accountSize) {
2705
3892
  throw new Error("Slab data too short for account");
2706
3893
  }
2707
- const isV12_1 = layout.engineOff === V12_1_ENGINE_OFF && (layout.accountSize === V12_1_ACCOUNT_SIZE || layout.accountSize === V12_1_ACCOUNT_SIZE_SBF);
2708
- const isAdl = layout.accountSize >= 312 || isV12_1;
3894
+ const isV12_17 = layout.accountSize === V12_17_ACCOUNT_SIZE || layout.accountSize === V12_17_ACCOUNT_SIZE_SBF;
3895
+ const isV12_15 = !isV12_17 && (layout.accountSize === V12_15_ACCOUNT_SIZE || layout.accountSize === V12_15_ACCOUNT_SIZE_SMALL);
3896
+ const isV12_1EP = !isV12_17 && !isV12_15 && layout.accountSize === V12_1_EP_SBF_ACCOUNT_SIZE && layout.engineOff === V12_1_SBF_ENGINE_OFF;
3897
+ const isV12_1 = !isV12_17 && !isV12_15 && !isV12_1EP && (layout.engineOff === V12_1_ENGINE_OFF || layout.engineOff === V12_1_SBF_ENGINE_OFF) && (layout.accountSize === V12_1_ACCOUNT_SIZE || layout.accountSize === V12_1_ACCOUNT_SIZE_SBF);
3898
+ const isAdl = !isV12_17 && !isV12_15 && (layout.accountSize >= 312 || isV12_1 || isV12_1EP);
3899
+ if (isV12_17) {
3900
+ const isSbf = layout.accountSize === V12_17_ACCOUNT_SIZE_SBF;
3901
+ const d1 = isSbf ? 8 : 0;
3902
+ const d2 = isSbf ? 16 : 0;
3903
+ const kindByte2 = readU8(data, base + V12_17_ACCT_KIND_OFF);
3904
+ const kind2 = kindByte2 === 1 ? 1 /* LP */ : 0 /* User */;
3905
+ return {
3906
+ kind: kind2,
3907
+ accountId: 0n,
3908
+ // removed in v12.17
3909
+ capital: readU128LE(data, base + V12_17_ACCT_CAPITAL_OFF),
3910
+ pnl: readI128LE(data, base + V12_17_ACCT_PNL_OFF - d1),
3911
+ reservedPnl: readU128LE(data, base + V12_17_ACCT_RESERVED_PNL_OFF - d1),
3912
+ warmupStartedAtSlot: 0n,
3913
+ // removed
3914
+ warmupSlopePerStep: 0n,
3915
+ // removed
3916
+ positionSize: readI128LE(data, base + V12_17_ACCT_POSITION_BASIS_Q_OFF - d1),
3917
+ entryPrice: 0n,
3918
+ // removed — compute off-chain from position_basis_q / effective_pos_q
3919
+ fundingIndex: 0n,
3920
+ // replaced by per-side f_long_num/f_short_num + per-account f_snap
3921
+ matcherProgram: new PublicKey5(data.subarray(base + V12_17_ACCT_MATCHER_PROGRAM_OFF - d1, base + V12_17_ACCT_MATCHER_PROGRAM_OFF - d1 + 32)),
3922
+ matcherContext: new PublicKey5(data.subarray(base + V12_17_ACCT_MATCHER_CONTEXT_OFF - d1, base + V12_17_ACCT_MATCHER_CONTEXT_OFF - d1 + 32)),
3923
+ owner: new PublicKey5(data.subarray(base + V12_17_ACCT_OWNER_OFF - d1, base + V12_17_ACCT_OWNER_OFF - d1 + 32)),
3924
+ feeCredits: readI128LE(data, base + V12_17_ACCT_FEE_CREDITS_OFF - d1),
3925
+ lastFeeSlot: 0n,
3926
+ // removed
3927
+ feesEarnedTotal: 0n,
3928
+ // removed in v12.17
3929
+ exactReserveCohorts: null,
3930
+ // replaced by two-bucket warmup
3931
+ exactCohortCount: null,
3932
+ overflowOlder: null,
3933
+ overflowOlderPresent: null,
3934
+ overflowNewest: null,
3935
+ overflowNewestPresent: null,
3936
+ // V12_17 fields
3937
+ fSnap: readI128LE(data, base + V12_17_ACCT_F_SNAP_OFF - d1),
3938
+ adlABasis: readU128LE(data, base + V12_17_ACCT_ADL_A_BASIS_OFF - d1),
3939
+ adlKSnap: readI128LE(data, base + V12_17_ACCT_ADL_K_SNAP_OFF - d1),
3940
+ adlEpochSnap: readU64LE(data, base + V12_17_ACCT_ADL_EPOCH_SNAP_OFF - d1),
3941
+ schedPresent: readU8(data, base + V12_17_ACCT_SCHED_PRESENT_OFF - d1) !== 0,
3942
+ schedRemainingQ: readU128LE(data, base + V12_17_ACCT_SCHED_REMAINING_Q_OFF - d1),
3943
+ schedAnchorQ: readU128LE(data, base + V12_17_ACCT_SCHED_ANCHOR_Q_OFF - d1),
3944
+ schedStartSlot: readU64LE(data, base + V12_17_ACCT_SCHED_START_SLOT_OFF - d1),
3945
+ schedHorizon: readU64LE(data, base + V12_17_ACCT_SCHED_HORIZON_OFF - d1),
3946
+ schedReleaseQ: readU128LE(data, base + V12_17_ACCT_SCHED_RELEASE_Q_OFF - d1),
3947
+ pendingPresent: readU8(data, base + V12_17_ACCT_PENDING_PRESENT_OFF - d1) !== 0,
3948
+ pendingRemainingQ: readU128LE(data, base + V12_17_ACCT_PENDING_REMAINING_Q_OFF - d2),
3949
+ pendingHorizon: readU64LE(data, base + V12_17_ACCT_PENDING_HORIZON_OFF - d2),
3950
+ pendingCreatedSlot: readU64LE(data, base + V12_17_ACCT_PENDING_CREATED_SLOT_OFF - d2)
3951
+ };
3952
+ }
3953
+ if (isV12_15) {
3954
+ const kindByte2 = readU8(data, base + V12_15_ACCT_KIND_OFF);
3955
+ const kind2 = kindByte2 === 1 ? 1 /* LP */ : 0 /* User */;
3956
+ const cohortCount = readU8(data, base + V12_15_ACCT_EXACT_COHORT_COUNT_OFF);
3957
+ const exactReserveCohorts = [];
3958
+ for (let i = 0; i < 62; i++) {
3959
+ const cohortOff = base + V12_15_ACCT_EXACT_RESERVE_COHORTS_OFF + i * 64;
3960
+ exactReserveCohorts.push(data.slice(cohortOff, cohortOff + 64));
3961
+ }
3962
+ const overflowOlderPresent = readU8(data, base + V12_15_ACCT_OVERFLOW_OLDER_PRESENT_OFF) !== 0;
3963
+ const overflowNewestPresent = readU8(data, base + V12_15_ACCT_OVERFLOW_NEWEST_PRESENT_OFF) !== 0;
3964
+ return {
3965
+ kind: kind2,
3966
+ accountId: readU64LE(data, base + V12_15_ACCT_ACCOUNT_ID_OFF),
3967
+ capital: readU128LE(data, base + V12_15_ACCT_CAPITAL_OFF),
3968
+ pnl: readI128LE(data, base + V12_15_ACCT_PNL_OFF),
3969
+ reservedPnl: readU128LE(data, base + V12_15_ACCT_RESERVED_PNL_OFF),
3970
+ warmupStartedAtSlot: 0n,
3971
+ // removed in v12.15
3972
+ warmupSlopePerStep: 0n,
3973
+ // removed in v12.15
3974
+ positionSize: readI128LE(data, base + V12_15_ACCT_POSITION_BASIS_Q_OFF),
3975
+ entryPrice: readU64LE(data, base + V12_15_ACCT_ENTRY_PRICE_OFF),
3976
+ fundingIndex: 0n,
3977
+ // not present in v12.15 account struct
3978
+ matcherProgram: new PublicKey5(data.subarray(base + V12_15_ACCT_MATCHER_PROGRAM_OFF, base + V12_15_ACCT_MATCHER_PROGRAM_OFF + 32)),
3979
+ matcherContext: new PublicKey5(data.subarray(base + V12_15_ACCT_MATCHER_CONTEXT_OFF, base + V12_15_ACCT_MATCHER_CONTEXT_OFF + 32)),
3980
+ owner: new PublicKey5(data.subarray(base + V12_15_ACCT_OWNER_OFF, base + V12_15_ACCT_OWNER_OFF + 32)),
3981
+ feeCredits: readI128LE(data, base + V12_15_ACCT_FEE_CREDITS_OFF),
3982
+ lastFeeSlot: 0n,
3983
+ // removed in v12.15
3984
+ feesEarnedTotal: readU128LE(data, base + V12_15_ACCT_FEES_EARNED_TOTAL_OFF),
3985
+ exactReserveCohorts,
3986
+ exactCohortCount: cohortCount,
3987
+ overflowOlder: data.slice(base + V12_15_ACCT_OVERFLOW_OLDER_OFF, base + V12_15_ACCT_OVERFLOW_OLDER_OFF + 64),
3988
+ overflowOlderPresent,
3989
+ overflowNewest: data.slice(base + V12_15_ACCT_OVERFLOW_NEWEST_OFF, base + V12_15_ACCT_OVERFLOW_NEWEST_OFF + 64),
3990
+ overflowNewestPresent,
3991
+ // v12.17 fields (not present in v12.15)
3992
+ fSnap: 0n,
3993
+ adlABasis: 0n,
3994
+ adlKSnap: 0n,
3995
+ adlEpochSnap: 0n,
3996
+ schedPresent: null,
3997
+ schedRemainingQ: null,
3998
+ schedAnchorQ: null,
3999
+ schedStartSlot: null,
4000
+ schedHorizon: null,
4001
+ schedReleaseQ: null,
4002
+ pendingPresent: null,
4003
+ pendingRemainingQ: null,
4004
+ pendingHorizon: null,
4005
+ pendingCreatedSlot: null
4006
+ };
4007
+ }
2709
4008
  const warmupStartedOff = isAdl ? V_ADL_ACCT_WARMUP_STARTED_OFF : ACCT_WARMUP_STARTED_OFF;
2710
4009
  const warmupSlopeOff = isAdl ? V_ADL_ACCT_WARMUP_SLOPE_OFF : ACCT_WARMUP_SLOPE_OFF;
2711
- const positionSizeOff = isV12_1 ? V12_1_ACCT_POSITION_SIZE_OFF : isAdl ? V_ADL_ACCT_POSITION_SIZE_OFF : ACCT_POSITION_SIZE_OFF;
2712
- const entryPriceOff = isV12_1 ? V12_1_ACCT_ENTRY_PRICE_OFF : isAdl ? V_ADL_ACCT_ENTRY_PRICE_OFF : ACCT_ENTRY_PRICE_OFF;
2713
- const fundingIndexOff = isV12_1 ? V12_1_ACCT_FUNDING_INDEX_OFF : isAdl ? V_ADL_ACCT_FUNDING_INDEX_OFF : ACCT_FUNDING_INDEX_OFF;
2714
- const matcherProgOff = isV12_1 ? V12_1_ACCT_MATCHER_PROGRAM_OFF : isAdl ? V_ADL_ACCT_MATCHER_PROGRAM_OFF : ACCT_MATCHER_PROGRAM_OFF;
2715
- const matcherCtxOff = isV12_1 ? V12_1_ACCT_MATCHER_CONTEXT_OFF : isAdl ? V_ADL_ACCT_MATCHER_CONTEXT_OFF : ACCT_MATCHER_CONTEXT_OFF;
2716
- const feeCreditsOff = isV12_1 ? V12_1_ACCT_FEE_CREDITS_OFF : isAdl ? V_ADL_ACCT_FEE_CREDITS_OFF : ACCT_FEE_CREDITS_OFF;
2717
- const lastFeeSlotOff = isV12_1 ? V12_1_ACCT_LAST_FEE_SLOT_OFF : isAdl ? V_ADL_ACCT_LAST_FEE_SLOT_OFF : ACCT_LAST_FEE_SLOT_OFF;
4010
+ const positionSizeOff = isV12_1 || isV12_1EP ? V12_1_ACCT_POSITION_SIZE_OFF : isAdl ? V_ADL_ACCT_POSITION_SIZE_OFF : ACCT_POSITION_SIZE_OFF;
4011
+ const entryPriceOff = isV12_1EP ? V12_1_EP_ACCT_ENTRY_PRICE_OFF : isV12_1 ? V12_1_ACCT_ENTRY_PRICE_OFF : isAdl ? V_ADL_ACCT_ENTRY_PRICE_OFF : ACCT_ENTRY_PRICE_OFF;
4012
+ const fundingIndexOff = isV12_1 || isV12_1EP ? -1 : isAdl ? V_ADL_ACCT_FUNDING_INDEX_OFF : ACCT_FUNDING_INDEX_OFF;
4013
+ const matcherProgOff = isV12_1EP ? V12_1_EP_ACCT_MATCHER_PROGRAM_OFF : isV12_1 ? V12_1_ACCT_MATCHER_PROGRAM_OFF : isAdl ? V_ADL_ACCT_MATCHER_PROGRAM_OFF : ACCT_MATCHER_PROGRAM_OFF;
4014
+ const matcherCtxOff = isV12_1EP ? V12_1_EP_ACCT_MATCHER_CONTEXT_OFF : isV12_1 ? V12_1_ACCT_MATCHER_CONTEXT_OFF : isAdl ? V_ADL_ACCT_MATCHER_CONTEXT_OFF : ACCT_MATCHER_CONTEXT_OFF;
4015
+ const feeCreditsOff = isV12_1EP ? V12_1_EP_ACCT_FEE_CREDITS_OFF : isV12_1 ? V12_1_ACCT_FEE_CREDITS_OFF : isAdl ? V_ADL_ACCT_FEE_CREDITS_OFF : ACCT_FEE_CREDITS_OFF;
4016
+ const lastFeeSlotOff = isV12_1EP ? V12_1_EP_ACCT_LAST_FEE_SLOT_OFF : isV12_1 ? V12_1_ACCT_LAST_FEE_SLOT_OFF : isAdl ? V_ADL_ACCT_LAST_FEE_SLOT_OFF : ACCT_LAST_FEE_SLOT_OFF;
2718
4017
  const kindByte = readU8(data, base + ACCT_KIND_OFF);
2719
4018
  const kind = kindByte === 1 ? 1 /* LP */ : 0 /* User */;
2720
4019
  return {
@@ -2727,14 +4026,37 @@ function parseAccount(data, idx) {
2727
4026
  warmupSlopePerStep: readU128LE(data, base + warmupSlopeOff),
2728
4027
  positionSize: readI128LE(data, base + positionSizeOff),
2729
4028
  entryPrice: entryPriceOff >= 0 ? readU64LE(data, base + entryPriceOff) : 0n,
2730
- // V12_1: entry_price removed
2731
- // V12_1 changed funding_index from i128 to i64 (legacy field moved to end of account)
2732
- fundingIndex: isV12_1 ? BigInt(readI64LE(data, base + fundingIndexOff)) : readI128LE(data, base + fundingIndexOff),
2733
- matcherProgram: new PublicKey3(data.subarray(base + matcherProgOff, base + matcherProgOff + 32)),
2734
- matcherContext: new PublicKey3(data.subarray(base + matcherCtxOff, base + matcherCtxOff + 32)),
2735
- owner: new PublicKey3(data.subarray(base + layout.acctOwnerOff, base + layout.acctOwnerOff + 32)),
4029
+ // V12_1/V12_1_EP: funding_index not present in SBF layout
4030
+ fundingIndex: isV12_1 || isV12_1EP ? fundingIndexOff >= 0 ? BigInt(readI64LE(data, base + fundingIndexOff)) : 0n : readI128LE(data, base + fundingIndexOff),
4031
+ matcherProgram: new PublicKey5(data.subarray(base + matcherProgOff, base + matcherProgOff + 32)),
4032
+ matcherContext: new PublicKey5(data.subarray(base + matcherCtxOff, base + matcherCtxOff + 32)),
4033
+ owner: new PublicKey5(data.subarray(base + layout.acctOwnerOff, base + layout.acctOwnerOff + 32)),
2736
4034
  feeCredits: readI128LE(data, base + feeCreditsOff),
2737
- lastFeeSlot: readU64LE(data, base + lastFeeSlotOff)
4035
+ lastFeeSlot: readU64LE(data, base + lastFeeSlotOff),
4036
+ feesEarnedTotal: 0n,
4037
+ // not present in pre-v12.15 layouts
4038
+ exactReserveCohorts: null,
4039
+ // not present in pre-v12.15 layouts
4040
+ exactCohortCount: null,
4041
+ overflowOlder: null,
4042
+ overflowOlderPresent: null,
4043
+ overflowNewest: null,
4044
+ overflowNewestPresent: null,
4045
+ // v12.17 fields (not present in pre-v12.17)
4046
+ fSnap: 0n,
4047
+ adlABasis: 0n,
4048
+ adlKSnap: 0n,
4049
+ adlEpochSnap: 0n,
4050
+ schedPresent: null,
4051
+ schedRemainingQ: null,
4052
+ schedAnchorQ: null,
4053
+ schedStartSlot: null,
4054
+ schedHorizon: null,
4055
+ schedReleaseQ: null,
4056
+ pendingPresent: null,
4057
+ pendingRemainingQ: null,
4058
+ pendingHorizon: null,
4059
+ pendingCreatedSlot: null
2738
4060
  };
2739
4061
  }
2740
4062
  function parseAllAccounts(data) {
@@ -2754,14 +4076,20 @@ function parseAllAccounts(data) {
2754
4076
  }
2755
4077
 
2756
4078
  // src/solana/pda.ts
2757
- import { PublicKey as PublicKey4 } from "@solana/web3.js";
4079
+ import { PublicKey as PublicKey6 } from "@solana/web3.js";
2758
4080
  var textEncoder = new TextEncoder();
2759
4081
  function deriveVaultAuthority(programId, slab) {
2760
- return PublicKey4.findProgramAddressSync(
4082
+ return PublicKey6.findProgramAddressSync(
2761
4083
  [textEncoder.encode("vault"), slab.toBytes()],
2762
4084
  programId
2763
4085
  );
2764
4086
  }
4087
+ function deriveInsuranceLpMint(programId, slab) {
4088
+ return PublicKey6.findProgramAddressSync(
4089
+ [textEncoder.encode("lp_vault_mint"), slab.toBytes()],
4090
+ programId
4091
+ );
4092
+ }
2765
4093
  var LP_INDEX_U16_MAX = 65535;
2766
4094
  function deriveLpPda(programId, slab, lpIdx) {
2767
4095
  if (typeof lpIdx !== "number" || !Number.isInteger(lpIdx) || lpIdx < 0 || lpIdx > LP_INDEX_U16_MAX) {
@@ -2769,34 +4097,28 @@ function deriveLpPda(programId, slab, lpIdx) {
2769
4097
  `deriveLpPda: lpIdx must be an integer in [0, ${LP_INDEX_U16_MAX}], got ${lpIdx}`
2770
4098
  );
2771
4099
  }
2772
- const idxBuf = new Uint8Array(2);
2773
- new DataView(idxBuf.buffer).setUint16(0, lpIdx, true);
2774
- return PublicKey4.findProgramAddressSync(
2775
- [textEncoder.encode("lp"), slab.toBytes(), idxBuf],
2776
- programId
2777
- );
2778
- }
2779
- function deriveKeeperFund(programId, slab) {
2780
- return PublicKey4.findProgramAddressSync(
2781
- [textEncoder.encode("keeper_fund"), slab.toBytes()],
4100
+ const idxBuf2 = new Uint8Array(2);
4101
+ new DataView(idxBuf2.buffer).setUint16(0, lpIdx, true);
4102
+ return PublicKey6.findProgramAddressSync(
4103
+ [textEncoder.encode("lp"), slab.toBytes(), idxBuf2],
2782
4104
  programId
2783
4105
  );
2784
4106
  }
2785
- var PUMPSWAP_PROGRAM_ID = new PublicKey4(
4107
+ var PUMPSWAP_PROGRAM_ID = new PublicKey6(
2786
4108
  "pAMMBay6oceH9fJKBRHGP5D4bD4sWpmSwMn52FMfXEA"
2787
4109
  );
2788
- var RAYDIUM_CLMM_PROGRAM_ID = new PublicKey4(
4110
+ var RAYDIUM_CLMM_PROGRAM_ID = new PublicKey6(
2789
4111
  "CAMMCzo5YL8w4VFF8KVHrK22GGUsp5VTaW7grrKgrWqK"
2790
4112
  );
2791
- var METEORA_DLMM_PROGRAM_ID = new PublicKey4(
4113
+ var METEORA_DLMM_PROGRAM_ID = new PublicKey6(
2792
4114
  "LBUZKhRxPF3XUpBCjp4YzTKgLccjZhTSDM9YuVaPwxo"
2793
4115
  );
2794
- var PYTH_PUSH_ORACLE_PROGRAM_ID = new PublicKey4(
4116
+ var PYTH_PUSH_ORACLE_PROGRAM_ID = new PublicKey6(
2795
4117
  "pythWSnswVUd12oZpeFP8e9CVaEqJg25g1Vtc2biRsT"
2796
4118
  );
2797
4119
  var CREATOR_LOCK_SEED = "creator_lock";
2798
4120
  function deriveCreatorLockPda(programId, slab) {
2799
- return PublicKey4.findProgramAddressSync(
4121
+ return PublicKey6.findProgramAddressSync(
2800
4122
  [textEncoder.encode(CREATOR_LOCK_SEED), slab.toBytes()],
2801
4123
  programId
2802
4124
  );
@@ -2818,17 +4140,10 @@ function derivePythPushOraclePDA(feedIdHex) {
2818
4140
  }
2819
4141
  const feedId = new Uint8Array(32);
2820
4142
  for (let i = 0; i < 32; i++) {
2821
- const hexPair = normalized.substring(i * 2, i * 2 + 2);
2822
- const byte = parseInt(hexPair, 16);
2823
- if (Number.isNaN(byte)) {
2824
- throw new Error(
2825
- `derivePythPushOraclePDA: failed to parse hex byte at position ${i}: "${hexPair}"`
2826
- );
2827
- }
2828
- feedId[i] = byte;
4143
+ feedId[i] = parseInt(normalized.substring(i * 2, i * 2 + 2), 16);
2829
4144
  }
2830
4145
  const shardBuf = new Uint8Array(2);
2831
- return PublicKey4.findProgramAddressSync(
4146
+ return PublicKey6.findProgramAddressSync(
2832
4147
  [shardBuf, feedId],
2833
4148
  PYTH_PUSH_ORACLE_PROGRAM_ID
2834
4149
  );
@@ -2852,14 +4167,12 @@ async function fetchTokenAccount(connection, address, tokenProgramId = TOKEN_PRO
2852
4167
  }
2853
4168
 
2854
4169
  // src/solana/discovery.ts
2855
- import { PublicKey as PublicKey6 } from "@solana/web3.js";
4170
+ import { PublicKey as PublicKey8 } from "@solana/web3.js";
2856
4171
 
2857
4172
  // src/solana/static-markets.ts
2858
- import { PublicKey as PublicKey5 } from "@solana/web3.js";
4173
+ import { PublicKey as PublicKey7 } from "@solana/web3.js";
2859
4174
  var MAINNET_MARKETS = [
2860
- // Populated at mainnet launch currently empty.
2861
- // To add entries:
2862
- // { slabAddress: "ABC123...", symbol: "SOL-PERP", name: "SOL Perpetual" },
4175
+ { slabAddress: "7psyeWRts4pRX2cyAWD1NH87bR9ugXP7pe6ARgfG79Do", symbol: "SOL-PERP", name: "SOL/USDC Perpetual" }
2863
4176
  ];
2864
4177
  var DEVNET_MARKETS = [
2865
4178
  // Populated from prior discoverMarkets() runs on devnet.
@@ -2893,7 +4206,7 @@ function registerStaticMarkets(network, entries) {
2893
4206
  if (!entry.slabAddress) continue;
2894
4207
  if (seen.has(entry.slabAddress)) continue;
2895
4208
  try {
2896
- new PublicKey5(entry.slabAddress);
4209
+ new PublicKey7(entry.slabAddress);
2897
4210
  } catch {
2898
4211
  console.warn(
2899
4212
  `[registerStaticMarkets] Skipping invalid slabAddress: ${entry.slabAddress}`
@@ -2917,10 +4230,9 @@ function clearStaticMarkets(network) {
2917
4230
  var ENGINE_BITMAP_OFF_V0 = 320;
2918
4231
  var MAGIC_BYTES = new Uint8Array([84, 65, 76, 79, 67, 82, 69, 80]);
2919
4232
  var SLAB_TIERS = {
2920
- micro: SLAB_TIERS_V12_1["micro"],
2921
- small: SLAB_TIERS_V12_1["small"],
2922
- medium: SLAB_TIERS_V12_1["medium"],
2923
- large: SLAB_TIERS_V12_1["large"]
4233
+ small: SLAB_TIERS_V12_17["small"],
4234
+ medium: SLAB_TIERS_V12_17["medium"],
4235
+ large: SLAB_TIERS_V12_17["large"]
2924
4236
  };
2925
4237
  var SLAB_TIERS_V0 = {
2926
4238
  small: { maxAccounts: 256, dataSize: 62808, label: "Small", description: "256 slots \xB7 ~0.44 SOL" },
@@ -3027,6 +4339,8 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3027
4339
  fundingIndexQpbE6: readI128LE2(data, base + 112),
3028
4340
  lastFundingSlot: readU64LE2(data, base + 128),
3029
4341
  fundingRateBpsPerSlotLast: readI64LE2(data, base + 136),
4342
+ fundingRateE9: 0n,
4343
+ marketMode: null,
3030
4344
  lastCrankSlot: readU64LE2(data, base + 144),
3031
4345
  maxCrankStalenessSlots: readU64LE2(data, base + 152),
3032
4346
  totalOpenInterest: readU128LE2(data, base + 160),
@@ -3034,6 +4348,7 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3034
4348
  shortOi: 0n,
3035
4349
  cTot: readU128LE2(data, base + 176),
3036
4350
  pnlPosTot: readU128LE2(data, base + 192),
4351
+ pnlMaturedPosTot: 0n,
3037
4352
  liqCursor: readU16LE2(data, base + 208),
3038
4353
  gcCursor: readU16LE2(data, base + 210),
3039
4354
  lastSweepStartSlot: readU64LE2(data, base + 216),
@@ -3051,6 +4366,14 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3051
4366
  lastBreakerSlot: 0n,
3052
4367
  markPriceE6: 0n,
3053
4368
  // V0 engine has no mark_price field
4369
+ oraclePriceE6: 0n,
4370
+ fLongNum: 0n,
4371
+ fShortNum: 0n,
4372
+ negPnlAccountCount: 0n,
4373
+ fundPxLast: 0n,
4374
+ resolvedKLongTerminalDelta: 0n,
4375
+ resolvedKShortTerminalDelta: 0n,
4376
+ resolvedLivePrice: 0n,
3054
4377
  numUsedAccounts: canReadNumUsed ? readU16LE2(data, base + numUsedOff) : 0,
3055
4378
  nextAccountId: canReadNextId ? readU64LE2(data, base + nextAccountIdOff) : 0n
3056
4379
  };
@@ -3069,6 +4392,8 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3069
4392
  fundingIndexQpbE6: readI128LE2(data, base + 360),
3070
4393
  lastFundingSlot: readU64LE2(data, base + 376),
3071
4394
  fundingRateBpsPerSlotLast: readI64LE2(data, base + 384),
4395
+ fundingRateE9: 0n,
4396
+ marketMode: null,
3072
4397
  lastCrankSlot: readU64LE2(data, base + 392),
3073
4398
  maxCrankStalenessSlots: readU64LE2(data, base + 400),
3074
4399
  totalOpenInterest: readU128LE2(data, base + 408),
@@ -3078,6 +4403,7 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3078
4403
  // V2 has no short_oi
3079
4404
  cTot: readU128LE2(data, base + 424),
3080
4405
  pnlPosTot: readU128LE2(data, base + 440),
4406
+ pnlMaturedPosTot: 0n,
3081
4407
  liqCursor: readU16LE2(data, base + 456),
3082
4408
  gcCursor: readU16LE2(data, base + 458),
3083
4409
  lastSweepStartSlot: readU64LE2(data, base + 464),
@@ -3096,6 +4422,14 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3096
4422
  lastBreakerSlot: 0n,
3097
4423
  markPriceE6: 0n,
3098
4424
  // V2 has no mark_price
4425
+ oraclePriceE6: 0n,
4426
+ fLongNum: 0n,
4427
+ fShortNum: 0n,
4428
+ negPnlAccountCount: 0n,
4429
+ fundPxLast: 0n,
4430
+ resolvedKLongTerminalDelta: 0n,
4431
+ resolvedKShortTerminalDelta: 0n,
4432
+ resolvedLivePrice: 0n,
3099
4433
  numUsedAccounts: canReadNumUsed ? readU16LE2(data, base + numUsedOff) : 0,
3100
4434
  nextAccountId: canReadNextId ? readU64LE2(data, base + nextAccountIdOff) : 0n
3101
4435
  };
@@ -3115,6 +4449,8 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3115
4449
  fundingIndexQpbE6: readI128LE2(data, base + l.engineFundingIndexOff),
3116
4450
  lastFundingSlot: readU64LE2(data, base + l.engineLastFundingSlotOff),
3117
4451
  fundingRateBpsPerSlotLast: readI64LE2(data, base + l.engineFundingRateBpsOff),
4452
+ fundingRateE9: 0n,
4453
+ marketMode: null,
3118
4454
  lastCrankSlot: readU64LE2(data, base + l.engineLastCrankSlotOff),
3119
4455
  maxCrankStalenessSlots: readU64LE2(data, base + l.engineMaxCrankStalenessOff),
3120
4456
  totalOpenInterest: readU128LE2(data, base + l.engineTotalOiOff),
@@ -3122,6 +4458,7 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3122
4458
  shortOi: l.engineShortOiOff >= 0 ? readU128LE2(data, base + l.engineShortOiOff) : 0n,
3123
4459
  cTot: readU128LE2(data, base + l.engineCTotOff),
3124
4460
  pnlPosTot: readU128LE2(data, base + l.enginePnlPosTotOff),
4461
+ pnlMaturedPosTot: 0n,
3125
4462
  liqCursor: readU16LE2(data, base + l.engineLiqCursorOff),
3126
4463
  gcCursor: readU16LE2(data, base + l.engineGcCursorOff),
3127
4464
  lastSweepStartSlot: readU64LE2(data, base + l.engineLastSweepStartOff),
@@ -3138,6 +4475,14 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3138
4475
  emergencyStartSlot: l.engineEmergencyStartSlotOff >= 0 ? readU64LE2(data, base + l.engineEmergencyStartSlotOff) : 0n,
3139
4476
  lastBreakerSlot: l.engineLastBreakerSlotOff >= 0 ? readU64LE2(data, base + l.engineLastBreakerSlotOff) : 0n,
3140
4477
  markPriceE6: l.engineMarkPriceOff >= 0 ? readU64LE2(data, base + l.engineMarkPriceOff) : 0n,
4478
+ oraclePriceE6: 0n,
4479
+ fLongNum: 0n,
4480
+ fShortNum: 0n,
4481
+ negPnlAccountCount: 0n,
4482
+ fundPxLast: 0n,
4483
+ resolvedKLongTerminalDelta: 0n,
4484
+ resolvedKShortTerminalDelta: 0n,
4485
+ resolvedLivePrice: 0n,
3141
4486
  numUsedAccounts: canReadNumUsed ? readU16LE2(data, base + numUsedOff) : 0,
3142
4487
  nextAccountId: canReadNextId ? readU64LE2(data, base + nextAccountIdOff) : 0n
3143
4488
  };
@@ -3155,6 +4500,8 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3155
4500
  fundingIndexQpbE6: readI128LE2(data, base + 368),
3156
4501
  lastFundingSlot: readU64LE2(data, base + 384),
3157
4502
  fundingRateBpsPerSlotLast: readI64LE2(data, base + 392),
4503
+ fundingRateE9: 0n,
4504
+ marketMode: null,
3158
4505
  lastCrankSlot: readU64LE2(data, base + 424),
3159
4506
  maxCrankStalenessSlots: readU64LE2(data, base + 408),
3160
4507
  totalOpenInterest: readU128LE2(data, base + 416),
@@ -3162,6 +4509,7 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3162
4509
  shortOi: readU128LE2(data, base + 448),
3163
4510
  cTot: readU128LE2(data, base + 464),
3164
4511
  pnlPosTot: readU128LE2(data, base + 480),
4512
+ pnlMaturedPosTot: 0n,
3165
4513
  liqCursor: readU16LE2(data, base + 496),
3166
4514
  gcCursor: readU16LE2(data, base + 498),
3167
4515
  lastSweepStartSlot: readU64LE2(data, base + 504),
@@ -3179,6 +4527,14 @@ function parseEngineLight(data, layout, maxAccounts = 4096) {
3179
4527
  lastBreakerSlot: readU64LE2(data, base + 624),
3180
4528
  markPriceE6: readU64LE2(data, base + 400),
3181
4529
  // PERC-1094: was 392
4530
+ oraclePriceE6: 0n,
4531
+ fLongNum: 0n,
4532
+ fShortNum: 0n,
4533
+ negPnlAccountCount: 0n,
4534
+ fundPxLast: 0n,
4535
+ resolvedKLongTerminalDelta: 0n,
4536
+ resolvedKShortTerminalDelta: 0n,
4537
+ resolvedLivePrice: 0n,
3182
4538
  numUsedAccounts: canReadNumUsed ? readU16LE2(data, base + numUsedOff) : 0,
3183
4539
  nextAccountId: canReadNextId ? readU64LE2(data, base + nextAccountIdOff) : 0n
3184
4540
  };
@@ -3200,12 +4556,19 @@ async function discoverMarkets(connection, programId, options = {}) {
3200
4556
  } = options;
3201
4557
  const ALL_TIERS = [
3202
4558
  ...Object.values(SLAB_TIERS),
4559
+ // v12.17 (default)
4560
+ ...Object.values(SLAB_TIERS_V12_15),
4561
+ // v12.15
4562
+ ...Object.values(SLAB_TIERS_V12_1),
4563
+ // v12.1
3203
4564
  ...Object.values(SLAB_TIERS_V0),
3204
4565
  ...Object.values(SLAB_TIERS_V1D),
3205
4566
  ...Object.values(SLAB_TIERS_V1D_LEGACY),
3206
4567
  ...Object.values(SLAB_TIERS_V2),
3207
4568
  ...Object.values(SLAB_TIERS_V1M),
3208
- ...Object.values(SLAB_TIERS_V_ADL)
4569
+ ...Object.values(SLAB_TIERS_V1M2),
4570
+ ...Object.values(SLAB_TIERS_V_ADL),
4571
+ ...Object.values(SLAB_TIERS_V_SETDEXPOOL)
3209
4572
  ];
3210
4573
  let rawAccounts = [];
3211
4574
  async function fetchTierWithRetry(tier) {
@@ -3503,7 +4866,7 @@ async function discoverMarketsViaApi(connection, programId, apiBaseUrl, options
3503
4866
  for (const entry of apiMarkets) {
3504
4867
  if (!entry.slab_address || typeof entry.slab_address !== "string") continue;
3505
4868
  try {
3506
- addresses.push(new PublicKey6(entry.slab_address));
4869
+ addresses.push(new PublicKey8(entry.slab_address));
3507
4870
  } catch {
3508
4871
  console.warn(
3509
4872
  `[discoverMarketsViaApi] Skipping invalid slab address: ${entry.slab_address}`
@@ -3525,7 +4888,7 @@ async function discoverMarketsViaStaticBundle(connection, programId, entries, op
3525
4888
  for (const entry of entries) {
3526
4889
  if (!entry.slabAddress || typeof entry.slabAddress !== "string") continue;
3527
4890
  try {
3528
- addresses.push(new PublicKey6(entry.slabAddress));
4891
+ addresses.push(new PublicKey8(entry.slabAddress));
3529
4892
  } catch {
3530
4893
  console.warn(
3531
4894
  `[discoverMarketsViaStaticBundle] Skipping invalid slab address: ${entry.slabAddress}`
@@ -3543,7 +4906,7 @@ async function discoverMarketsViaStaticBundle(connection, programId, entries, op
3543
4906
  }
3544
4907
 
3545
4908
  // src/solana/dex-oracle.ts
3546
- import { PublicKey as PublicKey7 } from "@solana/web3.js";
4909
+ import { PublicKey as PublicKey9 } from "@solana/web3.js";
3547
4910
  function detectDexType(ownerProgramId) {
3548
4911
  if (ownerProgramId.equals(PUMPSWAP_PROGRAM_ID)) return "pumpswap";
3549
4912
  if (ownerProgramId.equals(RAYDIUM_CLMM_PROGRAM_ID)) return "raydium-clmm";
@@ -3579,10 +4942,10 @@ function parsePumpSwapPool(poolAddress, data) {
3579
4942
  return {
3580
4943
  dexType: "pumpswap",
3581
4944
  poolAddress,
3582
- baseMint: new PublicKey7(data.slice(35, 67)),
3583
- quoteMint: new PublicKey7(data.slice(67, 99)),
3584
- baseVault: new PublicKey7(data.slice(131, 163)),
3585
- quoteVault: new PublicKey7(data.slice(163, 195))
4945
+ baseMint: new PublicKey9(data.slice(35, 67)),
4946
+ quoteMint: new PublicKey9(data.slice(67, 99)),
4947
+ baseVault: new PublicKey9(data.slice(131, 163)),
4948
+ quoteVault: new PublicKey9(data.slice(163, 195))
3586
4949
  };
3587
4950
  }
3588
4951
  var SPL_TOKEN_AMOUNT_MIN_LEN = 72;
@@ -3608,8 +4971,8 @@ function parseRaydiumClmmPool(poolAddress, data) {
3608
4971
  return {
3609
4972
  dexType: "raydium-clmm",
3610
4973
  poolAddress,
3611
- baseMint: new PublicKey7(data.slice(73, 105)),
3612
- quoteMint: new PublicKey7(data.slice(105, 137))
4974
+ baseMint: new PublicKey9(data.slice(73, 105)),
4975
+ quoteMint: new PublicKey9(data.slice(105, 137))
3613
4976
  };
3614
4977
  }
3615
4978
  var MAX_TOKEN_DECIMALS = 24;
@@ -3627,7 +4990,9 @@ function computeRaydiumClmmPriceE6(data) {
3627
4990
  }
3628
4991
  const sqrtPriceX64 = readU128LE3(dv3, 253);
3629
4992
  if (sqrtPriceX64 === 0n) return 0n;
3630
- const priceE6Raw = sqrtPriceX64 * sqrtPriceX64 * 1000000n >> 128n;
4993
+ const scaledSqrt = sqrtPriceX64 * 1000000n;
4994
+ const term = scaledSqrt >> 64n;
4995
+ const priceE6Raw = term * sqrtPriceX64 >> 64n;
3631
4996
  const decimalDiff = 6 + decimals0 - decimals1;
3632
4997
  const adjustedDiff = decimalDiff - 6;
3633
4998
  if (adjustedDiff >= 0) {
@@ -3646,8 +5011,8 @@ function parseMeteoraPool(poolAddress, data) {
3646
5011
  return {
3647
5012
  dexType: "meteora-dlmm",
3648
5013
  poolAddress,
3649
- baseMint: new PublicKey7(data.slice(81, 113)),
3650
- quoteMint: new PublicKey7(data.slice(113, 145))
5014
+ baseMint: new PublicKey9(data.slice(81, 113)),
5015
+ quoteMint: new PublicKey9(data.slice(113, 145))
3651
5016
  };
3652
5017
  }
3653
5018
  var MAX_BIN_STEP = 1e4;
@@ -3668,26 +5033,13 @@ function computeMeteoraDlmmPriceE6(data) {
3668
5033
  `Meteora DLMM: |activeId| ${Math.abs(activeId)} exceeds max ${MAX_ACTIVE_ID_ABS}`
3669
5034
  );
3670
5035
  }
3671
- const MAX_ABS_BIN_ID = 5e5;
3672
- if (activeId > MAX_ABS_BIN_ID || activeId < -MAX_ABS_BIN_ID) {
3673
- throw new Error(
3674
- `Meteora DLMM: activeId ${activeId} exceeds safe range (\xB1${MAX_ABS_BIN_ID})`
3675
- );
3676
- }
3677
5036
  const SCALE = 1000000000000000000n;
3678
5037
  const base = SCALE + BigInt(binStep) * SCALE / 10000n;
3679
5038
  const isNeg = activeId < 0;
3680
5039
  let exp = isNeg ? BigInt(-activeId) : BigInt(activeId);
3681
5040
  let result = SCALE;
3682
5041
  let b = base;
3683
- let iterations = 0;
3684
- const MAX_ITERATIONS = 25;
3685
5042
  while (exp > 0n) {
3686
- if (iterations++ >= MAX_ITERATIONS) {
3687
- throw new Error(
3688
- `Meteora DLMM: exponentiation loop exceeded ${MAX_ITERATIONS} iterations (activeId=${activeId})`
3689
- );
3690
- }
3691
5043
  if (exp & 1n) {
3692
5044
  result = result * b / SCALE;
3693
5045
  }
@@ -3718,7 +5070,6 @@ function readU128LE3(dv3, offset) {
3718
5070
  var CHAINLINK_MIN_SIZE = 224;
3719
5071
  var MAX_DECIMALS = 18;
3720
5072
  var CHAINLINK_DECIMALS_OFFSET = 138;
3721
- var CHAINLINK_TIMESTAMP_OFFSET = 168;
3722
5073
  var CHAINLINK_ANSWER_OFFSET = 216;
3723
5074
  function readU82(data, off) {
3724
5075
  return data[off];
@@ -3726,7 +5077,7 @@ function readU82(data, off) {
3726
5077
  function readBigInt64LE(data, off) {
3727
5078
  return new DataView(data.buffer, data.byteOffset, data.byteLength).getBigInt64(off, true);
3728
5079
  }
3729
- function parseChainlinkPrice(data, options) {
5080
+ function parseChainlinkPrice(data) {
3730
5081
  if (data.length < CHAINLINK_MIN_SIZE) {
3731
5082
  throw new Error(
3732
5083
  `Oracle account data too small: ${data.length} bytes (need at least ${CHAINLINK_MIN_SIZE})`
@@ -3744,18 +5095,7 @@ function parseChainlinkPrice(data, options) {
3744
5095
  `Oracle price is non-positive: ${price}`
3745
5096
  );
3746
5097
  }
3747
- const updatedAtBig = readBigInt64LE(data, CHAINLINK_TIMESTAMP_OFFSET);
3748
- const updatedAt = Number(updatedAtBig);
3749
- if (options?.maxStalenessSeconds !== void 0 && updatedAt > 0) {
3750
- const now = Math.floor(Date.now() / 1e3);
3751
- const age = now - updatedAt;
3752
- if (age > options.maxStalenessSeconds) {
3753
- throw new Error(
3754
- `Oracle price is stale: last updated ${age}s ago (max ${options.maxStalenessSeconds}s)`
3755
- );
3756
- }
3757
- }
3758
- return { price, decimals, updatedAt: updatedAt > 0 ? updatedAt : void 0 };
5098
+ return { price, decimals };
3759
5099
  }
3760
5100
  function isValidChainlinkOracle(data) {
3761
5101
  try {
@@ -3767,19 +5107,15 @@ function isValidChainlinkOracle(data) {
3767
5107
  }
3768
5108
 
3769
5109
  // src/solana/token-program.ts
3770
- import { PublicKey as PublicKey8 } from "@solana/web3.js";
5110
+ import { PublicKey as PublicKey10 } from "@solana/web3.js";
3771
5111
  import { TOKEN_PROGRAM_ID as TOKEN_PROGRAM_ID3 } from "@solana/spl-token";
3772
- var TOKEN_2022_PROGRAM_ID = new PublicKey8(
5112
+ var TOKEN_2022_PROGRAM_ID = new PublicKey10(
3773
5113
  "TokenzQdBNbLqP5VEhdkAS6EPFLC1PHnBqCXEpPxuEb"
3774
5114
  );
3775
5115
  async function detectTokenProgram(connection, mint) {
3776
5116
  const info = await connection.getAccountInfo(mint);
3777
5117
  if (!info) throw new Error(`Mint account not found: ${mint.toBase58()}`);
3778
- if (info.owner.equals(TOKEN_PROGRAM_ID3)) return TOKEN_PROGRAM_ID3;
3779
- if (info.owner.equals(TOKEN_2022_PROGRAM_ID)) return TOKEN_2022_PROGRAM_ID;
3780
- throw new Error(
3781
- `Mint ${mint.toBase58()} is owned by ${info.owner.toBase58()}, which is neither TOKEN_PROGRAM_ID nor TOKEN_2022_PROGRAM_ID`
3782
- );
5118
+ return info.owner;
3783
5119
  }
3784
5120
  function isToken2022(tokenProgramId) {
3785
5121
  return tokenProgramId.equals(TOKEN_2022_PROGRAM_ID);
@@ -3789,70 +5125,8 @@ function isStandardToken(tokenProgramId) {
3789
5125
  }
3790
5126
 
3791
5127
  // src/solana/stake.ts
3792
- import { PublicKey as PublicKey10, SystemProgram as SystemProgram2, SYSVAR_RENT_PUBKEY as SYSVAR_RENT_PUBKEY2, SYSVAR_CLOCK_PUBKEY as SYSVAR_CLOCK_PUBKEY2 } from "@solana/web3.js";
5128
+ import { PublicKey as PublicKey11, SystemProgram as SystemProgram2, SYSVAR_RENT_PUBKEY as SYSVAR_RENT_PUBKEY2, SYSVAR_CLOCK_PUBKEY as SYSVAR_CLOCK_PUBKEY2 } from "@solana/web3.js";
3793
5129
  import { TOKEN_PROGRAM_ID as TOKEN_PROGRAM_ID4 } from "@solana/spl-token";
3794
-
3795
- // src/config/program-ids.ts
3796
- import { PublicKey as PublicKey9 } from "@solana/web3.js";
3797
- function safeEnv(key) {
3798
- try {
3799
- return typeof process !== "undefined" && process?.env ? process.env[key] : void 0;
3800
- } catch {
3801
- return void 0;
3802
- }
3803
- }
3804
- var PROGRAM_IDS = {
3805
- devnet: {
3806
- percolator: "FxfD37s1AZTeWfFQps9Zpebi2dNQ9QSSDtfMKdbsfKrD",
3807
- matcher: "GTRgyTDfrMvBubALAqtHuQwT8tbGyXid7svXZKtWfC9k"
3808
- },
3809
- mainnet: {
3810
- percolator: "ESa89R5Es3rJ5mnwGybVRG1GrNt9etP11Z5V2QWD4edv",
3811
- matcher: "DHP6DtwXP1yJsz8YzfoeigRFPB979gzmumkmCxDLSkUX"
3812
- }
3813
- };
3814
- function getProgramId(network) {
3815
- if (!network) {
3816
- const override = safeEnv("PROGRAM_ID");
3817
- if (override) {
3818
- console.warn(
3819
- `[percolator-sdk] PROGRAM_ID env override active: ${override} \u2014 ensure this points to a trusted program`
3820
- );
3821
- return new PublicKey9(override);
3822
- }
3823
- }
3824
- const detectedNetwork = getCurrentNetwork();
3825
- const targetNetwork = network ?? detectedNetwork;
3826
- const programId = PROGRAM_IDS[targetNetwork].percolator;
3827
- return new PublicKey9(programId);
3828
- }
3829
- function getMatcherProgramId(network) {
3830
- if (!network) {
3831
- const override = safeEnv("MATCHER_PROGRAM_ID");
3832
- if (override) {
3833
- console.warn(
3834
- `[percolator-sdk] MATCHER_PROGRAM_ID env override active: ${override} \u2014 ensure this points to a trusted program`
3835
- );
3836
- return new PublicKey9(override);
3837
- }
3838
- }
3839
- const detectedNetwork = getCurrentNetwork();
3840
- const targetNetwork = network ?? detectedNetwork;
3841
- const programId = PROGRAM_IDS[targetNetwork].matcher;
3842
- if (!programId) {
3843
- throw new Error(`Matcher program not deployed on ${targetNetwork}`);
3844
- }
3845
- return new PublicKey9(programId);
3846
- }
3847
- function getCurrentNetwork() {
3848
- const network = safeEnv("NETWORK")?.toLowerCase();
3849
- if (network === "mainnet" || network === "mainnet-beta") {
3850
- return "mainnet";
3851
- }
3852
- return "devnet";
3853
- }
3854
-
3855
- // src/solana/stake.ts
3856
5130
  var STAKE_PROGRAM_IDS = {
3857
5131
  devnet: "6aJb1F9CDCVWCNYFwj8aQsVb696YnW6J1FznteHq4Q6k",
3858
5132
  mainnet: "DC5fovFQD5SZYsetwvEqd4Wi4PFY1Yfnc669VMe6oa7F"
@@ -3863,11 +5137,14 @@ function getStakeProgramId(network) {
3863
5137
  console.warn(
3864
5138
  `[percolator-sdk] STAKE_PROGRAM_ID env override active: ${override} \u2014 ensure this points to a trusted program`
3865
5139
  );
3866
- return new PublicKey10(override);
5140
+ return new PublicKey11(override);
3867
5141
  }
3868
5142
  const detectedNetwork = network ?? (() => {
3869
5143
  const n = safeEnv("NEXT_PUBLIC_DEFAULT_NETWORK")?.toLowerCase() ?? safeEnv("NETWORK")?.toLowerCase() ?? "";
3870
- return n === "mainnet" || n === "mainnet-beta" ? "mainnet" : "devnet";
5144
+ if (n === "mainnet" || n === "mainnet-beta") return "mainnet";
5145
+ if (n === "devnet") return "devnet";
5146
+ if (typeof window !== "undefined") return "mainnet";
5147
+ return "devnet";
3871
5148
  })();
3872
5149
  const id = STAKE_PROGRAM_IDS[detectedNetwork];
3873
5150
  if (!id) {
@@ -3875,21 +5152,30 @@ function getStakeProgramId(network) {
3875
5152
  `Stake program not deployed on ${detectedNetwork}. Set STAKE_PROGRAM_ID env var or wait for DevOps to deploy and update STAKE_PROGRAM_IDS.mainnet.`
3876
5153
  );
3877
5154
  }
3878
- return new PublicKey10(id);
5155
+ return new PublicKey11(id);
3879
5156
  }
3880
- var STAKE_PROGRAM_ID = new PublicKey10(STAKE_PROGRAM_IDS.mainnet);
5157
+ var STAKE_PROGRAM_ID = new PublicKey11(STAKE_PROGRAM_IDS.devnet);
3881
5158
  var STAKE_IX = {
3882
5159
  InitPool: 0,
3883
5160
  Deposit: 1,
3884
5161
  Withdraw: 2,
3885
5162
  FlushToInsurance: 3,
3886
5163
  UpdateConfig: 4,
5164
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3887
5165
  TransferAdmin: 5,
5166
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3888
5167
  AdminSetOracleAuthority: 6,
5168
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3889
5169
  AdminSetRiskThreshold: 7,
5170
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3890
5171
  AdminSetMaintenanceFee: 8,
5172
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3891
5173
  AdminResolveMarket: 9,
5174
+ /** Current on-chain tag 10: transfer withdrawn insurance back into the pool vault. */
5175
+ ReturnInsurance: 10,
5176
+ /** @deprecated Legacy alias for ReturnInsurance. */
3892
5177
  AdminWithdrawInsurance: 10,
5178
+ /** @deprecated Removed on-chain in stake v3. This tag now rejects. */
3893
5179
  AdminSetInsurancePolicy: 11,
3894
5180
  /** PERC-272: Accrue trading fees to LP vault */
3895
5181
  AccrueFees: 12,
@@ -3900,24 +5186,26 @@ var STAKE_IX = {
3900
5186
  /** PERC-303: Enable/configure senior-junior LP tranches */
3901
5187
  AdminSetTrancheConfig: 15,
3902
5188
  /** PERC-303: Deposit into junior (first-loss) tranche */
3903
- DepositJunior: 16
5189
+ DepositJunior: 16,
5190
+ /** Mark the pool as resolved after the wrapper market has been resolved directly. */
5191
+ SetMarketResolved: 18
3904
5192
  };
3905
- var TEXT = new TextEncoder();
5193
+ var TEXT2 = new TextEncoder();
3906
5194
  function deriveStakePool(slab, programId) {
3907
- return PublicKey10.findProgramAddressSync(
3908
- [TEXT.encode("stake_pool"), slab.toBytes()],
5195
+ return PublicKey11.findProgramAddressSync(
5196
+ [TEXT2.encode("stake_pool"), slab.toBytes()],
3909
5197
  programId ?? getStakeProgramId()
3910
5198
  );
3911
5199
  }
3912
5200
  function deriveStakeVaultAuth(pool, programId) {
3913
- return PublicKey10.findProgramAddressSync(
3914
- [TEXT.encode("vault_auth"), pool.toBytes()],
5201
+ return PublicKey11.findProgramAddressSync(
5202
+ [TEXT2.encode("vault_auth"), pool.toBytes()],
3915
5203
  programId ?? getStakeProgramId()
3916
5204
  );
3917
5205
  }
3918
5206
  function deriveDepositPda(pool, user, programId) {
3919
- return PublicKey10.findProgramAddressSync(
3920
- [TEXT.encode("deposit"), pool.toBytes(), user.toBytes()],
5207
+ return PublicKey11.findProgramAddressSync(
5208
+ [TEXT2.encode("stake_deposit"), pool.toBytes(), user.toBytes()],
3921
5209
  programId ?? getStakeProgramId()
3922
5210
  );
3923
5211
  }
@@ -3938,9 +5226,6 @@ function readU16LE3(data, off) {
3938
5226
  );
3939
5227
  }
3940
5228
  function u64Le(v) {
3941
- if (typeof v === "number" && !Number.isSafeInteger(v)) {
3942
- throw new Error(`u64Le: number ${v} exceeds Number.MAX_SAFE_INTEGER \u2014 use BigInt`);
3943
- }
3944
5229
  const big = BigInt(v);
3945
5230
  if (big < 0n) throw new Error(`u64Le: value must be non-negative, got ${big}`);
3946
5231
  if (big > 0xFFFFFFFFFFFFFFFFn) throw new Error(`u64Le: value exceeds u64 max`);
@@ -3948,21 +5233,8 @@ function u64Le(v) {
3948
5233
  new DataView(arr.buffer).setBigUint64(0, big, true);
3949
5234
  return arr;
3950
5235
  }
3951
- function u128Le(v) {
3952
- if (typeof v === "number" && !Number.isSafeInteger(v)) {
3953
- throw new Error(`u128Le: number ${v} exceeds Number.MAX_SAFE_INTEGER \u2014 use BigInt`);
3954
- }
3955
- const big = BigInt(v);
3956
- if (big < 0n) throw new Error(`u128Le: value must be non-negative, got ${big}`);
3957
- if (big > (1n << 128n) - 1n) throw new Error(`u128Le: value exceeds u128 max`);
3958
- const arr = new Uint8Array(16);
3959
- const view = new DataView(arr.buffer);
3960
- view.setBigUint64(0, big & 0xFFFFFFFFFFFFFFFFn, true);
3961
- view.setBigUint64(8, big >> 64n, true);
3962
- return arr;
3963
- }
3964
5236
  function u16Le(v) {
3965
- if (!Number.isInteger(v) || v < 0 || v > 65535) throw new Error(`u16Le: value must be integer in range 0..65535, got ${v}`);
5237
+ if (v < 0 || v > 65535) throw new Error(`u16Le: value out of u16 range (0..65535), got ${v}`);
3966
5238
  const arr = new Uint8Array(2);
3967
5239
  new DataView(arr.buffer).setUint16(0, v, true);
3968
5240
  return arr;
@@ -3992,36 +5264,38 @@ function encodeStakeUpdateConfig(newCooldownSlots, newDepositCap) {
3992
5264
  u64Le(newDepositCap ?? 0n)
3993
5265
  );
3994
5266
  }
5267
+ function removedStakeInstruction(name, tag) {
5268
+ throw new Error(
5269
+ `${name} (stake tag ${tag}) was removed on-chain in percolator-stake v3 and must not be sent.`
5270
+ );
5271
+ }
3995
5272
  function encodeStakeTransferAdmin() {
3996
- return new Uint8Array([STAKE_IX.TransferAdmin]);
5273
+ return removedStakeInstruction("encodeStakeTransferAdmin", STAKE_IX.TransferAdmin);
3997
5274
  }
3998
5275
  function encodeStakeAdminSetOracleAuthority(newAuthority) {
3999
- return concatBytes(
4000
- new Uint8Array([STAKE_IX.AdminSetOracleAuthority]),
4001
- newAuthority.toBytes()
4002
- );
5276
+ void newAuthority;
5277
+ return removedStakeInstruction("encodeStakeAdminSetOracleAuthority", STAKE_IX.AdminSetOracleAuthority);
4003
5278
  }
4004
5279
  function encodeStakeAdminSetRiskThreshold(newThreshold) {
4005
- return concatBytes(
4006
- new Uint8Array([STAKE_IX.AdminSetRiskThreshold]),
4007
- u128Le(newThreshold)
4008
- );
5280
+ void newThreshold;
5281
+ return removedStakeInstruction("encodeStakeAdminSetRiskThreshold", STAKE_IX.AdminSetRiskThreshold);
4009
5282
  }
4010
5283
  function encodeStakeAdminSetMaintenanceFee(newFee) {
4011
- return concatBytes(
4012
- new Uint8Array([STAKE_IX.AdminSetMaintenanceFee]),
4013
- u128Le(newFee)
4014
- );
5284
+ void newFee;
5285
+ return removedStakeInstruction("encodeStakeAdminSetMaintenanceFee", STAKE_IX.AdminSetMaintenanceFee);
4015
5286
  }
4016
5287
  function encodeStakeAdminResolveMarket() {
4017
- return new Uint8Array([STAKE_IX.AdminResolveMarket]);
5288
+ return removedStakeInstruction("encodeStakeAdminResolveMarket", STAKE_IX.AdminResolveMarket);
4018
5289
  }
4019
- function encodeStakeAdminWithdrawInsurance(amount) {
5290
+ function encodeStakeReturnInsurance(amount) {
4020
5291
  return concatBytes(
4021
- new Uint8Array([STAKE_IX.AdminWithdrawInsurance]),
5292
+ new Uint8Array([STAKE_IX.ReturnInsurance]),
4022
5293
  u64Le(amount)
4023
5294
  );
4024
5295
  }
5296
+ function encodeStakeAdminWithdrawInsurance(amount) {
5297
+ return encodeStakeReturnInsurance(amount);
5298
+ }
4025
5299
  function encodeStakeAccrueFees() {
4026
5300
  return new Uint8Array([STAKE_IX.AccrueFees]);
4027
5301
  }
@@ -4048,14 +5322,15 @@ function encodeStakeAdminSetTrancheConfig(juniorFeeMultBps) {
4048
5322
  function encodeStakeDepositJunior(amount) {
4049
5323
  return concatBytes(new Uint8Array([STAKE_IX.DepositJunior]), u64Le(amount));
4050
5324
  }
5325
+ function encodeStakeSetMarketResolved() {
5326
+ return new Uint8Array([STAKE_IX.SetMarketResolved]);
5327
+ }
4051
5328
  function encodeStakeAdminSetInsurancePolicy(authority, minWithdrawBase, maxWithdrawBps, cooldownSlots) {
4052
- return concatBytes(
4053
- new Uint8Array([STAKE_IX.AdminSetInsurancePolicy]),
4054
- authority.toBytes(),
4055
- u64Le(minWithdrawBase),
4056
- u16Le(maxWithdrawBps),
4057
- u64Le(cooldownSlots)
4058
- );
5329
+ void authority;
5330
+ void minWithdrawBase;
5331
+ void maxWithdrawBps;
5332
+ void cooldownSlots;
5333
+ return removedStakeInstruction("encodeStakeAdminSetInsurancePolicy", STAKE_IX.AdminSetInsurancePolicy);
4059
5334
  }
4060
5335
  var STAKE_POOL_SIZE = 352;
4061
5336
  function decodeStakePool(data) {
@@ -4073,15 +5348,15 @@ function decodeStakePool(data) {
4073
5348
  const adminTransferred = bytes[off] === 1;
4074
5349
  off += 1;
4075
5350
  off += 4;
4076
- const slab = new PublicKey10(bytes.subarray(off, off + 32));
5351
+ const slab = new PublicKey11(bytes.subarray(off, off + 32));
4077
5352
  off += 32;
4078
- const admin = new PublicKey10(bytes.subarray(off, off + 32));
5353
+ const admin = new PublicKey11(bytes.subarray(off, off + 32));
4079
5354
  off += 32;
4080
- const collateralMint = new PublicKey10(bytes.subarray(off, off + 32));
5355
+ const collateralMint = new PublicKey11(bytes.subarray(off, off + 32));
4081
5356
  off += 32;
4082
- const lpMint = new PublicKey10(bytes.subarray(off, off + 32));
5357
+ const lpMint = new PublicKey11(bytes.subarray(off, off + 32));
4083
5358
  off += 32;
4084
- const vault = new PublicKey10(bytes.subarray(off, off + 32));
5359
+ const vault = new PublicKey11(bytes.subarray(off, off + 32));
4085
5360
  off += 32;
4086
5361
  const totalDeposited = readU64LE4(bytes, off);
4087
5362
  off += 8;
@@ -4097,7 +5372,7 @@ function decodeStakePool(data) {
4097
5372
  off += 8;
4098
5373
  const totalWithdrawn = readU64LE4(bytes, off);
4099
5374
  off += 8;
4100
- const percolatorProgram = new PublicKey10(bytes.subarray(off, off + 32));
5375
+ const percolatorProgram = new PublicKey11(bytes.subarray(off, off + 32));
4101
5376
  off += 32;
4102
5377
  const totalFeesEarned = readU64LE4(bytes, off);
4103
5378
  off += 8;
@@ -4109,11 +5384,11 @@ function decodeStakePool(data) {
4109
5384
  off += 1;
4110
5385
  off += 7;
4111
5386
  const reservedStart = off;
4112
- const hwmEnabled = bytes[reservedStart + 9] === 1;
4113
- const hwmTvlLow = readU64LE4(bytes, reservedStart + 10);
4114
- const hwmTvlHigh = readU64LE4(bytes, reservedStart + 18);
4115
- const epochHighWaterTvl = hwmTvlLow | hwmTvlHigh << 64n;
4116
- const hwmFloorBps = readU16LE3(bytes, reservedStart + 26);
5387
+ const marketResolved = bytes[reservedStart + 9] === 1;
5388
+ const hwmEnabled = bytes[reservedStart + 10] === 1;
5389
+ const hwmFloorBps = readU16LE3(bytes, reservedStart + 11);
5390
+ const epochHighWaterTvl = readU64LE4(bytes, reservedStart + 16);
5391
+ const hwmLastEpoch = readU64LE4(bytes, reservedStart + 24);
4117
5392
  const trancheEnabled = bytes[reservedStart + 32] === 1;
4118
5393
  const juniorBalance = readU64LE4(bytes, reservedStart + 33);
4119
5394
  const juniorTotalLp = readU64LE4(bytes, reservedStart + 41);
@@ -4123,6 +5398,7 @@ function decodeStakePool(data) {
4123
5398
  bump,
4124
5399
  vaultAuthorityBump,
4125
5400
  adminTransferred,
5401
+ marketResolved,
4126
5402
  slab,
4127
5403
  admin,
4128
5404
  collateralMint,
@@ -4143,12 +5419,27 @@ function decodeStakePool(data) {
4143
5419
  hwmEnabled,
4144
5420
  epochHighWaterTvl,
4145
5421
  hwmFloorBps,
5422
+ hwmLastEpoch,
4146
5423
  trancheEnabled,
4147
5424
  juniorBalance,
4148
5425
  juniorTotalLp,
4149
5426
  juniorFeeMultBps
4150
5427
  };
4151
5428
  }
5429
+ var STAKE_DEPOSIT_SIZE = 152;
5430
+ function decodeDepositPda(data) {
5431
+ if (data.length < STAKE_DEPOSIT_SIZE) {
5432
+ throw new Error(`StakeDeposit data too short: ${data.length} < ${STAKE_DEPOSIT_SIZE}`);
5433
+ }
5434
+ return {
5435
+ isInitialized: data[0] === 1,
5436
+ bump: data[1],
5437
+ pool: new PublicKey11(data.subarray(8, 40)),
5438
+ user: new PublicKey11(data.subarray(40, 72)),
5439
+ lastDepositSlot: readU64LE4(data, 72),
5440
+ lpAmount: readU64LE4(data, 80)
5441
+ };
5442
+ }
4152
5443
  function initPoolAccounts(a) {
4153
5444
  return [
4154
5445
  { pubkey: a.admin, isSigner: true, isWritable: true },
@@ -4217,9 +5508,7 @@ function computePnlPct(pnl, capital) {
4217
5508
  }
4218
5509
  function isAdlTriggered(slabData) {
4219
5510
  const layout = detectSlabLayout(slabData.length);
4220
- if (!layout) {
4221
- return false;
4222
- }
5511
+ if (!layout) return false;
4223
5512
  try {
4224
5513
  const engine = parseEngine(slabData);
4225
5514
  if (engine.pnlPosTot === 0n) return false;
@@ -4262,14 +5551,6 @@ function rankAdlPositions(slabData) {
4262
5551
  if (account.kind !== 0 /* User */) continue;
4263
5552
  if (account.positionSize === 0n) continue;
4264
5553
  const side = account.positionSize > 0n ? "long" : "short";
4265
- if (side === "long" && account.positionSize <= 0n) {
4266
- console.warn(`[fetchAdlRankedPositions] account idx=${idx}: side=long but positionSize=${account.positionSize}`);
4267
- continue;
4268
- }
4269
- if (side === "short" && account.positionSize >= 0n) {
4270
- console.warn(`[fetchAdlRankedPositions] account idx=${idx}: side=short but positionSize=${account.positionSize}`);
4271
- continue;
4272
- }
4273
5554
  const pnlPct = computePnlPct(account.pnl, account.capital);
4274
5555
  positions.push({
4275
5556
  idx,
@@ -4302,8 +5583,7 @@ function buildAdlInstruction(caller, slab, oracle, programId, targetIdx, backupO
4302
5583
  `buildAdlInstruction: targetIdx must be a non-negative integer, got ${targetIdx}`
4303
5584
  );
4304
5585
  }
4305
- const dataBytes = encodeExecuteAdl({ targetIdx });
4306
- const data = Buffer.from(dataBytes);
5586
+ const data = Buffer.from(encodeExecuteAdl({ targetIdx }));
4307
5587
  const keys = [
4308
5588
  { pubkey: caller, isSigner: true, isWritable: false },
4309
5589
  { pubkey: slab, isSigner: false, isWritable: true },
@@ -4343,11 +5623,7 @@ function parseAdlEvent(logs) {
4343
5623
  }
4344
5624
  if (tag !== ADL_EVENT_TAG) continue;
4345
5625
  try {
4346
- const targetIdxBig = BigInt(match[2]);
4347
- if (targetIdxBig < 0n || targetIdxBig > 65535n) {
4348
- continue;
4349
- }
4350
- const targetIdx = Number(targetIdxBig);
5626
+ const targetIdx = Number(BigInt(match[2]));
4351
5627
  const price = BigInt(match[3]);
4352
5628
  const closedLo = BigInt(match[4]);
4353
5629
  const closedHi = BigInt(match[5]);
@@ -4375,22 +5651,6 @@ async function fetchAdlRankings(apiBase, slab, fetchFn = fetch) {
4375
5651
  );
4376
5652
  }
4377
5653
  const json = await res.json();
4378
- if (typeof json !== "object" || json === null) {
4379
- throw new Error("fetchAdlRankings: API returned non-object response");
4380
- }
4381
- const obj = json;
4382
- if (!Array.isArray(obj.rankings)) {
4383
- throw new Error("fetchAdlRankings: API response missing rankings array");
4384
- }
4385
- for (const entry of obj.rankings) {
4386
- if (typeof entry !== "object" || entry === null) {
4387
- throw new Error("fetchAdlRankings: invalid ranking entry (not an object)");
4388
- }
4389
- const r = entry;
4390
- if (typeof r.idx !== "number" || !Number.isInteger(r.idx) || r.idx < 0) {
4391
- throw new Error(`fetchAdlRankings: invalid ranking idx: ${r.idx}`);
4392
- }
4393
- }
4394
5654
  return json;
4395
5655
  }
4396
5656
 
@@ -4908,11 +6168,11 @@ function formatResult(result, jsonMode) {
4908
6168
  }
4909
6169
 
4910
6170
  // src/runtime/lighthouse.ts
4911
- import { PublicKey as PublicKey13, Transaction as Transaction2 } from "@solana/web3.js";
4912
- var LIGHTHOUSE_PROGRAM_ID = new PublicKey13(
6171
+ import { PublicKey as PublicKey14, Transaction as Transaction2 } from "@solana/web3.js";
6172
+ var LIGHTHOUSE_PROGRAM_ID = new PublicKey14(
4913
6173
  "L2TExMFKdjpN9kozasaurPirfHy9P8sbXoAN1qA3S95"
4914
6174
  );
4915
- var LIGHTHOUSE_PROGRAM_ID_STR2 = "L2TExMFKdjpN9kozasaurPirfHy9P8sbXoAN1qA3S95";
6175
+ var LIGHTHOUSE_PROGRAM_ID_STR = "L2TExMFKdjpN9kozasaurPirfHy9P8sbXoAN1qA3S95";
4916
6176
  var LIGHTHOUSE_CONSTRAINT_ADDRESS = 6400;
4917
6177
  var LIGHTHOUSE_ERROR_CODES = /* @__PURE__ */ new Set([
4918
6178
  6e3,
@@ -4958,7 +6218,7 @@ function isLighthouseInstruction(ix) {
4958
6218
  function isLighthouseError(error) {
4959
6219
  const msg = extractErrorMessage(error);
4960
6220
  if (!msg) return false;
4961
- if (msg.includes(LIGHTHOUSE_PROGRAM_ID_STR2)) return true;
6221
+ if (msg.includes(LIGHTHOUSE_PROGRAM_ID_STR)) return true;
4962
6222
  if (/custom\s+program\s+error:\s*0x1900\b/i.test(msg)) return true;
4963
6223
  if (/"Custom"\s*:\s*6400\b/.test(msg) && /InstructionError/i.test(msg)) return true;
4964
6224
  return false;
@@ -4968,18 +6228,18 @@ function isLighthouseFailureInLogs(logs) {
4968
6228
  let insideLighthouse = false;
4969
6229
  for (const line of logs) {
4970
6230
  if (typeof line !== "string") continue;
4971
- if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR2} invoke`)) {
6231
+ if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR} invoke`)) {
4972
6232
  insideLighthouse = true;
4973
6233
  continue;
4974
6234
  }
4975
- if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR2} success`)) {
6235
+ if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR} success`)) {
4976
6236
  insideLighthouse = false;
4977
6237
  continue;
4978
6238
  }
4979
6239
  if (insideLighthouse && /failed/i.test(line)) {
4980
6240
  return true;
4981
6241
  }
4982
- if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR2} failed`)) {
6242
+ if (line.includes(`Program ${LIGHTHOUSE_PROGRAM_ID_STR} failed`)) {
4983
6243
  return true;
4984
6244
  }
4985
6245
  }
@@ -5064,10 +6324,16 @@ function computeLiqPrice(entryPrice, capital, positionSize, maintenanceMarginBps
5064
6324
  function computePreTradeLiqPrice(oracleE6, margin, posSize, maintBps, feeBps, direction) {
5065
6325
  if (oracleE6 === 0n || margin === 0n || posSize === 0n) return 0n;
5066
6326
  const absPos = posSize < 0n ? -posSize : posSize;
5067
- const fee = absPos * feeBps / 10000n;
5068
- const effectiveCapital = margin > fee ? margin - fee : 0n;
5069
6327
  const signedPos = direction === "long" ? absPos : -absPos;
5070
- return computeLiqPrice(oracleE6, effectiveCapital, signedPos, maintBps);
6328
+ const feeAdjust = oracleE6 * feeBps / 10000n;
6329
+ let adjustedEntry;
6330
+ if (direction === "long") {
6331
+ adjustedEntry = oracleE6 + feeAdjust;
6332
+ } else {
6333
+ const shortEntry = oracleE6 - feeAdjust;
6334
+ adjustedEntry = shortEntry > 0n ? shortEntry : 1n;
6335
+ }
6336
+ return computeLiqPrice(adjustedEntry, margin, signedPos, maintBps);
5071
6337
  }
5072
6338
  function computeTradingFee(notional, tradingFeeBps) {
5073
6339
  return notional * tradingFeeBps / 10000n;
@@ -5087,20 +6353,9 @@ function computeFeeSplit(totalFee, config) {
5087
6353
  if (config.lpBps === 0n && config.protocolBps === 0n && config.creatorBps === 0n) {
5088
6354
  return [totalFee, 0n, 0n];
5089
6355
  }
5090
- const totalBps = config.lpBps + config.protocolBps + config.creatorBps;
5091
- if (totalBps !== 10000n) {
5092
- throw new Error(
5093
- `Fee split must equal exactly 10000 bps (100%): lpBps=${config.lpBps} + protocolBps=${config.protocolBps} + creatorBps=${config.creatorBps} = ${totalBps}`
5094
- );
5095
- }
5096
6356
  const lp = totalFee * config.lpBps / 10000n;
5097
6357
  const protocol = totalFee * config.protocolBps / 10000n;
5098
6358
  const creator = totalFee - lp - protocol;
5099
- if (creator < 0n) {
5100
- throw new Error(
5101
- `Internal error: creator fee is negative (${creator}). This should not happen if lpBps + protocolBps + creatorBps === 10000.`
5102
- );
5103
- }
5104
6359
  return [lp, protocol, creator];
5105
6360
  }
5106
6361
  function computePnlPercent(pnlTokens, capital) {
@@ -5115,17 +6370,10 @@ function computePnlPercent(pnlTokens, capital) {
5115
6370
  }
5116
6371
  function computeEstimatedEntryPrice(oracleE6, tradingFeeBps, direction) {
5117
6372
  if (oracleE6 === 0n) return 0n;
5118
- if (tradingFeeBps < 0n) {
5119
- throw new Error(`computeEstimatedEntryPrice: tradingFeeBps must be non-negative, got ${tradingFeeBps}`);
5120
- }
5121
6373
  const feeImpact = oracleE6 * tradingFeeBps / 10000n;
5122
- const result = direction === "long" ? oracleE6 + feeImpact : oracleE6 - feeImpact;
5123
- if (result <= 0n) {
5124
- throw new Error(
5125
- `computeEstimatedEntryPrice: result ${result} is non-positive (tradingFeeBps=${tradingFeeBps} too high for oracle=${oracleE6})`
5126
- );
5127
- }
5128
- return result;
6374
+ if (direction === "long") return oracleE6 + feeImpact;
6375
+ const shortEntry = oracleE6 - feeImpact;
6376
+ return shortEntry > 0n ? shortEntry : 1n;
5129
6377
  }
5130
6378
  var MAX_SAFE_BIGINT = BigInt(Number.MAX_SAFE_INTEGER);
5131
6379
  var MIN_SAFE_BIGINT = BigInt(-Number.MAX_SAFE_INTEGER);
@@ -5146,12 +6394,7 @@ function computeMaxLeverage(initialMarginBps) {
5146
6394
  if (initialMarginBps <= 0n) {
5147
6395
  throw new Error("computeMaxLeverage: initialMarginBps must be positive");
5148
6396
  }
5149
- const scaledResult = 10000n * 1000000n / initialMarginBps;
5150
- return Number(scaledResult) / 1e6;
5151
- }
5152
- function computeMaxWithdrawable(capital, pnl, reservedPnl) {
5153
- const maturedPnl = pnl - reservedPnl;
5154
- return capital + (maturedPnl > 0n ? maturedPnl : 0n);
6397
+ return Number(10000n / initialMarginBps);
5155
6398
  }
5156
6399
 
5157
6400
  // src/math/warmup.ts
@@ -5163,9 +6406,6 @@ function computeWarmupUnlockedCapital(totalCapital, currentSlot, warmupStartSlot
5163
6406
  return totalCapital * elapsed / warmupPeriodSlots;
5164
6407
  }
5165
6408
  function computeWarmupLeverageCap(initialMarginBps, totalCapital, currentSlot, warmupStartSlot, warmupPeriodSlots) {
5166
- if (initialMarginBps <= 0n) {
5167
- throw new Error("computeWarmupLeverageCap: initialMarginBps must be positive");
5168
- }
5169
6409
  const maxLev = computeMaxLeverage(initialMarginBps);
5170
6410
  if (warmupPeriodSlots === 0n || warmupStartSlot === 0n) return maxLev;
5171
6411
  if (totalCapital <= 0n) return 1;
@@ -5176,14 +6416,7 @@ function computeWarmupLeverageCap(initialMarginBps, totalCapital, currentSlot, w
5176
6416
  warmupPeriodSlots
5177
6417
  );
5178
6418
  if (unlocked <= 0n) return 1;
5179
- const scaledResult = BigInt(maxLev) * unlocked / totalCapital;
5180
- if (scaledResult > BigInt(Number.MAX_SAFE_INTEGER)) {
5181
- console.warn(
5182
- `[computeWarmupLeverageCap] Warning: effective leverage ${scaledResult} exceeds MAX_SAFE_INTEGER, returning MAX_SAFE_INTEGER as a safety bound`
5183
- );
5184
- return Number.MAX_SAFE_INTEGER;
5185
- }
5186
- const effectiveLev = Number(scaledResult);
6419
+ const effectiveLev = Number(BigInt(maxLev) * unlocked / totalCapital);
5187
6420
  return Math.max(1, effectiveLev);
5188
6421
  }
5189
6422
  function computeWarmupMaxPositionSize(initialMarginBps, totalCapital, currentSlot, warmupStartSlot, warmupPeriodSlots) {
@@ -5196,41 +6429,10 @@ function computeWarmupMaxPositionSize(initialMarginBps, totalCapital, currentSlo
5196
6429
  );
5197
6430
  return unlocked * BigInt(maxLev);
5198
6431
  }
5199
- function computeWarmupProgress(currentSlot, warmupStartedAtSlot, warmupPeriodSlots, pnl, reservedPnl) {
5200
- if (warmupPeriodSlots === 0n || warmupStartedAtSlot === 0n) {
5201
- return {
5202
- maturedPnl: pnl > 0n ? pnl : 0n,
5203
- reservedPnl: 0n,
5204
- progressBps: 10000n,
5205
- // 100%
5206
- slotsRemaining: 0n
5207
- };
5208
- }
5209
- const elapsed = currentSlot >= warmupStartedAtSlot ? currentSlot - warmupStartedAtSlot : 0n;
5210
- if (elapsed >= warmupPeriodSlots) {
5211
- return {
5212
- maturedPnl: pnl > 0n ? pnl : 0n,
5213
- reservedPnl: 0n,
5214
- progressBps: 10000n,
5215
- // 100%
5216
- slotsRemaining: 0n
5217
- };
5218
- }
5219
- const progressBps = elapsed * 10000n / warmupPeriodSlots;
5220
- const slotsRemaining = warmupPeriodSlots - elapsed;
5221
- const maturedPnl = pnl > 0n ? pnl * progressBps / 10000n : 0n;
5222
- const locked = reservedPnl > 0n ? reservedPnl : 0n;
5223
- return {
5224
- maturedPnl,
5225
- reservedPnl: locked,
5226
- progressBps,
5227
- slotsRemaining
5228
- };
5229
- }
5230
6432
 
5231
6433
  // src/validation.ts
5232
- import { PublicKey as PublicKey14 } from "@solana/web3.js";
5233
- var U16_MAX = 65535;
6434
+ import { PublicKey as PublicKey15 } from "@solana/web3.js";
6435
+ var U16_MAX2 = 65535;
5234
6436
  var U64_MAX = BigInt("18446744073709551615");
5235
6437
  var I64_MIN = BigInt("-9223372036854775808");
5236
6438
  var I64_MAX = BigInt("9223372036854775807");
@@ -5259,7 +6461,7 @@ var ValidationError = class extends Error {
5259
6461
  };
5260
6462
  function validatePublicKey(value, field) {
5261
6463
  try {
5262
- return new PublicKey14(value);
6464
+ return new PublicKey15(value);
5263
6465
  } catch {
5264
6466
  throw new ValidationError(
5265
6467
  field,
@@ -5270,26 +6472,24 @@ function validatePublicKey(value, field) {
5270
6472
  function validateIndex(value, field) {
5271
6473
  const t = requireDecimalUIntString(value, field);
5272
6474
  const bi = BigInt(t);
5273
- if (bi > BigInt(U16_MAX)) {
6475
+ if (bi > BigInt(U16_MAX2)) {
5274
6476
  throw new ValidationError(
5275
6477
  field,
5276
- `must be <= ${U16_MAX} (u16 max), got ${t}`
6478
+ `must be <= ${U16_MAX2} (u16 max), got ${t}`
5277
6479
  );
5278
6480
  }
5279
- if (bi > BigInt(Number.MAX_SAFE_INTEGER)) {
5280
- throw new ValidationError(field, `internal error: u16 value exceeds MAX_SAFE_INTEGER`);
5281
- }
5282
6481
  return Number(bi);
5283
6482
  }
5284
6483
  function validateAmount(value, field) {
5285
- const t = value.trim();
5286
- if (!/^(0|[1-9]\d*)$/.test(t)) {
6484
+ let num;
6485
+ try {
6486
+ num = BigInt(value);
6487
+ } catch {
5287
6488
  throw new ValidationError(
5288
6489
  field,
5289
- `"${value}" is not a valid non-negative integer. Use decimal digits only.`
6490
+ `"${value}" is not a valid number. Use decimal digits only.`
5290
6491
  );
5291
6492
  }
5292
- const num = BigInt(t);
5293
6493
  if (num < 0n) {
5294
6494
  throw new ValidationError(field, `must be non-negative, got ${num}`);
5295
6495
  }
@@ -5302,14 +6502,15 @@ function validateAmount(value, field) {
5302
6502
  return num;
5303
6503
  }
5304
6504
  function validateU128(value, field) {
5305
- const t = value.trim();
5306
- if (!/^(0|[1-9]\d*)$/.test(t)) {
6505
+ let num;
6506
+ try {
6507
+ num = BigInt(value);
6508
+ } catch {
5307
6509
  throw new ValidationError(
5308
6510
  field,
5309
- `"${value}" is not a valid non-negative integer. Use decimal digits only.`
6511
+ `"${value}" is not a valid number. Use decimal digits only.`
5310
6512
  );
5311
6513
  }
5312
- const num = BigInt(t);
5313
6514
  if (num < 0n) {
5314
6515
  throw new ValidationError(field, `must be non-negative, got ${num}`);
5315
6516
  }
@@ -5322,14 +6523,15 @@ function validateU128(value, field) {
5322
6523
  return num;
5323
6524
  }
5324
6525
  function validateI64(value, field) {
5325
- const t = value.trim();
5326
- if (!/^-?(0|[1-9]\d*)$/.test(t)) {
6526
+ let num;
6527
+ try {
6528
+ num = BigInt(value);
6529
+ } catch {
5327
6530
  throw new ValidationError(
5328
6531
  field,
5329
- `"${value}" is not a valid integer. Use decimal digits only, with optional leading minus.`
6532
+ `"${value}" is not a valid number. Use decimal digits only, with optional leading minus.`
5330
6533
  );
5331
6534
  }
5332
- const num = BigInt(t);
5333
6535
  if (num < I64_MIN) {
5334
6536
  throw new ValidationError(
5335
6537
  field,
@@ -5345,14 +6547,15 @@ function validateI64(value, field) {
5345
6547
  return num;
5346
6548
  }
5347
6549
  function validateI128(value, field) {
5348
- const t = value.trim();
5349
- if (!/^-?(0|[1-9]\d*)$/.test(t)) {
6550
+ let num;
6551
+ try {
6552
+ num = BigInt(value);
6553
+ } catch {
5350
6554
  throw new ValidationError(
5351
6555
  field,
5352
- `"${value}" is not a valid integer. Use decimal digits only, with optional leading minus.`
6556
+ `"${value}" is not a valid number. Use decimal digits only, with optional leading minus.`
5353
6557
  );
5354
6558
  }
5355
- const num = BigInt(t);
5356
6559
  if (num < I128_MIN) {
5357
6560
  throw new ValidationError(
5358
6561
  field,
@@ -5376,9 +6579,6 @@ function validateBps(value, field) {
5376
6579
  `must be <= 10000 (100%), got ${t}`
5377
6580
  );
5378
6581
  }
5379
- if (bi > BigInt(Number.MAX_SAFE_INTEGER)) {
5380
- throw new ValidationError(field, `internal error: bps value exceeds MAX_SAFE_INTEGER`);
5381
- }
5382
6582
  return Number(bi);
5383
6583
  }
5384
6584
  function validateU64(value, field) {
@@ -5387,15 +6587,12 @@ function validateU64(value, field) {
5387
6587
  function validateU16(value, field) {
5388
6588
  const t = requireDecimalUIntString(value, field);
5389
6589
  const bi = BigInt(t);
5390
- if (bi > BigInt(U16_MAX)) {
6590
+ if (bi > BigInt(U16_MAX2)) {
5391
6591
  throw new ValidationError(
5392
6592
  field,
5393
- `must be <= ${U16_MAX} (u16 max), got ${t}`
6593
+ `must be <= ${U16_MAX2} (u16 max), got ${t}`
5394
6594
  );
5395
6595
  }
5396
- if (bi > BigInt(Number.MAX_SAFE_INTEGER)) {
5397
- throw new ValidationError(field, `internal error: u16 value exceeds MAX_SAFE_INTEGER`);
5398
- }
5399
6596
  return Number(bi);
5400
6597
  }
5401
6598
 
@@ -5446,9 +6643,7 @@ function parseDexScreenerPairs(json) {
5446
6643
  else if (liquidity > 1e4) confidence = 60;
5447
6644
  else if (liquidity > 1e3) confidence = 45;
5448
6645
  const priceUsd = pair.priceUsd;
5449
- const rawPrice = typeof priceUsd === "string" || typeof priceUsd === "number" ? parseFloat(String(priceUsd)) : NaN;
5450
- if (!Number.isFinite(rawPrice) || rawPrice <= 0) continue;
5451
- const price = rawPrice;
6646
+ const price = typeof priceUsd === "string" || typeof priceUsd === "number" ? parseFloat(String(priceUsd)) || 0 : 0;
5452
6647
  let baseSym = "?";
5453
6648
  let quoteSym = "?";
5454
6649
  if (isRecord(pair.baseToken) && typeof pair.baseToken.symbol === "string") {
@@ -5479,8 +6674,8 @@ function parseJupiterMintEntry(json, mint) {
5479
6674
  if (!isRecord(row)) return null;
5480
6675
  const rawPrice = row.price;
5481
6676
  if (rawPrice === void 0 || rawPrice === null) return null;
5482
- const price = parseFloat(String(rawPrice));
5483
- if (!Number.isFinite(price) || price <= 0) return null;
6677
+ const price = parseFloat(String(rawPrice)) || 0;
6678
+ if (price <= 0) return null;
5484
6679
  let mintSymbol = "?";
5485
6680
  if (typeof row.mintSymbol === "string") mintSymbol = row.mintSymbol;
5486
6681
  return { price, mintSymbol };
@@ -5546,17 +6741,10 @@ async function fetchDexSources(mint, signal) {
5546
6741
  headers: { "User-Agent": "percolator/1.0" }
5547
6742
  }
5548
6743
  );
5549
- if (!resp.ok) {
5550
- console.debug(`[fetchDexSources] HTTP ${resp.status} for mint ${mint}`);
5551
- return [];
5552
- }
6744
+ if (!resp.ok) return [];
5553
6745
  const json = await resp.json();
5554
6746
  return parseDexScreenerPairs(json);
5555
- } catch (err) {
5556
- console.warn(
5557
- `[fetchDexSources] Error fetching DexScreener data for mint ${mint}:`,
5558
- err instanceof Error ? err.message : String(err)
5559
- );
6747
+ } catch {
5560
6748
  return [];
5561
6749
  }
5562
6750
  }
@@ -5567,7 +6755,7 @@ function lookupPythSource(mint) {
5567
6755
  type: "pyth",
5568
6756
  address: entry.feedId,
5569
6757
  pairLabel: `${entry.symbol} / USD (Pyth)`,
5570
- liquidity: Number.MAX_SAFE_INTEGER,
6758
+ liquidity: Infinity,
5571
6759
  // Pyth is considered deep liquidity
5572
6760
  price: 0,
5573
6761
  // We don't fetch live price here; caller can enrich
@@ -5584,16 +6772,10 @@ async function fetchJupiterSource(mint, signal) {
5584
6772
  headers: { "User-Agent": "percolator/1.0" }
5585
6773
  }
5586
6774
  );
5587
- if (!resp.ok) {
5588
- console.debug(`[fetchJupiterSource] HTTP ${resp.status} for mint ${mint}`);
5589
- return null;
5590
- }
6775
+ if (!resp.ok) return null;
5591
6776
  const json = await resp.json();
5592
6777
  const row = parseJupiterMintEntry(json, mint);
5593
- if (!row) {
5594
- console.debug(`[fetchJupiterSource] No price data from Jupiter for mint ${mint}`);
5595
- return null;
5596
- }
6778
+ if (!row) return null;
5597
6779
  return {
5598
6780
  type: "jupiter",
5599
6781
  address: mint,
@@ -5604,39 +6786,23 @@ async function fetchJupiterSource(mint, signal) {
5604
6786
  confidence: 40
5605
6787
  // Fallback — lower confidence
5606
6788
  };
5607
- } catch (err) {
5608
- console.warn(
5609
- `[fetchJupiterSource] Error fetching Jupiter data for mint ${mint}:`,
5610
- err instanceof Error ? err.message : String(err)
5611
- );
6789
+ } catch {
5612
6790
  return null;
5613
6791
  }
5614
6792
  }
5615
6793
  async function resolvePrice(mint, signal, options) {
5616
6794
  const timeoutMs = options?.timeoutMs ?? DEFAULT_RESOLVE_TIMEOUT_MS;
5617
6795
  const timeoutSignal = AbortSignal.timeout(timeoutMs);
5618
- const effectiveSignal2 = signal ? combineAbortSignals([signal, timeoutSignal]) : timeoutSignal;
6796
+ const combinedSignal = signal ? combineAbortSignals([signal, timeoutSignal]) : timeoutSignal;
5619
6797
  const [dexSources, jupiterSource] = await Promise.all([
5620
- fetchDexSources(mint, effectiveSignal2),
5621
- fetchJupiterSource(mint, effectiveSignal2)
6798
+ fetchDexSources(mint, combinedSignal),
6799
+ fetchJupiterSource(mint, combinedSignal)
5622
6800
  ]);
5623
6801
  const pythSource = lookupPythSource(mint);
5624
6802
  const allSources = [];
5625
6803
  if (pythSource) {
5626
- const dexPrice = dexSources[0]?.price ?? 0;
5627
- const jupPrice = jupiterSource?.price ?? 0;
5628
- if (dexPrice > 0 && jupPrice > 0) {
5629
- const mid = (dexPrice + jupPrice) / 2;
5630
- const deviation = Math.abs(dexPrice - jupPrice) / mid;
5631
- if (deviation > 0.5) {
5632
- pythSource.price = 0;
5633
- pythSource.confidence = 20;
5634
- } else {
5635
- pythSource.price = mid;
5636
- }
5637
- } else {
5638
- pythSource.price = dexPrice || jupPrice || 0;
5639
- }
6804
+ const refPrice = dexSources[0]?.price || jupiterSource?.price || 0;
6805
+ pythSource.price = refPrice;
5640
6806
  allSources.push(pythSource);
5641
6807
  }
5642
6808
  allSources.push(...dexSources);
@@ -5652,17 +6818,29 @@ async function resolvePrice(mint, signal, options) {
5652
6818
  };
5653
6819
  }
5654
6820
  export {
6821
+ ACCOUNTS_ACCEPT_ADMIN,
6822
+ ACCOUNTS_ADMIN_FORCE_CLOSE,
5655
6823
  ACCOUNTS_ADVANCE_ORACLE_PHASE,
6824
+ ACCOUNTS_ATTEST_CROSS_MARGIN,
5656
6825
  ACCOUNTS_AUDIT_CRANK,
5657
6826
  ACCOUNTS_BURN_POSITION_NFT,
5658
6827
  ACCOUNTS_CANCEL_QUEUED_WITHDRAWAL,
6828
+ ACCOUNTS_CHALLENGE_SETTLEMENT,
5659
6829
  ACCOUNTS_CLAIM_QUEUED_WITHDRAWAL,
5660
6830
  ACCOUNTS_CLEAR_PENDING_SETTLEMENT,
5661
6831
  ACCOUNTS_CLOSE_ACCOUNT,
6832
+ ACCOUNTS_CLOSE_ORPHAN_SLAB,
5662
6833
  ACCOUNTS_CLOSE_SLAB,
5663
6834
  ACCOUNTS_CLOSE_STALE_SLABS,
6835
+ ACCOUNTS_CONVERT_RELEASED_PNL,
6836
+ ACCOUNTS_CREATE_INSURANCE_MINT,
6837
+ ACCOUNTS_CREATE_LP_VAULT,
5664
6838
  ACCOUNTS_DEPOSIT_COLLATERAL,
6839
+ ACCOUNTS_DEPOSIT_FEE_CREDITS,
6840
+ ACCOUNTS_DEPOSIT_INSURANCE_LP,
6841
+ ACCOUNTS_DEPOSIT_LP_COLLATERAL,
5665
6842
  ACCOUNTS_EXECUTE_ADL,
6843
+ ACCOUNTS_FORCE_CLOSE_RESOLVED,
5666
6844
  ACCOUNTS_FUND_MARKET_INSURANCE,
5667
6845
  ACCOUNTS_INIT_LP,
5668
6846
  ACCOUNTS_INIT_MARKET,
@@ -5670,52 +6848,82 @@ export {
5670
6848
  ACCOUNTS_INIT_USER,
5671
6849
  ACCOUNTS_KEEPER_CRANK,
5672
6850
  ACCOUNTS_LIQUIDATE_AT_ORACLE,
6851
+ ACCOUNTS_LP_VAULT_CRANK_FEES,
6852
+ ACCOUNTS_LP_VAULT_DEPOSIT,
5673
6853
  ACCOUNTS_LP_VAULT_WITHDRAW,
5674
6854
  ACCOUNTS_MINT_POSITION_NFT,
6855
+ ACCOUNTS_NFT_BURN,
6856
+ ACCOUNTS_NFT_EMERGENCY_BURN,
6857
+ ACCOUNTS_NFT_MINT,
5675
6858
  ACCOUNTS_PAUSE_MARKET,
5676
- ACCOUNTS_PUSH_ORACLE_PRICE,
5677
6859
  ACCOUNTS_QUEUE_WITHDRAWAL,
6860
+ ACCOUNTS_RECLAIM_EMPTY_ACCOUNT,
5678
6861
  ACCOUNTS_RECLAIM_SLAB_RENT,
6862
+ ACCOUNTS_RESCUE_ORPHAN_VAULT,
6863
+ ACCOUNTS_RESOLVE_DISPUTE,
5679
6864
  ACCOUNTS_RESOLVE_MARKET,
6865
+ ACCOUNTS_RESOLVE_PERMISSIONLESS,
6866
+ ACCOUNTS_SETTLE_ACCOUNT,
6867
+ ACCOUNTS_SET_DEX_POOL,
6868
+ ACCOUNTS_SET_DISPUTE_PARAMS,
5680
6869
  ACCOUNTS_SET_INSURANCE_ISOLATION,
6870
+ ACCOUNTS_SET_INSURANCE_WITHDRAW_POLICY,
6871
+ ACCOUNTS_SET_LP_COLLATERAL_PARAMS,
5681
6872
  ACCOUNTS_SET_MAINTENANCE_FEE,
6873
+ ACCOUNTS_SET_MAX_PNL_CAP,
6874
+ ACCOUNTS_SET_OFFSET_PAIR,
6875
+ ACCOUNTS_SET_OI_CAP_MULTIPLIER,
5682
6876
  ACCOUNTS_SET_OI_IMBALANCE_HARD_BLOCK,
5683
- ACCOUNTS_SET_ORACLE_AUTHORITY,
5684
6877
  ACCOUNTS_SET_ORACLE_PRICE_CAP,
5685
6878
  ACCOUNTS_SET_PENDING_SETTLEMENT,
5686
6879
  ACCOUNTS_SET_RISK_THRESHOLD,
5687
6880
  ACCOUNTS_SET_WALLET_CAP,
5688
6881
  ACCOUNTS_TOPUP_INSURANCE,
5689
- ACCOUNTS_TOPUP_KEEPER_FUND,
5690
6882
  ACCOUNTS_TRADE_CPI,
5691
6883
  ACCOUNTS_TRADE_NOCPI,
6884
+ ACCOUNTS_TRANSFER_OWNERSHIP_CPI,
5692
6885
  ACCOUNTS_TRANSFER_POSITION_OWNERSHIP,
5693
6886
  ACCOUNTS_UNPAUSE_MARKET,
5694
6887
  ACCOUNTS_UPDATE_ADMIN,
6888
+ ACCOUNTS_UPDATE_AUTHORITY,
5695
6889
  ACCOUNTS_UPDATE_CONFIG,
6890
+ ACCOUNTS_UPDATE_HYPERP_MARK,
5696
6891
  ACCOUNTS_WITHDRAW_COLLATERAL,
5697
6892
  ACCOUNTS_WITHDRAW_INSURANCE,
6893
+ ACCOUNTS_WITHDRAW_INSURANCE_LIMITED_LIVE,
6894
+ ACCOUNTS_WITHDRAW_INSURANCE_LIMITED_RESOLVED,
6895
+ ACCOUNTS_WITHDRAW_INSURANCE_LP,
6896
+ ACCOUNTS_WITHDRAW_LP_COLLATERAL,
6897
+ AUTHORITY_KIND,
5698
6898
  AccountKind,
5699
6899
  CHAINLINK_ANSWER_OFFSET,
5700
6900
  CHAINLINK_DECIMALS_OFFSET,
5701
6901
  CHAINLINK_MIN_SIZE,
5702
- CHAINLINK_TIMESTAMP_OFFSET,
5703
6902
  CREATOR_LOCK_SEED,
6903
+ CTX_RETURN_OFFSET,
6904
+ CTX_VAMM_LEN,
5704
6905
  CTX_VAMM_OFFSET,
5705
6906
  DEFAULT_OI_RAMP_SLOTS,
5706
6907
  ENGINE_MARK_PRICE_OFF,
5707
6908
  ENGINE_OFF,
6909
+ INIT_CTX_LEN,
5708
6910
  IX_TAG,
5709
6911
  LIGHTHOUSE_CONSTRAINT_ADDRESS,
5710
6912
  LIGHTHOUSE_ERROR_CODES,
5711
6913
  LIGHTHOUSE_PROGRAM_ID,
5712
- LIGHTHOUSE_PROGRAM_ID_STR2 as LIGHTHOUSE_PROGRAM_ID_STR,
6914
+ LIGHTHOUSE_PROGRAM_ID_STR,
5713
6915
  LIGHTHOUSE_USER_MESSAGE,
6916
+ LiquidationPolicyTag,
5714
6917
  MARK_PRICE_EMA_ALPHA_E6,
5715
6918
  MARK_PRICE_EMA_WINDOW_SLOTS,
6919
+ MATCHER_CALL_LEN,
6920
+ MATCHER_CONTEXT_LEN,
6921
+ MATCHER_MAGIC,
6922
+ MATCHER_RETURN_LEN,
5716
6923
  MAX_DECIMALS,
5717
- MAX_ORACLE_PRICE,
5718
6924
  METEORA_DLMM_PROGRAM_ID,
6925
+ NFT_IX_TAG,
6926
+ NFT_PROGRAM_ID,
5719
6927
  ORACLE_PHASE_GROWING,
5720
6928
  ORACLE_PHASE_MATURE,
5721
6929
  ORACLE_PHASE_NASCENT,
@@ -5724,6 +6932,7 @@ export {
5724
6932
  PHASE1_VOLUME_MIN_SLOTS,
5725
6933
  PHASE2_MATURITY_SLOTS,
5726
6934
  PHASE2_VOLUME_THRESHOLD,
6935
+ POSITION_NFT_STATE_LEN,
5727
6936
  PROGRAM_IDS,
5728
6937
  PUMPSWAP_PROGRAM_ID,
5729
6938
  PYTH_PUSH_ORACLE_PROGRAM_ID,
@@ -5733,10 +6942,13 @@ export {
5733
6942
  RAYDIUM_CLMM_PROGRAM_ID,
5734
6943
  RENOUNCE_ADMIN_CONFIRMATION,
5735
6944
  RpcPool,
6945
+ SLAB_MAGIC,
5736
6946
  SLAB_TIERS,
5737
6947
  SLAB_TIERS_V0,
5738
6948
  SLAB_TIERS_V1,
5739
6949
  SLAB_TIERS_V12_1,
6950
+ SLAB_TIERS_V12_15,
6951
+ SLAB_TIERS_V12_17,
5740
6952
  SLAB_TIERS_V1D,
5741
6953
  SLAB_TIERS_V1D_LEGACY,
5742
6954
  SLAB_TIERS_V1M,
@@ -5745,6 +6957,7 @@ export {
5745
6957
  SLAB_TIERS_V_ADL,
5746
6958
  SLAB_TIERS_V_ADL_DISCOVERY,
5747
6959
  SLAB_TIERS_V_SETDEXPOOL,
6960
+ STAKE_DEPOSIT_SIZE,
5748
6961
  STAKE_IX,
5749
6962
  STAKE_POOL_SIZE,
5750
6963
  STAKE_PROGRAM_ID,
@@ -5774,7 +6987,6 @@ export {
5774
6987
  computeLiqPrice,
5775
6988
  computeMarkPnl,
5776
6989
  computeMaxLeverage,
5777
- computeMaxWithdrawable,
5778
6990
  computePnlPercent,
5779
6991
  computePreTradeLiqPrice,
5780
6992
  computeRequiredMargin,
@@ -5782,17 +6994,20 @@ export {
5782
6994
  computeVammQuote,
5783
6995
  computeWarmupLeverageCap,
5784
6996
  computeWarmupMaxPositionSize,
5785
- computeWarmupProgress,
5786
6997
  computeWarmupUnlockedCapital,
5787
6998
  concatBytes,
5788
6999
  countLighthouseInstructions,
7000
+ decodeDepositPda,
5789
7001
  decodeError,
5790
7002
  decodeStakePool,
5791
7003
  depositAccounts,
5792
7004
  deriveCreatorLockPda,
5793
7005
  deriveDepositPda,
5794
- deriveKeeperFund,
7006
+ deriveInsuranceLpMint,
5795
7007
  deriveLpPda,
7008
+ deriveMintAuthority,
7009
+ deriveNftMint,
7010
+ deriveNftPda,
5796
7011
  derivePythPriceUpdateAccount,
5797
7012
  derivePythPushOraclePDA,
5798
7013
  deriveStakePool,
@@ -5814,6 +7029,7 @@ export {
5814
7029
  encU32,
5815
7030
  encU64,
5816
7031
  encU8,
7032
+ encodeAcceptAdmin,
5817
7033
  encodeAdminForceClose,
5818
7034
  encodeAdvanceEpoch,
5819
7035
  encodeAdvanceOraclePhase,
@@ -5830,8 +7046,12 @@ export {
5830
7046
  encodeCloseOrphanSlab,
5831
7047
  encodeCloseSlab,
5832
7048
  encodeCloseStaleSlabs,
7049
+ encodeConvertReleasedPnl,
7050
+ encodeCreateInsuranceMint,
5833
7051
  encodeCreateLpVault,
5834
7052
  encodeDepositCollateral,
7053
+ encodeDepositFeeCredits,
7054
+ encodeDepositInsuranceLP,
5835
7055
  encodeDepositLpCollateral,
5836
7056
  encodeExecuteAdl,
5837
7057
  encodeForceCloseResolved,
@@ -5847,10 +7067,14 @@ export {
5847
7067
  encodeLpVaultDeposit,
5848
7068
  encodeLpVaultWithdraw,
5849
7069
  encodeMintPositionNft,
7070
+ encodeNftBurn,
7071
+ encodeNftEmergencyBurn,
7072
+ encodeNftMint,
7073
+ encodeNftSettleFunding,
5850
7074
  encodePauseMarket,
5851
- encodePushOraclePrice,
5852
7075
  encodeQueueWithdrawal,
5853
7076
  encodeQueueWithdrawalSV,
7077
+ encodeReclaimEmptyAccount,
5854
7078
  encodeReclaimSlabRent,
5855
7079
  encodeRenounceAdmin,
5856
7080
  encodeRescueOrphanVault,
@@ -5858,17 +7082,21 @@ export {
5858
7082
  encodeResolveMarket,
5859
7083
  encodeResolvePermissionless,
5860
7084
  encodeSetDexPool,
7085
+ encodeSetDisputeParams,
5861
7086
  encodeSetInsuranceIsolation,
5862
7087
  encodeSetInsuranceWithdrawPolicy,
7088
+ encodeSetLpCollateralParams,
5863
7089
  encodeSetMaintenanceFee,
7090
+ encodeSetMaxPnlCap,
5864
7091
  encodeSetOffsetPair,
7092
+ encodeSetOiCapMultiplier,
5865
7093
  encodeSetOiImbalanceHardBlock,
5866
- encodeSetOracleAuthority,
5867
7094
  encodeSetOraclePriceCap,
5868
7095
  encodeSetPendingSettlement,
5869
7096
  encodeSetPythOracle,
5870
7097
  encodeSetRiskThreshold,
5871
7098
  encodeSetWalletCap,
7099
+ encodeSettleAccount,
5872
7100
  encodeSlashCreationDeposit,
5873
7101
  encodeStakeAccrueFees,
5874
7102
  encodeStakeAdminResolveMarket,
@@ -5884,24 +7112,28 @@ export {
5884
7112
  encodeStakeFlushToInsurance,
5885
7113
  encodeStakeInitPool,
5886
7114
  encodeStakeInitTradingPool,
7115
+ encodeStakeReturnInsurance,
7116
+ encodeStakeSetMarketResolved,
5887
7117
  encodeStakeTransferAdmin,
5888
7118
  encodeStakeUpdateConfig,
5889
7119
  encodeStakeWithdraw,
5890
7120
  encodeTopUpInsurance,
5891
- encodeTopUpKeeperFund,
5892
7121
  encodeTradeCpi,
5893
7122
  encodeTradeCpiV2,
5894
7123
  encodeTradeNoCpi,
5895
7124
  encodeTransferOwnershipCpi,
5896
7125
  encodeTransferPositionOwnership,
5897
7126
  encodeUnpauseMarket,
7127
+ encodeUnresolveMarket,
5898
7128
  encodeUpdateAdmin,
7129
+ encodeUpdateAuthority,
5899
7130
  encodeUpdateConfig,
5900
7131
  encodeUpdateHyperpMark,
5901
7132
  encodeUpdateMarkPrice,
5902
7133
  encodeUpdateRiskParams,
5903
7134
  encodeWithdrawCollateral,
5904
7135
  encodeWithdrawInsurance,
7136
+ encodeWithdrawInsuranceLP,
5905
7137
  encodeWithdrawInsuranceLimited,
5906
7138
  encodeWithdrawLpCollateral,
5907
7139
  fetchAdlRankedPositions,
@@ -5917,13 +7149,13 @@ export {
5917
7149
  getErrorName,
5918
7150
  getMarketsByAddress,
5919
7151
  getMatcherProgramId,
7152
+ getNftProgramId,
5920
7153
  getProgramId,
5921
7154
  getStakeProgramId,
5922
7155
  getStaticMarkets,
5923
7156
  initPoolAccounts,
5924
7157
  isAccountUsed,
5925
7158
  isAdlTriggered,
5926
- isAnchorErrorCode,
5927
7159
  isLighthouseError,
5928
7160
  isLighthouseFailureInLogs,
5929
7161
  isLighthouseInstruction,
@@ -5931,6 +7163,7 @@ export {
5931
7163
  isToken2022,
5932
7164
  isValidChainlinkOracle,
5933
7165
  maxAccountIndex,
7166
+ packOiCap,
5934
7167
  parseAccount,
5935
7168
  parseAdlEvent,
5936
7169
  parseAllAccounts,
@@ -5941,6 +7174,7 @@ export {
5941
7174
  parseErrorFromLogs,
5942
7175
  parseHeader,
5943
7176
  parseParams,
7177
+ parsePositionNftAccount,
5944
7178
  parseUsedIndices,
5945
7179
  rankAdlPositions,
5946
7180
  readLastThrUpdateSlot,