@@ -90,24 +90,19 @@ impl SlotInfo {
9090 if length_byte & 1 == 0 {
9191 // Short string/bytes (less than 32 bytes)
9292 let length = ( length_byte >> 1 ) as usize ;
93- if length == 0 {
94- let empty = if matches ! ( actual_type, DynSolType :: String ) {
95- DynSolValue :: String ( String :: new ( ) )
96- } else {
97- DynSolValue :: Bytes ( Vec :: new ( ) )
98- } ;
99- return Some ( empty) ;
100- }
101-
102- // Data is stored in the same slot, left-aligned
103- let data = & value. 0 [ 0 ..length] ;
93+ // Extract data
94+ let data = if length == 0 { Vec :: new ( ) } else { value. 0 [ 0 ..length] . to_vec ( ) } ;
10495
96+ // Create the appropriate value based on type
10597 if matches ! ( actual_type, DynSolType :: String ) {
106- // For strings, convert bytes to UTF-8
107- String :: from_utf8 ( data. to_vec ( ) ) . ok ( ) . map ( DynSolValue :: String )
98+ let str_val = if data. is_empty ( ) {
99+ String :: new ( )
100+ } else {
101+ String :: from_utf8 ( data) . unwrap_or_default ( )
102+ } ;
103+ Some ( DynSolValue :: String ( str_val) )
108104 } else {
109- // For bytes, return raw bytes
110- Some ( DynSolValue :: Bytes ( data. to_vec ( ) ) )
105+ Some ( DynSolValue :: Bytes ( data) )
111106 }
112107 } else {
113108 // Long string/bytes (32 bytes or more)
@@ -141,17 +136,15 @@ impl SlotInfo {
141136 }
142137
143138 // Try to handle as long bytes/string
144- if let Some ( data ) = self . aggregate_bytes_or_strings ( base_slot, storage_values) {
145- // Decode the full long bytes/string value
146- if matches ! ( self . slot_type . dyn_sol_type , DynSolType :: String ) {
147- let str_val = String :: from_utf8 ( data) . unwrap_or_default ( ) ;
148- Some ( DynSolValue :: String ( str_val ) )
149- } else {
150- Some ( DynSolValue :: Bytes ( data ) )
139+ self . aggregate_bytes_or_strings ( base_slot, storage_values) . map ( |data| {
140+ match self . slot_type . dyn_sol_type {
141+ DynSolType :: String => {
142+ DynSolValue :: String ( String :: from_utf8 ( data) . unwrap_or_default ( ) )
143+ }
144+ DynSolType :: Bytes => DynSolValue :: Bytes ( data ) ,
145+ _ => unreachable ! ( ) ,
151146 }
152- } else {
153- None
154- }
147+ } )
155148 }
156149
157150 /// Decodes both previous and new [`DynSolType::Bytes`] or [`DynSolType::String`] values
@@ -170,34 +163,27 @@ impl SlotInfo {
170163
171164 // Get both previous and new values from the storage accesses
172165 if let Some ( ( prev_base_value, new_base_value) ) = storage_accesses. get ( base_slot) {
173- let prev_length_byte = prev_base_value. 0 [ 31 ] ;
174- let new_length_byte = new_base_value. 0 [ 31 ] ;
166+ // Reusable closure to decode bytes/string based on length encoding
167+ let mut decode_value = |base_value : B256 , is_new : bool | {
168+ let length_byte = base_value. 0 [ 31 ] ;
169+ if length_byte & 1 == 1 {
170+ // Long bytes/string - aggregate from multiple slots
171+ let value_map = storage_accesses
172+ . iter ( )
173+ . map ( |( slot, ( prev, new) ) | ( * slot, if is_new { * new } else { * prev } ) )
174+ . collect :: < B256Map < _ > > ( ) ;
175+ self . decode_bytes_or_string ( base_slot, & value_map)
176+ } else {
177+ // Short bytes/string - decode directly from base slot
178+ self . decode ( base_value)
179+ }
180+ } ;
175181
176182 // Decode previous value
177- let prev_decoded = if prev_length_byte & 1 == 1 {
178- // Long bytes/string - aggregate from multiple slots
179- let prev_map = storage_accesses
180- . iter ( )
181- . map ( |( slot, ( prev_val, _) ) | ( * slot, * prev_val) )
182- . collect :: < B256Map < _ > > ( ) ;
183- self . decode_bytes_or_string ( base_slot, & prev_map)
184- } else {
185- // Short bytes/string - decode directly from base slot
186- self . decode ( * prev_base_value)
187- } ;
183+ let prev_decoded = decode_value ( * prev_base_value, false ) ;
188184
189- // Decode new value and populate members if it's long
190- let new_decoded = if new_length_byte & 1 == 1 {
191- // Long bytes/string - aggregate from multiple slots
192- let new_map = storage_accesses
193- . iter ( )
194- . map ( |( slot, ( _, new_val) ) | ( * slot, * new_val) )
195- . collect :: < B256Map < _ > > ( ) ;
196- self . decode_bytes_or_string ( base_slot, & new_map)
197- } else {
198- // Short bytes/string - decode directly from base slot
199- self . decode ( * new_base_value)
200- } ;
185+ // Decode new value
186+ let new_decoded = decode_value ( * new_base_value, true ) ;
201187
202188 // Set decoded values if both were successfully decoded
203189 if let ( Some ( prev) , Some ( new) ) = ( prev_decoded, new_decoded) {
0 commit comments