uni_core/primitives/
less_equal.rs1use crate::compat::format;
2use crate::interpreter::Interpreter;
3use crate::primitives::numeric_promotion::promote_pair;
4use crate::value::{RuntimeError, Value};
5
6pub fn less_equal_builtin(interp: &mut Interpreter) -> Result<(), RuntimeError> {
7 let b = interp.pop()?;
8 let a = interp.pop()?;
9
10 let (pa, pb) = promote_pair(&a, &b);
12
13 let result = match (&pa, &pb) {
14 (Value::Int32(i1), Value::Int32(i2)) => i1 <= i2,
15 (Value::Integer(i1), Value::Integer(i2)) => i1 <= i2,
16 (Value::Rational(r1), Value::Rational(r2)) => r1 <= r2,
17 (Value::Number(n1), Value::Number(n2)) => n1 <= n2,
18 _ => {
19 return Err(RuntimeError::TypeError(format!(
20 "Cannot compare {:?} and {:?}",
21 a, b
22 )))
23 }
24 };
25
26 interp.push(Value::Boolean(result));
27 Ok(())
28}
29
30#[cfg(test)]
31mod tests {
32 use super::*;
33 use crate::value::Value;
34
35 fn setup_interpreter() -> Interpreter {
36 Interpreter::new()
37 }
38
39 #[test]
40 fn test_less_equal_true_less() {
41 let mut interp = setup_interpreter();
42 interp.push(Value::Number(3.0));
43 interp.push(Value::Number(5.0));
44
45 less_equal_builtin(&mut interp).unwrap();
46
47 let result = interp.pop().unwrap();
48 assert!(matches!(result, Value::Boolean(true)));
49 }
50
51 #[test]
52 fn test_less_equal_true_equal() {
53 let mut interp = setup_interpreter();
54 interp.push(Value::Number(5.0));
55 interp.push(Value::Number(5.0));
56
57 less_equal_builtin(&mut interp).unwrap();
58
59 let result = interp.pop().unwrap();
60 assert!(matches!(result, Value::Boolean(true)));
61 }
62
63 #[test]
64 fn test_less_equal_false() {
65 let mut interp = setup_interpreter();
66 interp.push(Value::Number(7.0));
67 interp.push(Value::Number(3.0));
68
69 less_equal_builtin(&mut interp).unwrap();
70
71 let result = interp.pop().unwrap();
72 assert!(matches!(result, Value::Boolean(false)));
73 }
74
75 #[test]
76 fn test_less_equal_negative_numbers() {
77 let mut interp = setup_interpreter();
78 interp.push(Value::Number(-10.0));
79 interp.push(Value::Number(-10.0));
80
81 less_equal_builtin(&mut interp).unwrap();
82
83 let result = interp.pop().unwrap();
84 assert!(matches!(result, Value::Boolean(true)));
85 }
86
87 #[test]
88 fn test_less_equal_stack_underflow() {
89 let mut interp = setup_interpreter();
90
91 let result = less_equal_builtin(&mut interp);
92 assert!(matches!(result, Err(RuntimeError::StackUnderflow)));
93
94 interp.push(Value::Number(1.0));
95 let result = less_equal_builtin(&mut interp);
96 assert!(matches!(result, Err(RuntimeError::StackUnderflow)));
97 }
98
99 #[test]
100 fn test_less_equal_type_error() {
101 let mut interp = setup_interpreter();
102 interp.push(Value::String("hello".into()));
103 interp.push(Value::Number(5.0));
104
105 let result = less_equal_builtin(&mut interp);
106 assert!(matches!(result, Err(RuntimeError::TypeError(_))));
107 }
108}