Skip to content

Commit

Permalink
add get_u32_range to impl VirtualMachine add get_u32 and get_u32_rang…
Browse files Browse the repository at this point in the history
…e to impl Memory
  • Loading branch information
ohad-nir-starkware committed Feb 5, 2025
1 parent e15c6e6 commit 4bd3a02
Show file tree
Hide file tree
Showing 4 changed files with 62 additions and 0 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@

#### Upcoming Changes

* feat: add `get_u32_range` to `impl VirtualMachine` add `get_u32` and `get_u32_range` to `impl Memory` [#1936](https://github.com/lambdaclass/cairo-vm/pull/1936)

* feat: add the field `opcode_extension` to the structure of `Instruction` [#1933](https://github.com/lambdaclass/cairo-vm/pull/1933)

* fix(BREAKING): Fix no trace padding flow in proof mode [#1909](https://github.com/lambdaclass/cairo-vm/pull/1909)
Expand Down
2 changes: 2 additions & 0 deletions vm/src/vm/errors/memory_errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,8 @@ pub enum MemoryError {
UnrelocatedMemory,
#[error("Malformed public memory")]
MalformedPublicMemory,
#[error("Expected u32 valued at address {0} to be u32")]
ExpectedU32(Box<Relocatable>),
}

#[derive(Debug, PartialEq, Eq, Error)]
Expand Down
14 changes: 14 additions & 0 deletions vm/src/vm/vm_core.rs
Original file line number Diff line number Diff line change
Expand Up @@ -929,6 +929,11 @@ impl VirtualMachine {
self.segments.memory.get_integer_range(addr, size)
}

/// Gets n u32 values from memory starting from addr (n being size),
pub fn get_u32_range(&self, addr: Relocatable, size: usize) -> Result<Vec<u32>, MemoryError> {
self.segments.memory.get_u32_range(addr, size)
}

pub fn get_range_check_builtin(
&self,
) -> Result<&RangeCheckBuiltinRunner<RC_N_PARTS_STANDARD>, VirtualMachineError> {
Expand Down Expand Up @@ -4373,6 +4378,15 @@ mod tests {
);
}

#[test]
#[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
fn get_u32_range_ok() {
let mut vm = vm!();
vm.segments.memory = memory![((0, 0), 0), ((0, 1), 1), ((0, 2), 4294967295), ((0, 3), 3)];
let expected_vector = vec![1, 4294967295];
assert_eq!(vm.get_u32_range((0, 1).into(), 2), Ok(expected_vector));
}

#[test]
#[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
fn get_traceback_entries_bad_usort() {
Expand Down
44 changes: 44 additions & 0 deletions vm/src/vm/vm_memory/memory.rs
Original file line number Diff line number Diff line change
Expand Up @@ -414,6 +414,21 @@ impl Memory {
}
}

/// Gets a u32 value from memory address.
/// Returns an Error if the value at the memory address is missing or not a u32.
pub fn get_u32(&self, key: Relocatable) -> Result<u32, MemoryError> {
let value = Cow::into_owned(self.get_integer(key)?);
let le_digits = value.to_le_digits();
if le_digits[0] >= (1_u64 << 32)
|| le_digits[1] != 0
|| le_digits[2] != 0
|| le_digits[3] != 0
{
return Err(MemoryError::ExpectedU32(Box::new(key)));
}
Ok(le_digits[0] as u32)
}

/// Gets the value from memory address as a usize.
/// Returns an Error if the value at the memory address is missing not a Felt252, or can't be converted to usize.
pub fn get_usize(&self, key: Relocatable) -> Result<usize, MemoryError> {
Expand Down Expand Up @@ -623,6 +638,18 @@ impl Memory {
Ok(values)
}

/// Gets a range of u32 memory values from addr to addr + size
/// Fails if there if any of the values inside the range is missing (memory gap) or is not a u32
pub fn get_u32_range(&self, addr: Relocatable, size: usize) -> Result<Vec<u32>, MemoryError> {
let mut values = Vec::new();

for i in 0..size {
values.push(self.get_u32((addr + i)?)?);
}

Ok(values)
}

pub fn mark_as_accessed(&mut self, addr: Relocatable) {
let (i, j) = from_relocatable_to_indexes(addr);
let data = if addr.segment_index < 0 {
Expand Down Expand Up @@ -1135,6 +1162,23 @@ mod memory_tests {
);
}

#[test]
#[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
fn get_u32_too_big() {
let mut segments = MemorySegmentManager::new();
segments.add();
segments
.memory
.insert(Relocatable::from((0, 0)), &Felt252::from(1_u64 << 32))
.unwrap();
assert_matches!(
segments.memory.get_u32(Relocatable::from((0, 0))),
Err(MemoryError::ExpectedU32(
bx
)) if *bx == Relocatable::from((0, 0))
);
}

#[test]
#[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
fn default_memory() {
Expand Down

0 comments on commit 4bd3a02

Please sign in to comment.