HEX
Server: Apache/2.4.46 (Win64) OpenSSL/1.1.1j PHP/8.4.25
System: Windows NT DESKTOP-4TAV2RJ 10.0 build 19045 (Windows 10) AMD64
User: fred (0)
PHP: 8.4.25
Disabled: NONE
Upload Files
File: C:/Users/fred/anaconda3/Lib/site-packages/mypyc/test-data/irbuild-nested.test
[case testNestedFunctions]
from typing import Callable

def a() -> Callable[[], object]:
    def inner() -> object:
        return None
    return inner

def b() -> Callable[[], Callable[[], str]]:
    def first() -> Callable[[], str]:
        def second() -> str:
            return 'b.first.second: nested function'
        return second
    return first

def c(num: float) -> Callable[[str], str]:
    def inner(s: str) -> str:
        return s + '!'
    return inner

def d(num: float) -> str:
    def inner(s: str) -> str:
        return s + '?'
    a = inner('one')
    b = inner('two')
    return a

def inner() -> str:
    return 'inner: normal function'

def first() -> str:
    return 'first: normal function'

def second() -> str:
    return 'second: normal function'
[out]
def inner_a_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_a_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_a_obj
    r0 :: __main__.a_env
    r1 :: object
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = box(None, 1)
    return r1
def a():
    r0 :: __main__.a_env
    r1 :: __main__.inner_a_obj
    r2 :: bool
    inner :: object
L0:
    r0 = a_env()
    r1 = inner_a_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    inner = r1
    return inner
def second_b_first_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def second_b_first_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.second_b_first_obj
    r0 :: __main__.first_b_env
    r1 :: __main__.b_env
    r2 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.__mypyc_env__
    r2 = 'b.first.second: nested function'
    return r2
def first_b_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def first_b_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.first_b_obj
    r0 :: __main__.b_env
    r1 :: __main__.first_b_env
    r2 :: bool
    r3 :: __main__.second_b_first_obj
    r4 :: bool
    second :: object
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = first_b_env()
    r1.__mypyc_env__ = r0; r2 = is_error
    r3 = second_b_first_obj()
    r3.__mypyc_env__ = r1; r4 = is_error
    second = r3
    return second
def b():
    r0 :: __main__.b_env
    r1 :: __main__.first_b_obj
    r2 :: bool
    first :: object
L0:
    r0 = b_env()
    r1 = first_b_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    first = r1
    return first
def inner_c_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_c_obj.__call__(__mypyc_self__, s):
    __mypyc_self__ :: __main__.inner_c_obj
    s :: str
    r0 :: __main__.c_env
    r1, r2 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = '!'
    r2 = PyUnicode_Concat(s, r1)
    return r2
def c(num):
    num :: float
    r0 :: __main__.c_env
    r1 :: __main__.inner_c_obj
    r2 :: bool
    inner :: object
L0:
    r0 = c_env()
    r1 = inner_c_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    inner = r1
    return inner
def inner_d_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_d_obj.__call__(__mypyc_self__, s):
    __mypyc_self__ :: __main__.inner_d_obj
    s :: str
    r0 :: __main__.d_env
    r1, r2 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = '?'
    r2 = PyUnicode_Concat(s, r1)
    return r2
def d(num):
    num :: float
    r0 :: __main__.d_env
    r1 :: __main__.inner_d_obj
    r2 :: bool
    inner :: object
    r3 :: str
    r4 :: object
    r5, a, r6 :: str
    r7 :: object
    r8, b :: str
L0:
    r0 = d_env()
    r1 = inner_d_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    inner = r1
    r3 = 'one'
    r4 = PyObject_CallFunctionObjArgs(inner, r3, 0)
    r5 = cast(str, r4)
    a = r5
    r6 = 'two'
    r7 = PyObject_CallFunctionObjArgs(inner, r6, 0)
    r8 = cast(str, r7)
    b = r8
    return a
def inner():
    r0 :: str
