Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement first-class functions #468

Merged
merged 58 commits into from
Jan 17, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
f0a1175
Finish most of partial evaluator pass
jfecher Nov 8, 2022
c653f60
Get all tests working
jfecher Nov 10, 2022
60405db
Remove debug println
jfecher Nov 10, 2022
d11d686
Merge master
jfecher Nov 10, 2022
6760fe7
Implement first class functions
jfecher Nov 14, 2022
757a180
Fix clippy
jfecher Nov 14, 2022
c951875
Fix for loop desugaring
jfecher Nov 14, 2022
6dad4d4
Add Shared expression as an optimization
jfecher Nov 15, 2022
338538e
Merge partial evaluator branch
jfecher Nov 16, 2022
fdb9539
Revert 6_array test
jfecher Nov 16, 2022
8183cdd
Fix method resolution
jfecher Nov 16, 2022
cefc379
Fix comptime evaluation of for loops
jfecher Nov 16, 2022
7bee007
Fix merge conflicts
jfecher Nov 16, 2022
24d729f
cargo fmt
jfecher Nov 16, 2022
b40ad17
Remove debug printout
jfecher Nov 16, 2022
7ff0aa3
Merge branch 'master' into jf/hof
jfecher Nov 17, 2022
f2f987b
Fix short-circuiting bug
jfecher Nov 17, 2022
dc07ee5
Fix copying arrays of main parameters
jfecher Nov 17, 2022
68b6ee5
Remove partial evaluator
jfecher Nov 29, 2022
db9f643
Resolve merge conflicts
jfecher Nov 29, 2022
f6ede68
Start evaluator changes
jfecher Nov 30, 2022
5a43419
Fix compile errors
jfecher Nov 30, 2022
e6523d0
Generate functions when referenced by a variable
jfecher Nov 30, 2022
4dc9218
Start working on supporting builtin and lowlevel functions
jfecher Dec 1, 2022
fe6bae6
Add debug information
jfecher Dec 5, 2022
a7de65a
Add hack to get existing tests working
jfecher Dec 5, 2022
5d7b18a
Add missing map* cases, and add test
jfecher Dec 6, 2022
2232aa9
Satisfy clippy lints
jfecher Dec 6, 2022
f01c020
Fix merge conflicts
jfecher Dec 6, 2022
81577d5
Remove for loop element type; for loops return unit now
jfecher Dec 6, 2022
d19d9f7
Remove now-unused length fields
jfecher Dec 6, 2022
4b6c09a
Merge branch 'master' into jf/hof
jfecher Dec 6, 2022
0044c6f
Fix frontend tests
jfecher Dec 6, 2022
38fb30e
Merge branch 'jf/hof' of https://github.com/noir-lang/noir into jf/hof
jfecher Dec 6, 2022
58d1ee2
Fix merge conflicts
jfecher Dec 6, 2022
50670d9
Cargo fmt
jfecher Dec 6, 2022
98c31bf
Implement function types; add example to show passing functions is br…
jfecher Dec 7, 2022
7dfc841
Remove special case causing hof to fail when passed as parameters
jfecher Dec 8, 2022
d0025a5
Update workflow to run on 20.04 to fix CI
jfecher Dec 8, 2022
f6bfb36
Fix merge conflicts
jfecher Jan 3, 2023
d5944a4
Remove extra println
jfecher Jan 3, 2023
2c1c9e9
Edit comments
jfecher Jan 4, 2023
d16af68
Add efficiency comment
jfecher Jan 4, 2023
9a2eb94
Add panic when converting an array type into ObjectType directly
jfecher Jan 4, 2023
abcfcda
Fix test fail caused by new panic when converting array types. Fix ca…
jfecher Jan 5, 2023
0674621
Add function argument count check
jfecher Jan 11, 2023
98c9560
Code review; remove printlns
jfecher Jan 11, 2023
41a0037
Fix merge conflicts
jfecher Jan 11, 2023
ee0c4e7
Remove returned_arrays and ArraySetId tracking
jfecher Jan 12, 2023
6a06443
Fix merge conflicts
jfecher Jan 13, 2023
1382d81
Revert "Remove returned_arrays and ArraySetId tracking"
jfecher Jan 13, 2023
c5b8d66
Revert "Revert "Remove returned_arrays and ArraySetId tracking""
jfecher Jan 17, 2023
3df1183
Fix Results handling and add function name to debug output
jfecher Jan 17, 2023
6225027
Some code review
jfecher Jan 17, 2023
dd764ba
Fix last bug introduced by the function name commit
jfecher Jan 17, 2023
4001386
Revert inlining changes
jfecher Jan 17, 2023
c4f58ff
Re-add returned_arrays. Higher-order functions that return arrays are…
jfecher Jan 17, 2023
31f05b6
Dont update call graph for higher order functions
jfecher Jan 17, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 10 additions & 1 deletion crates/iter-extended/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,16 @@ where
iterable.into_iter().map(f).collect()
}

/// Equivalent to .into_iter().map(f).collect()
/// Equivalent to .into_iter().map(f).collect::<Result<Vec<_>,_>>()
pub fn try_vecmap<T, U, E, F>(iterable: T, f: F) -> Result<Vec<U>, E>
where
T: IntoIterator,
F: FnMut(T::Item) -> Result<U, E>,
{
iterable.into_iter().map(f).collect()
}

