@@ -208,6 +208,10 @@ impl TestByEmulationHarness {
208208 pub fn step_over ( & mut self ) -> Result < EmulatorEvent , EmulationError > {
209209 self . emulator . step_over ( )
210210 }
211+
212+ fn reset ( & mut self ) {
213+ self . emulator . reset ( ) ;
214+ }
211215}
212216
213217#[ test]
@@ -453,6 +457,75 @@ fn i32_checked_neg() {
453457 harness. invoke ( neg, & [ min] ) . expect ( "execution failed" ) ;
454458}
455459
460+ #[ test]
461+ fn codegen_mem_store_sw ( ) {
462+ const MEMORY_SIZE_BYTES : u32 = 1048576 * 10 ;
463+ const MEMORY_SIZE_VM_WORDS : u32 = MEMORY_SIZE_BYTES / 16 ;
464+ let mut harness = TestByEmulationHarness :: with_emulator_config (
465+ MEMORY_SIZE_VM_WORDS as usize ,
466+ Emulator :: DEFAULT_HEAP_START as usize ,
467+ Emulator :: DEFAULT_LOCALS_START as usize ,
468+ true ,
469+ ) ;
470+ let mut builder = ProgramBuilder :: new ( & harness. context . session . diagnostics ) ;
471+ let mut mb = builder. module ( "test" ) ;
472+ let id = {
473+ let mut fb = mb
474+ . function (
475+ "store_load_sw" ,
476+ Signature :: new (
477+ [ AbiParam :: new ( Type :: U32 ) , AbiParam :: new ( Type :: U32 ) ] ,
478+ [ AbiParam :: new ( Type :: U32 ) ] ,
479+ ) ,
480+ )
481+ . expect ( "unexpected symbol conflict" ) ;
482+ let entry = fb. current_block ( ) ;
483+ let ( ptr_u32, value) = {
484+ let args = fb. block_params ( entry) ;
485+ ( args[ 0 ] , args[ 1 ] )
486+ } ;
487+ let ptr = fb. ins ( ) . inttoptr ( ptr_u32, Type :: Ptr ( Type :: U32 . into ( ) ) , SourceSpan :: UNKNOWN ) ;
488+ fb. ins ( ) . store ( ptr, value, SourceSpan :: UNKNOWN ) ;
489+ let loaded_value = fb. ins ( ) . load ( ptr, SourceSpan :: UNKNOWN ) ;
490+ fb. ins ( ) . ret ( Some ( loaded_value) , SourceSpan :: UNKNOWN ) ;
491+ fb. build ( ) . expect ( "unexpected error building function" )
492+ } ;
493+
494+ mb. build ( ) . expect ( "unexpected error constructing test module" ) ;
495+
496+ let program = builder. with_entrypoint ( id) . link ( ) . expect ( "failed to link program" ) ;
497+
498+ let mut compiler = MasmCompiler :: new ( & harness. context . session ) ;
499+ let program = compiler. compile ( program) . expect ( "compilation failed" ) . freeze ( ) ;
500+
501+ eprintln ! ( "{}" , program) ;
502+
503+ let mut test = |ptr : u32 , value : u32 | {
504+ eprintln ! ( "---------------------------------" ) ;
505+ eprintln ! ( "testing ptr: {ptr}, value: {value}" ) ;
506+ eprintln ! ( "---------------------------------" ) ;
507+ let mut stack = harness
508+ . execute_program ( program. clone ( ) , & [ Felt :: new ( ptr as u64 ) , Felt :: new ( value as u64 ) ] )
509+ . expect ( "execution failed" ) ;
510+ assert_eq ! ( stack. len( ) , 1 ) ;
511+ assert_eq ! (
512+ stack. pop( ) ,
513+ Some ( Felt :: new( value as u64 ) ) ,
514+ "failed stor_sw->load_sw at ptr: {ptr}"
515+ ) ;
516+ harness. reset ( ) ;
517+ } ;
518+
519+ // TODO: on ptr % 4 == 0 load_sw always returns 0
520+ // test(0, 999);
521+ // test(8, 999);
522+ test ( 1 , 42 ) ;
523+ test ( 25 , u32:: MAX ) ;
524+ // assert in replace_element fails
525+ test ( 64 , 42 ) ;
526+ test ( MEMORY_SIZE_BYTES - 4 , u32:: MAX ) ;
527+ }
528+
456529macro_rules! proptest_unary_numeric_op {
457530 ( $ty_name: ident :: $op: ident, $ty: ty => $ret: ty, $rust_op: ident) => {
458531 proptest_unary_numeric_op_impl!( $ty_name :: $op, $ty => $ret, $rust_op, 0 ..$ty_name:: MAX ) ;
0 commit comments