//! > Test simple inlining.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(n: felt252) -> felt252 {
-n
}
//! > function_name
foo
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- core::Felt252Neg::neg(v0)
End:
Return(v1)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v2: core::felt252) <- -1
(v3: core::felt252) <- core::felt252_mul(v0, v2)
End:
Goto(blk2, {v3 -> v1})
blk2:
Statements:
End:
Return(v1)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test generic function inlining.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(val: Option<felt252>) -> felt252 {
bar(val, 2)
}
//! > function_name
foo
//! > module_code
/// If `val` is `Some(x)`, returns `x`. Otherwise, panics.
#[inline]
fn bar<T, impl TDrop: Drop<T>>(val: Option<T>, val2: T) -> T {
match val {
Some(x) => x,
None => val2,
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::option::Option::<core::felt252>
blk0 (root):
Statements:
(v1: core::felt252) <- 2
(v2: core::felt252) <- test::bar::<core::felt252, core::felt252Drop>(v0, v1)
End:
Return(v2)
//! > after
Parameters: v0: core::option::Option::<core::felt252>
blk0 (root):
Statements:
(v1: core::felt252) <- 2
End:
Goto(blk1, {})
blk1:
Statements:
End:
Match(match_enum(v0) {
Option::Some(v3) => blk2,
Option::None(v4) => blk3,
})
blk2:
Statements:
End:
Goto(blk4, {v3 -> v2})
blk3:
Statements:
End:
Goto(blk4, {v1 -> v2})
blk4:
Statements:
End:
Return(v2)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test inlining same arg twice.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(n: felt252) -> felt252 {
bar(n, n)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn bar(a: felt252, b: felt252) -> felt252 {
a + b
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0, v0)
End:
Return(v1)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v2: core::felt252) <- core::felt252_add(v0, v0)
End:
Goto(blk2, {v2 -> v1})
blk2:
Statements:
End:
Return(v1)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test inlining.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: felt252, b: felt252) -> felt252 {
bar(a + b, b)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn bar(a: felt252, b: felt252) -> felt252 implicits() {
bar2(a, b) + bar2(b, a)
}
#[inline(always)]
fn bar2(a: felt252, b: felt252) -> felt252 implicits() {
a * b
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252, v1: core::felt252
blk0 (root):
Statements:
(v2: core::felt252) <- core::Felt252Add::add(v0, v1)
(v3: core::felt252) <- test::bar(v2, v1)
End:
Return(v3)
//! > after
Parameters: v0: core::felt252, v1: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v4: core::felt252) <- core::felt252_add(v0, v1)
End:
Goto(blk2, {v4 -> v2})
blk2:
Statements:
End:
Goto(blk3, {})
blk3:
Statements:
(v5: core::felt252) <- core::felt252_mul(v2, v1)
(v6: core::felt252) <- core::felt252_mul(v1, v2)
(v7: core::felt252) <- core::felt252_add(v5, v6)
End:
Goto(blk4, {v7 -> v3})
blk4:
Statements:
End:
Return(v3)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test recursive inlining.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: felt252) -> felt252 {
first(a)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn first(a: felt252) -> felt252 {
second(a)
}
#[inline(always)]
fn second(a: felt252) -> felt252 {
third(a)
}
#[inline(always)]
fn third(a: felt252) -> felt252 {
a * a
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::first(v0)
End:
Return(v1)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v2: core::felt252) <- core::felt252_mul(v0, v0)
End:
Goto(blk2, {v2 -> v1})
blk2:
Statements:
End:
Return(v1)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test impl inlining.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo() {
let mut arr = array![];
arr.append(5)
}
//! > function_name
foo
//! > semantic_diagnostics
//! > before
Parameters:
blk0 (root):
Statements:
(v0: core::array::Array::<core::felt252>) <- core::array::ArrayImpl::<core::felt252>::new()
(v1: core::felt252) <- 5
(v3: core::array::Array::<core::felt252>) <- core::array::ArrayImpl::<core::felt252>::append(v0, v1)
(v2: ()) <- struct_construct()
() <- struct_destructure(v2)
End:
Return()
//! > after
Parameters:
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v4: core::array::Array::<core::felt252>) <- core::array::array_new::<core::felt252>()
End:
Goto(blk2, {v4 -> v0})
blk2:
Statements:
(v1: core::felt252) <- 5
End:
Goto(blk3, {})
blk3:
Statements:
(v5: core::array::Array::<core::felt252>) <- core::array::array_append::<core::felt252>(v0, v1)
End:
Goto(blk4, {v5 -> v3})
blk4:
Statements:
(v2: ()) <- struct_construct()
() <- struct_destructure(v2)
End:
Return()
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test inlining of a function with an early return.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: felt252) -> felt252 {
if a == 2 {
bar(a)
} else {
a
}
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn bar(a: felt252) -> felt252 {
if a == 0 {
return 1;
}
0
}
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252, v2: @core::felt252) <- snapshot(v0)
(v3: core::felt252) <- 2
(v4: core::felt252, v5: @core::felt252) <- snapshot(v3)
(v6: core::bool) <- core::Felt252PartialEq::eq(v2, v5)
End:
Match(match_enum(v6) {
bool::False(v8) => blk2,
bool::True(v7) => blk1,
})
blk1:
Statements:
(v9: core::felt252) <- test::bar(v1)
End:
Goto(blk3, {v9 -> v10})
blk2:
Statements:
End:
Goto(blk3, {v1 -> v10})
blk3:
Statements:
End:
Return(v10)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252, v2: @core::felt252) <- snapshot(v0)
(v3: core::felt252) <- 2
(v4: core::felt252, v5: @core::felt252) <- snapshot(v3)
End:
Goto(blk4, {})
blk1:
Statements:
End:
Goto(blk8, {})
blk2:
Statements:
End:
Goto(blk3, {v1 -> v10})
blk3:
Statements:
End:
Return(v10)
blk4:
Statements:
(v11: core::felt252) <- desnap(v2)
(v12: core::felt252) <- desnap(v5)
(v13: core::felt252) <- core::felt252_sub(v11, v12)
End:
Match(match core::felt252_is_zero(v13) {
IsZeroResult::Zero => blk5,
IsZeroResult::NonZero(v14) => blk6,
})
blk5:
Statements:
(v15: ()) <- struct_construct()
(v16: core::bool) <- bool::True(v15)
End:
Goto(blk7, {v16 -> v6})
blk6:
Statements:
(v17: ()) <- struct_construct()
(v18: core::bool) <- bool::False(v17)
End:
Goto(blk7, {v18 -> v6})
blk7:
Statements:
End:
Match(match_enum(v6) {
bool::False(v8) => blk2,
bool::True(v7) => blk1,
})
blk8:
Statements:
End:
Match(match core::felt252_is_zero(v1) {
IsZeroResult::Zero => blk9,
IsZeroResult::NonZero(v19) => blk10,
})
blk9:
Statements:
(v20: core::felt252) <- 1
End:
Goto(blk11, {v20 -> v9})
blk10:
Statements:
(v21: core::felt252) <- 0
End:
Goto(blk11, {v21 -> v9})
blk11:
Statements:
End:
Goto(blk3, {v9 -> v10})
//! > lowering_diagnostics
//! > semantic_diagnostics
//! > ==========================================================================
//! > Test inlining heuristic
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: felt252) -> felt252 {
bar(a) + bar2(a)
}
//! > function_name
foo
//! > module_code
fn bar(a: felt252) -> felt252 {
bar2(a)
}
fn bar2(a: felt252) -> felt252 {
1
}
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0)
(v2: core::felt252) <- test::bar2(v0)
(v3: core::felt252) <- core::Felt252Add::add(v1, v2)
End:
Return(v3)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
(v4: core::felt252) <- 1
End:
Goto(blk2, {v4 -> v1})
blk2:
Statements:
End:
Goto(blk3, {})
blk3:
Statements:
(v5: core::felt252) <- 1
End:
Goto(blk4, {v5 -> v2})
blk4:
Statements:
End:
Goto(blk5, {})
blk5:
Statements:
(v6: core::felt252) <- core::felt252_add(v1, v2)
End:
Goto(blk6, {v6 -> v3})
blk6:
Statements:
End:
Return(v3)
//! > lowering_diagnostics
//! > semantic_diagnostics
//! > ==========================================================================
//! > Test preventing inlining heuristic
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: felt252) -> felt252 {
bar(a) + bar2(a)
}
//! > function_name
foo
//! > module_code
#[inline(never)]
fn bar(a: felt252) -> felt252 {
bar2(a)
}
#[inline(never)]
fn bar2(a: felt252) -> felt252 {
1
}
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0)
(v2: core::felt252) <- test::bar2(v0)
(v3: core::felt252) <- core::Felt252Add::add(v1, v2)
End:
Return(v3)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0)
(v2: core::felt252) <- test::bar2(v0)
End:
Goto(blk1, {})
blk1:
Statements:
(v4: core::felt252) <- core::felt252_add(v1, v2)
End:
Goto(blk2, {v4 -> v3})
blk2:
Statements:
End:
Return(v3)
//! > lowering_diagnostics
//! > semantic_diagnostics
//! > ==========================================================================
//! > Test returning an input variable as is (not in the last block).
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo() -> felt252 {
bar(0)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn bar(a: felt252) -> felt252 {
if a == 0 {
return a;
}
1
}
//! > semantic_diagnostics
//! > lowering_diagnostics
//! > before
Parameters:
blk0 (root):
Statements:
(v0: core::felt252) <- 0
(v1: core::felt252) <- test::bar(v0)
End:
Return(v1)
//! > after
Parameters:
blk0 (root):
Statements:
(v0: core::felt252) <- 0
End:
Goto(blk1, {})
blk1:
Statements:
End:
Match(match core::felt252_is_zero(v0) {
IsZeroResult::Zero => blk2,
IsZeroResult::NonZero(v2) => blk3,
})
blk2:
Statements:
End:
Goto(blk4, {v0 -> v1})
blk3:
Statements:
(v3: core::felt252) <- 1
End:
Goto(blk4, {v3 -> v1})
blk4:
Statements:
End:
Return(v1)
//! > ==========================================================================
//! > Test inlining of identity function.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(n: felt252) -> felt252 {
identity(n)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn identity(n: felt252) -> felt252 {
n
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::identity(v0)
End:
Return(v1)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
End:
Goto(blk2, {v0 -> v1})
blk2:
Statements:
End:
Return(v1)
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test match where is there is a return in one branch.
//! > Motivation:
// The goal of this test is to test the block renaming logic.
// A panicable function can have a block with a low `block_id` with a match_arm that goes
// to a higher 'block_id'.
// We want to test this outside of the outer scope as the last block is rebuilt last.
//! > test_runner_name
test_function_inlining
//! > function_code
fn foo(a: u128, b: u128) -> u128 {
bar1(a, b)
}
//! > function_name
foo
//! > module_code
#[inline(always)]
fn bar1(a: u128, b: u128) -> u128 {
if a == 1_u128 {
return bar2(b, a);
}
a
}
#[inline(always)]
fn bar2(a: u128, b: u128) -> u128 {
a + b
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::integer::u128, v1: core::integer::u128
blk0 (root):
Statements:
(v3: core::panics::PanicResult::<(core::integer::u128,)>) <- test::bar1(v0, v1)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk2,
PanicResult::Err(v6) => blk3,
})
blk1:
Statements:
(v7: (core::integer::u128,)) <- struct_construct(v2)
(v8: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Ok(v7)
End:
Return(v8)
blk2:
Statements:
(v5: core::integer::u128) <- struct_destructure(v4)
End:
Goto(blk1, {v5 -> v2})
blk3:
Statements:
(v9: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Err(v6)
End:
Return(v9)
//! > after
Parameters: v0: core::integer::u128, v1: core::integer::u128
blk0 (root):
Statements:
End:
Goto(blk4, {})
blk1:
Statements:
(v7: (core::integer::u128,)) <- struct_construct(v2)
(v8: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Ok(v7)
End:
Return(v8)
blk2:
Statements:
(v5: core::integer::u128) <- struct_destructure(v4)
End:
Goto(blk1, {v5 -> v2})
blk3:
Statements:
(v9: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Err(v6)
End:
Return(v9)
blk4:
Statements:
(v10: core::integer::u128) <- 1
End:
Match(match core::integer::u128_eq(v0, v10) {
bool::False => blk5,
bool::True => blk6,
})
blk5:
Statements:
(v11: (core::integer::u128,)) <- struct_construct(v0)
(v12: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Ok(v11)
End:
Goto(blk9, {v12 -> v3})
blk6:
Statements:
End:
Match(match core::integer::u128_overflowing_add(v1, v0) {
Result::Ok(v13) => blk7,
Result::Err(v14) => blk8,
})
blk7:
Statements:
(v15: (core::integer::u128,)) <- struct_construct(v13)
(v16: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Ok(v15)
End:
Goto(blk9, {v16 -> v3})
blk8:
Statements:
(v17: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<39878429859757942499084499860145094553463>()
(v18: core::panics::PanicResult::<(core::integer::u128,)>) <- PanicResult::Err(v17)
End:
Goto(blk9, {v18 -> v3})
blk9:
Statements:
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk2,
PanicResult::Err(v6) => blk3,
})
//! > lowering_diagnostics
//! > ==========================================================================
//! > Test inlining a function where the root block does not return.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline(always)]
fn bar(n: felt252) -> felt252 {
if n == 0 {
return 1;
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0)
End:
Return(v1)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
End:
Match(match core::felt252_is_zero(v0) {
IsZeroResult::Zero => blk2,
IsZeroResult::NonZero(v2) => blk3,
})
blk2:
Statements:
End:
Goto(blk4, {})
blk3:
Statements:
End:
Goto(blk4, {})
blk4:
Statements:
(v3: core::felt252) <- 1
End:
Goto(blk5, {v3 -> v1})
blk5:
Statements:
End:
Return(v1)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with indirect self call.
//! > Motivation:
//! #[inline] functions should inline a function unless they are on a call cycle.
//! in this test `bar` should not be inlined into `foo`.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
if n == 0 {
foo(n - 1)
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with direct self call.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
foo(n)
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::foo(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::foo(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with direct self call in a called function.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
if n == 0 {
bar(n - 1)
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v2: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v2: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with direct self call inside two levels of called functions.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
baz(n)
}
#[inline]
fn baz(n: felt252) -> felt252 {
if n == 0 {
baz(n - 1)
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v2: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk4, {})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
blk4:
Statements:
(v9: core::panics::PanicResult::<(core::felt252,)>) <- test::baz(v0)
End:
Goto(blk5, {v9 -> v2})
blk5:
Statements:
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with call a callee from a called function.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
baz(n)
}
#[inline]
fn baz(n: felt252) -> felt252 {
if n == 0 {
bar(n - 1)
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v2: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v2: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v2) {
PanicResult::Ok(v3) => blk2,
PanicResult::Err(v5) => blk3,
})
blk1:
Statements:
(v6: (core::felt252,)) <- struct_construct(v1)
(v7: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v6)
End:
Return(v7)
blk2:
Statements:
(v4: core::felt252) <- struct_destructure(v3)
End:
Goto(blk1, {v4 -> v1})
blk3:
Statements:
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v5)
End:
Return(v8)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with call a two levels above callee from a called function.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
#[inline]
fn foo(n: felt252) -> felt252 {
bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
baz(n)
}
#[inline]
fn baz(n: felt252) -> felt252 {
if n == 0 {
foo(n - 1)
} else {
return 1;
}
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Match(match core::gas::withdraw_gas() {
Option::Some => blk1,
Option::None => blk2,
})
blk1:
Statements:
(v3: core::panics::PanicResult::<(core::felt252,)>) <- test::bar(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk4,
PanicResult::Err(v6) => blk5,
})
blk2:
Statements:
(v7: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<375233589013918064796019>()
(v8: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v7)
End:
Return(v8)
blk3:
Statements:
(v9: (core::felt252,)) <- struct_construct(v1)
(v10: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Ok(v9)
End:
Return(v10)
blk4:
Statements:
(v5: core::felt252) <- struct_destructure(v4)
End:
Goto(blk3, {v5 -> v1})
blk5:
Statements:
(v11: core::panics::PanicResult::<(core::felt252,)>) <- PanicResult::Err(v6)
End:
Return(v11)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test #[inline] with call a function twice.
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
fn foo(n: felt252) -> felt252 {
bar(n) + bar(n)
}
//! > module_code
#[inline]
fn bar(n: felt252) -> felt252 {
n
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v1: core::felt252) <- test::bar(v0)
(v2: core::felt252) <- test::bar(v0)
(v3: core::felt252) <- core::Felt252Add::add(v1, v2)
End:
Return(v3)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk1, {})
blk1:
Statements:
End:
Goto(blk2, {v0 -> v1})
blk2:
Statements:
End:
Goto(blk3, {})
blk3:
Statements:
End:
Goto(blk4, {v0 -> v2})
blk4:
Statements:
End:
Goto(blk5, {})
blk5:
Statements:
(v4: core::felt252) <- core::felt252_add(v1, v2)
End:
Goto(blk6, {v4 -> v3})
blk6:
Statements:
End:
Return(v3)
//! > lowering_diagnostics
//! > ==========================================================================
//! > test panic destruct impl
//! > test_runner_name
test_function_inlining
//! > function_name
foo
//! > function_code
fn foo(n: felt252) {
bar(n);
}
//! > module_code
#[inline]
fn bar<T, +PanicDestruct<T>>(n: T) {
panic_with_felt252('panic')
}
//! > semantic_diagnostics
//! > before
Parameters: v0: core::felt252
blk0 (root):
Statements:
(v3: core::panics::PanicResult::<((),)>) <- test::bar::<core::felt252, core::traits::PanicDestructForDestruct::<core::felt252, core::traits::DestructFromDrop::<core::felt252, core::felt252Drop>>>(v0)
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk2,
PanicResult::Err(v6) => blk3,
})
blk1:
Statements:
(v2: ()) <- struct_construct()
(v7: ((),)) <- struct_construct(v2)
(v8: core::panics::PanicResult::<((),)>) <- PanicResult::Ok(v7)
End:
Return(v8)
blk2:
Statements:
(v5: ()) <- struct_destructure(v4)
End:
Goto(blk1, {v5 -> v1})
blk3:
Statements:
(v9: core::panics::PanicResult::<((),)>) <- PanicResult::Err(v6)
End:
Return(v9)
//! > after
Parameters: v0: core::felt252
blk0 (root):
Statements:
End:
Goto(blk4, {})
blk1:
Statements:
(v2: ()) <- struct_construct()
(v7: ((),)) <- struct_construct(v2)
(v8: core::panics::PanicResult::<((),)>) <- PanicResult::Ok(v7)
End:
Return(v8)
blk2:
Statements:
(v5: ()) <- struct_destructure(v4)
End:
Goto(blk1, {v5 -> v1})
blk3:
Statements:
(v9: core::panics::PanicResult::<((),)>) <- PanicResult::Err(v6)
End:
Return(v9)
blk4:
Statements:
(v10: (core::panics::Panic, core::array::Array::<core::felt252>)) <- core::panic_with_const_felt252::<482670963043>()
(v11: core::panics::PanicResult::<((),)>) <- PanicResult::Err(v10)
End:
Goto(blk5, {v11 -> v3})
blk5:
Statements:
End:
Match(match_enum(v3) {
PanicResult::Ok(v4) => blk2,
PanicResult::Err(v6) => blk3,
})
//! > lowering_diagnostics