Merge pull request #1185 from AleoHQ/bug/ternary-different-types

[Bugfix] Ternary Type Check
This commit is contained in:
Alessandro Coglio 2021-07-24 13:21:59 -07:00 committed by GitHub
commit 49a51d6026
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 40 additions and 6 deletions

View File

@ -204,6 +204,12 @@ impl AsgConvertError {
Self::new_from_span(format!("array index out of bounds: '{}'", index), span)
}
pub fn ternary_different_types(left: &str, right: &str, span: &Span) -> Self {
let message = format!("ternary sides had different types: left {}, right {}", left, right);
Self::new_from_span(message, span)
}
pub fn unknown_array_size(span: &Span) -> Self {
Self::new_from_span("array size cannot be inferred, add explicit types".to_string(), span)
}

View File

@ -79,6 +79,24 @@ impl<'a> FromAst<'a, leo_ast::TernaryExpression> for TernaryExpression<'a> {
value: &leo_ast::TernaryExpression,
expected_type: Option<PartialType<'a>>,
) -> Result<TernaryExpression<'a>, AsgConvertError> {
let if_true = Cell::new(<&Expression<'a>>::from_ast(
scope,
&*value.if_true,
expected_type.clone(),
)?);
let left: PartialType = if_true.get().get_type().unwrap().into();
let if_false = Cell::new(<&Expression<'a>>::from_ast(scope, &*value.if_false, expected_type)?);
let right = if_false.get().get_type().unwrap().into();
if left != right {
return Err(AsgConvertError::ternary_different_types(
&left.to_string(),
&right.to_string(),
&value.span,
));
}
Ok(TernaryExpression {
parent: Cell::new(None),
span: Some(value.span.clone()),
@ -87,12 +105,8 @@ impl<'a> FromAst<'a, leo_ast::TernaryExpression> for TernaryExpression<'a> {
&*value.condition,
Some(Type::Boolean.partial()),
)?),
if_true: Cell::new(<&Expression<'a>>::from_ast(
scope,
&*value.if_true,
expected_type.clone(),
)?),
if_false: Cell::new(<&Expression<'a>>::from_ast(scope, &*value.if_false, expected_type)?),
if_true,
if_false,
})
}
}

View File

@ -0,0 +1,9 @@
/*
namespace: Compile
expectation: Fail
input_file: inputs/u32_3.in
*/
function main(x: u32) {
let x = true ? x: true;
}

View File

@ -0,0 +1,5 @@
---
namespace: Compile
expectation: Fail
outputs:
- " --> compiler-test:4:13\n |\n 4 | let x = true ? x: true;\n | ^^^^^^^^^^^^^^\n |\n = ternary sides had different types: left u32, right bool"