cairo_vm/hint_processor/builtin_hint_processor/
segments.rs

1use crate::stdlib::{collections::HashMap, prelude::*};
2
3use crate::hint_processor::builtin_hint_processor::hint_utils::get_ptr_from_var_name;
4use crate::hint_processor::{
5    builtin_hint_processor::hint_utils::insert_value_from_var_name,
6    hint_processor_definition::HintReference,
7};
8use crate::serde::deserialize_program::ApTracking;
9use crate::vm::errors::hint_errors::HintError;
10use crate::vm::vm_core::VirtualMachine;
11
12/*
13Implements hint:
14%{ memory.add_relocation_rule(src_ptr=ids.src_ptr, dest_ptr=ids.dest_ptr) %}
15*/
16pub fn relocate_segment(
17    vm: &mut VirtualMachine,
18    ids_data: &HashMap<String, HintReference>,
19    ap_tracking: &ApTracking,
20) -> Result<(), HintError> {
21    let src_ptr = get_ptr_from_var_name("src_ptr", vm, ids_data, ap_tracking)?;
22    #[cfg(not(feature = "extensive_hints"))]
23    let dest_ptr = get_ptr_from_var_name("dest_ptr", vm, ids_data, ap_tracking)?;
24    #[cfg(feature = "extensive_hints")]
25    let dest_ptr = crate::hint_processor::builtin_hint_processor::hint_utils::get_maybe_relocatable_from_var_name("dest_ptr", vm, ids_data, ap_tracking)?;
26
27    vm.add_relocation_rule(src_ptr, dest_ptr)
28        .map_err(HintError::Memory)?;
29    Ok(())
30}
31
32/*
33This hint doesn't belong to the Cairo common library
34It's only added for testing proposes
35
36Implements hint:
37%{ ids.temporary_array = segments.add_temp_segment() %}
38*/
39pub fn temporary_array(
40    vm: &mut VirtualMachine,
41    ids_data: &HashMap<String, HintReference>,
42    ap_tracking: &ApTracking,
43) -> Result<(), HintError> {
44    let temp_segment = vm.add_temporary_segment();
45    insert_value_from_var_name("temporary_array", temp_segment, vm, ids_data, ap_tracking)?;
46
47    Ok(())
48}
49
50#[cfg(test)]
51mod tests {
52    use super::*;
53
54    use crate::{
55        any_box,
56        hint_processor::{
57            builtin_hint_processor::{
58                builtin_hint_processor_definition::{BuiltinHintProcessor, HintProcessorData},
59                hint_code,
60            },
61            hint_processor_definition::HintProcessorLogic,
62        },
63        utils::test_utils::*,
64    };
65    use assert_matches::assert_matches;
66
67    #[cfg(target_arch = "wasm32")]
68    use wasm_bindgen_test::*;
69
70    #[test]
71    #[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
72    fn run_relocate_segment() {
73        let hint_code = hint_code::RELOCATE_SEGMENT;
74        //Initialize vm
75        let mut vm = vm!();
76        //Initialize fp
77        vm.run_context.fp = 2;
78        //Insert ids into memory
79        vm.segments = segments![((1, 0), (-2, 0)), ((1, 1), (3, 0)), ((3, 0), 42)];
80
81        //Create ids_data & hint_data
82        let ids_data = ids_data!["src_ptr", "dest_ptr"];
83
84        //Execute the hint
85        assert_matches!(run_hint!(vm, ids_data, hint_code), Ok(()));
86
87        vm.segments
88            .memory
89            .relocate_memory()
90            .expect("Couldn't relocate memory.");
91    }
92
93    #[test]
94    #[cfg_attr(target_arch = "wasm32", wasm_bindgen_test)]
95    fn run_temporary_array() {
96        let hint_code = hint_code::TEMPORARY_ARRAY;
97        //Initialize vm
98        let mut vm = vm!();
99        vm.segments.add();
100        vm.segments.add();
101        //Initialize fp
102        vm.run_context.fp = 1;
103
104        //Create ids_data & hint_data
105        let ids_data = ids_data!["temporary_array"];
106
107        //Execute the hint
108        assert_matches!(run_hint!(vm, ids_data, hint_code), Ok(()));
109        check_memory!(vm.segments.memory, ((1, 0), (-1, 0)));
110    }
111}