From c72cf61ad2db4a73afdf165410cc60c61a8f9657 Mon Sep 17 00:00:00 2001 From: collin Date: Fri, 5 Jun 2020 15:34:06 -0700 Subject: [PATCH] impl integer gadget tests. test u32 --- compiler/src/constraints/expression.rs | 16 ++ compiler/src/types.rs | 2 +- compiler/tests/integer/macros.rs | 203 ++++++++++++++++++++++- compiler/tests/integer/mod.rs | 22 +++ compiler/tests/integer/u32/assert_eq.leo | 3 + compiler/tests/integer/u32/eq.leo | 3 + compiler/tests/integer/u32/ge.leo | 3 + compiler/tests/integer/u32/gt.leo | 3 + compiler/tests/integer/u32/le.leo | 3 + compiler/tests/integer/u32/lt.leo | 3 + compiler/tests/integer/u32/mod.rs | 15 +- compiler/tests/integer/u32/ternary.leo | 3 + 12 files changed, 275 insertions(+), 4 deletions(-) create mode 100644 compiler/tests/integer/u32/assert_eq.leo create mode 100644 compiler/tests/integer/u32/eq.leo create mode 100644 compiler/tests/integer/u32/ge.leo create mode 100644 compiler/tests/integer/u32/gt.leo create mode 100644 compiler/tests/integer/u32/le.leo create mode 100644 compiler/tests/integer/u32/lt.leo create mode 100644 compiler/tests/integer/u32/ternary.leo diff --git a/compiler/src/constraints/expression.rs b/compiler/src/constraints/expression.rs index 56ba256cda..37ec207eb4 100644 --- a/compiler/src/constraints/expression.rs +++ b/compiler/src/constraints/expression.rs @@ -236,6 +236,10 @@ impl, CS: ConstraintSystem> Constraine right: ConstrainedValue, ) -> Result, ExpressionError> { match (left, right) { + (ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => { + let result = num_1.ge(&num_2); + Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) + } (ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => { let result = fe_1.ge(&fe_2); Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) @@ -261,6 +265,10 @@ impl, CS: ConstraintSystem> Constraine right: ConstrainedValue, ) -> Result, ExpressionError> { match (left, right) { + (ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => { + let result = num_1.gt(&num_2); + Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) + } (ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => { let result = fe_1.gt(&fe_2); Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) @@ -286,6 +294,10 @@ impl, CS: ConstraintSystem> Constraine right: ConstrainedValue, ) -> Result, ExpressionError> { match (left, right) { + (ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => { + let result = num_1.le(&num_2); + Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) + } (ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => { let result = fe_1.le(&fe_2); Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) @@ -311,6 +323,10 @@ impl, CS: ConstraintSystem> Constraine right: ConstrainedValue, ) -> Result, ExpressionError> { match (left, right) { + (ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => { + let result = num_1.lt(&num_2); + Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) + } (ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => { let result = fe_1.lt(&fe_2); Ok(ConstrainedValue::Boolean(Boolean::Constant(result))) diff --git a/compiler/src/types.rs b/compiler/src/types.rs index d867b3fa87..272e44a974 100644 --- a/compiler/src/types.rs +++ b/compiler/src/types.rs @@ -34,7 +34,7 @@ pub struct Variable { } /// An integer type enum wrapping the integer value. Used only in expressions. -#[derive(Debug, Clone, PartialEq, Eq)] +#[derive(Debug, Clone, PartialEq, Eq, PartialOrd)] pub enum Integer { U8(UInt8), U16(UInt16), diff --git a/compiler/tests/integer/macros.rs b/compiler/tests/integer/macros.rs index 6f45831e42..34a32cfa29 100644 --- a/compiler/tests/integer/macros.rs +++ b/compiler/tests/integer/macros.rs @@ -127,7 +127,7 @@ macro_rules! test_uint { let r1: $_type = rand::random(); let r2: $_type = rand::random(); - let sum = r1.wrapping_pow(r2); + let sum = r1.wrapping_pow(r2 as u32); let cs = TestConstraintSystem::::new(); let sum_allocated = <$gadget>::alloc(cs, || Ok(sum)).unwrap(); @@ -141,6 +141,207 @@ macro_rules! test_uint { output_expected_allocated(program, sum_allocated); } } + + fn test_eq() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "eq.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + output_true(program); + + // test not equal + let r2: $_type = rand::random(); + + let result = r1.eq(&r2); + + let mut program = compile_program($directory, "eq.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_boolean(program, result); + } + } + + fn test_ge() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "ge.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + output_true(program); + + // test not equal + let r2: $_type = rand::random(); + + let result = r1.ge(&r2); + + let mut program = compile_program($directory, "ge.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_boolean(program, result); + } + } + + fn test_gt() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "gt.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + output_false(program); + + // test not equal + let r2: $_type = rand::random(); + + let result = r1.gt(&r2); + + let mut program = compile_program($directory, "gt.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_boolean(program, result); + } + } + + fn test_le() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "le.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + output_true(program); + + // test not equal + let r2: $_type = rand::random(); + + let result = r1.le(&r2); + + let mut program = compile_program($directory, "le.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_boolean(program, result); + } + } + + fn test_lt() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "lt.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + output_false(program); + + // test not equal + let r2: $_type = rand::random(); + + let result = r1.lt(&r2); + + let mut program = compile_program($directory, "lt.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_boolean(program, result); + } + } + + fn test_assert_eq() { + for _ in 0..10 { + let r1: $_type = rand::random(); + + // test equal + let mut program = compile_program($directory, "assert_eq.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r1 as usize)), + ]); + + let _ = get_output(program); + + // test not equal + let r2: $_type = rand::random(); + + if r1 == r2 { + continue; + } + + let mut program = compile_program($directory, "assert_eq.leo").unwrap(); + program.set_inputs(vec![ + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + let mut cs = TestConstraintSystem::::new(); + let _ = program.compile_constraints(&mut cs).unwrap(); + assert!(!cs.is_satisfied()); + } + } + + fn test_ternary() { + let r1: $_type = rand::random(); + let r2: $_type = rand::random(); + + let g1 = <$gadget>::constant(r1); + let g2 = <$gadget>::constant(r2); + + let mut program_1 = compile_program($directory, "ternary.leo").unwrap(); + let mut program_2 = program_1.clone(); + + // true -> field 1 + program_1.set_inputs(vec![ + Some(InputValue::Boolean(true)), + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_allocated(program_1, g1); + + // false -> field 2 + program_2.set_inputs(vec![ + Some(InputValue::Boolean(false)), + Some(InputValue::Integer(r1 as usize)), + Some(InputValue::Integer(r2 as usize)), + ]); + + output_expected_allocated(program_2, g2); + } } }; } diff --git a/compiler/tests/integer/mod.rs b/compiler/tests/integer/mod.rs index eff9278236..6a99b77336 100644 --- a/compiler/tests/integer/mod.rs +++ b/compiler/tests/integer/mod.rs @@ -20,7 +20,29 @@ pub trait IntegerTester { /// Tests a wrapping exponentiation fn test_pow(); + + /// Tests == evaluation + fn test_eq(); + + /// Tests >= evaluation + fn test_ge(); + + /// Tests > evaluation + fn test_gt(); + + /// Tests <= evaluation + fn test_le(); + + /// Tests < evaluation + fn test_lt(); + + /// Test assert equals constraint keyword + fn test_assert_eq(); + + /// Test ternary if bool ? num_1 : num_2; + fn test_ternary(); } // must be below macro definitions! +// pub mod u8; pub mod u32; diff --git a/compiler/tests/integer/u32/assert_eq.leo b/compiler/tests/integer/u32/assert_eq.leo new file mode 100644 index 0000000000..768816d9c8 --- /dev/null +++ b/compiler/tests/integer/u32/assert_eq.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) { + assert_eq!(a, b); +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/eq.leo b/compiler/tests/integer/u32/eq.leo new file mode 100644 index 0000000000..65c5501219 --- /dev/null +++ b/compiler/tests/integer/u32/eq.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) -> bool { + return a == b +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/ge.leo b/compiler/tests/integer/u32/ge.leo new file mode 100644 index 0000000000..d08a3e8708 --- /dev/null +++ b/compiler/tests/integer/u32/ge.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) -> bool { + return a >= b +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/gt.leo b/compiler/tests/integer/u32/gt.leo new file mode 100644 index 0000000000..abd9832804 --- /dev/null +++ b/compiler/tests/integer/u32/gt.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) -> bool { + return a > b +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/le.leo b/compiler/tests/integer/u32/le.leo new file mode 100644 index 0000000000..c16b861679 --- /dev/null +++ b/compiler/tests/integer/u32/le.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) -> bool { + return a <= b +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/lt.leo b/compiler/tests/integer/u32/lt.leo new file mode 100644 index 0000000000..3d06c38456 --- /dev/null +++ b/compiler/tests/integer/u32/lt.leo @@ -0,0 +1,3 @@ +function main(a: u32, b: u32) -> bool { + return a < b +} \ No newline at end of file diff --git a/compiler/tests/integer/u32/mod.rs b/compiler/tests/integer/u32/mod.rs index bf4c1976ca..2645f29f82 100644 --- a/compiler/tests/integer/u32/mod.rs +++ b/compiler/tests/integer/u32/mod.rs @@ -1,6 +1,8 @@ use crate::{ - compile_program, get_error, get_output, integer::IntegerTester, EdwardsConstrainedValue, - EdwardsTestCompiler, + boolean::{output_expected_boolean, output_false, output_true}, + compile_program, get_error, get_output, + integer::IntegerTester, + EdwardsConstrainedValue, EdwardsTestCompiler, }; use leo_compiler::{ errors::{CompilerError, FunctionError, IntegerError}, @@ -80,6 +82,15 @@ fn test_u32() { TestU32::test_mul(); TestU32::test_div(); TestU32::test_pow(); + + TestU32::test_eq(); + TestU32::test_ge(); + TestU32::test_gt(); + TestU32::test_le(); + TestU32::test_gt(); + + TestU32::test_assert_eq(); + TestU32::test_ternary(); } #[test] diff --git a/compiler/tests/integer/u32/ternary.leo b/compiler/tests/integer/u32/ternary.leo new file mode 100644 index 0000000000..ffbeec8a3b --- /dev/null +++ b/compiler/tests/integer/u32/ternary.leo @@ -0,0 +1,3 @@ +function main(b: bool, x: u32, y: u32) -> u32 { + return if b ? x : y +} \ No newline at end of file