/// Equivalent to .into_iter().map(f).collect::<BTreeMap<K, V>>()
pub fn btree_map<T, K, V, F>(iterable: T, f: F) -> BTreeMap<K, V>
where
T: IntoIterator,
Expand Down
20 changes: 15 additions & 5 deletions crates/nargo/tests/prove_and_verify.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,11 +41,21 @@ mod tests {
cdir.push(TEST_DATA_DIR);

for c in fs::read_dir(cdir.as_path()).unwrap().flatten() {
let test_name = c.file_name().into_string();
if let Ok(str) = test_name {
if c.path().is_dir() && !conf_data["exclude"].contains(&str) {
let r = nargo::cli::prove_and_verify("pp", &c.path(), false);
if conf_data["fail"].contains(&str) {
if let Ok(test_name) = c.file_name().into_string() {
println!("Running test {:?}", test_name);
if c.path().is_dir() && !conf_data["exclude"].contains(&test_name) {
let verified = std::panic::catch_unwind(|| {
nargo::cli::prove_and_verify("pp", &c.path(), false)
});

let r = match verified {
Ok(result) => result,
Err(_) => {
panic!("\n\n\nPanic occured while running test {:?} (ignore the following panic)", c.file_name());
}
};

if conf_data["fail"].contains(&test_name) {
assert!(!r, "{:?} should not succeed", c.file_name());
} else {
assert!(r, "verification fail for {:?}", c.file_name());
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
return = "5"
22 changes: 22 additions & 0 deletions crates/nargo/tests/test_data/higher-order-functions/src/main.nr
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
fn main() -> pub Field {
let f = if 3 * 7 > 200 { foo } else { bar };
constrain f()[1] == 2;

twice(add1, 3)
}

fn foo() -> [u32; 2] {
[1, 3]
}

fn bar() -> [u32; 2] {
[3, 2]
}

fn add1(x: Field) -> Field {
x + 1
}

fn twice(f: fn(Field) -> Field, x: Field) -> Field {
f(f(x))
}
4 changes: 2 additions & 2 deletions crates/noirc_driver/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -186,10 +186,10 @@ impl Driver {
let func_meta = self.context.def_interner.function_meta(&main_function);
let abi = func_meta.into_abi(&self.context.def_interner);

let ast = monomorphise(main_function, self.context.def_interner);
let program = monomorphise(main_function, self.context.def_interner);

// Compile Program
let circuit = match create_circuit(ast, np_language, show_ssa) {
let circuit = match create_circuit(program, np_language, show_ssa) {
Ok(circuit) => circuit,
Err(err) => {
// The FileId here will be the file id of the file with the main file
Expand Down
40 changes: 0 additions & 40 deletions crates/noirc_evaluator/src/builtin/mod.rs

This file was deleted.

9 changes: 5 additions & 4 deletions crates/noirc_evaluator/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,7 @@ impl Evaluator {
fn param_to_var(
&mut self,
name: &str,
def: DefinitionId,
def: Definition,
param_type: &AbiType,
visibility: &AbiVisibility,
igen: &mut IRGenerator,
Expand Down Expand Up @@ -235,9 +235,10 @@ impl Evaluator {
let abi_params = std::mem::take(&mut igen.program.abi.parameters);
assert_eq!(main_params.len(), abi_params.len());

for ((param_id, _, param_name1, _), abi_param) in main_params.iter().zip(abi_params) {
assert_eq!(param_name1, &abi_param.name);
self.param_to_var(param_name1, *param_id, &abi_param.typ, &abi_param.visibility, igen)
for ((param_id, _, param_name, _), abi_param) in main_params.iter().zip(abi_params) {
assert_eq!(param_name, &abi_param.name);
let def = Definition::Local(*param_id);
self.param_to_var(param_name, def, &abi_param.typ, &abi_param.visibility, igen)
.unwrap();
}
}
Expand Down
12 changes: 7 additions & 5 deletions crates/noirc_evaluator/src/ssa/block.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::errors::RuntimeError;

use super::{
conditional::AssumptionId,
context::SsaContext,
Expand Down Expand Up @@ -110,11 +112,11 @@ impl BasicBlock {
result.insert(a);
}
}
node::Operation::Call { func_id, returned_arrays, .. } => {
node::Operation::Call { func, returned_arrays, .. } => {
for a in returned_arrays {
result.insert(a.0);
}
if let Some(f) = ctx.get_ssafunc(*func_id) {
if let Some(f) = ctx.try_get_ssafunc(*func) {
for typ in &f.result_types {
if let node::ObjectType::Pointer(a) = typ {
result.insert(*a);
Expand Down Expand Up @@ -474,7 +476,7 @@ pub fn merge_path(
start: BlockId,
end: BlockId,
assumption: Option<NodeId>,
) -> VecDeque<BlockId> {
) -> Result<VecDeque<BlockId>, RuntimeError> {
let mut removed_blocks = VecDeque::new();
if start != end {
let mut next = start;
Expand Down Expand Up @@ -518,7 +520,7 @@ pub fn merge_path(

//we assign the concatened list of instructions to the start block, using a CSE pass
let mut modified = false;
super::optim::cse_block(ctx, start, &mut instructions, &mut modified).unwrap();
super::optim::cse_block(ctx, start, &mut instructions, &mut modified)?;
//Wires start to end
if !end.is_dummy() {
rewire_block_left(ctx, start, end);
Expand All @@ -528,7 +530,7 @@ pub fn merge_path(
removed_blocks.pop_front();
}
//housekeeping for the caller
removed_blocks
Ok(removed_blocks)
}

// retrieve written arrays along the CFG until we reach stop
Expand Down
Loading