L0:
    r0 = 'inner: normal function'
    return r0
def first():
    r0 :: str
L0:
    r0 = 'first: normal function'
    return r0
def second():
    r0 :: str
L0:
    r0 = 'second: normal function'
    return r0

[case testFreeVars]
from typing import Callable

def a(num: int) -> int:
    def inner() -> int:
        return num
    return inner()

def b() -> int:
    num = 3
    def inner() -> int:
        nonlocal num
        num = 4
        foo = 6
        return num
    return inner() + num

def c(flag: bool) -> str:
    if flag:
        def inner() -> str:
            return 'f.inner: first definition'
    else:
        def inner() -> str:
            return 'f.inner: second definition'
    return inner()

[out]
def inner_a_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_a_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_a_obj
    r0 :: __main__.a_env
    r1 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.num
    return r1
def a(num):
    num :: int
    r0 :: __main__.a_env
    r1 :: bool
    r2 :: __main__.inner_a_obj
    r3 :: bool
    inner, r4 :: object
    r5 :: int
L0:
    r0 = a_env()
    r0.num = num; r1 = is_error
    r2 = inner_a_obj()
    r2.__mypyc_env__ = r0; r3 = is_error
    inner = r2
    r4 = PyObject_CallFunctionObjArgs(inner, 0)
    r5 = unbox(int, r4)
    return r5
def inner_b_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_b_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_b_obj
    r0 :: __main__.b_env
    r1 :: bool
    foo, r2 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r0.num = 8; r1 = is_error
    foo = 12
    r2 = r0.num
    return r2
def b():
    r0 :: __main__.b_env
    r1 :: bool
    r2 :: __main__.inner_b_obj
    r3 :: bool
    inner, r4 :: object
    r5, r6, r7 :: int
L0:
    r0 = b_env()
    r0.num = 6; r1 = is_error
    r2 = inner_b_obj()
    r2.__mypyc_env__ = r0; r3 = is_error
    inner = r2
    r4 = PyObject_CallFunctionObjArgs(inner, 0)
    r5 = unbox(int, r4)
    r6 = r0.num
    r7 = CPyTagged_Add(r5, r6)
    return r7
def inner_c_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_c_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_c_obj
    r0 :: __main__.c_env
    r1 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = 'f.inner: first definition'
    return r1
def inner_c_obj_0.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_c_obj_0.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_c_obj_0
    r0 :: __main__.c_env
    r1 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = 'f.inner: second definition'
    return r1
def c(flag):
    flag :: bool
    r0 :: __main__.c_env
    r1 :: __main__.inner_c_obj
    r2 :: bool
    inner :: object
    r3 :: __main__.inner_c_obj_0
    r4 :: bool
    r5 :: object
    r6 :: str
L0:
    r0 = c_env()
    if flag goto L1 else goto L2 :: bool
L1:
    r1 = inner_c_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    inner = r1
    goto L3
L2:
    r3 = inner_c_obj_0()
    r3.__mypyc_env__ = r0; r4 = is_error
    inner = r3
L3:
    r5 = PyObject_CallFunctionObjArgs(inner, 0)
    r6 = cast(str, r5)
    return r6

[case testSpecialNested]
def a() -> int:
    x = 1
    def b() -> int:
        x += 1
        def c() -> int:
            return x
        return c()
    return b()

[out]
def c_a_b_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def c_a_b_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.c_a_b_obj
    r0 :: __main__.b_a_env
    r1 :: __main__.a_env
    r2 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.__mypyc_env__
    r2 = r1.x
    return r2
def b_a_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def b_a_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.b_a_obj
    r0 :: __main__.a_env
    r1 :: __main__.b_a_env
    r2 :: bool
    r3, r4 :: int
    r5 :: bool
    r6 :: __main__.c_a_b_obj
    r7 :: bool
    c, r8 :: object
    r9 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = b_a_env()
    r1.__mypyc_env__ = r0; r2 = is_error
    r3 = r0.x
    r4 = CPyTagged_Add(r3, 2)
    r0.x = r4; r5 = is_error
    r6 = c_a_b_obj()
    r6.__mypyc_env__ = r1; r7 = is_error
    c = r6
    r8 = PyObject_CallFunctionObjArgs(c, 0)
    r9 = unbox(int, r8)
    return r9
