traverse_solidity/
interpreter.rs

1//! Solidity Expression Interpreter
2//! 
3//! A Rust-based interpreter for Solidity expressions with focus on predicate evaluation.
4//! Evaluates boolean expressions, comparisons, and logical operations commonly used in smart contracts.
5//! 
6//! # Features
7//! 
8//! - **Predicate evaluation**: expressions that return boolean values
9//! - **Variable context**: support for variable bindings and lookups  
10//! - **Type system**: handle Solidity's basic types (bool, uint, int, string, address, bytes)
11//! - **Error handling**: comprehensive error reporting for runtime issues
12//! 
13//! # Supported Operations
14//! 
15//! - **Literals**: `true`, `false`, `42`, `"hello"`, `hex"deadbeef"`, `unicode"hello"`
16//! - **Binary ops**: `+`, `-`, `*`, `/`, `%`, `**`, `==`, `!=`, `<`, `<=`, `>`, `>=`, `&&`, `||`, `&`, `|`, `^`, `<<`, `>>`, `>>>`
17//! - **Unary ops**: `+`, `-`, `!`, `~`
18//! - **Conditional**: `condition ? true_expr : false_expr`
19//! - **Variables**: variable lookup with context management
20//! - **Built-ins**: `keccak256()`, `sha256()`, `ripemd160()`, `ecrecover()` (mock implementations)
21//! 
22//! # Value Types
23//! 
24//! - `Bool(bool)`: `true`, `false`
25//! - `UInt(u64)`: `0`, `42`, `1000`  
26//! - `Int(i64)`: `-1`, `0`, `42`
27//! - `String(String)`: `"hello"`, `"world"`
28//! - `Address(String)`: `"0x1234..."`
29//! - `Bytes(Vec<u8>)`: `[0x12, 0x34, ...]`
30//! - `Null`: null/undefined
31//! 
32//! # Boolean Conversion
33//! 
34//! All values convert to boolean for predicate evaluation:
35//! - `Bool(true)` → `true`, `Bool(false)` → `false`
36//! - `UInt(0)` → `false`, `UInt(n)` → `true`
37//! - `Int(0)` → `false`, `Int(n)` → `true`  
38//! - `String("")` → `false`, `String(s)` → `true`
39//! - `Address("0x0000...")` → `false`, other addresses → `true`
40//! - `Bytes([])` → `false`, non-empty bytes → `true`
41//! - `Null` → `false`
42//! 
43//! # Limitations
44//! 
45//! Intentional limitations for predicate evaluation:
46//! - No assignment operations (predicate evaluation shouldn 't mutate state)
47//! - No object creation (new expressions not supported)
48//! - No complex types (arrays/mappings/structs limited)
49//! - No member/index access (not yet implemented)
50//! 
51//! # Architecture
52//! 
53//! - **Parser integration**: uses existing Solidity parser to generate AST
54//! - **Context management**: maintains variable bindings and function definitions
55//! - **Type system**: runtime type checking and conversion
56//! - **Error propagation**: comprehensive error handling throughout evaluation
57//! - **Extensibility**: designed to be easily extended with new operations and types
58
59use crate::ast::*;
60use std::collections::HashMap;
61use std::fmt;
62
63#[derive(Debug, Clone, PartialEq)]
64pub enum Value {
65    Bool(bool),
66    UInt(u64),
67    Int(i64),
68    String(String),
69    Address(String),
70    Bytes(Vec<u8>),
71    Null,
72}
73
74impl Value {
75    pub fn to_bool(&self) -> Result<bool, InterpreterError> {
76        match self {
77            Value::Bool(b) => Ok(*b),
78            Value::UInt(n) => Ok(*n != 0),
79            Value::Int(n) => Ok(*n != 0),
80            Value::String(s) => Ok(!s.is_empty()),
81            Value::Address(addr) => Ok(addr != "0x0000000000000000000000000000000000000000"),
82            Value::Bytes(b) => Ok(!b.is_empty()),
83            Value::Null => Ok(false),
84        }
85    }
86
87    pub fn type_name(&self) -> &'static str {
88        match self {
89            Value::Bool(_) => "bool",
90            Value::UInt(_) => "uint",
91            Value::Int(_) => "int",
92            Value::String(_) => "string",
93            Value::Address(_) => "address",
94            Value::Bytes(_) => "bytes",
95            Value::Null => "null",
96        }
97    }
98}
99
100impl fmt::Display for Value {
101    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
102        match self {
103            Value::Bool(b) => write!(f, "{}", b),
104            Value::UInt(n) => write!(f, "{}", n),
105            Value::Int(n) => write!(f, "{}", n),
106            Value::String(s) => write!(f, "\"{}\"", s),
107            Value::Address(addr) => write!(f, "{}", addr),
108            Value::Bytes(b) => write!(f, "0x{}", hex::encode(b)),
109            Value::Null => write!(f, "null"),
110        }
111    }
112}
113
114#[derive(Debug, Clone, PartialEq)]
115pub enum InterpreterError {
116    UndefinedVariable(String),
117    TypeMismatch { expected: String, found: String },
118    UnsupportedOperation(String),
119    DivisionByZero,
120    InvalidLiteral(String),
121    FunctionNotFound(String),
122    InvalidArguments(String),
123    RuntimeError(String),
124}
125
126impl fmt::Display for InterpreterError {
127    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
128        match self {
129            InterpreterError::UndefinedVariable(name) => write!(f, "Undefined variable: {}", name),
130            InterpreterError::TypeMismatch { expected, found } => {
131                write!(f, "Type mismatch: expected {}, found {}", expected, found)
132            }
133            InterpreterError::UnsupportedOperation(op) => write!(f, "Unsupported operation: {}", op),
134            InterpreterError::DivisionByZero => write!(f, "Division by zero"),
135            InterpreterError::InvalidLiteral(lit) => write!(f, "Invalid literal: {}", lit),
136            InterpreterError::FunctionNotFound(name) => write!(f, "Function not found: {}", name),
137            InterpreterError::InvalidArguments(msg) => write!(f, "Invalid arguments: {}", msg),
138            InterpreterError::RuntimeError(msg) => write!(f, "Runtime error: {}", msg),
139        }
140    }
141}
142
143impl std::error::Error for InterpreterError {}
144
145#[derive(Debug, Clone)]
146pub struct InterpreterContext {
147    variables: HashMap<String, Value>,
148    functions: HashMap<String, BuiltinFunction>,
149}
150
151impl Default for InterpreterContext {
152    fn default() -> Self {
153        let mut context = Self {
154            variables: HashMap::new(),
155            functions: HashMap::new(),
156        };
157        context.register_builtin_functions();
158        context
159    }
160}
161
162impl InterpreterContext {
163    pub fn new() -> Self {
164        Self::default()
165    }
166
167    pub fn set_variable(&mut self, name: String, value: Value) {
168        self.variables.insert(name, value);
169    }
170
171    pub fn get_variable(&self, name: &str) -> Option<&Value> {
172        self.variables.get(name)
173    }
174
175    fn register_builtin_functions(&mut self) {
176        self.functions.insert("keccak256".to_string(), BuiltinFunction::Keccak256);
177        self.functions.insert("sha256".to_string(), BuiltinFunction::Sha256);
178        self.functions.insert("ripemd160".to_string(), BuiltinFunction::Ripemd160);
179        self.functions.insert("ecrecover".to_string(), BuiltinFunction::Ecrecover);
180    }
181
182    pub fn get_function(&self, name: &str) -> Option<&BuiltinFunction> {
183        self.functions.get(name)
184    }
185}
186
187#[derive(Debug, Clone, PartialEq)]
188pub enum BuiltinFunction {
189    Keccak256,
190    Sha256,
191    Ripemd160,
192    Ecrecover,
193}
194
195#[derive(Debug)]
196pub struct SolidityInterpreter {
197    context: InterpreterContext,
198}
199
200impl Default for SolidityInterpreter {
201    fn default() -> Self {
202        Self::new()
203    }
204}
205
206impl SolidityInterpreter {
207    pub fn new() -> Self {
208        Self {
209            context: InterpreterContext::new(),
210        }
211    }
212
213    pub fn with_context(context: InterpreterContext) -> Self {
214        Self { context }
215    }
216
217    pub fn context_mut(&mut self) -> &mut InterpreterContext {
218        &mut self.context
219    }
220
221    pub fn context(&self) -> &InterpreterContext {
222        &self.context
223    }
224
225    pub fn evaluate(&self, expr: &Expression) -> Result<Value, InterpreterError> {
226        match expr {
227            Expression::Literal(lit) => self.evaluate_literal(lit),
228            Expression::Identifier(name) => self.evaluate_identifier(name),
229            Expression::Binary(bin_expr) => self.evaluate_binary_expression(bin_expr),
230            Expression::Unary(unary_expr) => self.evaluate_unary_expression(unary_expr),
231            Expression::FunctionCall(call_expr) => self.evaluate_function_call(call_expr),
232            Expression::MemberAccess(member_expr) => self.evaluate_member_access(member_expr),
233            Expression::IndexAccess(index_expr) => self.evaluate_index_access(index_expr),
234            Expression::Conditional(cond_expr) => self.evaluate_conditional(cond_expr),
235            Expression::Tuple(tuple_expr) => self.evaluate_tuple(tuple_expr),
236            Expression::Array(array_expr) => self.evaluate_array(array_expr),
237            Expression::TypeConversion(conv_expr) => self.evaluate_type_conversion(conv_expr),
238            Expression::Assignment(_) => Err(InterpreterError::UnsupportedOperation(
239                "Assignment expressions are not supported in predicate evaluation".to_string(),
240            )),
241            Expression::New(_) => Err(InterpreterError::UnsupportedOperation(
242                "New expressions are not supported in predicate evaluation".to_string(),
243            )),
244        }
245    }
246
247    pub fn evaluate_predicate(&self, expr: &Expression) -> Result<bool, InterpreterError> {
248        let value = self.evaluate(expr)?;
249        value.to_bool()
250    }
251
252    fn evaluate_literal(&self, literal: &Literal) -> Result<Value, InterpreterError> {
253        match literal {
254            Literal::Boolean(b) => Ok(Value::Bool(*b)),
255            Literal::Number(num_lit) => self.evaluate_number_literal(num_lit),
256            Literal::String(str_lit) => Ok(Value::String(str_lit.value.clone())),
257            Literal::HexString(hex_lit) => self.evaluate_hex_string_literal(hex_lit),
258            Literal::UnicodeString(unicode_lit) => Ok(Value::String(unicode_lit.value.clone())),
259        }
260    }
261
262    fn evaluate_number_literal(&self, num_lit: &NumberLiteral) -> Result<Value, InterpreterError> {
263        let trimmed_value = num_lit.value.trim();
264        if let Ok(uint_val) = trimmed_value.parse::<u64>() {
265            Ok(Value::UInt(uint_val))
266        } else if let Ok(int_val) = trimmed_value.parse::<i64>() {
267            Ok(Value::Int(int_val))
268        } else {
269            Err(InterpreterError::InvalidLiteral(format!(
270                "Cannot parse number: {}",
271                num_lit.value
272            )))
273        }
274    }
275
276    fn evaluate_hex_string_literal(&self, hex_lit: &HexStringLiteral) -> Result<Value, InterpreterError> {
277        let hex_str = hex_lit.value.strip_prefix("0x").unwrap_or(&hex_lit.value);
278        
279        // Try to decode as bytes
280        match hex::decode(hex_str) {
281            Ok(bytes) => Ok(Value::Bytes(bytes)),
282            Err(_) => Err(InterpreterError::InvalidLiteral(format!(
283                "Invalid hex string: {}",
284                hex_lit.value
285            ))),
286        }
287    }
288
289    fn evaluate_identifier(&self, name: &str) -> Result<Value, InterpreterError> {
290        self.context
291            .get_variable(name)
292            .cloned()
293            .ok_or_else(|| InterpreterError::UndefinedVariable(name.to_string()))
294    }
295
296    fn evaluate_binary_expression(&self, bin_expr: &BinaryExpression) -> Result<Value, InterpreterError> {
297        let left = self.evaluate(&bin_expr.left)?;
298        let right = self.evaluate(&bin_expr.right)?;
299
300        match &bin_expr.operator {
301            BinaryOperator::Add => self.evaluate_add(&left, &right),
302            BinaryOperator::Sub => self.evaluate_sub(&left, &right),
303            BinaryOperator::Mul => self.evaluate_mul(&left, &right),
304            BinaryOperator::Div => self.evaluate_div(&left, &right),
305            BinaryOperator::Mod => self.evaluate_mod(&left, &right),
306            BinaryOperator::Exp => self.evaluate_exp(&left, &right),
307            BinaryOperator::Equal => Ok(Value::Bool(self.values_equal(&left, &right))),
308            BinaryOperator::NotEqual => Ok(Value::Bool(!self.values_equal(&left, &right))),
309            BinaryOperator::LessThan => self.evaluate_less_than(&left, &right),
310            BinaryOperator::LessThanOrEqual => self.evaluate_less_than_or_equal(&left, &right),
311            BinaryOperator::GreaterThan => self.evaluate_greater_than(&left, &right),
312            BinaryOperator::GreaterThanOrEqual => self.evaluate_greater_than_or_equal(&left, &right),
313            BinaryOperator::And => self.evaluate_logical_and(&left, &right),
314            BinaryOperator::Or => self.evaluate_logical_or(&left, &right),
315            BinaryOperator::BitAnd => self.evaluate_bit_and(&left, &right),
316            BinaryOperator::BitOr => self.evaluate_bit_or(&left, &right),
317            BinaryOperator::BitXor => self.evaluate_bit_xor(&left, &right),
318            BinaryOperator::ShiftLeft => self.evaluate_shift_left(&left, &right),
319            BinaryOperator::ShiftRight => self.evaluate_shift_right(&left, &right),
320            BinaryOperator::ShiftRightArithmetic => self.evaluate_shift_right_arithmetic(&left, &right),
321        }
322    }
323
324    fn evaluate_unary_expression(&self, unary_expr: &UnaryExpression) -> Result<Value, InterpreterError> {
325        let operand = self.evaluate(&unary_expr.operand)?;
326
327        match &unary_expr.operator {
328            UnaryOperator::Plus => Ok(operand), // Unary plus is a no-op
329            UnaryOperator::Minus => self.evaluate_unary_minus(&operand),
330            UnaryOperator::Not => self.evaluate_logical_not(&operand),
331            UnaryOperator::BitNot => self.evaluate_bit_not(&operand),
332            UnaryOperator::Increment | UnaryOperator::Decrement => {
333                Err(InterpreterError::UnsupportedOperation(
334                    "Increment/decrement operators are not supported in predicate evaluation".to_string(),
335                ))
336            }
337            UnaryOperator::Delete => Err(InterpreterError::UnsupportedOperation(
338                "Delete operator is not supported in predicate evaluation".to_string(),
339            )),
340        }
341    }
342
343    fn evaluate_function_call(&self, call_expr: &FunctionCallExpression) -> Result<Value, InterpreterError> {
344        // For now, we only support built-in functions identified by simple identifiers
345        if let Expression::Identifier(func_name) = &*call_expr.function {
346            if let Some(builtin_func) = self.context.get_function(func_name) {
347                let args: Result<Vec<Value>, InterpreterError> = call_expr
348                    .arguments
349                    .iter()
350                    .map(|arg| self.evaluate(arg))
351                    .collect();
352                let args = args?;
353                return self.evaluate_builtin_function(builtin_func, &args);
354            }
355        }
356
357        Err(InterpreterError::FunctionNotFound(
358            "Complex function calls are not yet supported".to_string(),
359        ))
360    }
361
362    fn evaluate_member_access(&self, member_expr: &MemberAccessExpression) -> Result<Value, InterpreterError> {
363        let _object = self.evaluate(&member_expr.object)?;
364        // For now, we don't support member access in predicate evaluation
365        Err(InterpreterError::UnsupportedOperation(
366            "Member access is not yet supported in predicate evaluation".to_string(),
367        ))
368    }
369
370    fn evaluate_index_access(&self, index_expr: &IndexAccessExpression) -> Result<Value, InterpreterError> {
371        let _object = self.evaluate(&index_expr.object)?;
372        // For now, we don't support index access in predicate evaluation
373        Err(InterpreterError::UnsupportedOperation(
374            "Index access is not yet supported in predicate evaluation".to_string(),
375        ))
376    }
377
378    fn evaluate_conditional(&self, cond_expr: &ConditionalExpression) -> Result<Value, InterpreterError> {
379        let condition = self.evaluate(&cond_expr.condition)?;
380        let condition_bool = condition.to_bool()?;
381
382        if condition_bool {
383            self.evaluate(&cond_expr.true_expr)
384        } else {
385            self.evaluate(&cond_expr.false_expr)
386        }
387    }
388
389    fn evaluate_tuple(&self, tuple_expr: &TupleExpression) -> Result<Value, InterpreterError> {
390        // For predicate evaluation, we don't support tuples
391        Err(InterpreterError::UnsupportedOperation(
392            format!("Tuple expressions are not supported in predicate evaluation (found {} elements)", 
393                   tuple_expr.elements.len())
394        ))
395    }
396
397    fn evaluate_array(&self, array_expr: &ArrayExpression) -> Result<Value, InterpreterError> {
398        // For predicate evaluation, we don't support arrays
399        Err(InterpreterError::UnsupportedOperation(
400            format!("Array expressions are not supported in predicate evaluation (found {} elements)", 
401                   array_expr.elements.len())
402        ))
403    }
404
405    fn evaluate_type_conversion(&self, conv_expr: &TypeConversionExpression) -> Result<Value, InterpreterError> {
406        let value = self.evaluate(&conv_expr.expression)?;
407        // For now, we don't support type conversions in predicate evaluation
408        Err(InterpreterError::UnsupportedOperation(
409            format!("Type conversion is not yet supported in predicate evaluation (converting {} to type)", 
410                   value.type_name())
411        ))
412    }
413
414    fn evaluate_add(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
415        match (left, right) {
416            (Value::UInt(a), Value::UInt(b)) => Ok(Value::UInt(a + b)),
417            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a + b)),
418            (Value::UInt(a), Value::Int(b)) => Ok(Value::Int(*a as i64 + b)),
419            (Value::Int(a), Value::UInt(b)) => Ok(Value::Int(a + *b as i64)),
420            (Value::String(a), Value::String(b)) => Ok(Value::String(format!("{}{}", a, b))),
421            _ => Err(InterpreterError::TypeMismatch {
422                expected: "numeric or string".to_string(),
423                found: format!("{} and {}", left.type_name(), right.type_name()),
424            }),
425        }
426    }
427
428    fn evaluate_sub(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
429        match (left, right) {
430            (Value::UInt(a), Value::UInt(b)) => {
431                if a >= b {
432                    Ok(Value::UInt(a - b))
433                } else {
434                    Ok(Value::Int(*a as i64 - *b as i64))
435                }
436            }
437            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a - b)),
438            (Value::UInt(a), Value::Int(b)) => Ok(Value::Int(*a as i64 - b)),
439            (Value::Int(a), Value::UInt(b)) => Ok(Value::Int(a - *b as i64)),
440            _ => Err(InterpreterError::TypeMismatch {
441                expected: "numeric".to_string(),
442                found: format!("{} and {}", left.type_name(), right.type_name()),
443            }),
444        }
445    }
446
447    fn evaluate_mul(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
448        match (left, right) {
449            (Value::UInt(a), Value::UInt(b)) => Ok(Value::UInt(a * b)),
450            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a * b)),
451            (Value::UInt(a), Value::Int(b)) => Ok(Value::Int(*a as i64 * b)),
452            (Value::Int(a), Value::UInt(b)) => Ok(Value::Int(a * *b as i64)),
453            _ => Err(InterpreterError::TypeMismatch {
454                expected: "numeric".to_string(),
455                found: format!("{} and {}", left.type_name(), right.type_name()),
456            }),
457        }
458    }
459
460    fn evaluate_div(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
461        match (left, right) {
462            (Value::UInt(a), Value::UInt(b)) => {
463                if *b == 0 {
464                    Err(InterpreterError::DivisionByZero)
465                } else {
466                    Ok(Value::UInt(a / b))
467                }
468            }
469            (Value::Int(a), Value::Int(b)) => {
470                if *b == 0 {
471                    Err(InterpreterError::DivisionByZero)
472                } else {
473                    Ok(Value::Int(a / b))
474                }
475            }
476            (Value::UInt(a), Value::Int(b)) => {
477                if *b == 0 {
478                    Err(InterpreterError::DivisionByZero)
479                } else {
480                    Ok(Value::Int(*a as i64 / b))
481                }
482            }
483            (Value::Int(a), Value::UInt(b)) => {
484                if *b == 0 {
485                    Err(InterpreterError::DivisionByZero)
486                } else {
487                    Ok(Value::Int(a / *b as i64))
488                }
489            }
490            _ => Err(InterpreterError::TypeMismatch {
491                expected: "numeric".to_string(),
492                found: format!("{} and {}", left.type_name(), right.type_name()),
493            }),
494        }
495    }
496
497    fn evaluate_mod(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
498        match (left, right) {
499            (Value::UInt(a), Value::UInt(b)) => {
500                if *b == 0 {
501                    Err(InterpreterError::DivisionByZero)
502                } else {
503                    Ok(Value::UInt(a % b))
504                }
505            }
506            (Value::Int(a), Value::Int(b)) => {
507                if *b == 0 {
508                    Err(InterpreterError::DivisionByZero)
509                } else {
510                    Ok(Value::Int(a % b))
511                }
512            }
513            _ => Err(InterpreterError::TypeMismatch {
514                expected: "numeric".to_string(),
515                found: format!("{} and {}", left.type_name(), right.type_name()),
516            }),
517        }
518    }
519
520    fn evaluate_exp(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
521        match (left, right) {
522            (Value::UInt(base), Value::UInt(exp)) => {
523                if *exp > 32 {
524                    Err(InterpreterError::RuntimeError("Exponent too large".to_string()))
525                } else {
526                    Ok(Value::UInt(base.pow(*exp as u32)))
527                }
528            }
529            _ => Err(InterpreterError::TypeMismatch {
530                expected: "uint".to_string(),
531                found: format!("{} and {}", left.type_name(), right.type_name()),
532            }),
533        }
534    }
535
536    fn values_equal(&self, left: &Value, right: &Value) -> bool {
537        match (left, right) {
538            (Value::Bool(a), Value::Bool(b)) => a == b,
539            (Value::UInt(a), Value::UInt(b)) => a == b,
540            (Value::Int(a), Value::Int(b)) => a == b,
541            (Value::UInt(a), Value::Int(b)) => *a as i64 == *b,
542            (Value::Int(a), Value::UInt(b)) => *a == *b as i64,
543            (Value::String(a), Value::String(b)) => a == b,
544            (Value::Address(a), Value::Address(b)) => a == b,
545            (Value::Bytes(a), Value::Bytes(b)) => a == b,
546            (Value::Null, Value::Null) => true,
547            _ => false,
548        }
549    }
550
551    fn evaluate_less_than(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
552        match (left, right) {
553            (Value::UInt(a), Value::UInt(b)) => Ok(Value::Bool(a < b)),
554            (Value::Int(a), Value::Int(b)) => Ok(Value::Bool(a < b)),
555            (Value::UInt(a), Value::Int(b)) => Ok(Value::Bool((*a as i64) < *b)),
556            (Value::Int(a), Value::UInt(b)) => Ok(Value::Bool(*a < (*b as i64))),
557            _ => Err(InterpreterError::TypeMismatch {
558                expected: "numeric".to_string(),
559                found: format!("{} and {}", left.type_name(), right.type_name()),
560            }),
561        }
562    }
563
564    fn evaluate_less_than_or_equal(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
565        match (left, right) {
566            (Value::UInt(a), Value::UInt(b)) => Ok(Value::Bool(a <= b)),
567            (Value::Int(a), Value::Int(b)) => Ok(Value::Bool(a <= b)),
568            (Value::UInt(a), Value::Int(b)) => Ok(Value::Bool((*a as i64) <= *b)),
569            (Value::Int(a), Value::UInt(b)) => Ok(Value::Bool(*a <= (*b as i64))),
570            _ => Err(InterpreterError::TypeMismatch {
571                expected: "numeric".to_string(),
572                found: format!("{} and {}", left.type_name(), right.type_name()),
573            }),
574        }
575    }
576
577    fn evaluate_greater_than(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
578        match (left, right) {
579            (Value::UInt(a), Value::UInt(b)) => Ok(Value::Bool(a > b)),
580            (Value::Int(a), Value::Int(b)) => Ok(Value::Bool(a > b)),
581            (Value::UInt(a), Value::Int(b)) => Ok(Value::Bool((*a as i64) > *b)),
582            (Value::Int(a), Value::UInt(b)) => Ok(Value::Bool(*a > (*b as i64))),
583            _ => Err(InterpreterError::TypeMismatch {
584                expected: "numeric".to_string(),
585                found: format!("{} and {}", left.type_name(), right.type_name()),
586            }),
587        }
588    }
589
590    fn evaluate_greater_than_or_equal(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
591        match (left, right) {
592            (Value::UInt(a), Value::UInt(b)) => Ok(Value::Bool(a >= b)),
593            (Value::Int(a), Value::Int(b)) => Ok(Value::Bool(a >= b)),
594            (Value::UInt(a), Value::Int(b)) => Ok(Value::Bool((*a as i64) >= *b)),
595            (Value::Int(a), Value::UInt(b)) => Ok(Value::Bool(*a >= (*b as i64))),
596            _ => Err(InterpreterError::TypeMismatch {
597                expected: "numeric".to_string(),
598                found: format!("{} and {}", left.type_name(), right.type_name()),
599            }),
600        }
601    }
602
603    fn evaluate_logical_and(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
604        let left_bool = left.to_bool()?;
605        let right_bool = right.to_bool()?;
606        Ok(Value::Bool(left_bool && right_bool))
607    }
608
609    fn evaluate_logical_or(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
610        let left_bool = left.to_bool()?;
611        let right_bool = right.to_bool()?;
612        Ok(Value::Bool(left_bool || right_bool))
613    }
614
615    fn evaluate_bit_and(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
616        match (left, right) {
617            (Value::UInt(a), Value::UInt(b)) => Ok(Value::UInt(a & b)),
618            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a & b)),
619            _ => Err(InterpreterError::TypeMismatch {
620                expected: "integer".to_string(),
621                found: format!("{} and {}", left.type_name(), right.type_name()),
622            }),
623        }
624    }
625
626    fn evaluate_bit_or(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
627        match (left, right) {
628            (Value::UInt(a), Value::UInt(b)) => Ok(Value::UInt(a | b)),
629            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a | b)),
630            _ => Err(InterpreterError::TypeMismatch {
631                expected: "integer".to_string(),
632                found: format!("{} and {}", left.type_name(), right.type_name()),
633            }),
634        }
635    }
636
637    fn evaluate_bit_xor(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
638        match (left, right) {
639            (Value::UInt(a), Value::UInt(b)) => Ok(Value::UInt(a ^ b)),
640            (Value::Int(a), Value::Int(b)) => Ok(Value::Int(a ^ b)),
641            _ => Err(InterpreterError::TypeMismatch {
642                expected: "integer".to_string(),
643                found: format!("{} and {}", left.type_name(), right.type_name()),
644            }),
645        }
646    }
647
648    fn evaluate_shift_left(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
649        match (left, right) {
650            (Value::UInt(a), Value::UInt(b)) => {
651                if *b > 64 {
652                    Err(InterpreterError::RuntimeError("Shift amount too large".to_string()))
653                } else {
654                    Ok(Value::UInt(a << b))
655                }
656            }
657            _ => Err(InterpreterError::TypeMismatch {
658                expected: "uint".to_string(),
659                found: format!("{} and {}", left.type_name(), right.type_name()),
660            }),
661        }
662    }
663
664    fn evaluate_shift_right(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
665        match (left, right) {
666            (Value::UInt(a), Value::UInt(b)) => {
667                if *b > 64 {
668                    Err(InterpreterError::RuntimeError("Shift amount too large".to_string()))
669                } else {
670                    Ok(Value::UInt(a >> b))
671                }
672            }
673            _ => Err(InterpreterError::TypeMismatch {
674                expected: "uint".to_string(),
675                found: format!("{} and {}", left.type_name(), right.type_name()),
676            }),
677        }
678    }
679
680    fn evaluate_shift_right_arithmetic(&self, left: &Value, right: &Value) -> Result<Value, InterpreterError> {
681        match (left, right) {
682            (Value::Int(a), Value::UInt(b)) => {
683                if *b > 64 {
684                    Err(InterpreterError::RuntimeError("Shift amount too large".to_string()))
685                } else {
686                    Ok(Value::Int(a >> b))
687                }
688            }
689            _ => Err(InterpreterError::TypeMismatch {
690                expected: "int and uint".to_string(),
691                found: format!("{} and {}", left.type_name(), right.type_name()),
692            }),
693        }
694    }
695
696    fn evaluate_unary_minus(&self, operand: &Value) -> Result<Value, InterpreterError> {
697        match operand {
698            Value::UInt(n) => Ok(Value::Int(-(*n as i64))),
699            Value::Int(n) => Ok(Value::Int(-n)),
700            _ => Err(InterpreterError::TypeMismatch {
701                expected: "numeric".to_string(),
702                found: operand.type_name().to_string(),
703            }),
704        }
705    }
706
707    fn evaluate_logical_not(&self, operand: &Value) -> Result<Value, InterpreterError> {
708        let bool_val = operand.to_bool()?;
709        Ok(Value::Bool(!bool_val))
710    }
711
712    fn evaluate_bit_not(&self, operand: &Value) -> Result<Value, InterpreterError> {
713        match operand {
714            Value::UInt(n) => Ok(Value::UInt(!n)),
715            Value::Int(n) => Ok(Value::Int(!n)),
716            _ => Err(InterpreterError::TypeMismatch {
717                expected: "integer".to_string(),
718                found: operand.type_name().to_string(),
719            }),
720        }
721    }
722
723    fn evaluate_builtin_function(
724        &self,
725        func: &BuiltinFunction,
726        args: &[Value],
727    ) -> Result<Value, InterpreterError> {
728        match func {
729            BuiltinFunction::Keccak256 => {
730                if args.len() != 1 {
731                    return Err(InterpreterError::InvalidArguments(
732                        "keccak256 expects exactly 1 argument".to_string(),
733                    ));
734                }
735                Ok(Value::Bytes(vec![0u8; 32])) // Mock 32-byte hash
736            }
737            BuiltinFunction::Sha256 => {
738                if args.len() != 1 {
739                    return Err(InterpreterError::InvalidArguments(
740                        "sha256 expects exactly 1 argument".to_string(),
741                    ));
742                }
743                Ok(Value::Bytes(vec![1u8; 32])) // Mock 32-byte hash
744            }
745            BuiltinFunction::Ripemd160 => {
746                if args.len() != 1 {
747                    return Err(InterpreterError::InvalidArguments(
748                        "ripemd160 expects exactly 1 argument".to_string(),
749                    ));
750                }
751                Ok(Value::Bytes(vec![2u8; 20])) // Mock 20-byte hash
752            }
753            BuiltinFunction::Ecrecover => {
754                if args.len() != 4 {
755                    return Err(InterpreterError::InvalidArguments(
756                        "ecrecover expects exactly 4 arguments".to_string(),
757                    ));
758                }
759                // For predicate evaluation, we'll return a mock address
760                Ok(Value::Address("0x0000000000000000000000000000000000000000".to_string()))
761            }
762        }
763    }
764}
765
766#[cfg(test)]
767mod tests {
768    use super::*;
769    use crate::parser::parse_expression; // Added for parsing expressions in tests
770
771    #[test]
772    fn test_evaluate_boolean_literal() {
773        let interpreter = SolidityInterpreter::new();
774        
775        let true_expr = Expression::Literal(Literal::Boolean(true));
776        let false_expr = Expression::Literal(Literal::Boolean(false));
777        
778        assert_eq!(interpreter.evaluate(&true_expr).unwrap(), Value::Bool(true));
779        assert_eq!(interpreter.evaluate(&false_expr).unwrap(), Value::Bool(false));
780    }
781
782    #[test]
783    fn test_evaluate_number_literal() {
784        let interpreter = SolidityInterpreter::new();
785        
786        let num_expr = Expression::Literal(Literal::Number(NumberLiteral {
787            value: "42".to_string(),
788            sub_denomination: None,
789        }));
790        
791        assert_eq!(interpreter.evaluate(&num_expr).unwrap(), Value::UInt(42));
792    }
793
794    #[test]
795    fn test_evaluate_binary_comparison() {
796        let interpreter = SolidityInterpreter::new();
797        
798        let left = Box::new(Expression::Literal(Literal::Number(NumberLiteral {
799            value: "10".to_string(),
800            sub_denomination: None,
801        })));
802        
803        let right = Box::new(Expression::Literal(Literal::Number(NumberLiteral {
804            value: "5".to_string(),
805            sub_denomination: None,
806        })));
807        
808        let gt_expr = Expression::Binary(BinaryExpression {
809            left: left.clone(),
810            operator: BinaryOperator::GreaterThan,
811            right: right.clone(),
812        });
813        
814        let lt_expr = Expression::Binary(BinaryExpression {
815            left: left.clone(),
816            operator: BinaryOperator::LessThan,
817            right: right.clone(),
818        });
819        
820        assert!(interpreter.evaluate_predicate(&gt_expr).unwrap());
821        assert!(!interpreter.evaluate_predicate(&lt_expr).unwrap());
822    }
823
824    #[test]
825    fn test_evaluate_logical_and() {
826        let interpreter = SolidityInterpreter::new();
827        
828        let true_expr = Box::new(Expression::Literal(Literal::Boolean(true)));
829        let false_expr = Box::new(Expression::Literal(Literal::Boolean(false)));
830        
831        let and_expr = Expression::Binary(BinaryExpression {
832            left: true_expr.clone(),
833            operator: BinaryOperator::And,
834            right: false_expr.clone(),
835        });
836        
837        assert!(!interpreter.evaluate_predicate(&and_expr).unwrap());
838    }
839
840    #[test]
841    fn test_evaluate_logical_not() {
842        let interpreter = SolidityInterpreter::new();
843        
844        let true_expr = Box::new(Expression::Literal(Literal::Boolean(true)));
845        
846        let not_expr = Expression::Unary(UnaryExpression {
847            operator: UnaryOperator::Not,
848            operand: true_expr,
849            is_prefix: true,
850        });
851        
852        assert!(!interpreter.evaluate_predicate(&not_expr).unwrap());
853    }
854
855    #[test]
856    fn test_evaluate_conditional() {
857        let interpreter = SolidityInterpreter::new();
858        
859        let condition = Box::new(Expression::Literal(Literal::Boolean(true)));
860        let true_branch = Box::new(Expression::Literal(Literal::Number(NumberLiteral {
861            value: "1".to_string(),
862            sub_denomination: None,
863        })));
864        let false_branch = Box::new(Expression::Literal(Literal::Number(NumberLiteral {
865            value: "0".to_string(),
866            sub_denomination: None,
867        })));
868        
869        let cond_expr = Expression::Conditional(ConditionalExpression {
870            condition,
871            true_expr: true_branch,
872            false_expr: false_branch,
873        });
874        
875        assert_eq!(interpreter.evaluate(&cond_expr).unwrap(), Value::UInt(1));
876    }
877
878    #[test]
879    fn test_variable_lookup() {
880        let mut interpreter = SolidityInterpreter::new();
881        interpreter.context_mut().set_variable("x".to_string(), Value::Bool(true));
882        
883        let var_expr = Expression::Identifier("x".to_string());
884        
885        assert!(interpreter.evaluate_predicate(&var_expr).unwrap());
886    }
887
888    #[test]
889    fn test_undefined_variable() {
890        let interpreter = SolidityInterpreter::new();
891        
892        let var_expr = Expression::Identifier("undefined".to_string());
893        
894        match interpreter.evaluate(&var_expr) {
895            Err(InterpreterError::UndefinedVariable(name)) => {
896                assert_eq!(name, "undefined");
897            }
898            _ => panic!("Expected UndefinedVariable error"),
899        }
900    }
901
902    #[test]
903    fn test_value_to_bool_conversion() {
904        assert!(Value::Bool(true).to_bool().unwrap());
905        assert!(!Value::Bool(false).to_bool().unwrap());
906        assert!(Value::UInt(1).to_bool().unwrap());
907        assert!(!Value::UInt(0).to_bool().unwrap());
908        assert!(Value::Int(-1).to_bool().unwrap());
909        assert!(!Value::Int(0).to_bool().unwrap());
910        assert!(Value::String("hello".to_string()).to_bool().unwrap());
911        assert!(!Value::String("".to_string()).to_bool().unwrap());
912        assert!(!Value::Null.to_bool().unwrap());
913    }
914
915    #[test]
916    fn test_evaluate_new_value_gt_zero_predicate() {
917        let mut interpreter = SolidityInterpreter::new();
918
919        // Construct the expression: _newValue > 0
920        let new_value_ident = Expression::Identifier("_newValue".to_string());
921        let zero_literal = Expression::Literal(Literal::Number(NumberLiteral {
922            value: "0".to_string(),
923            sub_denomination: None,
924        }));
925        let expr = Expression::Binary(BinaryExpression {
926            left: Box::new(new_value_ident),
927            operator: BinaryOperator::GreaterThan,
928            right: Box::new(zero_literal),
929        });
930
931        // Case 1: _newValue = 42 (positive)
932        // Expected: _newValue > 0  =>  42 > 0  =>  true
933        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(42));
934        match interpreter.evaluate_predicate(&expr) {
935            Ok(result) => assert!(result, "Expected '42 > 0' to be true"),
936            Err(e) => panic!("Evaluation failed for _newValue = 42: {}", e),
937        }
938
939        // Case 2: _newValue = 0
940        // Expected: _newValue > 0  =>  0 > 0  =>  false
941        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(0));
942        match interpreter.evaluate_predicate(&expr) {
943            Ok(result) => assert!(!result, "Expected '0 > 0' to be false"),
944            Err(e) => panic!("Evaluation failed for _newValue = 0: {}", e),
945        }
946        
947        // Case 3: _newValue = 1 (positive, edge case near 0)
948        // Expected: _newValue > 0  =>  1 > 0  =>  true
949        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(1));
950        match interpreter.evaluate_predicate(&expr) {
951            Ok(result) => assert!(result, "Expected '1 > 0' to be true"),
952            Err(e) => panic!("Evaluation failed for _newValue = 1: {}", e),
953        }
954    }
955
956    #[test]
957    fn test_evaluate_parsed_expression_new_value_gt_zero() {
958        let mut interpreter = SolidityInterpreter::new();
959
960        // Parse the expression string into an AST
961        let expression_str = "_newValue > 0";
962        let parsed_expr = match parse_expression(expression_str) {
963            Ok(expr) => expr,
964            Err(e) => panic!("Failed to parse expression '{}': {}", expression_str, e),
965        };
966
967        // Case 1: _newValue = 42 (positive)
968        // Expected: _newValue > 0  =>  42 > 0  =>  true
969        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(42));
970        match interpreter.evaluate_predicate(&parsed_expr) {
971            Ok(result) => assert!(result, "Expected '42 > 0' (parsed) to be true"),
972            Err(e) => panic!("Parsed evaluation failed for _newValue = 42: {}", e),
973        }
974
975        // Case 2: _newValue = 0
976        // Expected: _newValue > 0  =>  0 > 0  =>  false
977        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(0));
978        match interpreter.evaluate_predicate(&parsed_expr) {
979            Ok(result) => assert!(!result, "Expected '0 > 0' (parsed) to be false"),
980            Err(e) => panic!("Parsed evaluation failed for _newValue = 0: {}", e),
981        }
982        
983        // Case 3: _newValue = 1 (positive, edge case near 0)
984        // Expected: _newValue > 0  =>  1 > 0  =>  true
985        interpreter.context_mut().set_variable("_newValue".to_string(), Value::UInt(1));
986        match interpreter.evaluate_predicate(&parsed_expr) {
987            Ok(result) => assert!(result, "Expected '1 > 0' (parsed) to be true"),
988            Err(e) => panic!("Parsed evaluation failed for _newValue = 1: {}", e),
989        }
990    }
991
992    #[test]
993    fn test_evaluate_parsed_expression_new_value_gt_zero_signed() {
994        let mut interpreter = SolidityInterpreter::new();
995
996        // Parse the expression string into an AST
997        let expression_str = "_newValue > 0";
998        let parsed_expr = match parse_expression(expression_str) {
999            Ok(expr) => expr,
1000            Err(e) => panic!("Failed to parse expression '{}': {}", expression_str, e),
1001        };
1002
1003        // Case 1: _newValue = 42 (positive)
1004        // Expected: _newValue > 0  =>  42 > 0  =>  true
1005        interpreter.context_mut().set_variable("_newValue".to_string(), Value::Int(42));
1006        match interpreter.evaluate_predicate(&parsed_expr) {
1007            Ok(result) => assert!(result, "Expected '42 > 0' (parsed) to be true"),
1008            Err(e) => panic!("Parsed evaluation failed for _newValue = 42: {}", e),
1009        }
1010
1011        // Case 2: _newValue = 0
1012        // Expected: _newValue > 0  =>  0 > 0  =>  false
1013        interpreter.context_mut().set_variable("_newValue".to_string(), Value::Int(0));
1014        match interpreter.evaluate_predicate(&parsed_expr) {
1015            Ok(result) => assert!(!result, "Expected '0 > 0' (parsed) to be false"),
1016            Err(e) => panic!("Parsed evaluation failed for _newValue = 0: {}", e),
1017        }
1018        
1019        // Case 3: _newValue = 1 (positive, edge case near 0)
1020        // Expected: _newValue > 0  =>  1 > 0  =>  true
1021        interpreter.context_mut().set_variable("_newValue".to_string(), Value::Int(1));
1022        match interpreter.evaluate_predicate(&parsed_expr) {
1023            Ok(result) => assert!(result, "Expected '1 > 0' (parsed) to be true"),
1024            Err(e) => panic!("Parsed evaluation failed for _newValue = 1: {}", e),
1025        }
1026    }
1027
1028
1029}