Skip to content

Commit b82ea0d

Browse files
author
Lorenzo Feroleto
committed
fix(SharedMemory): restore cfg memory limit
1 parent b6ed337 commit b82ea0d

File tree

3 files changed

+33
-1
lines changed

3 files changed

+33
-1
lines changed

crates/interpreter/src/instructions/macros.rs

+6
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,12 @@ macro_rules! shared_memory_resize {
5555
if let Some(new_size) =
5656
crate::interpreter::next_multiple_of_32($offset.saturating_add($len))
5757
{
58+
#[cfg(feature = "memory_limit")]
59+
if $interp.shared_memory.limit_reached(new_size) {
60+
$interp.instruction_result = InstructionResult::MemoryLimitOOG;
61+
return;
62+
}
63+
5864
if new_size > $interp.shared_memory.len() {
5965
if crate::USE_GAS {
6066
let num_bytes = new_size / 32;

crates/interpreter/src/interpreter/shared_memory.rs

+24-1
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,9 @@ pub struct SharedMemory {
1818
checkpoints: Vec<usize>,
1919
/// How much memory has been used in the current context
2020
current_len: usize,
21+
/// Memory limit. See [`crate::CfgEnv`].
22+
#[cfg(feature = "memory_limit")]
23+
pub memory_limit: u64,
2124
}
2225

2326
impl fmt::Debug for SharedMemory {
@@ -45,9 +48,29 @@ impl SharedMemory {
4548
data: Vec::with_capacity(4 * 1024), // from evmone
4649
checkpoints: Vec::with_capacity(32),
4750
current_len: 0,
51+
#[cfg(feature = "memory_limit")]
52+
memory_limit: u64::MAX,
4853
}
4954
}
5055

56+
/// Allocate memory to be shared between calls, with `memory_limit`
57+
/// as upper bound for allocation size.
58+
/// Initial capacity is 4KiB which is expanded if needed
59+
#[cfg(feature = "memory_limit")]
60+
pub fn new_with_memory_limit(memory_limit: u64) -> Self {
61+
Self {
62+
memory_limit,
63+
..Self::new()
64+
}
65+
}
66+
67+
/// Returns true if the `new_size` for the current context memory will
68+
/// make the shared buffer length exceed the `memory_limit`
69+
#[cfg(feature = "memory_limit")]
70+
pub fn limit_reached(&self, new_size: usize) -> bool {
71+
(self.last_checkpoint() + new_size) as u64 > self.memory_limit
72+
}
73+
5174
/// Prepares the shared memory for a new context
5275
pub fn new_context_memory(&mut self) {
5376
let base_offset = self.last_checkpoint();
@@ -221,7 +244,7 @@ impl SharedMemory {
221244
/// Get the last memory checkpoint
222245
#[inline(always)]
223246
fn last_checkpoint(&self) -> usize {
224-
*self.checkpoints.last().unwrap_or(&0)
247+
self.checkpoints.last().cloned().unwrap_or_default()
225248
}
226249
}
227250

crates/revm/src/evm_impl.rs

+3
Original file line numberDiff line numberDiff line change
@@ -288,6 +288,9 @@ impl<'a, GSPEC: Spec, DB: Database, const INSPECT: bool> Transact<DB::Error>
288288

289289
let transact_gas_limit = tx_gas_limit - initial_gas_spend;
290290

291+
#[cfg(feature = "memory_limit")]
292+
let mut shared_memory = SharedMemory::new_with_memory_limit(self.data.env.cfg.memory_limit);
293+
#[cfg(not(feature = "memory_limit"))]
291294
let mut shared_memory = SharedMemory::new();
292295

293296
// call inner handling of call/create

0 commit comments

Comments
 (0)