def a():
    r0 :: __main__.a_env
    r1 :: bool
    r2 :: __main__.b_a_obj
    r3 :: bool
    b, r4 :: object
    r5 :: int
L0:
    r0 = a_env()
    r0.x = 2; r1 = is_error
    r2 = b_a_obj()
    r2.__mypyc_env__ = r0; r3 = is_error
    b = r2
    r4 = PyObject_CallFunctionObjArgs(b, 0)
    r5 = unbox(int, r4)
    return r5

[case testNestedFunctionInsideStatements]
def f(flag: bool) -> str:
    if flag:
        def inner() -> str:
            return 'f.inner: first definition'
    else:
        def inner() -> str:
            return 'f.inner: second definition'
    return inner()
[out]
def inner_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_f_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_f_obj
    r0 :: __main__.f_env
    r1 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = 'f.inner: first definition'
    return r1
def inner_f_obj_0.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def inner_f_obj_0.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.inner_f_obj_0
    r0 :: __main__.f_env
    r1 :: str
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = 'f.inner: second definition'
    return r1
def f(flag):
    flag :: bool
    r0 :: __main__.f_env
    r1 :: __main__.inner_f_obj
    r2 :: bool
    inner :: object
    r3 :: __main__.inner_f_obj_0
    r4 :: bool
    r5 :: object
    r6 :: str
L0:
    r0 = f_env()
    if flag goto L1 else goto L2 :: bool
L1:
    r1 = inner_f_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    inner = r1
    goto L3
L2:
    r3 = inner_f_obj_0()
    r3.__mypyc_env__ = r0; r4 = is_error
    inner = r3
L3:
    r5 = PyObject_CallFunctionObjArgs(inner, 0)
    r6 = cast(str, r5)
    return r6

[case testNestedFunctionsCallEachOther]
from typing import Callable, List

def f(a: int) -> int:
    def foo() -> int:
        return a + 1

    def bar() -> int:
        return foo()

    def baz(n: int) -> int:
        if n == 0:
            return 0
        return n + baz(n - 1)

    return bar() + baz(a)

[out]
def foo_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def foo_f_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.foo_f_obj
    r0 :: __main__.f_env
    r1, r2 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.a
    r2 = CPyTagged_Add(r1, 2)
    return r2
def bar_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def bar_f_obj.__call__(__mypyc_self__):
    __mypyc_self__ :: __main__.bar_f_obj
    r0 :: __main__.f_env
    r1, r2 :: object
    r3 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.foo
    r2 = PyObject_CallFunctionObjArgs(r1, 0)
    r3 = unbox(int, r2)
    return r3
def baz_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def baz_f_obj.__call__(__mypyc_self__, n):
    __mypyc_self__ :: __main__.baz_f_obj
    n :: int
    r0 :: __main__.f_env
    r1 :: bit
    r2 :: int
    r3, r4, r5 :: object
    r6, r7 :: int
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = int_eq n, 0
    if r1 goto L1 else goto L2 :: bool
L1:
    return 0
L2:
    r2 = CPyTagged_Subtract(n, 2)
    r3 = r0.baz
    r4 = box(int, r2)
    r5 = PyObject_CallFunctionObjArgs(r3, r4, 0)
    r6 = unbox(int, r5)
    r7 = CPyTagged_Add(n, r6)
    return r7
def f(a):
    a :: int
    r0 :: __main__.f_env
    r1 :: bool
    r2 :: __main__.foo_f_obj
    r3, r4 :: bool
    r5 :: __main__.bar_f_obj
    r6, r7 :: bool
    r8 :: __main__.baz_f_obj
    r9, r10 :: bool
    r11, r12 :: object
    r13, r14 :: int
    r15, r16, r17 :: object
    r18, r19 :: int
