-
Notifications
You must be signed in to change notification settings - Fork 200
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
fix: Allow macros to change types on each iteration of a comptime loop (
#6105) # Description ## Problem\* Resolves #6086 (comment) ## Summary\* Allows macros to have differing result types on different loop iterations again after it was banned by the unification in #6086. This is a difficult feature to use since users will still have to work around the type system only type checking loops once. The recommended technique found for this PR is to delay type checks by quoting the relevant function calls that need to be re-typechecked so that when they are unquoted by the interpreter they are forced to be typechecked every loop iteration. The downside of this is that it requires some knowledge of when to do this. If we go back to the naive approach of `comptime_change_type_each_loop_iteration` before the quoting: ```noir fn main() { comptime { for i in 9..11 { // Lengths are different on each iteration: "foo9", "foo10" let name = f"foo{i}".as_ctstring().as_quoted_str!(); let hash = from_signature(name); assert(hash > 3); } } } fn from_signature<let N: u32>(_signature: str<N>) -> u32 { N } ``` We get a confusing error now that the unification is gone: "Non-integer array length `_`" pointing to the body of `from_signature`. The fix for this is to quote & unquote the `from_signature` call: ```noir let hash = unquote!(quote { from_signature($name) }); ``` But there's nothing telling users this. Ideally we could warn users when a type changes like this and perhaps have them opt-in to it with a "I know what I'm doing" of some kind. ## Additional Context ## Documentation\* Check one: - [ ] No documentation needed. - [ ] Documentation included in this PR. - [ ] **[For Experimental Features]** Documentation to be submitted in a separate PR. # PR Checklist\* - [ ] I have tested the changes locally. - [ ] I have formatted the changes with [Prettier](https://prettier.io/) and/or `cargo fmt` on default settings.
- Loading branch information
Showing
8 changed files
with
76 additions
and
23 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
File renamed without changes.
File renamed without changes.
7 changes: 7 additions & 0 deletions
7
test_programs/compile_success_empty/comptime_change_type_each_iteration/Nargo.toml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
[package] | ||
name = "comptime_change_type_each_iteration" | ||
type = "bin" | ||
authors = [""] | ||
compiler_version = ">=0.34.0" | ||
|
||
[dependencies] |
19 changes: 19 additions & 0 deletions
19
test_programs/compile_success_empty/comptime_change_type_each_iteration/src/main.nr
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
fn main() { | ||
comptime | ||
{ | ||
for i in 9..11 { | ||
// Lengths are different on each iteration: | ||
// foo9, foo10 | ||
let name = f"foo{i}".as_ctstring().as_quoted_str!(); | ||
|
||
// So to call `from_signature` we need to delay the type check | ||
// by quoting the function call so that we re-typecheck on each iteration | ||
let hash = std::meta::unquote!(quote { from_signature($name) }); | ||
assert(hash > 3); | ||
} | ||
} | ||
} | ||
|
||
fn from_signature<let N: u32>(_signature: str<N>) -> u32 { | ||
N | ||
} |
12 changes: 0 additions & 12 deletions
12
test_programs/compile_success_empty/macro_result_type/t.rs
This file was deleted.
Oops, something went wrong.