#![cfg(any(
not(any(
feature = "parser_tests",
feature = "analyzer_tests",
feature = "codegen_tests",
feature = "interpreter_tests",
feature = "conformance_tests",
feature = "integration_tests",
)),
feature = "analyzer_tests",
))]
#[path = "common/test_utils.rs"]
mod test_utils;
#[test]
fn test_multiplication_x_times_1_0() {
let source = r#"
pub fn scale(x: f32) -> f32 {
x * 1.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.0_f32"),
"x * 1.0 where x: f32 should generate 1.0_f32, got:\n{}",
output
);
assert!(
!output.contains("1.0_f64"),
"Should not generate 1.0_f64 when LHS is f32, got:\n{}",
output
);
}
#[test]
fn test_addition_x_plus_1_0() {
let source = r#"
pub fn add_one(x: f32) -> f32 {
x + 1.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.0_f32"),
"x + 1.0 where x: f32 should generate 1.0_f32, got:\n{}",
output
);
}
#[test]
fn test_division_x_over_2_0() {
let source = r#"
pub fn half(x: f32) -> f32 {
x / 2.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("2.0_f32"),
"x / 2.0 where x: f32 should generate 2.0_f32, got:\n{}",
output
);
}
#[test]
fn test_subtraction_x_minus_0_5() {
let source = r#"
pub fn sub(x: f32) -> f32 {
x - 0.5
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("0.5_f32"),
"x - 0.5 where x: f32 should generate 0.5_f32, got:\n{}",
output
);
}
#[test]
fn test_comparison_x_gt_1_0() {
let source = r#"
pub fn is_greater(x: f32) -> bool {
x > 1.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.0_f32"),
"x > 1.0 where x: f32 should generate 1.0_f32, got:\n{}",
output
);
}
#[test]
fn test_compound_assignment_x_times_eq_1_5() {
let source = r#"
pub fn scale_in_place(mut x: f32) -> f32 {
x *= 1.5
x
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.5_f32"),
"x *= 1.5 where x: f32 should generate 1.5_f32, got:\n{}",
output
);
}
#[test]
fn test_chained_binary_ops() {
let source = r#"
pub fn chained(x: f32) -> f32 {
x * 1.0 + 2.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.0_f32") && output.contains("2.0_f32"),
"x * 1.0 + 2.0 should generate both literals as f32, got:\n{}",
output
);
}
#[test]
fn test_method_call_result_times_literal() {
let source = r#"
struct Holder { value: f32 }
impl Holder {
pub fn get_value(self) -> f32 {
self.value
}
}
pub fn scale_holder(h: Holder) -> f32 {
h.get_value() * 1.0
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.0_f32"),
"get_value() * 1.0 where get_value returns f32 should generate 1.0_f32, got:\n{}",
output
);
}
#[test]
fn test_field_access_times_literal() {
let source = r#"
pub struct Point { pub x: f32, pub y: f32 }
impl Point {
pub fn scaled(self) -> Point {
Point {
x: self.x * 0.5,
y: self.y * 2.0,
}
}
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("0.5_f32") && output.contains("2.0_f32"),
"self.x * 0.5 and self.y * 2.0 should generate f32 literals, got:\n{}",
output
);
}
#[test]
fn test_variable_times_literal() {
let source = r#"
pub fn compute() -> f32 {
let x: f32 = 10.0
x * 0.5
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("0.5_f32"),
"x * 0.5 where x: f32 should generate 0.5_f32, got:\n{}",
output
);
}
#[test]
fn test_unconstrained_defaults_to_f64() {
let source = r#"
pub fn unconstrained() -> f64 {
let x = 1.0 + 2.0
x
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("_f64"),
"Unconstrained 1.0 + 2.0 with f64 return should use f64, got:\n{}",
output
);
}
#[test]
fn test_intermediate_variable_times_literal() {
let source = r#"
pub fn get_distance(x: f32, y: f32) -> f32 {
let dx = x * x
let dy = y * y
let dist_sq = dx + dy
dist_sq * 1.414
}
"#;
let output = test_utils::compile_single(source);
assert!(
output.contains("1.414_f32"),
"dist_sq * 1.414 where dist_sq is f32 should generate 1.414_f32, got:\n{}",
output
);
assert!(
!output.contains("1.414_f64"),
"Should NOT generate 1.414_f64, got:\n{}",
output
);
}