salient-lang / salient

http://salient-lang.dev/
MIT License
0 stars 0 forks source link

Fix operator precedence not applying correctly #12

Closed AjaniBilby closed 5 months ago

AjaniBilby commented 5 months ago

Operator precedence is being incorrectly applied within this file, rewrite to fix the issue.
/compiler/codegen/expression/precedence.ts

This function should return true, but is instead returning false:

fn main(): bool {
    // (-2.5 % 2.0) * -3.0 == 10.0 - ((1.0 / 2.0) % 10.0) - 8.0;
    // 1.5 == 1.5
    // true == 1
    return -2.5 % 2.0 * -3.0 == 10.0 - 1.0 / 2.0 % 10.0 - 8.0;
}
AjaniBilby commented 5 months ago

Based on the fact that this test case fails on return 41 it implies the precedence of - is causing an issue.

fn main(): i32 {
  // (-2.5 % 2.0) * -3.0 == 10.0 - ((1.0 / 2.0) % 10.0) - 8.0;
  // 1.5 == 1.5
  // true == 1

  // doing this in a single expression to also ensure == is applied correctly
  if ( (-2.5 % 2.0) * -3.0 ) != ( 10.0 - ( (1.0 / 2.0) % 10.0 ) - 8.0 ) {
    return 25;
  };

  if ( (-2.5 % 2.0) * -3.0 != 10.0 - ( (1.0 / 2.0) % 10.0 ) - 8.0 ) {
    return 29;
  };

  if ( (-2.5 % 2.0) * -3.0 != 10.0 - ( 1.0 / 2.0 % 10.0 ) - 8.0 ) {
    return 33;
  };

  if ( -2.5 % 2.0 * -3.0 != 10.0 - ( 1.0 / 2.0 % 10.0 ) - 8.0 ) {
    return 37;
  };

  if ( -2.5 % 2.0 * -3.0 != 10.0 - 1.0 / 2.0 % 10.0 - 8.0 ) {
    return 41;
  };

  return 36;
}
AjaniBilby commented 5 months ago
fn left(): f32 {
  return 10.0 - ( 3.0 / 2.0 ) - 8.0;
}

fn right(): f32 {
  return 10.0 - 3.0 / 2.0 - 8.0;
}

fn main(): bool {
  left();
  right();

  return 10.0 - ( 3.0 / 2.0 ) - 8.0 == 10.0 - 3.0 / 2.0 - 8.0;
}
(module
  (type (;0;) (func (result i32)))
  (type (;1;) (func (result f32)))
  (func (;0;) (type 0) (result i32)
    call 1
    drop
    call 2
    drop

    f32.const 0x1.4p+3 (;=10;)
    f32.const 0x1.8p+1 (;=3;)
    f32.const 0x1p+1 (;=2;)
    f32.div
    f32.sub
    f32.const 0x1p+3 (;=8;)
    f32.sub

    f32.const 0x1.4p+3 (;=10;)
    f32.const 0x1.8p+1 (;=3;)
    f32.sub                    ;; FLIPPED
    f32.const 0x1p+1 (;=2;)
    f32.div                    ;; FLIPPED
    f32.const 0x1p+3 (;=8;)
    f32.sub
    f32.eq
    return
    unreachable)
  (func (;1;) (type 1) (result f32)
    f32.const 0x1.4p+3 (;=10;)
    f32.const 0x1.8p+1 (;=3;)
    f32.const 0x1p+1 (;=2;)
    f32.div
    f32.sub
    f32.const 0x1p+3 (;=8;)
    f32.sub
    return
    unreachable)
  (func (;2;) (type 1) (result f32)
    f32.const 0x1.4p+3 (;=10;)
    f32.const 0x1.8p+1 (;=3;)
    f32.const 0x1p+1 (;=2;)
    f32.div
    f32.sub
    f32.const 0x1p+3 (;=8;)
    f32.sub
    return
    unreachable)
  (memory (;0;) 1 1)
  (global (;0;) (mut i32) (i32.const 0))
  (export "_start" (func 0))
  (export "main" (func 0)))