Skip to content

Commit 157a971

Browse files
authored
fix(wallets): add gas limit margin to handle WebAuthn/P256 signing (#14416)
fix(wallets): add gas limit margin to handle WebAuthn/P256 signing
1 parent 72feeda commit 157a971

5 files changed

Lines changed: 53 additions & 3 deletions

File tree

crates/cast/src/cmd/erc20.rs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ use foundry_common::{
2323
fmt::{UIfmt, UIfmtReceiptExt},
2424
provider::{ProviderBuilder, RetryProviderWithSigner},
2525
shell,
26+
tempo::TEMPO_BROWSER_GAS_BUFFER,
2627
};
2728
#[doc(hidden)]
2829
pub use foundry_config::{Chain, utils::*};
@@ -591,7 +592,16 @@ where
591592
}
592593

593594
if tx.gas_limit().is_none() {
594-
tx.set_gas_limit(provider.estimate_gas(tx.clone()).await?);
595+
let mut estimated = provider.estimate_gas(tx.clone()).await?;
596+
597+
// Browser wallets may sign with P256/WebAuthn instead of secp256k1, which
598+
// costs more gas for signature verification on Tempo chains. Add a
599+
// conservative buffer since we can't determine the signature type beforehand.
600+
if chain.is_tempo() {
601+
estimated += TEMPO_BROWSER_GAS_BUFFER;
602+
}
603+
604+
tx.set_gas_limit(estimated);
595605
}
596606

597607
Ok(())

crates/cast/src/cmd/send.rs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ use foundry_common::{
1313
FoundryTransactionBuilder,
1414
fmt::{UIfmt, UIfmtReceiptExt},
1515
provider::ProviderBuilder,
16+
tempo::TEMPO_BROWSER_GAS_BUFFER,
1617
};
1718
use foundry_wallets::{TempoAccessKeyConfig, WalletSigner};
1819
use tempo_alloy::TempoNetwork;
@@ -258,7 +259,18 @@ impl SendTxArgs {
258259
// Case 2:
259260
// Browser wallet signs and sends the transaction in one step.
260261
} else if let Some(browser) = browser {
261-
let (tx_request, _) = builder.build(browser.address()).await?;
262+
let chain = builder.chain();
263+
let (mut tx_request, _) = builder.build(browser.address()).await?;
264+
265+
// Browser wallets may sign with P256/WebAuthn instead of secp256k1, which
266+
// costs more gas for signature verification on Tempo chains. Add a
267+
// conservative buffer since we can't determine the signature type beforehand.
268+
if chain.is_tempo()
269+
&& let Some(gas) = tx_request.gas_limit()
270+
{
271+
tx_request.set_gas_limit(gas + TEMPO_BROWSER_GAS_BUFFER);
272+
}
273+
262274
let tx_hash = browser.send_transaction_via_browser(tx_request).await?;
263275

264276
let cast = CastTxSender::new(&provider);

crates/cast/src/tx.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -398,6 +398,13 @@ pub struct CastTxBuilder<N: Network, P, S> {
398398
state: S,
399399
}
400400

401+
impl<N: Network, P, S> CastTxBuilder<N, P, S> {
402+
/// Returns the resolved chain for this builder.
403+
pub const fn chain(&self) -> Chain {
404+
self.chain
405+
}
406+
}
407+
401408
impl<N: Network, P: Provider<N>> CastTxBuilder<N, P, InitState>
402409
where
403410
N::TransactionRequest: FoundryTransactionBuilder<N>,

crates/common/src/tempo/mod.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,3 +2,14 @@
22
33
mod keystore;
44
pub use keystore::*;
5+
6+
/// Conservative gas buffer for browser wallet transactions on Tempo chains.
7+
///
8+
/// Browser wallets may sign with P256 or WebAuthn instead of secp256k1, which costs more gas
9+
/// for signature verification. Since we can't determine the signature type before signing,
10+
/// we add the worst-case (WebAuthn) overhead:
11+
/// - P256: +5,000 gas (P256 precompile cost minus ecrecover savings)
12+
/// - WebAuthn: ~6,500 gas (P256 cost + calldata for webauthn_data)
13+
///
14+
/// See <https://github.com/tempoxyz/tempo/blob/6ebf1a8/crates/revm/src/handler.rs#L108-L124>
15+
pub const TEMPO_BROWSER_GAS_BUFFER: u64 = 7_000;

crates/forge/src/cmd/create.rs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ use foundry_common::{
2121
fmt::parse_tokens,
2222
provider::ProviderBuilder,
2323
shell,
24+
tempo::TEMPO_BROWSER_GAS_BUFFER,
2425
};
2526
use foundry_compilers::{
2627
ArtifactId, artifacts::BytecodeObject, info::ContractInfo, utils::canonicalize,
@@ -433,7 +434,16 @@ impl CreateArgs {
433434
}
434435

435436
if self.tx.gas_limit.is_none() {
436-
deployer.tx.set_gas_limit(provider.estimate_gas(deployer.tx.clone()).await?);
437+
let mut estimated = provider.estimate_gas(deployer.tx.clone()).await?;
438+
439+
// Browser wallets may sign with P256/WebAuthn instead of secp256k1, which
440+
// costs more gas for signature verification on Tempo chains. Add a
441+
// conservative buffer since we can't determine the signature type beforehand.
442+
if browser_signer.is_some() && chain.is_tempo() {
443+
estimated += TEMPO_BROWSER_GAS_BUFFER;
444+
}
445+
446+
deployer.tx.set_gas_limit(estimated);
437447
}
438448

439449
if is_legacy {

0 commit comments

Comments
 (0)