Skip to content

Commit 1a1eb6f

Browse files
authored
fix: compare Quoted by expanding interned values (#7602)
1 parent 073625a commit 1a1eb6f

3 files changed

Lines changed: 34 additions & 4 deletions

File tree

compiler/noirc_frontend/src/hir/comptime/interpreter/builtin.rs

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ use crate::{
2828
hir::{
2929
comptime::{
3030
InterpreterError, Value,
31+
display::tokens_to_string,
3132
errors::IResult,
3233
value::{ExprValue, TypedExpr},
3334
},
@@ -166,7 +167,7 @@ impl Interpreter<'_, '_> {
166167
"quoted_as_module" => quoted_as_module(self, arguments, return_type, location),
167168
"quoted_as_trait_constraint" => quoted_as_trait_constraint(self, arguments, location),
168169
"quoted_as_type" => quoted_as_type(self, arguments, location),
169-
"quoted_eq" => quoted_eq(arguments, location),
170+
"quoted_eq" => quoted_eq(self.elaborator.interner, arguments, location),
170171
"quoted_hash" => quoted_hash(arguments, location),
171172
"quoted_tokens" => quoted_tokens(arguments, location),
172173
"slice_insert" => slice_insert(interner, arguments, location),
@@ -2913,10 +2914,24 @@ fn modulus_num_bits(arguments: Vec<(Value, Location)>, location: Location) -> IR
29132914
}
29142915

29152916
// fn quoted_eq(_first: Quoted, _second: Quoted) -> bool
2916-
fn quoted_eq(arguments: Vec<(Value, Location)>, location: Location) -> IResult<Value> {
2917-
eq_item(arguments, location, get_quoted)
2918-
}
2917+
fn quoted_eq(
2918+
interner: &NodeInterner,
2919+
arguments: Vec<(Value, Location)>,
2920+
location: Location,
2921+
) -> IResult<Value> {
2922+
let (self_arg, other_arg) = check_two_arguments(arguments, location)?;
2923+
let self_arg = get_quoted(self_arg)?;
2924+
let other_arg = get_quoted(other_arg)?;
2925+
2926+
// Comparing tokens one against each other doesn't work in the general case because tokens
2927+
// might be refer to interned expressions/statements/etc. We'd need to convert those nodes
2928+
// to tokens and compare the final result, but comparing their string representation works
2929+
// equally well and, for simplicity, that's what we do here.
2930+
let self_string = tokens_to_string(&self_arg, interner);
2931+
let other_string = tokens_to_string(&other_arg, interner);
29192932

2933+
Ok(Value::Bool(self_string == other_string))
2934+
}
29202935
fn quoted_hash(arguments: Vec<(Value, Location)>, location: Location) -> IResult<Value> {
29212936
hash_item(arguments, location, get_quoted)
29222937
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
[package]
2+
name = "comptime_quoted"
3+
type = "bin"
4+
authors = [""]
5+
compiler_version = ">=0.31.0"
6+
7+
[dependencies]
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
fn main() {
2+
comptime {
3+
let array = quote { [1, 2, 3] }.as_expr().unwrap();
4+
let expr1 = quote { [1, 2, 3]};
5+
let expr2 = quote { $array };
6+
assert_eq(expr1, expr2);
7+
}
8+
}

0 commit comments

Comments
 (0)