L0:
    r0 = f_env()
    r0.a = a; r1 = is_error
    r2 = foo_f_obj()
    r2.__mypyc_env__ = r0; r3 = is_error
    r0.foo = r2; r4 = is_error
    r5 = bar_f_obj()
    r5.__mypyc_env__ = r0; r6 = is_error
    r0.bar = r5; r7 = is_error
    r8 = baz_f_obj()
    r8.__mypyc_env__ = r0; r9 = is_error
    r0.baz = r8; r10 = is_error
    r11 = r0.bar
    r12 = PyObject_CallFunctionObjArgs(r11, 0)
    r13 = unbox(int, r12)
    r14 = r0.a
    r15 = r0.baz
    r16 = box(int, r14)
    r17 = PyObject_CallFunctionObjArgs(r15, r16, 0)
    r18 = unbox(int, r17)
    r19 = CPyTagged_Add(r13, r18)
    return r19

[case testLambdas]
def f(x: int, y: int) -> None:
    s = lambda a, b: a + b
    t = lambda a, b: s(a, b)
    return t(x, y)

[out]
def __mypyc_lambda__0_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def __mypyc_lambda__0_f_obj.__call__(__mypyc_self__, a, b):
    __mypyc_self__ :: __main__.__mypyc_lambda__0_f_obj
    a, b :: object
    r0 :: __main__.f_env
    r1 :: object
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = PyNumber_Add(a, b)
    return r1
def __mypyc_lambda__1_f_obj.__get__(__mypyc_self__, instance, owner):
    __mypyc_self__, instance, owner, r0 :: object
    r1 :: bit
    r2 :: object
L0:
    r0 = load_address _Py_NoneStruct
    r1 = instance == r0
    if r1 goto L1 else goto L2 :: bool
L1:
    return __mypyc_self__
L2:
    r2 = PyMethod_New(__mypyc_self__, instance)
    return r2
def __mypyc_lambda__1_f_obj.__call__(__mypyc_self__, a, b):
    __mypyc_self__ :: __main__.__mypyc_lambda__1_f_obj
    a, b :: object
    r0 :: __main__.f_env
    r1, r2 :: object
L0:
    r0 = __mypyc_self__.__mypyc_env__
    r1 = r0.s
    r2 = PyObject_CallFunctionObjArgs(r1, a, b, 0)
    return r2
def f(x, y):
    x, y :: int
    r0 :: __main__.f_env
    r1 :: __main__.__mypyc_lambda__0_f_obj
    r2, r3 :: bool
    r4 :: __main__.__mypyc_lambda__1_f_obj
    r5 :: bool
    t, r6, r7, r8 :: object
    r9 :: None
L0:
    r0 = f_env()
    r1 = __mypyc_lambda__0_f_obj()
    r1.__mypyc_env__ = r0; r2 = is_error
    r0.s = r1; r3 = is_error
    r4 = __mypyc_lambda__1_f_obj()
    r4.__mypyc_env__ = r0; r5 = is_error
    t = r4
    r6 = box(int, x)
    r7 = box(int, y)
    r8 = PyObject_CallFunctionObjArgs(t, r6, r7, 0)
    r9 = unbox(None, r8)
    return r9

[case testRecursiveFunction]
from typing import Callable

def baz(n: int) -> int:
    if n == 0:
        return 0
    return n + baz(n - 1)

[out]
def baz(n):
    n :: int
    r0 :: bit
    r1, r2, r3 :: int
L0:
    r0 = int_eq n, 0
    if r0 goto L1 else goto L2 :: bool
L1:
    return 0
L2:
    r1 = CPyTagged_Subtract(n, 2)
    r2 = baz(r1)
    r3 = CPyTagged_Add(n, r2)
    return r3