@gvnrdao/dh-sdk 0.0.298 → 0.0.300
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/browser/dist/browser.js +1 -1
- package/dist/deployments.js +10 -3
- package/dist/deployments.mjs +10 -3
- package/dist/index.js +107 -54
- package/dist/index.mjs +107 -54
- package/dist/utils/chunks/eip1559-broadcast.utils.d.ts +3 -2
- package/dist/utils/quantum-revert.utils.d.ts +32 -0
- package/package.json +1 -1
package/dist/deployments.js
CHANGED
|
@@ -136,9 +136,9 @@ var SEPOLIA_DEPLOYMENT = {
|
|
|
136
136
|
reason: "Shared upgrade script: PositionManagerCoreModule implementation update"
|
|
137
137
|
},
|
|
138
138
|
CollateralManagerModule: {
|
|
139
|
-
previousImplementation: "
|
|
140
|
-
newImplementation: "
|
|
141
|
-
upgradedAt: "2026-07-
|
|
139
|
+
previousImplementation: "0xCf5d2b210C8e30bE8e05bFC79593b9439b8b9670",
|
|
140
|
+
newImplementation: "0xF57BBbb4818371605e308228A04F8Ec4Dcc5E7Ba",
|
|
141
|
+
upgradedAt: "2026-07-07T16:59:13.883Z",
|
|
142
142
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
143
143
|
reason: "Shared upgrade script: CollateralManagerModule implementation update"
|
|
144
144
|
},
|
|
@@ -214,6 +214,13 @@ var SEPOLIA_DEPLOYMENT = {
|
|
|
214
214
|
upgradedAt: "2026-05-27T12:16:13.356Z",
|
|
215
215
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
216
216
|
reason: "Audit C-7: BitcoinProviderRegistry v1.0.0 \u2192 v1.1.0 \u2014 per-chainId CID allowlist (addAllowedCid / removeAllowedCid / isAllowedCid views). Storage gap 46 \u2192 43."
|
|
217
|
+
},
|
|
218
|
+
BitcoinWithdrawalAddressRegistry: {
|
|
219
|
+
previousImplementation: "0xFF270BC4470dBA80430Bd1a3a66EB691599354fA",
|
|
220
|
+
newImplementation: "0x76E0a2c9d89562fD7c50b5f554d7fa25957e39Db",
|
|
221
|
+
upgradedAt: "2026-07-07T16:56:49.844Z",
|
|
222
|
+
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
223
|
+
reason: "Shared upgrade script: BitcoinWithdrawalAddressRegistry implementation update"
|
|
217
224
|
}
|
|
218
225
|
},
|
|
219
226
|
history: {
|
package/dist/deployments.mjs
CHANGED
|
@@ -103,9 +103,9 @@ var SEPOLIA_DEPLOYMENT = {
|
|
|
103
103
|
reason: "Shared upgrade script: PositionManagerCoreModule implementation update"
|
|
104
104
|
},
|
|
105
105
|
CollateralManagerModule: {
|
|
106
|
-
previousImplementation: "
|
|
107
|
-
newImplementation: "
|
|
108
|
-
upgradedAt: "2026-07-
|
|
106
|
+
previousImplementation: "0xCf5d2b210C8e30bE8e05bFC79593b9439b8b9670",
|
|
107
|
+
newImplementation: "0xF57BBbb4818371605e308228A04F8Ec4Dcc5E7Ba",
|
|
108
|
+
upgradedAt: "2026-07-07T16:59:13.883Z",
|
|
109
109
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
110
110
|
reason: "Shared upgrade script: CollateralManagerModule implementation update"
|
|
111
111
|
},
|
|
@@ -181,6 +181,13 @@ var SEPOLIA_DEPLOYMENT = {
|
|
|
181
181
|
upgradedAt: "2026-05-27T12:16:13.356Z",
|
|
182
182
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
183
183
|
reason: "Audit C-7: BitcoinProviderRegistry v1.0.0 \u2192 v1.1.0 \u2014 per-chainId CID allowlist (addAllowedCid / removeAllowedCid / isAllowedCid views). Storage gap 46 \u2192 43."
|
|
184
|
+
},
|
|
185
|
+
BitcoinWithdrawalAddressRegistry: {
|
|
186
|
+
previousImplementation: "0xFF270BC4470dBA80430Bd1a3a66EB691599354fA",
|
|
187
|
+
newImplementation: "0x76E0a2c9d89562fD7c50b5f554d7fa25957e39Db",
|
|
188
|
+
upgradedAt: "2026-07-07T16:56:49.844Z",
|
|
189
|
+
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
190
|
+
reason: "Shared upgrade script: BitcoinWithdrawalAddressRegistry implementation update"
|
|
184
191
|
}
|
|
185
192
|
},
|
|
186
193
|
history: {
|
package/dist/index.js
CHANGED
|
@@ -161,9 +161,9 @@ var init_deployment_addresses = __esm({
|
|
|
161
161
|
reason: "Shared upgrade script: PositionManagerCoreModule implementation update"
|
|
162
162
|
},
|
|
163
163
|
CollateralManagerModule: {
|
|
164
|
-
previousImplementation: "
|
|
165
|
-
newImplementation: "
|
|
166
|
-
upgradedAt: "2026-07-
|
|
164
|
+
previousImplementation: "0xCf5d2b210C8e30bE8e05bFC79593b9439b8b9670",
|
|
165
|
+
newImplementation: "0xF57BBbb4818371605e308228A04F8Ec4Dcc5E7Ba",
|
|
166
|
+
upgradedAt: "2026-07-07T16:59:13.883Z",
|
|
167
167
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
168
168
|
reason: "Shared upgrade script: CollateralManagerModule implementation update"
|
|
169
169
|
},
|
|
@@ -239,6 +239,13 @@ var init_deployment_addresses = __esm({
|
|
|
239
239
|
upgradedAt: "2026-05-27T12:16:13.356Z",
|
|
240
240
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
241
241
|
reason: "Audit C-7: BitcoinProviderRegistry v1.0.0 \u2192 v1.1.0 \u2014 per-chainId CID allowlist (addAllowedCid / removeAllowedCid / isAllowedCid views). Storage gap 46 \u2192 43."
|
|
242
|
+
},
|
|
243
|
+
BitcoinWithdrawalAddressRegistry: {
|
|
244
|
+
previousImplementation: "0xFF270BC4470dBA80430Bd1a3a66EB691599354fA",
|
|
245
|
+
newImplementation: "0x76E0a2c9d89562fD7c50b5f554d7fa25957e39Db",
|
|
246
|
+
upgradedAt: "2026-07-07T16:56:49.844Z",
|
|
247
|
+
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
248
|
+
reason: "Shared upgrade script: BitcoinWithdrawalAddressRegistry implementation update"
|
|
242
249
|
}
|
|
243
250
|
},
|
|
244
251
|
history: {
|
|
@@ -5908,6 +5915,35 @@ var ServerSession = class {
|
|
|
5908
5915
|
}
|
|
5909
5916
|
};
|
|
5910
5917
|
|
|
5918
|
+
// src/utils/quantum-revert.utils.ts
|
|
5919
|
+
var DEAD_ZONE_VIOLATION_SELECTOR = "0xbe4b82c1";
|
|
5920
|
+
var QUANTUM_REVERT_NAMES = {
|
|
5921
|
+
"0xbe4b82c1": "DeadZoneViolation()",
|
|
5922
|
+
"0x137f3b70": "InDeadZone()",
|
|
5923
|
+
"0x131d9a21": "QuantumExpired()",
|
|
5924
|
+
"0x52ce5d58": "QuantumAlreadyUsed()",
|
|
5925
|
+
"0x3e76a3c9": "QuantumOutsideWindow()",
|
|
5926
|
+
"0x8baa579f": "InvalidSignature()",
|
|
5927
|
+
"0x62278171": "InvalidValidatorSignature()",
|
|
5928
|
+
"0x3ee5aeb5": "OperationNotAuthorized()",
|
|
5929
|
+
"0x48f5c3ed": "Unauthorized()",
|
|
5930
|
+
"0x70f4b32a": "UnauthorizedSigner()",
|
|
5931
|
+
"0xd92e233d": "ValidationFailed()",
|
|
5932
|
+
"0x36bfdeea": "StateHashMismatch()",
|
|
5933
|
+
"0xb9d419a7": "DebtUpdateVerificationFailed()",
|
|
5934
|
+
"0xc7e20553": "DebtUpdateVerificationFailedDetailed(bytes32,uint256,uint256,uint256,uint256,uint256)",
|
|
5935
|
+
"0x0cfd2a97": "MintVerificationMismatch(uint256,uint256)",
|
|
5936
|
+
"0x07637bd8": "MintFailed()"
|
|
5937
|
+
};
|
|
5938
|
+
function decodeQuantumRevert(e) {
|
|
5939
|
+
const raw = e?.data ?? e?.info?.error?.data ?? // ethers v6 BrowserProvider (MetaMask)
|
|
5940
|
+
e?.error?.data?.data ?? e?.error?.data ?? e?.error?.error?.data;
|
|
5941
|
+
const data = typeof raw === "string" && raw.startsWith("0x") ? raw : null;
|
|
5942
|
+
const selector = data && data.length >= 10 ? data.slice(0, 10) : null;
|
|
5943
|
+
const name = selector ? QUANTUM_REVERT_NAMES[selector] ?? null : null;
|
|
5944
|
+
return { data, selector, name };
|
|
5945
|
+
}
|
|
5946
|
+
|
|
5911
5947
|
// src/utils/btc-withdrawal-message.ts
|
|
5912
5948
|
var import_ethers5 = require("ethers");
|
|
5913
5949
|
var QUANTUM_SECONDS = 60;
|
|
@@ -15958,8 +15994,8 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
15958
15994
|
};
|
|
15959
15995
|
}
|
|
15960
15996
|
}
|
|
15961
|
-
const
|
|
15962
|
-
const chainId = Number(
|
|
15997
|
+
const network = await this.getProviderOrThrow().getNetwork();
|
|
15998
|
+
const chainId = Number(network.chainId);
|
|
15963
15999
|
const signer2 = this.getSignerOrThrow();
|
|
15964
16000
|
const contracts = {
|
|
15965
16001
|
PositionManager: this.config.contractAddresses?.positionManager || "",
|
|
@@ -15987,10 +16023,10 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
15987
16023
|
` UCDController: ${contracts?.UCDController || "MISSING"}`
|
|
15988
16024
|
);
|
|
15989
16025
|
}
|
|
15990
|
-
const chain = this.config.chain || (Number(
|
|
16026
|
+
const chain = this.config.chain || (Number(network.chainId) === 1 ? "ethereum" : "sepolia");
|
|
15991
16027
|
const devBitcoinProviderUrl = request.customBitcoinRpcUrl || this.config.bitcoinProviders?.[0]?.url;
|
|
15992
16028
|
if (this.config.debug) {
|
|
15993
|
-
log.info(` Network: ${chain} (chainId: ${
|
|
16029
|
+
log.info(` Network: ${chain} (chainId: ${network.chainId})`);
|
|
15994
16030
|
}
|
|
15995
16031
|
const MAX_RETRIES = 3;
|
|
15996
16032
|
const RETRY_DELAY_MS = 2e3;
|
|
@@ -16383,7 +16419,7 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
16383
16419
|
{}
|
|
16384
16420
|
);
|
|
16385
16421
|
}
|
|
16386
|
-
let errorData = preflightError?.data || preflightError?.error?.data?.data || preflightError?.error?.data || preflightError?.error?.error?.data;
|
|
16422
|
+
let errorData = preflightError?.data || preflightError?.info?.error?.data || preflightError?.error?.data?.data || preflightError?.error?.data || preflightError?.error?.error?.data;
|
|
16387
16423
|
const errorMessage = preflightError?.reason || preflightError?.error?.reason || preflightError?.error?.error?.reason || preflightError?.message || "Unknown error";
|
|
16388
16424
|
let requireMessage;
|
|
16389
16425
|
if (errorData && typeof errorData === "string" && errorData.startsWith("0x") && errorData.length > 138) {
|
|
@@ -16399,7 +16435,31 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
16399
16435
|
} catch (e) {
|
|
16400
16436
|
}
|
|
16401
16437
|
}
|
|
16402
|
-
|
|
16438
|
+
const isDeadZonePreflightArtifact = decodeQuantumRevert(preflightError).selector === DEAD_ZONE_VIOLATION_SELECTOR;
|
|
16439
|
+
if (isDeadZonePreflightArtifact) {
|
|
16440
|
+
const nowSec = Math.floor(Date.now() / 1e3);
|
|
16441
|
+
const sigQuantum2 = Math.floor(Number(validationResponse.timestamp) / 60) * 60;
|
|
16442
|
+
const realCurrentQuantum = Math.floor(nowSec / 60) * 60;
|
|
16443
|
+
if (sigQuantum2 === realCurrentQuantum) {
|
|
16444
|
+
if (this.config.debug) {
|
|
16445
|
+
log.info(
|
|
16446
|
+
"\u21AA\uFE0F Preflight DeadZoneViolation is a stale-latest-block artifact (signature is the current quantum) \u2014 proceeding to broadcast",
|
|
16447
|
+
{}
|
|
16448
|
+
);
|
|
16449
|
+
}
|
|
16450
|
+
} else {
|
|
16451
|
+
if (this.config.debug) {
|
|
16452
|
+
log.info(
|
|
16453
|
+
"\u{1F501} Preflight DeadZoneViolation near the boundary \u2014 deferring across it, then proceeding",
|
|
16454
|
+
{}
|
|
16455
|
+
);
|
|
16456
|
+
}
|
|
16457
|
+
await awaitSafeSubmissionWindow(
|
|
16458
|
+
Number(validationResponse.timestamp)
|
|
16459
|
+
);
|
|
16460
|
+
}
|
|
16461
|
+
}
|
|
16462
|
+
if (requireMessage && !isDeadZonePreflightArtifact) {
|
|
16403
16463
|
throw new Error(
|
|
16404
16464
|
`Preflight check failed - mintUCD would revert:
|
|
16405
16465
|
${requireMessage}
|
|
@@ -16460,13 +16520,15 @@ Quantum Timing Analysis:
|
|
|
16460
16520
|
Status: ${sigQuantum2 < currentQuantum ? "\u274C EXPIRED - Signature created in older quantum window" : "\u2705 VALID"}
|
|
16461
16521
|
Note: QuantumOutsideWindow can also occur if the tx is mined outside the accepted past/current/next quantum set.`;
|
|
16462
16522
|
}
|
|
16463
|
-
|
|
16464
|
-
|
|
16523
|
+
if (!isDeadZonePreflightArtifact) {
|
|
16524
|
+
throw new Error(
|
|
16525
|
+
`Preflight check failed - mintUCD would revert:
|
|
16465
16526
|
Error: ${errorName}
|
|
16466
16527
|
Selector: ${selector}
|
|
16467
16528
|
Message: ${errorMessage}
|
|
16468
16529
|
Data: ${errorData}${quantumContext}${mintDebtDiagnostics}`
|
|
16469
|
-
|
|
16530
|
+
);
|
|
16531
|
+
}
|
|
16470
16532
|
} else {
|
|
16471
16533
|
const currentTime2 = Math.floor(Date.now() / 1e3);
|
|
16472
16534
|
const timeSinceSig = currentTime2 - validationResponse.timestamp;
|
|
@@ -16613,10 +16675,6 @@ Position: ${request.positionId}`
|
|
|
16613
16675
|
if (!signerProvider) {
|
|
16614
16676
|
throw new Error("Signer must have a provider attached");
|
|
16615
16677
|
}
|
|
16616
|
-
const network = await signerProvider.getNetwork();
|
|
16617
|
-
const networkChainIdNum = Number(network.chainId);
|
|
16618
|
-
const isSepolia = networkChainIdNum === 11155111;
|
|
16619
|
-
const isLocalhost = networkChainIdNum === 1337 || networkChainIdNum === 31337;
|
|
16620
16678
|
const MAX_SKEW_SECONDS = 300;
|
|
16621
16679
|
const FINAL_SAFETY_MARGIN = 60;
|
|
16622
16680
|
const QUANTUM_WINDOW_SECONDS2 = 60;
|
|
@@ -16701,7 +16759,6 @@ Position: ${request.positionId}`
|
|
|
16701
16759
|
validationResponse.timestamp,
|
|
16702
16760
|
signatureHexMint
|
|
16703
16761
|
]);
|
|
16704
|
-
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16705
16762
|
const fromAddress = await signer.getAddress();
|
|
16706
16763
|
const estimatedGas = await estimateContractCallGasWithMargin(
|
|
16707
16764
|
signerProvider,
|
|
@@ -16719,6 +16776,7 @@ Position: ${request.positionId}`
|
|
|
16719
16776
|
{}
|
|
16720
16777
|
);
|
|
16721
16778
|
}
|
|
16779
|
+
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16722
16780
|
tx = await sendEip1559Transaction({
|
|
16723
16781
|
signer,
|
|
16724
16782
|
to: positionManagerAddress,
|
|
@@ -16746,9 +16804,16 @@ Position: ${request.positionId}`
|
|
|
16746
16804
|
log.info(` Error data type: ${typeof callError?.data}`, {});
|
|
16747
16805
|
log.info(` Error data value: ${callError?.data}`, {});
|
|
16748
16806
|
}
|
|
16749
|
-
let errorData = callError?.data || callError?.error?.data?.data || callError?.error?.data;
|
|
16807
|
+
let errorData = callError?.data || callError?.info?.error?.data || callError?.error?.data?.data || callError?.error?.data;
|
|
16750
16808
|
const errorMessage = callError?.reason || callError?.message || "Unknown error";
|
|
16751
|
-
|
|
16809
|
+
const isDeadZoneArtifact = decodeQuantumRevert(callError).selector === DEAD_ZONE_VIOLATION_SELECTOR;
|
|
16810
|
+
if (isDeadZoneArtifact && this.config.debug) {
|
|
16811
|
+
log.info(
|
|
16812
|
+
"\u{1F536} mintUCD static-call DeadZoneViolation is a stale-latest-block artifact; broadcasting anyway (gated)",
|
|
16813
|
+
{}
|
|
16814
|
+
);
|
|
16815
|
+
}
|
|
16816
|
+
if (!isDeadZoneArtifact && errorData && typeof errorData === "string" && errorData.startsWith("0x") && errorData.length > 10) {
|
|
16752
16817
|
const selector = errorData.slice(0, 10);
|
|
16753
16818
|
const knownErrors = {
|
|
16754
16819
|
"0x8baa579f": "InvalidSignature()",
|
|
@@ -16814,29 +16879,26 @@ Message: ${errorMessage}`
|
|
|
16814
16879
|
}
|
|
16815
16880
|
}
|
|
16816
16881
|
}
|
|
16817
|
-
|
|
16818
|
-
|
|
16882
|
+
if (!isDeadZoneArtifact) {
|
|
16883
|
+
throw new Error(
|
|
16884
|
+
`mintUCD reverted: ${errorMessage}
|
|
16819
16885
|
Error data: ${errorData || "none"}`
|
|
16820
|
-
);
|
|
16821
|
-
}
|
|
16822
|
-
if (isSepolia || isLocalhost) {
|
|
16823
|
-
if (this.config.debug) {
|
|
16824
|
-
log.info(
|
|
16825
|
-
"\u2705 Static call OK \u2014 broadcasting mintUCD with gas ceiling (Sepolia)",
|
|
16826
|
-
{}
|
|
16827
16886
|
);
|
|
16828
16887
|
}
|
|
16829
|
-
|
|
16830
|
-
|
|
16831
|
-
|
|
16832
|
-
|
|
16833
|
-
|
|
16834
|
-
});
|
|
16835
|
-
} else {
|
|
16836
|
-
throw new Error(
|
|
16837
|
-
`mintUCD: eth_estimateGas failed (chainId ${network.chainId}). Static call succeeded; fixed gas ceiling fallback is only supported on Sepolia (11155111) and localhost.`
|
|
16888
|
+
}
|
|
16889
|
+
if (this.config.debug) {
|
|
16890
|
+
log.info(
|
|
16891
|
+
"\u2705 Static call clear \u2014 broadcasting mintUCD with fixed gas ceiling",
|
|
16892
|
+
{}
|
|
16838
16893
|
);
|
|
16839
16894
|
}
|
|
16895
|
+
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16896
|
+
tx = await sendEip1559Transaction({
|
|
16897
|
+
signer,
|
|
16898
|
+
to: positionManagerAddress,
|
|
16899
|
+
data: mintCalldata,
|
|
16900
|
+
gasLimit: MINT_UCD_GAS_CEILING
|
|
16901
|
+
});
|
|
16840
16902
|
}
|
|
16841
16903
|
const receipt = await signerProvider.waitForTransaction(
|
|
16842
16904
|
tx.hash,
|
|
@@ -18899,23 +18961,10 @@ Error data: ${errorData || "none"}`
|
|
|
18899
18961
|
signature
|
|
18900
18962
|
]);
|
|
18901
18963
|
const decodePaymentRevert = (e) => {
|
|
18902
|
-
const
|
|
18903
|
-
|
|
18904
|
-
if (!data || !data.startsWith("0x") || data.length < 10)
|
|
18964
|
+
const { selector, name } = decodeQuantumRevert(e);
|
|
18965
|
+
if (!selector)
|
|
18905
18966
|
return null;
|
|
18906
|
-
|
|
18907
|
-
const map2 = {
|
|
18908
|
-
"0xbe4b82c1": "DeadZoneViolation()",
|
|
18909
|
-
"0x137f3b70": "InDeadZone()",
|
|
18910
|
-
"0x52ce5d58": "QuantumAlreadyUsed()",
|
|
18911
|
-
"0x3e76a3c9": "QuantumOutsideWindow()",
|
|
18912
|
-
"0x131d9a21": "QuantumExpired()",
|
|
18913
|
-
"0x8baa579f": "InvalidSignature()",
|
|
18914
|
-
"0x62278171": "InvalidValidatorSignature()",
|
|
18915
|
-
"0x3ee5aeb5": "OperationNotAuthorized()",
|
|
18916
|
-
"0x48f5c3ed": "Unauthorized()"
|
|
18917
|
-
};
|
|
18918
|
-
return map2[selector] ?? `Unknown error ${selector}`;
|
|
18967
|
+
return name ?? `Unknown error ${selector}`;
|
|
18919
18968
|
};
|
|
18920
18969
|
const MAX_DEADZONE_RESIMULATIONS = 3;
|
|
18921
18970
|
for (let sim = 1; ; sim++) {
|
|
@@ -19681,7 +19730,8 @@ Error data: ${errorData || "none"}`
|
|
|
19681
19730
|
tx = await positionManagerContract["withdrawBTC"](
|
|
19682
19731
|
withdrawalParams,
|
|
19683
19732
|
signatureBytes,
|
|
19684
|
-
btcSpendAuthBytes
|
|
19733
|
+
btcSpendAuthBytes,
|
|
19734
|
+
{ gasLimit: WITHDRAW_BTC_GAS_CEILING }
|
|
19685
19735
|
);
|
|
19686
19736
|
} catch (txError) {
|
|
19687
19737
|
const txErrorMsg = txError instanceof Error ? txError.message : String(txError);
|
|
@@ -19712,6 +19762,9 @@ Error data: ${errorData || "none"}`
|
|
|
19712
19762
|
WITHDRAW_BTC_GAS_CEILING
|
|
19713
19763
|
);
|
|
19714
19764
|
const gasLimit = estimatedGas ?? WITHDRAW_BTC_GAS_CEILING;
|
|
19765
|
+
await awaitSafeSubmissionWindow(
|
|
19766
|
+
Number(withdrawalParams.quantumTimestamp)
|
|
19767
|
+
);
|
|
19715
19768
|
tx = await signer.sendTransaction({
|
|
19716
19769
|
to: contractAddress,
|
|
19717
19770
|
data: calldata,
|
package/dist/index.mjs
CHANGED
|
@@ -167,9 +167,9 @@ var init_deployment_addresses = __esm({
|
|
|
167
167
|
reason: "Shared upgrade script: PositionManagerCoreModule implementation update"
|
|
168
168
|
},
|
|
169
169
|
CollateralManagerModule: {
|
|
170
|
-
previousImplementation: "
|
|
171
|
-
newImplementation: "
|
|
172
|
-
upgradedAt: "2026-07-
|
|
170
|
+
previousImplementation: "0xCf5d2b210C8e30bE8e05bFC79593b9439b8b9670",
|
|
171
|
+
newImplementation: "0xF57BBbb4818371605e308228A04F8Ec4Dcc5E7Ba",
|
|
172
|
+
upgradedAt: "2026-07-07T16:59:13.883Z",
|
|
173
173
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
174
174
|
reason: "Shared upgrade script: CollateralManagerModule implementation update"
|
|
175
175
|
},
|
|
@@ -245,6 +245,13 @@ var init_deployment_addresses = __esm({
|
|
|
245
245
|
upgradedAt: "2026-05-27T12:16:13.356Z",
|
|
246
246
|
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
247
247
|
reason: "Audit C-7: BitcoinProviderRegistry v1.0.0 \u2192 v1.1.0 \u2014 per-chainId CID allowlist (addAllowedCid / removeAllowedCid / isAllowedCid views). Storage gap 46 \u2192 43."
|
|
248
|
+
},
|
|
249
|
+
BitcoinWithdrawalAddressRegistry: {
|
|
250
|
+
previousImplementation: "0xFF270BC4470dBA80430Bd1a3a66EB691599354fA",
|
|
251
|
+
newImplementation: "0x76E0a2c9d89562fD7c50b5f554d7fa25957e39Db",
|
|
252
|
+
upgradedAt: "2026-07-07T16:56:49.844Z",
|
|
253
|
+
upgradedBy: "0xF20986F02420EF443AE9BE5092FB8A4975cF3aA6",
|
|
254
|
+
reason: "Shared upgrade script: BitcoinWithdrawalAddressRegistry implementation update"
|
|
248
255
|
}
|
|
249
256
|
},
|
|
250
257
|
history: {
|
|
@@ -5832,6 +5839,35 @@ var ServerSession = class {
|
|
|
5832
5839
|
}
|
|
5833
5840
|
};
|
|
5834
5841
|
|
|
5842
|
+
// src/utils/quantum-revert.utils.ts
|
|
5843
|
+
var DEAD_ZONE_VIOLATION_SELECTOR = "0xbe4b82c1";
|
|
5844
|
+
var QUANTUM_REVERT_NAMES = {
|
|
5845
|
+
"0xbe4b82c1": "DeadZoneViolation()",
|
|
5846
|
+
"0x137f3b70": "InDeadZone()",
|
|
5847
|
+
"0x131d9a21": "QuantumExpired()",
|
|
5848
|
+
"0x52ce5d58": "QuantumAlreadyUsed()",
|
|
5849
|
+
"0x3e76a3c9": "QuantumOutsideWindow()",
|
|
5850
|
+
"0x8baa579f": "InvalidSignature()",
|
|
5851
|
+
"0x62278171": "InvalidValidatorSignature()",
|
|
5852
|
+
"0x3ee5aeb5": "OperationNotAuthorized()",
|
|
5853
|
+
"0x48f5c3ed": "Unauthorized()",
|
|
5854
|
+
"0x70f4b32a": "UnauthorizedSigner()",
|
|
5855
|
+
"0xd92e233d": "ValidationFailed()",
|
|
5856
|
+
"0x36bfdeea": "StateHashMismatch()",
|
|
5857
|
+
"0xb9d419a7": "DebtUpdateVerificationFailed()",
|
|
5858
|
+
"0xc7e20553": "DebtUpdateVerificationFailedDetailed(bytes32,uint256,uint256,uint256,uint256,uint256)",
|
|
5859
|
+
"0x0cfd2a97": "MintVerificationMismatch(uint256,uint256)",
|
|
5860
|
+
"0x07637bd8": "MintFailed()"
|
|
5861
|
+
};
|
|
5862
|
+
function decodeQuantumRevert(e) {
|
|
5863
|
+
const raw = e?.data ?? e?.info?.error?.data ?? // ethers v6 BrowserProvider (MetaMask)
|
|
5864
|
+
e?.error?.data?.data ?? e?.error?.data ?? e?.error?.error?.data;
|
|
5865
|
+
const data = typeof raw === "string" && raw.startsWith("0x") ? raw : null;
|
|
5866
|
+
const selector = data && data.length >= 10 ? data.slice(0, 10) : null;
|
|
5867
|
+
const name = selector ? QUANTUM_REVERT_NAMES[selector] ?? null : null;
|
|
5868
|
+
return { data, selector, name };
|
|
5869
|
+
}
|
|
5870
|
+
|
|
5835
5871
|
// src/utils/btc-withdrawal-message.ts
|
|
5836
5872
|
import { keccak256 as keccak2563, toUtf8Bytes as toUtf8Bytes3, solidityPackedKeccak256 as solidityPackedKeccak2563, getBytes as getBytes3, zeroPadValue } from "ethers";
|
|
5837
5873
|
var QUANTUM_SECONDS = 60;
|
|
@@ -15886,8 +15922,8 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
15886
15922
|
};
|
|
15887
15923
|
}
|
|
15888
15924
|
}
|
|
15889
|
-
const
|
|
15890
|
-
const chainId = Number(
|
|
15925
|
+
const network = await this.getProviderOrThrow().getNetwork();
|
|
15926
|
+
const chainId = Number(network.chainId);
|
|
15891
15927
|
const signer2 = this.getSignerOrThrow();
|
|
15892
15928
|
const contracts = {
|
|
15893
15929
|
PositionManager: this.config.contractAddresses?.positionManager || "",
|
|
@@ -15915,10 +15951,10 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
15915
15951
|
` UCDController: ${contracts?.UCDController || "MISSING"}`
|
|
15916
15952
|
);
|
|
15917
15953
|
}
|
|
15918
|
-
const chain = this.config.chain || (Number(
|
|
15954
|
+
const chain = this.config.chain || (Number(network.chainId) === 1 ? "ethereum" : "sepolia");
|
|
15919
15955
|
const devBitcoinProviderUrl = request.customBitcoinRpcUrl || this.config.bitcoinProviders?.[0]?.url;
|
|
15920
15956
|
if (this.config.debug) {
|
|
15921
|
-
log.info(` Network: ${chain} (chainId: ${
|
|
15957
|
+
log.info(` Network: ${chain} (chainId: ${network.chainId})`);
|
|
15922
15958
|
}
|
|
15923
15959
|
const MAX_RETRIES = 3;
|
|
15924
15960
|
const RETRY_DELAY_MS = 2e3;
|
|
@@ -16311,7 +16347,7 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
16311
16347
|
{}
|
|
16312
16348
|
);
|
|
16313
16349
|
}
|
|
16314
|
-
let errorData = preflightError?.data || preflightError?.error?.data?.data || preflightError?.error?.data || preflightError?.error?.error?.data;
|
|
16350
|
+
let errorData = preflightError?.data || preflightError?.info?.error?.data || preflightError?.error?.data?.data || preflightError?.error?.data || preflightError?.error?.error?.data;
|
|
16315
16351
|
const errorMessage = preflightError?.reason || preflightError?.error?.reason || preflightError?.error?.error?.reason || preflightError?.message || "Unknown error";
|
|
16316
16352
|
let requireMessage;
|
|
16317
16353
|
if (errorData && typeof errorData === "string" && errorData.startsWith("0x") && errorData.length > 138) {
|
|
@@ -16327,7 +16363,31 @@ var DiamondHandsSDK = class _DiamondHandsSDK {
|
|
|
16327
16363
|
} catch (e) {
|
|
16328
16364
|
}
|
|
16329
16365
|
}
|
|
16330
|
-
|
|
16366
|
+
const isDeadZonePreflightArtifact = decodeQuantumRevert(preflightError).selector === DEAD_ZONE_VIOLATION_SELECTOR;
|
|
16367
|
+
if (isDeadZonePreflightArtifact) {
|
|
16368
|
+
const nowSec = Math.floor(Date.now() / 1e3);
|
|
16369
|
+
const sigQuantum2 = Math.floor(Number(validationResponse.timestamp) / 60) * 60;
|
|
16370
|
+
const realCurrentQuantum = Math.floor(nowSec / 60) * 60;
|
|
16371
|
+
if (sigQuantum2 === realCurrentQuantum) {
|
|
16372
|
+
if (this.config.debug) {
|
|
16373
|
+
log.info(
|
|
16374
|
+
"\u21AA\uFE0F Preflight DeadZoneViolation is a stale-latest-block artifact (signature is the current quantum) \u2014 proceeding to broadcast",
|
|
16375
|
+
{}
|
|
16376
|
+
);
|
|
16377
|
+
}
|
|
16378
|
+
} else {
|
|
16379
|
+
if (this.config.debug) {
|
|
16380
|
+
log.info(
|
|
16381
|
+
"\u{1F501} Preflight DeadZoneViolation near the boundary \u2014 deferring across it, then proceeding",
|
|
16382
|
+
{}
|
|
16383
|
+
);
|
|
16384
|
+
}
|
|
16385
|
+
await awaitSafeSubmissionWindow(
|
|
16386
|
+
Number(validationResponse.timestamp)
|
|
16387
|
+
);
|
|
16388
|
+
}
|
|
16389
|
+
}
|
|
16390
|
+
if (requireMessage && !isDeadZonePreflightArtifact) {
|
|
16331
16391
|
throw new Error(
|
|
16332
16392
|
`Preflight check failed - mintUCD would revert:
|
|
16333
16393
|
${requireMessage}
|
|
@@ -16388,13 +16448,15 @@ Quantum Timing Analysis:
|
|
|
16388
16448
|
Status: ${sigQuantum2 < currentQuantum ? "\u274C EXPIRED - Signature created in older quantum window" : "\u2705 VALID"}
|
|
16389
16449
|
Note: QuantumOutsideWindow can also occur if the tx is mined outside the accepted past/current/next quantum set.`;
|
|
16390
16450
|
}
|
|
16391
|
-
|
|
16392
|
-
|
|
16451
|
+
if (!isDeadZonePreflightArtifact) {
|
|
16452
|
+
throw new Error(
|
|
16453
|
+
`Preflight check failed - mintUCD would revert:
|
|
16393
16454
|
Error: ${errorName}
|
|
16394
16455
|
Selector: ${selector}
|
|
16395
16456
|
Message: ${errorMessage}
|
|
16396
16457
|
Data: ${errorData}${quantumContext}${mintDebtDiagnostics}`
|
|
16397
|
-
|
|
16458
|
+
);
|
|
16459
|
+
}
|
|
16398
16460
|
} else {
|
|
16399
16461
|
const currentTime2 = Math.floor(Date.now() / 1e3);
|
|
16400
16462
|
const timeSinceSig = currentTime2 - validationResponse.timestamp;
|
|
@@ -16541,10 +16603,6 @@ Position: ${request.positionId}`
|
|
|
16541
16603
|
if (!signerProvider) {
|
|
16542
16604
|
throw new Error("Signer must have a provider attached");
|
|
16543
16605
|
}
|
|
16544
|
-
const network = await signerProvider.getNetwork();
|
|
16545
|
-
const networkChainIdNum = Number(network.chainId);
|
|
16546
|
-
const isSepolia = networkChainIdNum === 11155111;
|
|
16547
|
-
const isLocalhost = networkChainIdNum === 1337 || networkChainIdNum === 31337;
|
|
16548
16606
|
const MAX_SKEW_SECONDS = 300;
|
|
16549
16607
|
const FINAL_SAFETY_MARGIN = 60;
|
|
16550
16608
|
const QUANTUM_WINDOW_SECONDS2 = 60;
|
|
@@ -16629,7 +16687,6 @@ Position: ${request.positionId}`
|
|
|
16629
16687
|
validationResponse.timestamp,
|
|
16630
16688
|
signatureHexMint
|
|
16631
16689
|
]);
|
|
16632
|
-
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16633
16690
|
const fromAddress = await signer.getAddress();
|
|
16634
16691
|
const estimatedGas = await estimateContractCallGasWithMargin(
|
|
16635
16692
|
signerProvider,
|
|
@@ -16647,6 +16704,7 @@ Position: ${request.positionId}`
|
|
|
16647
16704
|
{}
|
|
16648
16705
|
);
|
|
16649
16706
|
}
|
|
16707
|
+
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16650
16708
|
tx = await sendEip1559Transaction({
|
|
16651
16709
|
signer,
|
|
16652
16710
|
to: positionManagerAddress,
|
|
@@ -16674,9 +16732,16 @@ Position: ${request.positionId}`
|
|
|
16674
16732
|
log.info(` Error data type: ${typeof callError?.data}`, {});
|
|
16675
16733
|
log.info(` Error data value: ${callError?.data}`, {});
|
|
16676
16734
|
}
|
|
16677
|
-
let errorData = callError?.data || callError?.error?.data?.data || callError?.error?.data;
|
|
16735
|
+
let errorData = callError?.data || callError?.info?.error?.data || callError?.error?.data?.data || callError?.error?.data;
|
|
16678
16736
|
const errorMessage = callError?.reason || callError?.message || "Unknown error";
|
|
16679
|
-
|
|
16737
|
+
const isDeadZoneArtifact = decodeQuantumRevert(callError).selector === DEAD_ZONE_VIOLATION_SELECTOR;
|
|
16738
|
+
if (isDeadZoneArtifact && this.config.debug) {
|
|
16739
|
+
log.info(
|
|
16740
|
+
"\u{1F536} mintUCD static-call DeadZoneViolation is a stale-latest-block artifact; broadcasting anyway (gated)",
|
|
16741
|
+
{}
|
|
16742
|
+
);
|
|
16743
|
+
}
|
|
16744
|
+
if (!isDeadZoneArtifact && errorData && typeof errorData === "string" && errorData.startsWith("0x") && errorData.length > 10) {
|
|
16680
16745
|
const selector = errorData.slice(0, 10);
|
|
16681
16746
|
const knownErrors = {
|
|
16682
16747
|
"0x8baa579f": "InvalidSignature()",
|
|
@@ -16742,29 +16807,26 @@ Message: ${errorMessage}`
|
|
|
16742
16807
|
}
|
|
16743
16808
|
}
|
|
16744
16809
|
}
|
|
16745
|
-
|
|
16746
|
-
|
|
16810
|
+
if (!isDeadZoneArtifact) {
|
|
16811
|
+
throw new Error(
|
|
16812
|
+
`mintUCD reverted: ${errorMessage}
|
|
16747
16813
|
Error data: ${errorData || "none"}`
|
|
16748
|
-
);
|
|
16749
|
-
}
|
|
16750
|
-
if (isSepolia || isLocalhost) {
|
|
16751
|
-
if (this.config.debug) {
|
|
16752
|
-
log.info(
|
|
16753
|
-
"\u2705 Static call OK \u2014 broadcasting mintUCD with gas ceiling (Sepolia)",
|
|
16754
|
-
{}
|
|
16755
16814
|
);
|
|
16756
16815
|
}
|
|
16757
|
-
|
|
16758
|
-
|
|
16759
|
-
|
|
16760
|
-
|
|
16761
|
-
|
|
16762
|
-
});
|
|
16763
|
-
} else {
|
|
16764
|
-
throw new Error(
|
|
16765
|
-
`mintUCD: eth_estimateGas failed (chainId ${network.chainId}). Static call succeeded; fixed gas ceiling fallback is only supported on Sepolia (11155111) and localhost.`
|
|
16816
|
+
}
|
|
16817
|
+
if (this.config.debug) {
|
|
16818
|
+
log.info(
|
|
16819
|
+
"\u2705 Static call clear \u2014 broadcasting mintUCD with fixed gas ceiling",
|
|
16820
|
+
{}
|
|
16766
16821
|
);
|
|
16767
16822
|
}
|
|
16823
|
+
await awaitSafeSubmissionWindow(Number(validationResponse.timestamp));
|
|
16824
|
+
tx = await sendEip1559Transaction({
|
|
16825
|
+
signer,
|
|
16826
|
+
to: positionManagerAddress,
|
|
16827
|
+
data: mintCalldata,
|
|
16828
|
+
gasLimit: MINT_UCD_GAS_CEILING
|
|
16829
|
+
});
|
|
16768
16830
|
}
|
|
16769
16831
|
const receipt = await signerProvider.waitForTransaction(
|
|
16770
16832
|
tx.hash,
|
|
@@ -18827,23 +18889,10 @@ Error data: ${errorData || "none"}`
|
|
|
18827
18889
|
signature
|
|
18828
18890
|
]);
|
|
18829
18891
|
const decodePaymentRevert = (e) => {
|
|
18830
|
-
const
|
|
18831
|
-
|
|
18832
|
-
if (!data || !data.startsWith("0x") || data.length < 10)
|
|
18892
|
+
const { selector, name } = decodeQuantumRevert(e);
|
|
18893
|
+
if (!selector)
|
|
18833
18894
|
return null;
|
|
18834
|
-
|
|
18835
|
-
const map2 = {
|
|
18836
|
-
"0xbe4b82c1": "DeadZoneViolation()",
|
|
18837
|
-
"0x137f3b70": "InDeadZone()",
|
|
18838
|
-
"0x52ce5d58": "QuantumAlreadyUsed()",
|
|
18839
|
-
"0x3e76a3c9": "QuantumOutsideWindow()",
|
|
18840
|
-
"0x131d9a21": "QuantumExpired()",
|
|
18841
|
-
"0x8baa579f": "InvalidSignature()",
|
|
18842
|
-
"0x62278171": "InvalidValidatorSignature()",
|
|
18843
|
-
"0x3ee5aeb5": "OperationNotAuthorized()",
|
|
18844
|
-
"0x48f5c3ed": "Unauthorized()"
|
|
18845
|
-
};
|
|
18846
|
-
return map2[selector] ?? `Unknown error ${selector}`;
|
|
18895
|
+
return name ?? `Unknown error ${selector}`;
|
|
18847
18896
|
};
|
|
18848
18897
|
const MAX_DEADZONE_RESIMULATIONS = 3;
|
|
18849
18898
|
for (let sim = 1; ; sim++) {
|
|
@@ -19609,7 +19658,8 @@ Error data: ${errorData || "none"}`
|
|
|
19609
19658
|
tx = await positionManagerContract["withdrawBTC"](
|
|
19610
19659
|
withdrawalParams,
|
|
19611
19660
|
signatureBytes,
|
|
19612
|
-
btcSpendAuthBytes
|
|
19661
|
+
btcSpendAuthBytes,
|
|
19662
|
+
{ gasLimit: WITHDRAW_BTC_GAS_CEILING }
|
|
19613
19663
|
);
|
|
19614
19664
|
} catch (txError) {
|
|
19615
19665
|
const txErrorMsg = txError instanceof Error ? txError.message : String(txError);
|
|
@@ -19640,6 +19690,9 @@ Error data: ${errorData || "none"}`
|
|
|
19640
19690
|
WITHDRAW_BTC_GAS_CEILING
|
|
19641
19691
|
);
|
|
19642
19692
|
const gasLimit = estimatedGas ?? WITHDRAW_BTC_GAS_CEILING;
|
|
19693
|
+
await awaitSafeSubmissionWindow(
|
|
19694
|
+
Number(withdrawalParams.quantumTimestamp)
|
|
19695
|
+
);
|
|
19643
19696
|
tx = await signer.sendTransaction({
|
|
19644
19697
|
to: contractAddress,
|
|
19645
19698
|
data: calldata,
|
|
@@ -8,8 +8,9 @@ import { type Provider, type Signer, type TransactionResponse } from "ethers";
|
|
|
8
8
|
* estimateContractCallGasWithMargin() (real eth_estimateGas + 25% margin) on
|
|
9
9
|
* mainnet, so this value is NOT normally what gets submitted -- it only
|
|
10
10
|
* becomes the literal gasLimit if (a) the estimate comes back anomalously
|
|
11
|
-
* high, or (b) eth_estimateGas itself fails
|
|
12
|
-
*
|
|
11
|
+
* high, or (b) eth_estimateGas itself fails (some RPCs return bare 0x even
|
|
12
|
+
* for valid txs), in which case — after a static call proves the tx valid —
|
|
13
|
+
* this raw value is used as the gasLimit on any chain.
|
|
13
14
|
* Previously 10,000,000 with a comment claiming "mintUCD + LIT validation
|
|
14
15
|
* can exceed 7M gas" -- no evidence of that was found across 16 real mint
|
|
15
16
|
* transactions checked (1 mainnet, 15 recent Sepolia, 2026-07-02): the
|