| [case testTrivialFunction] |
| def f() -> int: |
| return 1 |
| [out] |
| def f(): |
| L0: |
| return 2 |
| [case testFunctionArgument] |
| def f(x: int) -> int: |
| return x |
| [out] |
| def f(x): |
| x :: int |
| L0: |
| return x |
| |
| |
| [case testExplicitNoneReturn] |
| def f() -> None: |
| return |
| [out] |
| def f(): |
| L0: |
| return 1 |
| |
| [case testExplicitNoneReturn2] |
| def f() -> None: |
| return None |
| [out] |
| def f(): |
| L0: |
| return 1 |
| |
| [case testAssignment] |
| def f() -> int: |
| x = 1 |
| y = x |
| return y |
| [out] |
| def f(): |
| x, y :: int |
| L0: |
| x = 2 |
| y = x |
| return y |
| |
| [case testAssignmentTwice] |
| def f(x: int) -> None: |
| y = 1 |
| y = x |
| return |
| [out] |
| def f(x): |
| x, y :: int |
| L0: |
| y = 2 |
| y = x |
| return 1 |
| |
| [case testIntArithmetic] |
| def f(x: int, y: int) -> int: |
| return x * (y + 1) |
| [out] |
| def f(x, y): |
| x, y, r0, r1 :: int |
| L0: |
| r0 = CPyTagged_Add(y, 2) |
| r1 = CPyTagged_Multiply(x, r0) |
| return r1 |
| |
| [case testIf] |
| def f(x: int, y: int) -> int: |
| if x < y: |
| x = 1 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L4 else goto L5 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L4 else goto L5 :: bool |
| L4: |
| x = 2 |
| L5: |
| return x |
| |
| [case testIfElse] |
| def f(x: int, y: int) -> int: |
| if x < y: |
| x = 1 |
| else: |
| x = 2 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L4 else goto L5 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L4 else goto L5 :: bool |
| L4: |
| x = 2 |
| goto L6 |
| L5: |
| x = 4 |
| L6: |
| return x |
| |
| [case testAnd1] |
| def f(x: int, y: int) -> int: |
| if x < y and x > y: |
| x = 1 |
| else: |
| x = 2 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| r6 :: native_int |
| r7 :: bit |
| r8 :: native_int |
| r9, r10, r11 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L4 else goto L9 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L4 else goto L9 :: bool |
| L4: |
| r6 = x & 1 |
| r7 = r6 != 0 |
| if r7 goto L6 else goto L5 :: bool |
| L5: |
| r8 = y & 1 |
| r9 = r8 != 0 |
| if r9 goto L6 else goto L7 :: bool |
| L6: |
| r10 = CPyTagged_IsLt_(y, x) |
| if r10 goto L8 else goto L9 :: bool |
| L7: |
| r11 = x > y :: signed |
| if r11 goto L8 else goto L9 :: bool |
| L8: |
| x = 2 |
| goto L10 |
| L9: |
| x = 4 |
| L10: |
| return x |
| |
| [case testAnd2] |
| def f(x: object, y: object) -> str: |
| return str(x) or str(y) |
| [out] |
| def f(x, y): |
| x, y :: object |
| r0 :: str |
| r1 :: bit |
| r2, r3 :: str |
| L0: |
| r0 = PyObject_Str(x) |
| r1 = CPyStr_IsTrue(r0) |
| if r1 goto L1 else goto L2 :: bool |
| L1: |
| r2 = r0 |
| goto L3 |
| L2: |
| r3 = PyObject_Str(y) |
| r2 = r3 |
| L3: |
| return r2 |
| |
| [case testOr] |
| def f(x: int, y: int) -> int: |
| if x < y or x > y: |
| x = 1 |
| else: |
| x = 2 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| r6 :: native_int |
| r7 :: bit |
| r8 :: native_int |
| r9, r10, r11 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L8 else goto L4 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L8 else goto L4 :: bool |
| L4: |
| r6 = x & 1 |
| r7 = r6 != 0 |
| if r7 goto L6 else goto L5 :: bool |
| L5: |
| r8 = y & 1 |
| r9 = r8 != 0 |
| if r9 goto L6 else goto L7 :: bool |
| L6: |
| r10 = CPyTagged_IsLt_(y, x) |
| if r10 goto L8 else goto L9 :: bool |
| L7: |
| r11 = x > y :: signed |
| if r11 goto L8 else goto L9 :: bool |
| L8: |
| x = 2 |
| goto L10 |
| L9: |
| x = 4 |
| L10: |
| return x |
| |
| [case testOr2] |
| def f(x: object, y: object) -> str: |
| return str(x) and str(y) |
| [out] |
| def f(x, y): |
| x, y :: object |
| r0 :: str |
| r1 :: bit |
| r2, r3 :: str |
| L0: |
| r0 = PyObject_Str(x) |
| r1 = CPyStr_IsTrue(r0) |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = r0 |
| goto L3 |
| L2: |
| r3 = PyObject_Str(y) |
| r2 = r3 |
| L3: |
| return r2 |
| |
| [case testSimpleNot] |
| def f(x: int, y: int) -> int: |
| if not (x < y): |
| x = 1 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L5 else goto L4 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L5 else goto L4 :: bool |
| L4: |
| x = 2 |
| L5: |
| return x |
| |
| [case testNotAnd] |
| def f(x: int, y: int) -> int: |
| if not (x < y and x > y): |
| x = 1 |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| r6 :: native_int |
| r7 :: bit |
| r8 :: native_int |
| r9, r10, r11 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L4 else goto L8 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L4 else goto L8 :: bool |
| L4: |
| r6 = x & 1 |
| r7 = r6 != 0 |
| if r7 goto L6 else goto L5 :: bool |
| L5: |
| r8 = y & 1 |
| r9 = r8 != 0 |
| if r9 goto L6 else goto L7 :: bool |
| L6: |
| r10 = CPyTagged_IsLt_(y, x) |
| if r10 goto L9 else goto L8 :: bool |
| L7: |
| r11 = x > y :: signed |
| if r11 goto L9 else goto L8 :: bool |
| L8: |
| x = 2 |
| L9: |
| return x |
| |
| [case testWhile] |
| def f(x: int, y: int) -> int: |
| while x > y: |
| x = x - y |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| r6 :: int |
| L0: |
| L1: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L3 else goto L2 :: bool |
| L2: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L3 else goto L4 :: bool |
| L3: |
| r4 = CPyTagged_IsLt_(y, x) |
| if r4 goto L5 else goto L6 :: bool |
| L4: |
| r5 = x > y :: signed |
| if r5 goto L5 else goto L6 :: bool |
| L5: |
| r6 = CPyTagged_Subtract(x, y) |
| x = r6 |
| goto L1 |
| L6: |
| return x |
| |
| [case testWhile2] |
| def f(x: int, y: int) -> int: |
| x = 1 |
| while x > y: |
| x = x - y |
| return x |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| r6 :: int |
| L0: |
| x = 2 |
| L1: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L3 else goto L2 :: bool |
| L2: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L3 else goto L4 :: bool |
| L3: |
| r4 = CPyTagged_IsLt_(y, x) |
| if r4 goto L5 else goto L6 :: bool |
| L4: |
| r5 = x > y :: signed |
| if r5 goto L5 else goto L6 :: bool |
| L5: |
| r6 = CPyTagged_Subtract(x, y) |
| x = r6 |
| goto L1 |
| L6: |
| return x |
| |
| [case testImplicitNoneReturn] |
| def f() -> None: |
| pass |
| [out] |
| def f(): |
| L0: |
| return 1 |
| |
| [case testImplicitNoneReturn2] |
| def f() -> None: |
| x = 1 |
| [out] |
| def f(): |
| x :: int |
| L0: |
| x = 2 |
| return 1 |
| |
| [case testImplicitNoneReturnAndIf] |
| def f(x: int, y: int) -> None: |
| if x < y: |
| x = 1 |
| else: |
| y = 2 |
| [out] |
| def f(x, y): |
| x, y :: int |
| r0 :: native_int |
| r1 :: bit |
| r2 :: native_int |
| r3, r4, r5 :: bit |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L2 else goto L1 :: bool |
| L1: |
| r2 = y & 1 |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| r4 = CPyTagged_IsLt_(x, y) |
| if r4 goto L4 else goto L5 :: bool |
| L3: |
| r5 = x < y :: signed |
| if r5 goto L4 else goto L5 :: bool |
| L4: |
| x = 2 |
| goto L6 |
| L5: |
| y = 4 |
| L6: |
| return 1 |
| |
| [case testRecursion] |
| def f(n: int) -> int: |
| if n <= 1: |
| return 1 |
| else: |
| return f(n - 1) + f(n - 2) |
| [out] |
| def f(n): |
| n :: int |
| r0 :: native_int |
| r1, r2, r3 :: bit |
| r4, r5, r6, r7, r8 :: int |
| L0: |
| r0 = n & 1 |
| r1 = r0 != 0 |
| if r1 goto L1 else goto L2 :: bool |
| L1: |
| r2 = CPyTagged_IsLt_(2, n) |
| if r2 goto L4 else goto L3 :: bool |
| L2: |
| r3 = n <= 2 :: signed |
| if r3 goto L3 else goto L4 :: bool |
| L3: |
| return 2 |
| L4: |
| r4 = CPyTagged_Subtract(n, 2) |
| r5 = f(r4) |
| r6 = CPyTagged_Subtract(n, 4) |
| r7 = f(r6) |
| r8 = CPyTagged_Add(r5, r7) |
| return r8 |
| L5: |
| unreachable |
| |
| [case testReportTypeCheckError] |
| def f() -> None: |
| return 1 # E: No return value expected |
| |
| [case testReportSemanticaAnalysisError1] |
| def f(x: List[int]) -> None: pass # E: Name "List" is not defined \ |
| # N: Did you forget to import it from "typing"? (Suggestion: "from typing import List") |
| |
| [case testReportSemanticaAnalysisError2] |
| def f() -> None: |
| x # E: Name "x" is not defined |
| |
| [case testElif] |
| def f(n: int) -> int: |
| if n < 0: |
| x = 1 |
| elif n == 0: |
| x = 1 |
| else: |
| x = 2 |
| return x |
| [out] |
| def f(n): |
| n :: int |
| r0 :: native_int |
| r1, r2, r3 :: bit |
| x :: int |
| r4 :: bit |
| L0: |
| r0 = n & 1 |
| r1 = r0 != 0 |
| if r1 goto L1 else goto L2 :: bool |
| L1: |
| r2 = CPyTagged_IsLt_(n, 0) |
| if r2 goto L3 else goto L4 :: bool |
| L2: |
| r3 = n < 0 :: signed |
| if r3 goto L3 else goto L4 :: bool |
| L3: |
| x = 2 |
| goto L8 |
| L4: |
| r4 = n == 0 |
| if r4 goto L5 else goto L6 :: bool |
| L5: |
| x = 2 |
| goto L7 |
| L6: |
| x = 4 |
| L7: |
| L8: |
| return x |
| |
| [case testUnaryMinus] |
| def f(n: int) -> int: |
| return -n |
| [out] |
| def f(n): |
| n, r0 :: int |
| L0: |
| r0 = CPyTagged_Negate(n) |
| return r0 |
| |
| [case testConditionalExpr] |
| def f(n: int) -> int: |
| return 0 if n == 0 else 1 |
| [out] |
| def f(n): |
| n :: int |
| r0 :: bit |
| r1 :: int |
| L0: |
| r0 = n == 0 |
| if r0 goto L1 else goto L2 :: bool |
| L1: |
| r1 = 0 |
| goto L3 |
| L2: |
| r1 = 2 |
| L3: |
| return r1 |
| |
| [case testOperatorAssignment] |
| def f() -> int: |
| x = 0 |
| x += 1 |
| return x |
| [out] |
| def f(): |
| x, r0 :: int |
| L0: |
| x = 0 |
| r0 = CPyTagged_Add(x, 2) |
| x = r0 |
| return x |
| |
| [case testTrue] |
| def f() -> bool: |
| return True |
| [out] |
| def f(): |
| L0: |
| return 1 |
| |
| [case testFalse] |
| def f() -> bool: |
| return False |
| [out] |
| def f(): |
| L0: |
| return 0 |
| [case testBoolCond] |
| def f(x: bool) -> bool: |
| if x: |
| return False |
| else: |
| return True |
| [out] |
| def f(x): |
| x :: bool |
| L0: |
| if x goto L1 else goto L2 :: bool |
| L1: |
| return 0 |
| L2: |
| return 1 |
| L3: |
| unreachable |
| |
| [case testPycall] |
| import testmodule |
| |
| def f(x: int) -> int: |
| return testmodule.factorial(x) |
| [file testmodule.py] |
| def factorial(x: int) -> int: |
| if x == 0: |
| return 1 |
| else: |
| return x * factorial(x-1) |
| [out] |
| def f(x): |
| x :: int |
| r0 :: object |
| r1 :: str |
| r2, r3, r4 :: object |
| r5 :: int |
| L0: |
| r0 = testmodule :: module |
| r1 = 'factorial' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = box(int, x) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| r5 = unbox(int, r4) |
| return r5 |
| |
| [case testFromImport] |
| from testmodule import g |
| |
| def f(x: int) -> int: |
| return g(x) |
| [file testmodule.py] |
| def g(x: int) -> int: |
| return x + 1 |
| [out] |
| def f(x): |
| x :: int |
| r0 :: dict |
| r1 :: str |
| r2, r3, r4 :: object |
| r5 :: int |
| L0: |
| r0 = __main__.globals :: static |
| r1 = 'g' |
| r2 = CPyDict_GetItem(r0, r1) |
| r3 = box(int, x) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| r5 = unbox(int, r4) |
| return r5 |
| |
| [case testPrintFullname] |
| import builtins |
| def f(x: int) -> None: |
| builtins.print(5) |
| [out] |
| def f(x): |
| x :: int |
| r0 :: object |
| r1 :: str |
| r2, r3, r4 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = 'print' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = box(short_int, 10) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| return 1 |
| |
| [case testPrint] |
| import builtins |
| def f(x: int) -> None: |
| print(5) |
| [out] |
| def f(x): |
| x :: int |
| r0 :: object |
| r1 :: str |
| r2, r3, r4 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = 'print' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = box(short_int, 10) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| return 1 |
| |
| [case testUnicodeLiteral] |
| def f() -> str: |
| x = "some string" |
| return "some other string" |
| [out] |
| def f(): |
| r0, x, r1 :: str |
| L0: |
| r0 = 'some string' |
| x = r0 |
| r1 = 'some other string' |
| return r1 |
| |
| [case testBytesLiteral] |
| def f() -> bytes: |
| x = b'\xf0' |
| return b'1234' |
| [out] |
| def f(): |
| r0, x, r1 :: bytes |
| L0: |
| r0 = b'\xf0' |
| x = r0 |
| r1 = b'1234' |
| return r1 |
| |
| [case testPyMethodCall1] |
| from typing import Any |
| def f(x: Any) -> int: |
| y: int = x.pop() |
| return x.pop() |
| [out] |
| def f(x): |
| x :: object |
| r0 :: str |
| r1 :: object |
| r2, y :: int |
| r3 :: str |
| r4 :: object |
| r5 :: int |
| L0: |
| r0 = 'pop' |
| r1 = CPyObject_CallMethodObjArgs(x, r0, 0) |
| r2 = unbox(int, r1) |
| y = r2 |
| r3 = 'pop' |
| r4 = CPyObject_CallMethodObjArgs(x, r3, 0) |
| r5 = unbox(int, r4) |
| return r5 |
| |
| [case testObjectType] |
| def g(y: object) -> None: |
| g(y) |
| g([1]) |
| g(None) |
| [out] |
| def g(y): |
| y :: object |
| r0 :: None |
| r1 :: list |
| r2 :: object |
| r3, r4 :: ptr |
| r5 :: None |
| r6 :: object |
| r7 :: None |
| L0: |
| r0 = g(y) |
| r1 = PyList_New(1) |
| r2 = box(short_int, 2) |
| r3 = get_element_ptr r1 ob_item :: PyListObject |
| r4 = load_mem r3 :: ptr* |
| set_mem r4, r2 :: builtins.object* |
| keep_alive r1 |
| r5 = g(r1) |
| r6 = box(None, 1) |
| r7 = g(r6) |
| return 1 |
| |
| [case testCoerceToObject1] |
| def g(y: object) -> object: |
| g(1) |
| a = [y] |
| a[0] = (1, 2) |
| y = True |
| return 3 |
| [out] |
| def g(y): |
| y, r0, r1 :: object |
| r2 :: list |
| r3, r4 :: ptr |
| a :: list |
| r5 :: tuple[int, int] |
| r6 :: object |
| r7 :: bit |
| r8, r9 :: object |
| L0: |
| r0 = box(short_int, 2) |
| r1 = g(r0) |
| r2 = PyList_New(1) |
| r3 = get_element_ptr r2 ob_item :: PyListObject |
| r4 = load_mem r3 :: ptr* |
| set_mem r4, y :: builtins.object* |
| keep_alive r2 |
| a = r2 |
| r5 = (2, 4) |
| r6 = box(tuple[int, int], r5) |
| r7 = CPyList_SetItem(a, 0, r6) |
| r8 = box(bool, 1) |
| y = r8 |
| r9 = box(short_int, 6) |
| return r9 |
| |
| [case testCoerceToObject2] |
| class A: |
| x: object |
| n: int |
| def f(a: A, o: object) -> None: |
| a.x = 1 |
| o = a.n |
| [out] |
| def f(a, o): |
| a :: __main__.A |
| o, r0 :: object |
| r1 :: bool |
| r2 :: int |
| r3 :: object |
| L0: |
| r0 = box(short_int, 2) |
| a.x = r0; r1 = is_error |
| r2 = a.n |
| r3 = box(int, r2) |
| o = r3 |
| return 1 |
| |
| [case testDownCast] |
| from typing import cast, List, Tuple |
| class A: pass |
| def f(x: object) -> None: |
| n = cast(int, x) |
| b = cast(bool, x) |
| a = cast(A, x) |
| l = cast(List[int], x) |
| t = cast(Tuple[int, A], x) |
| [out] |
| def f(x): |
| x :: object |
| r0, n :: int |
| r1, b :: bool |
| r2, a :: __main__.A |
| r3, l :: list |
| r4, t :: tuple[int, __main__.A] |
| L0: |
| r0 = unbox(int, x) |
| n = r0 |
| r1 = unbox(bool, x) |
| b = r1 |
| r2 = cast(__main__.A, x) |
| a = r2 |
| r3 = cast(list, x) |
| l = r3 |
| r4 = unbox(tuple[int, __main__.A], x) |
| t = r4 |
| return 1 |
| |
| [case testDownCastSpecialCases] |
| from typing import cast, Optional, Tuple |
| class A: pass |
| def f(o: Optional[A], n: int, t: Tuple[int, ...]) -> None: |
| a = cast(A, o) |
| m = cast(bool, n) |
| tt: Tuple[int, int] |
| t = tt |
| [out] |
| def f(o, n, t): |
| o :: union[__main__.A, None] |
| n :: int |
| t :: tuple |
| r0, a :: __main__.A |
| r1 :: object |
| r2, m :: bool |
| tt :: tuple[int, int] |
| r3 :: object |
| L0: |
| r0 = cast(__main__.A, o) |
| a = r0 |
| r1 = box(int, n) |
| r2 = unbox(bool, r1) |
| m = r2 |
| r3 = box(tuple[int, int], tt) |
| t = r3 |
| return 1 |
| |
| [case testSuccessfulCast] |
| from typing import cast, Optional, Tuple, List, Dict |
| class A: pass |
| def f(o: object, |
| p: Optional[A], |
| n: int, |
| b: bool, |
| t: Tuple[int, ...], |
| s: Tuple[int, int], |
| a: A, |
| l: List[A], |
| d: Dict[int, str]) -> None: |
| o = cast(object, o) |
| p = cast(Optional[A], p) |
| n = cast(int, n) |
| b = cast(bool, b) |
| t = cast(Tuple[int, ...], t) |
| s = cast(Tuple[int, int], s) |
| o = cast(object, n) |
| a = cast(A, a) |
| l2 = cast(List[object], l) |
| d2 = cast(Dict[object, str], d) |
| [out] |
| def f(o, p, n, b, t, s, a, l, d): |
| o :: object |
| p :: union[__main__.A, None] |
| n :: int |
| b :: bool |
| t :: tuple |
| s :: tuple[int, int] |
| a :: __main__.A |
| l :: list |
| d :: dict |
| r0 :: object |
| l2 :: list |
| d2 :: dict |
| L0: |
| o = o |
| p = p |
| n = n |
| b = b |
| t = t |
| s = s |
| r0 = box(int, n) |
| o = r0 |
| a = a |
| l2 = l |
| d2 = d |
| return 1 |
| |
| [case testGenericSetItem] |
| from typing import Any |
| def f(x: Any, y: Any, z: Any) -> None: |
| x[y] = z |
| [out] |
| def f(x, y, z): |
| x, y, z :: object |
| r0 :: int32 |
| r1 :: bit |
| L0: |
| r0 = PyObject_SetItem(x, y, z) |
| r1 = r0 >= 0 :: signed |
| return 1 |
| |
| [case testLoadFloatSum] |
| def assign_and_return_float_sum() -> float: |
| f1 = 1.0 |
| f2 = 2.0 |
| f3 = 3.0 |
| return f1 * f2 + f3 |
| [out] |
| def assign_and_return_float_sum(): |
| r0, f1, r1, f2, r2, f3 :: float |
| r3 :: object |
| r4 :: float |
| r5 :: object |
| r6 :: float |
| L0: |
| r0 = 1.0 |
| f1 = r0 |
| r1 = 2.0 |
| f2 = r1 |
| r2 = 3.0 |
| f3 = r2 |
| r3 = PyNumber_Multiply(f1, f2) |
| r4 = cast(float, r3) |
| r5 = PyNumber_Add(r4, f3) |
| r6 = cast(float, r5) |
| return r6 |
| |
| [case testLoadComplex] |
| def load() -> complex: |
| return 5j+1.0 |
| [out] |
| def load(): |
| r0 :: object |
| r1 :: float |
| r2 :: object |
| L0: |
| r0 = 5j |
| r1 = 1.0 |
| r2 = PyNumber_Add(r0, r1) |
| return r2 |
| |
| [case testBigIntLiteral_64bit] |
| def big_int() -> None: |
| a_62_bit = 4611686018427387902 |
| max_62_bit = 4611686018427387903 |
| b_63_bit = 4611686018427387904 |
| c_63_bit = 9223372036854775806 |
| max_63_bit = 9223372036854775807 |
| d_64_bit = 9223372036854775808 |
| max_32_bit = 2147483647 |
| max_31_bit = 1073741823 |
| [out] |
| def big_int(): |
| a_62_bit, max_62_bit, r0, b_63_bit, r1, c_63_bit, r2, max_63_bit, r3, d_64_bit, max_32_bit, max_31_bit :: int |
| L0: |
| a_62_bit = 9223372036854775804 |
| max_62_bit = 9223372036854775806 |
| r0 = object 4611686018427387904 |
| b_63_bit = r0 |
| r1 = object 9223372036854775806 |
| c_63_bit = r1 |
| r2 = object 9223372036854775807 |
| max_63_bit = r2 |
| r3 = object 9223372036854775808 |
| d_64_bit = r3 |
| max_32_bit = 4294967294 |
| max_31_bit = 2147483646 |
| return 1 |
| |
| [case testBigIntLiteral_32bit] |
| def big_int() -> None: |
| a_62_bit = 4611686018427387902 |
| max_62_bit = 4611686018427387903 |
| b_63_bit = 4611686018427387904 |
| c_63_bit = 9223372036854775806 |
| max_63_bit = 9223372036854775807 |
| d_64_bit = 9223372036854775808 |
| max_32_bit = 2147483647 |
| max_31_bit = 1073741823 |
| [out] |
| def big_int(): |
| r0, a_62_bit, r1, max_62_bit, r2, b_63_bit, r3, c_63_bit, r4, max_63_bit, r5, d_64_bit, r6, max_32_bit, max_31_bit :: int |
| L0: |
| r0 = object 4611686018427387902 |
| a_62_bit = r0 |
| r1 = object 4611686018427387903 |
| max_62_bit = r1 |
| r2 = object 4611686018427387904 |
| b_63_bit = r2 |
| r3 = object 9223372036854775806 |
| c_63_bit = r3 |
| r4 = object 9223372036854775807 |
| max_63_bit = r4 |
| r5 = object 9223372036854775808 |
| d_64_bit = r5 |
| r6 = object 2147483647 |
| max_32_bit = r6 |
| max_31_bit = 2147483646 |
| return 1 |
| |
| [case testCallableTypes] |
| from typing import Callable |
| def absolute_value(x: int) -> int: |
| return x if x > 0 else -x |
| |
| def call_native_function(x: int) -> int: |
| return absolute_value(x) |
| |
| def call_python_function(x: int) -> int: |
| return int(x) |
| |
| def return_float() -> float: |
| return 5.0 |
| |
| def return_callable_type() -> Callable[[], float]: |
| return return_float |
| |
| def call_callable_type() -> float: |
| f = return_callable_type() |
| return f() |
| [out] |
| def absolute_value(x): |
| x :: int |
| r0 :: native_int |
| r1, r2, r3 :: bit |
| r4, r5 :: int |
| L0: |
| r0 = x & 1 |
| r1 = r0 != 0 |
| if r1 goto L1 else goto L2 :: bool |
| L1: |
| r2 = CPyTagged_IsLt_(0, x) |
| if r2 goto L3 else goto L4 :: bool |
| L2: |
| r3 = x > 0 :: signed |
| if r3 goto L3 else goto L4 :: bool |
| L3: |
| r4 = x |
| goto L5 |
| L4: |
| r5 = CPyTagged_Negate(x) |
| r4 = r5 |
| L5: |
| return r4 |
| def call_native_function(x): |
| x, r0 :: int |
| L0: |
| r0 = absolute_value(x) |
| return r0 |
| def call_python_function(x): |
| x :: int |
| r0, r1, r2 :: object |
| r3 :: int |
| L0: |
| r0 = load_address PyLong_Type |
| r1 = box(int, x) |
| r2 = PyObject_CallFunctionObjArgs(r0, r1, 0) |
| r3 = unbox(int, r2) |
| return r3 |
| def return_float(): |
| r0 :: float |
| L0: |
| r0 = 5.0 |
| return r0 |
| def return_callable_type(): |
| r0 :: dict |
| r1 :: str |
| r2 :: object |
| L0: |
| r0 = __main__.globals :: static |
| r1 = 'return_float' |
| r2 = CPyDict_GetItem(r0, r1) |
| return r2 |
| def call_callable_type(): |
| r0, f, r1 :: object |
| r2 :: float |
| L0: |
| r0 = return_callable_type() |
| f = r0 |
| r1 = PyObject_CallFunctionObjArgs(f, 0) |
| r2 = cast(float, r1) |
| return r2 |
| |
| [case testCallableTypesWithKeywordArgs] |
| from typing import List |
| |
| def call_python_function_with_keyword_arg(x: str) -> int: |
| return int(x, base=2) |
| |
| def call_python_method_with_keyword_args(xs: List[int], first: int, second: int) -> List[int]: |
| xs.insert(0, x=first) |
| xs.insert(x=second, i=1) |
| return xs |
| |
| [out] |
| def call_python_function_with_keyword_arg(x): |
| x :: str |
| r0 :: object |
| r1 :: str |
| r2 :: tuple |
| r3 :: object |
| r4 :: dict |
| r5 :: object |
| r6 :: int |
| L0: |
| r0 = load_address PyLong_Type |
| r1 = 'base' |
| r2 = PyTuple_Pack(1, x) |
| r3 = box(short_int, 4) |
| r4 = CPyDict_Build(1, r1, r3) |
| r5 = PyObject_Call(r0, r2, r4) |
| r6 = unbox(int, r5) |
| return r6 |
| def call_python_method_with_keyword_args(xs, first, second): |
| xs :: list |
| first, second :: int |
| r0 :: str |
| r1 :: object |
| r2 :: str |
| r3 :: object |
| r4 :: tuple |
| r5 :: object |
| r6 :: dict |
| r7 :: object |
| r8 :: str |
| r9 :: object |
| r10, r11 :: str |
| r12 :: tuple |
| r13, r14 :: object |
| r15 :: dict |
| r16 :: object |
| L0: |
| r0 = 'insert' |
| r1 = CPyObject_GetAttr(xs, r0) |
| r2 = 'x' |
| r3 = box(short_int, 0) |
| r4 = PyTuple_Pack(1, r3) |
| r5 = box(int, first) |
| r6 = CPyDict_Build(1, r2, r5) |
| r7 = PyObject_Call(r1, r4, r6) |
| r8 = 'insert' |
| r9 = CPyObject_GetAttr(xs, r8) |
| r10 = 'x' |
| r11 = 'i' |
| r12 = PyTuple_Pack(0) |
| r13 = box(int, second) |
| r14 = box(short_int, 2) |
| r15 = CPyDict_Build(2, r10, r13, r11, r14) |
| r16 = PyObject_Call(r9, r12, r15) |
| return xs |
| |
| [case testObjectAsBoolean] |
| from typing import List |
| |
| def obj(x: object) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| |
| def num(x: int) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| |
| def lst(x: List[int]) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| [out] |
| def obj(x): |
| x :: object |
| r0 :: int32 |
| r1 :: bit |
| r2 :: bool |
| L0: |
| r0 = PyObject_IsTrue(x) |
| r1 = r0 >= 0 :: signed |
| r2 = truncate r0: int32 to builtins.bool |
| if r2 goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| def num(x): |
| x :: int |
| r0 :: bit |
| L0: |
| r0 = x != 0 |
| if r0 goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| def lst(x): |
| x :: list |
| r0 :: ptr |
| r1 :: native_int |
| r2 :: short_int |
| r3 :: bit |
| L0: |
| r0 = get_element_ptr x ob_size :: PyVarObject |
| r1 = load_mem r0 :: native_int* |
| keep_alive x |
| r2 = r1 << 1 |
| r3 = r2 != 0 |
| if r3 goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| |
| [case testOptionalAsBoolean] |
| from typing import Optional |
| |
| class A: pass |
| |
| def opt_int(x: Optional[int]) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| |
| def opt_a(x: Optional[A]) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| |
| def opt_o(x: Optional[object]) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| [out] |
| def opt_int(x): |
| x :: union[int, None] |
| r0 :: object |
| r1 :: bit |
| r2 :: int |
| r3 :: bit |
| L0: |
| r0 = load_address _Py_NoneStruct |
| r1 = x != r0 |
| if r1 goto L1 else goto L3 :: bool |
| L1: |
| r2 = unbox(int, x) |
| r3 = r2 != 0 |
| if r3 goto L2 else goto L3 :: bool |
| L2: |
| return 2 |
| L3: |
| return 0 |
| L4: |
| unreachable |
| def opt_a(x): |
| x :: union[__main__.A, None] |
| r0 :: object |
| r1 :: bit |
| L0: |
| r0 = load_address _Py_NoneStruct |
| r1 = x != r0 |
| if r1 goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| def opt_o(x): |
| x :: union[object, None] |
| r0 :: object |
| r1 :: bit |
| r2 :: object |
| r3 :: int32 |
| r4 :: bit |
| r5 :: bool |
| L0: |
| r0 = load_address _Py_NoneStruct |
| r1 = x != r0 |
| if r1 goto L1 else goto L3 :: bool |
| L1: |
| r2 = cast(object, x) |
| r3 = PyObject_IsTrue(r2) |
| r4 = r3 >= 0 :: signed |
| r5 = truncate r3: int32 to builtins.bool |
| if r5 goto L2 else goto L3 :: bool |
| L2: |
| return 2 |
| L3: |
| return 0 |
| L4: |
| unreachable |
| |
| [case testRaise] |
| def foo() -> None: |
| raise Exception() |
| |
| def bar() -> None: |
| raise Exception |
| [out] |
| def foo(): |
| r0 :: object |
| r1 :: str |
| r2, r3 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = 'Exception' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = PyObject_CallFunctionObjArgs(r2, 0) |
| CPy_Raise(r3) |
| unreachable |
| def bar(): |
| r0 :: object |
| r1 :: str |
| r2 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = 'Exception' |
| r2 = CPyObject_GetAttr(r0, r1) |
| CPy_Raise(r2) |
| unreachable |
| |
| [case testModuleTopLevel_toplevel] |
| x = 1 |
| print(x) |
| |
| def f() -> None: |
| print(x) |
| [out] |
| def f(): |
| r0 :: dict |
| r1 :: str |
| r2 :: object |
| r3 :: int |
| r4 :: object |
| r5 :: str |
| r6, r7, r8 :: object |
| L0: |
| r0 = __main__.globals :: static |
| r1 = 'x' |
| r2 = CPyDict_GetItem(r0, r1) |
| r3 = unbox(int, r2) |
| r4 = builtins :: module |
| r5 = 'print' |
| r6 = CPyObject_GetAttr(r4, r5) |
| r7 = box(int, r3) |
| r8 = PyObject_CallFunctionObjArgs(r6, r7, 0) |
| return 1 |
| def __top_level__(): |
| r0, r1 :: object |
| r2 :: bit |
| r3 :: str |
| r4 :: object |
| r5 :: dict |
| r6 :: str |
| r7 :: object |
| r8 :: int32 |
| r9 :: bit |
| r10 :: dict |
| r11 :: str |
| r12 :: object |
| r13 :: int |
| r14 :: object |
| r15 :: str |
| r16, r17, r18 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = load_address _Py_NoneStruct |
| r2 = r0 != r1 |
| if r2 goto L2 else goto L1 :: bool |
| L1: |
| r3 = 'builtins' |
| r4 = PyImport_Import(r3) |
| builtins = r4 :: module |
| L2: |
| r5 = __main__.globals :: static |
| r6 = 'x' |
| r7 = box(short_int, 2) |
| r8 = CPyDict_SetItem(r5, r6, r7) |
| r9 = r8 >= 0 :: signed |
| r10 = __main__.globals :: static |
| r11 = 'x' |
| r12 = CPyDict_GetItem(r10, r11) |
| r13 = unbox(int, r12) |
| r14 = builtins :: module |
| r15 = 'print' |
| r16 = CPyObject_GetAttr(r14, r15) |
| r17 = box(int, r13) |
| r18 = PyObject_CallFunctionObjArgs(r16, r17, 0) |
| return 1 |
| |
| [case testCallOverloaded] |
| import m |
| def f() -> str: |
| return m.f(1) |
| [file m.pyi] |
| from typing import overload |
| @overload |
| def f(x: int) -> str: ... |
| @overload |
| def f(x: str) -> int: ... |
| [out] |
| def f(): |
| r0 :: object |
| r1 :: str |
| r2, r3, r4 :: object |
| r5 :: str |
| L0: |
| r0 = m :: module |
| r1 = 'f' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = box(short_int, 2) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| r5 = cast(str, r4) |
| return r5 |
| |
| [case testCallOverloadedNative] |
| from typing import overload, Union |
| |
| @overload |
| def foo(x: int) -> int: ... |
| |
| @overload |
| def foo(x: str) -> str: ... |
| |
| def foo(x: Union[int, str]) -> Union[int, str]: |
| return x |
| |
| def main() -> None: |
| x = foo(0) |
| [out] |
| def foo(x): |
| x :: union[int, str] |
| L0: |
| return x |
| def main(): |
| r0 :: object |
| r1 :: union[int, str] |
| r2, x :: int |
| L0: |
| r0 = box(short_int, 0) |
| r1 = foo(r0) |
| r2 = unbox(int, r1) |
| x = r2 |
| return 1 |
| |
| [case testCallOverloadedNativeSubclass] |
| from typing import overload, Union |
| |
| class A: |
| x: int |
| class B(A): |
| y: int |
| |
| @overload |
| def foo(x: int) -> B: ... |
| |
| @overload |
| def foo(x: Union[int, str]) -> A: ... |
| |
| def foo(x: Union[int, str]) -> A: |
| if isinstance(x, int): |
| return B() |
| return A() |
| |
| def main() -> None: |
| x = foo(0) |
| [out] |
| def foo(x): |
| x :: union[int, str] |
| r0 :: object |
| r1 :: int32 |
| r2 :: bit |
| r3 :: bool |
| r4 :: __main__.B |
| r5 :: __main__.A |
| L0: |
| r0 = load_address PyLong_Type |
| r1 = PyObject_IsInstance(x, r0) |
| r2 = r1 >= 0 :: signed |
| r3 = truncate r1: int32 to builtins.bool |
| if r3 goto L1 else goto L2 :: bool |
| L1: |
| r4 = B() |
| return r4 |
| L2: |
| r5 = A() |
| return r5 |
| def main(): |
| r0 :: object |
| r1 :: __main__.A |
| r2, x :: __main__.B |
| L0: |
| r0 = box(short_int, 0) |
| r1 = foo(r0) |
| r2 = cast(__main__.B, r1) |
| x = r2 |
| return 1 |
| |
| [case testFunctionCallWithKeywordArgs] |
| def f(x: int, y: str) -> None: pass |
| |
| def g() -> None: |
| f(y='a', x=0) |
| f(1, y='b') |
| [out] |
| def f(x, y): |
| x :: int |
| y :: str |
| L0: |
| return 1 |
| def g(): |
| r0 :: str |
| r1 :: None |
| r2 :: str |
| r3 :: None |
| L0: |
| r0 = 'a' |
| r1 = f(0, r0) |
| r2 = 'b' |
| r3 = f(2, r2) |
| return 1 |
| |
| [case testMethodCallWithKeywordArgs] |
| class A: |
| def f(self, x: int, y: str) -> None: pass |
| |
| def g(a: A) -> None: |
| a.f(y='a', x=0) |
| a.f(1, y='b') |
| [out] |
| def A.f(self, x, y): |
| self :: __main__.A |
| x :: int |
| y :: str |
| L0: |
| return 1 |
| def g(a): |
| a :: __main__.A |
| r0 :: str |
| r1 :: None |
| r2 :: str |
| r3 :: None |
| L0: |
| r0 = 'a' |
| r1 = a.f(0, r0) |
| r2 = 'b' |
| r3 = a.f(2, r2) |
| return 1 |
| |
| [case testStarArgs] |
| from typing import Tuple |
| def f(a: int, b: int, c: int) -> Tuple[int, int, int]: |
| return a, b, c |
| def g() -> Tuple[int, int, int]: |
| return f(*(1, 2, 3)) |
| def h() -> Tuple[int, int, int]: |
| return f(1, *(2, 3)) |
| [out] |
| def f(a, b, c): |
| a, b, c :: int |
| r0 :: tuple[int, int, int] |
| L0: |
| r0 = (a, b, c) |
| return r0 |
| def g(): |
| r0 :: tuple[int, int, int] |
| r1 :: dict |
| r2 :: str |
| r3 :: object |
| r4 :: list |
| r5, r6 :: object |
| r7 :: tuple |
| r8 :: dict |
| r9 :: object |
| r10 :: tuple[int, int, int] |
| L0: |
| r0 = (2, 4, 6) |
| r1 = __main__.globals :: static |
| r2 = 'f' |
| r3 = CPyDict_GetItem(r1, r2) |
| r4 = PyList_New(0) |
| r5 = box(tuple[int, int, int], r0) |
| r6 = CPyList_Extend(r4, r5) |
| r7 = PyList_AsTuple(r4) |
| r8 = PyDict_New() |
| r9 = PyObject_Call(r3, r7, r8) |
| r10 = unbox(tuple[int, int, int], r9) |
| return r10 |
| def h(): |
| r0 :: tuple[int, int] |
| r1 :: dict |
| r2 :: str |
| r3 :: object |
| r4 :: list |
| r5 :: object |
| r6, r7 :: ptr |
| r8, r9 :: object |
| r10 :: tuple |
| r11 :: dict |
| r12 :: object |
| r13 :: tuple[int, int, int] |
| L0: |
| r0 = (4, 6) |
| r1 = __main__.globals :: static |
| r2 = 'f' |
| r3 = CPyDict_GetItem(r1, r2) |
| r4 = PyList_New(1) |
| r5 = box(short_int, 2) |
| r6 = get_element_ptr r4 ob_item :: PyListObject |
| r7 = load_mem r6 :: ptr* |
| set_mem r7, r5 :: builtins.object* |
| keep_alive r4 |
| r8 = box(tuple[int, int], r0) |
| r9 = CPyList_Extend(r4, r8) |
| r10 = PyList_AsTuple(r4) |
| r11 = PyDict_New() |
| r12 = PyObject_Call(r3, r10, r11) |
| r13 = unbox(tuple[int, int, int], r12) |
| return r13 |
| |
| [case testStar2Args] |
| from typing import Tuple |
| def f(a: int, b: int, c: int) -> Tuple[int, int, int]: |
| return a, b, c |
| def g() -> Tuple[int, int, int]: |
| return f(**{'a': 1, 'b': 2, 'c': 3}) |
| def h() -> Tuple[int, int, int]: |
| return f(1, **{'b': 2, 'c': 3}) |
| [out] |
| def f(a, b, c): |
| a, b, c :: int |
| r0 :: tuple[int, int, int] |
| L0: |
| r0 = (a, b, c) |
| return r0 |
| def g(): |
| r0, r1, r2 :: str |
| r3, r4, r5 :: object |
| r6, r7 :: dict |
| r8 :: str |
| r9 :: object |
| r10 :: dict |
| r11 :: int32 |
| r12 :: bit |
| r13 :: tuple |
| r14 :: object |
| r15 :: tuple[int, int, int] |
| L0: |
| r0 = 'a' |
| r1 = 'b' |
| r2 = 'c' |
| r3 = box(short_int, 2) |
| r4 = box(short_int, 4) |
| r5 = box(short_int, 6) |
| r6 = CPyDict_Build(3, r0, r3, r1, r4, r2, r5) |
| r7 = __main__.globals :: static |
| r8 = 'f' |
| r9 = CPyDict_GetItem(r7, r8) |
| r10 = PyDict_New() |
| r11 = CPyDict_UpdateInDisplay(r10, r6) |
| r12 = r11 >= 0 :: signed |
| r13 = PyTuple_Pack(0) |
| r14 = PyObject_Call(r9, r13, r10) |
| r15 = unbox(tuple[int, int, int], r14) |
| return r15 |
| def h(): |
| r0, r1 :: str |
| r2, r3 :: object |
| r4, r5 :: dict |
| r6 :: str |
| r7 :: object |
| r8 :: dict |
| r9 :: int32 |
| r10 :: bit |
| r11 :: object |
| r12 :: tuple |
| r13 :: object |
| r14 :: tuple[int, int, int] |
| L0: |
| r0 = 'b' |
| r1 = 'c' |
| r2 = box(short_int, 4) |
| r3 = box(short_int, 6) |
| r4 = CPyDict_Build(2, r0, r2, r1, r3) |
| r5 = __main__.globals :: static |
| r6 = 'f' |
| r7 = CPyDict_GetItem(r5, r6) |
| r8 = PyDict_New() |
| r9 = CPyDict_UpdateInDisplay(r8, r4) |
| r10 = r9 >= 0 :: signed |
| r11 = box(short_int, 2) |
| r12 = PyTuple_Pack(1, r11) |
| r13 = PyObject_Call(r7, r12, r8) |
| r14 = unbox(tuple[int, int, int], r13) |
| return r14 |
| |
| [case testFunctionCallWithDefaultArgs] |
| def f(x: int, y: int = 3, z: str = "test") -> None: |
| return None |
| |
| def g() -> None: |
| f(2) |
| f(y = 3, x = 6) |
| [out] |
| def f(x, y, z): |
| x, y :: int |
| z, r0 :: str |
| L0: |
| if is_error(y) goto L1 else goto L2 |
| L1: |
| y = 6 |
| L2: |
| if is_error(z) goto L3 else goto L4 |
| L3: |
| r0 = 'test' |
| z = r0 |
| L4: |
| return 1 |
| def g(): |
| r0 :: int |
| r1 :: str |
| r2 :: None |
| r3 :: str |
| r4 :: None |
| L0: |
| r0 = <error> :: int |
| r1 = <error> :: str |
| r2 = f(4, r0, r1) |
| r3 = <error> :: str |
| r4 = f(12, 6, r3) |
| return 1 |
| |
| [case testMethodCallWithDefaultArgs] |
| class A: |
| def f(self, x: int, y: int = 3, z: str = "test") -> None: |
| return None |
| |
| def g() -> None: |
| a = A() |
| a.f(2) |
| a.f(y = 3, x = 6) |
| [out] |
| def A.f(self, x, y, z): |
| self :: __main__.A |
| x, y :: int |
| z, r0 :: str |
| L0: |
| if is_error(y) goto L1 else goto L2 |
| L1: |
| y = 6 |
| L2: |
| if is_error(z) goto L3 else goto L4 |
| L3: |
| r0 = 'test' |
| z = r0 |
| L4: |
| return 1 |
| def g(): |
| r0, a :: __main__.A |
| r1 :: int |
| r2 :: str |
| r3 :: None |
| r4 :: str |
| r5 :: None |
| L0: |
| r0 = A() |
| a = r0 |
| r1 = <error> :: int |
| r2 = <error> :: str |
| r3 = a.f(4, r1, r2) |
| r4 = <error> :: str |
| r5 = a.f(12, 6, r4) |
| return 1 |
| |
| [case testListComprehension] |
| from typing import List |
| |
| def f() -> List[int]: |
| return [x*x for x in [1,2,3] if x != 2 if x != 3] |
| [out] |
| def f(): |
| r0, r1 :: list |
| r2, r3, r4 :: object |
| r5, r6, r7, r8 :: ptr |
| r9 :: short_int |
| r10 :: ptr |
| r11 :: native_int |
| r12 :: short_int |
| r13 :: bit |
| r14 :: object |
| r15, x :: int |
| r16 :: native_int |
| r17, r18 :: bit |
| r19 :: bool |
| r20, r21 :: bit |
| r22 :: native_int |
| r23, r24 :: bit |
| r25 :: bool |
| r26, r27 :: bit |
| r28 :: int |
| r29 :: object |
| r30 :: int32 |
| r31 :: bit |
| r32 :: short_int |
| L0: |
| r0 = PyList_New(0) |
| r1 = PyList_New(3) |
| r2 = box(short_int, 2) |
| r3 = box(short_int, 4) |
| r4 = box(short_int, 6) |
| r5 = get_element_ptr r1 ob_item :: PyListObject |
| r6 = load_mem r5 :: ptr* |
| set_mem r6, r2 :: builtins.object* |
| r7 = r6 + WORD_SIZE*1 |
| set_mem r7, r3 :: builtins.object* |
| r8 = r6 + WORD_SIZE*2 |
| set_mem r8, r4 :: builtins.object* |
| keep_alive r1 |
| r9 = 0 |
| L1: |
| r10 = get_element_ptr r1 ob_size :: PyVarObject |
| r11 = load_mem r10 :: native_int* |
| keep_alive r1 |
| r12 = r11 << 1 |
| r13 = r9 < r12 :: signed |
| if r13 goto L2 else goto L14 :: bool |
| L2: |
| r14 = CPyList_GetItemUnsafe(r1, r9) |
| r15 = unbox(int, r14) |
| x = r15 |
| r16 = x & 1 |
| r17 = r16 == 0 |
| if r17 goto L3 else goto L4 :: bool |
| L3: |
| r18 = x != 4 |
| r19 = r18 |
| goto L5 |
| L4: |
| r20 = CPyTagged_IsEq_(x, 4) |
| r21 = r20 ^ 1 |
| r19 = r21 |
| L5: |
| if r19 goto L7 else goto L6 :: bool |
| L6: |
| goto L13 |
| L7: |
| r22 = x & 1 |
| r23 = r22 == 0 |
| if r23 goto L8 else goto L9 :: bool |
| L8: |
| r24 = x != 6 |
| r25 = r24 |
| goto L10 |
| L9: |
| r26 = CPyTagged_IsEq_(x, 6) |
| r27 = r26 ^ 1 |
| r25 = r27 |
| L10: |
| if r25 goto L12 else goto L11 :: bool |
| L11: |
| goto L13 |
| L12: |
| r28 = CPyTagged_Multiply(x, x) |
| r29 = box(int, r28) |
| r30 = PyList_Append(r0, r29) |
| r31 = r30 >= 0 :: signed |
| L13: |
| r32 = r9 + 2 |
| r9 = r32 |
| goto L1 |
| L14: |
| return r0 |
| |
| [case testDictComprehension] |
| from typing import Dict |
| def f() -> Dict[int, int]: |
| return {x: x*x for x in [1,2,3] if x != 2 if x != 3} |
| [out] |
| def f(): |
| r0 :: dict |
| r1 :: list |
| r2, r3, r4 :: object |
| r5, r6, r7, r8 :: ptr |
| r9 :: short_int |
| r10 :: ptr |
| r11 :: native_int |
| r12 :: short_int |
| r13 :: bit |
| r14 :: object |
| r15, x :: int |
| r16 :: native_int |
| r17, r18 :: bit |
| r19 :: bool |
| r20, r21 :: bit |
| r22 :: native_int |
| r23, r24 :: bit |
| r25 :: bool |
| r26, r27 :: bit |
| r28 :: int |
| r29, r30 :: object |
| r31 :: int32 |
| r32 :: bit |
| r33 :: short_int |
| L0: |
| r0 = PyDict_New() |
| r1 = PyList_New(3) |
| r2 = box(short_int, 2) |
| r3 = box(short_int, 4) |
| r4 = box(short_int, 6) |
| r5 = get_element_ptr r1 ob_item :: PyListObject |
| r6 = load_mem r5 :: ptr* |
| set_mem r6, r2 :: builtins.object* |
| r7 = r6 + WORD_SIZE*1 |
| set_mem r7, r3 :: builtins.object* |
| r8 = r6 + WORD_SIZE*2 |
| set_mem r8, r4 :: builtins.object* |
| keep_alive r1 |
| r9 = 0 |
| L1: |
| r10 = get_element_ptr r1 ob_size :: PyVarObject |
| r11 = load_mem r10 :: native_int* |
| keep_alive r1 |
| r12 = r11 << 1 |
| r13 = r9 < r12 :: signed |
| if r13 goto L2 else goto L14 :: bool |
| L2: |
| r14 = CPyList_GetItemUnsafe(r1, r9) |
| r15 = unbox(int, r14) |
| x = r15 |
| r16 = x & 1 |
| r17 = r16 == 0 |
| if r17 goto L3 else goto L4 :: bool |
| L3: |
| r18 = x != 4 |
| r19 = r18 |
| goto L5 |
| L4: |
| r20 = CPyTagged_IsEq_(x, 4) |
| r21 = r20 ^ 1 |
| r19 = r21 |
| L5: |
| if r19 goto L7 else goto L6 :: bool |
| L6: |
| goto L13 |
| L7: |
| r22 = x & 1 |
| r23 = r22 == 0 |
| if r23 goto L8 else goto L9 :: bool |
| L8: |
| r24 = x != 6 |
| r25 = r24 |
| goto L10 |
| L9: |
| r26 = CPyTagged_IsEq_(x, 6) |
| r27 = r26 ^ 1 |
| r25 = r27 |
| L10: |
| if r25 goto L12 else goto L11 :: bool |
| L11: |
| goto L13 |
| L12: |
| r28 = CPyTagged_Multiply(x, x) |
| r29 = box(int, x) |
| r30 = box(int, r28) |
| r31 = CPyDict_SetItem(r0, r29, r30) |
| r32 = r31 >= 0 :: signed |
| L13: |
| r33 = r9 + 2 |
| r9 = r33 |
| goto L1 |
| L14: |
| return r0 |
| |
| [case testLoopsMultipleAssign] |
| from typing import List, Tuple |
| def f(l: List[Tuple[int, int, int]]) -> List[int]: |
| for x, y, z in l: |
| pass |
| return [x+y+z for x, y, z in l] |
| [out] |
| def f(l): |
| l :: list |
| r0 :: short_int |
| r1 :: ptr |
| r2 :: native_int |
| r3 :: short_int |
| r4 :: bit |
| r5 :: object |
| r6 :: tuple[int, int, int] |
| r7, x, r8, y, r9, z :: int |
| r10 :: short_int |
| r11 :: ptr |
| r12 :: native_int |
| r13 :: list |
| r14 :: short_int |
| r15 :: ptr |
| r16 :: native_int |
| r17 :: short_int |
| r18 :: bit |
| r19 :: object |
| r20 :: tuple[int, int, int] |
| r21, x_2, r22, y_2, r23, z_2, r24, r25 :: int |
| r26 :: object |
| r27 :: bit |
| r28 :: short_int |
| L0: |
| r0 = 0 |
| L1: |
| r1 = get_element_ptr l ob_size :: PyVarObject |
| r2 = load_mem r1 :: native_int* |
| keep_alive l |
| r3 = r2 << 1 |
| r4 = r0 < r3 :: signed |
| if r4 goto L2 else goto L4 :: bool |
| L2: |
| r5 = CPyList_GetItemUnsafe(l, r0) |
| r6 = unbox(tuple[int, int, int], r5) |
| r7 = r6[0] |
| x = r7 |
| r8 = r6[1] |
| y = r8 |
| r9 = r6[2] |
| z = r9 |
| L3: |
| r10 = r0 + 2 |
| r0 = r10 |
| goto L1 |
| L4: |
| r11 = get_element_ptr l ob_size :: PyVarObject |
| r12 = load_mem r11 :: native_int* |
| keep_alive l |
| r13 = PyList_New(r12) |
| r14 = 0 |
| L5: |
| r15 = get_element_ptr l ob_size :: PyVarObject |
| r16 = load_mem r15 :: native_int* |
| keep_alive l |
| r17 = r16 << 1 |
| r18 = r14 < r17 :: signed |
| if r18 goto L6 else goto L8 :: bool |
| L6: |
| r19 = CPyList_GetItemUnsafe(l, r14) |
| r20 = unbox(tuple[int, int, int], r19) |
| r21 = r20[0] |
| x_2 = r21 |
| r22 = r20[1] |
| y_2 = r22 |
| r23 = r20[2] |
| z_2 = r23 |
| r24 = CPyTagged_Add(x_2, y_2) |
| r25 = CPyTagged_Add(r24, z_2) |
| r26 = box(int, r25) |
| r27 = CPyList_SetItemUnsafe(r13, r14, r26) |
| L7: |
| r28 = r14 + 2 |
| r14 = r28 |
| goto L5 |
| L8: |
| return r13 |
| |
| [case testProperty] |
| class PropertyHolder: |
| @property |
| def value(self) -> int: |
| return self.left + self.right if self.is_add else self.left - self.right |
| def __init__(self, left: int, right: int, is_add: bool) -> None: |
| self.left = left |
| self.right = right |
| self.is_add = is_add |
| def twice_value(self) -> int: |
| return 2 * self.value |
| [out] |
| def PropertyHolder.value(self): |
| self :: __main__.PropertyHolder |
| r0 :: bool |
| r1, r2, r3, r4, r5, r6, r7 :: int |
| L0: |
| r0 = self.is_add |
| if r0 goto L1 else goto L2 :: bool |
| L1: |
| r1 = self.left |
| r2 = self.right |
| r3 = CPyTagged_Add(r1, r2) |
| r4 = r3 |
| goto L3 |
| L2: |
| r5 = self.left |
| r6 = self.right |
| r7 = CPyTagged_Subtract(r5, r6) |
| r4 = r7 |
| L3: |
| return r4 |
| def PropertyHolder.__init__(self, left, right, is_add): |
| self :: __main__.PropertyHolder |
| left, right :: int |
| is_add, r0, r1, r2 :: bool |
| L0: |
| self.left = left; r0 = is_error |
| self.right = right; r1 = is_error |
| self.is_add = is_add; r2 = is_error |
| return 1 |
| def PropertyHolder.twice_value(self): |
| self :: __main__.PropertyHolder |
| r0, r1 :: int |
| L0: |
| r0 = self.value |
| r1 = CPyTagged_Multiply(4, r0) |
| return r1 |
| |
| [case testPropertyDerivedGen] |
| from typing import Callable |
| class BaseProperty: |
| @property |
| def value(self) -> object: |
| return self._incrementer |
| |
| @property |
| def bad_value(self) -> object: |
| return self._incrementer |
| |
| @property |
| def next(self) -> BaseProperty: |
| return BaseProperty(self._incrementer + 1) |
| |
| def __init__(self, value: int) -> None: |
| self._incrementer = value |
| |
| class DerivedProperty(BaseProperty): |
| @property |
| def value(self) -> int: |
| return self._incrementer |
| |
| @property |
| def bad_value(self) -> object: |
| return self._incrementer |
| |
| @property |
| def next(self) -> DerivedProperty: |
| return DerivedProperty(self._incr_func, self._incr_func(self.value)) |
| |
| def __init__(self, incr_func: Callable[[int], int], value: int) -> None: |
| BaseProperty.__init__(self, value) |
| self._incr_func = incr_func |
| |
| |
| class AgainProperty(DerivedProperty): |
| @property |
| def next(self) -> AgainProperty: |
| return AgainProperty(self._incr_func, self._incr_func(self._incr_func(self.value))) |
| |
| @property |
| def bad_value(self) -> int: |
| return self._incrementer |
| [out] |
| def BaseProperty.value(self): |
| self :: __main__.BaseProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = self._incrementer |
| r1 = box(int, r0) |
| return r1 |
| def BaseProperty.bad_value(self): |
| self :: __main__.BaseProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = self._incrementer |
| r1 = box(int, r0) |
| return r1 |
| def BaseProperty.next(self): |
| self :: __main__.BaseProperty |
| r0, r1 :: int |
| r2 :: __main__.BaseProperty |
| L0: |
| r0 = self._incrementer |
| r1 = CPyTagged_Add(r0, 2) |
| r2 = BaseProperty(r1) |
| return r2 |
| def BaseProperty.__init__(self, value): |
| self :: __main__.BaseProperty |
| value :: int |
| r0 :: bool |
| L0: |
| self._incrementer = value; r0 = is_error |
| return 1 |
| def DerivedProperty.value(self): |
| self :: __main__.DerivedProperty |
| r0 :: int |
| L0: |
| r0 = self._incrementer |
| return r0 |
| def DerivedProperty.value__BaseProperty_glue(__mypyc_self__): |
| __mypyc_self__ :: __main__.DerivedProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = __mypyc_self__.value |
| r1 = box(int, r0) |
| return r1 |
| def DerivedProperty.bad_value(self): |
| self :: __main__.DerivedProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = self._incrementer |
| r1 = box(int, r0) |
| return r1 |
| def DerivedProperty.next(self): |
| self :: __main__.DerivedProperty |
| r0 :: object |
| r1 :: int |
| r2, r3, r4 :: object |
| r5 :: int |
| r6 :: __main__.DerivedProperty |
| L0: |
| r0 = self._incr_func |
| r1 = self.value |
| r2 = self._incr_func |
| r3 = box(int, r1) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| r5 = unbox(int, r4) |
| r6 = DerivedProperty(r0, r5) |
| return r6 |
| def DerivedProperty.next__BaseProperty_glue(__mypyc_self__): |
| __mypyc_self__, r0 :: __main__.DerivedProperty |
| L0: |
| r0 = __mypyc_self__.next |
| return r0 |
| def DerivedProperty.__init__(self, incr_func, value): |
| self :: __main__.DerivedProperty |
| incr_func :: object |
| value :: int |
| r0 :: None |
| r1 :: bool |
| L0: |
| r0 = BaseProperty.__init__(self, value) |
| self._incr_func = incr_func; r1 = is_error |
| return 1 |
| def AgainProperty.next(self): |
| self :: __main__.AgainProperty |
| r0 :: object |
| r1 :: int |
| r2, r3, r4 :: object |
| r5 :: int |
| r6, r7, r8 :: object |
| r9 :: int |
| r10 :: __main__.AgainProperty |
| L0: |
| r0 = self._incr_func |
| r1 = self.value |
| r2 = self._incr_func |
| r3 = box(int, r1) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| r5 = unbox(int, r4) |
| r6 = self._incr_func |
| r7 = box(int, r5) |
| r8 = PyObject_CallFunctionObjArgs(r6, r7, 0) |
| r9 = unbox(int, r8) |
| r10 = AgainProperty(r0, r9) |
| return r10 |
| def AgainProperty.next__DerivedProperty_glue(__mypyc_self__): |
| __mypyc_self__, r0 :: __main__.AgainProperty |
| L0: |
| r0 = __mypyc_self__.next |
| return r0 |
| def AgainProperty.next__BaseProperty_glue(__mypyc_self__): |
| __mypyc_self__, r0 :: __main__.AgainProperty |
| L0: |
| r0 = __mypyc_self__.next |
| return r0 |
| def AgainProperty.bad_value(self): |
| self :: __main__.AgainProperty |
| r0 :: int |
| L0: |
| r0 = self._incrementer |
| return r0 |
| def AgainProperty.bad_value__DerivedProperty_glue(__mypyc_self__): |
| __mypyc_self__ :: __main__.AgainProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = __mypyc_self__.bad_value |
| r1 = box(int, r0) |
| return r1 |
| def AgainProperty.bad_value__BaseProperty_glue(__mypyc_self__): |
| __mypyc_self__ :: __main__.AgainProperty |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = __mypyc_self__.bad_value |
| r1 = box(int, r0) |
| return r1 |
| |
| [case testPropertyTraitSubclassing] |
| from mypy_extensions import trait |
| @trait |
| class SubclassedTrait: |
| @property |
| def this(self) -> SubclassedTrait: |
| return self |
| |
| @property |
| def boxed(self) -> object: |
| return 3 |
| |
| class DerivingObject(SubclassedTrait): |
| @property |
| def this(self) -> DerivingObject: |
| return self |
| |
| @property |
| def boxed(self) -> int: |
| return 5 |
| [out] |
| def SubclassedTrait.this(self): |
| self :: __main__.SubclassedTrait |
| L0: |
| return self |
| def SubclassedTrait.boxed(self): |
| self :: __main__.SubclassedTrait |
| r0 :: object |
| L0: |
| r0 = box(short_int, 6) |
| return r0 |
| def DerivingObject.this(self): |
| self :: __main__.DerivingObject |
| L0: |
| return self |
| def DerivingObject.this__SubclassedTrait_glue(__mypyc_self__): |
| __mypyc_self__, r0 :: __main__.DerivingObject |
| L0: |
| r0 = __mypyc_self__.this |
| return r0 |
| def DerivingObject.boxed(self): |
| self :: __main__.DerivingObject |
| L0: |
| return 10 |
| def DerivingObject.boxed__SubclassedTrait_glue(__mypyc_self__): |
| __mypyc_self__ :: __main__.DerivingObject |
| r0 :: int |
| r1 :: object |
| L0: |
| r0 = __mypyc_self__.boxed |
| r1 = box(int, r0) |
| return r1 |
| |
| [case testNativeIndex] |
| from typing import List |
| class A: |
| def __getitem__(self, index: int) -> int: pass |
| |
| def g(a: A, b: List[int], c: int) -> int: |
| return a[c] + b[c] |
| [out] |
| def A.__getitem__(self, index): |
| self :: __main__.A |
| index :: int |
| L0: |
| unreachable |
| def g(a, b, c): |
| a :: __main__.A |
| b :: list |
| c, r0 :: int |
| r1 :: object |
| r2, r3 :: int |
| L0: |
| r0 = a.__getitem__(c) |
| r1 = CPyList_GetItem(b, c) |
| r2 = unbox(int, r1) |
| r3 = CPyTagged_Add(r0, r2) |
| return r3 |
| |
| [case testTypeAlias_toplevel] |
| from typing import List, NewType, NamedTuple |
| Lol = NamedTuple('Lol', (('a', int), ('b', str))) |
| x = Lol(1, '') |
| Foo = List[int] |
| Bar = NewType('Bar', Foo) |
| y = Bar([1,2,3]) |
| [out] |
| def __top_level__(): |
| r0, r1 :: object |
| r2 :: bit |
| r3 :: str |
| r4 :: object |
| r5 :: dict |
| r6, r7, r8 :: str |
| r9 :: list |
| r10, r11, r12, r13 :: ptr |
| r14 :: str |
| r15 :: object |
| r16, r17, r18 :: str |
| r19 :: object |
| r20 :: str |
| r21 :: int32 |
| r22 :: bit |
| r23, r24, r25 :: str |
| r26 :: object |
| r27 :: str |
| r28 :: int32 |
| r29 :: bit |
| r30, r31, r32 :: str |
| r33 :: object |
| r34 :: str |
| r35 :: int32 |
| r36 :: bit |
| r37, r38 :: str |
| r39 :: object |
| r40 :: tuple[str, object] |
| r41 :: object |
| r42 :: str |
| r43 :: object |
| r44 :: tuple[str, object] |
| r45 :: object |
| r46 :: tuple[object, object] |
| r47 :: object |
| r48 :: dict |
| r49 :: str |
| r50, r51 :: object |
| r52 :: dict |
| r53 :: str |
| r54 :: int32 |
| r55 :: bit |
| r56 :: str |
| r57 :: dict |
| r58 :: str |
| r59, r60, r61 :: object |
| r62 :: tuple |
| r63 :: dict |
| r64 :: str |
| r65 :: int32 |
| r66 :: bit |
| r67 :: dict |
| r68 :: str |
| r69, r70, r71 :: object |
| r72 :: dict |
| r73 :: str |
| r74 :: int32 |
| r75 :: bit |
| r76 :: str |
| r77 :: dict |
| r78 :: str |
| r79 :: object |
| r80 :: dict |
| r81 :: str |
| r82, r83 :: object |
| r84 :: dict |
| r85 :: str |
| r86 :: int32 |
| r87 :: bit |
| r88 :: list |
| r89, r90, r91 :: object |
| r92, r93, r94, r95 :: ptr |
| r96 :: dict |
| r97 :: str |
| r98, r99 :: object |
| r100 :: dict |
| r101 :: str |
| r102 :: int32 |
| r103 :: bit |
| L0: |
| r0 = builtins :: module |
| r1 = load_address _Py_NoneStruct |
| r2 = r0 != r1 |
| if r2 goto L2 else goto L1 :: bool |
| L1: |
| r3 = 'builtins' |
| r4 = PyImport_Import(r3) |
| builtins = r4 :: module |
| L2: |
| r5 = __main__.globals :: static |
| r6 = 'List' |
| r7 = 'NewType' |
| r8 = 'NamedTuple' |
| r9 = PyList_New(3) |
| r10 = get_element_ptr r9 ob_item :: PyListObject |
| r11 = load_mem r10 :: ptr* |
| set_mem r11, r6 :: builtins.object* |
| r12 = r11 + WORD_SIZE*1 |
| set_mem r12, r7 :: builtins.object* |
| r13 = r11 + WORD_SIZE*2 |
| set_mem r13, r8 :: builtins.object* |
| keep_alive r9 |
| r14 = 'typing' |
| r15 = PyImport_ImportModuleLevelObject(r14, r5, 0, r9, 0) |
| typing = r15 :: module |
| r16 = 'typing' |
| r17 = 'List' |
| r18 = 'List' |
| r19 = CPyImport_ImportFrom(r15, r16, r17, r18) |
| r20 = 'List' |
| r21 = CPyDict_SetItem(r5, r20, r19) |
| r22 = r21 >= 0 :: signed |
| r23 = 'typing' |
| r24 = 'NewType' |
| r25 = 'NewType' |
| r26 = CPyImport_ImportFrom(r15, r23, r24, r25) |
| r27 = 'NewType' |
| r28 = CPyDict_SetItem(r5, r27, r26) |
| r29 = r28 >= 0 :: signed |
| r30 = 'typing' |
| r31 = 'NamedTuple' |
| r32 = 'NamedTuple' |
| r33 = CPyImport_ImportFrom(r15, r30, r31, r32) |
| r34 = 'NamedTuple' |
| r35 = CPyDict_SetItem(r5, r34, r33) |
| r36 = r35 >= 0 :: signed |
| r37 = 'Lol' |
| r38 = 'a' |
| r39 = load_address PyLong_Type |
| r40 = (r38, r39) |
| r41 = box(tuple[str, object], r40) |
| r42 = 'b' |
| r43 = load_address PyUnicode_Type |
| r44 = (r42, r43) |
| r45 = box(tuple[str, object], r44) |
| r46 = (r41, r45) |
| r47 = box(tuple[object, object], r46) |
| r48 = __main__.globals :: static |
| r49 = 'NamedTuple' |
| r50 = CPyDict_GetItem(r48, r49) |
| r51 = PyObject_CallFunctionObjArgs(r50, r37, r47, 0) |
| r52 = __main__.globals :: static |
| r53 = 'Lol' |
| r54 = CPyDict_SetItem(r52, r53, r51) |
| r55 = r54 >= 0 :: signed |
| r56 = '' |
| r57 = __main__.globals :: static |
| r58 = 'Lol' |
| r59 = CPyDict_GetItem(r57, r58) |
| r60 = box(short_int, 2) |
| r61 = PyObject_CallFunctionObjArgs(r59, r60, r56, 0) |
| r62 = cast(tuple, r61) |
| r63 = __main__.globals :: static |
| r64 = 'x' |
| r65 = CPyDict_SetItem(r63, r64, r62) |
| r66 = r65 >= 0 :: signed |
| r67 = __main__.globals :: static |
| r68 = 'List' |
| r69 = CPyDict_GetItem(r67, r68) |
| r70 = load_address PyLong_Type |
| r71 = PyObject_GetItem(r69, r70) |
| r72 = __main__.globals :: static |
| r73 = 'Foo' |
| r74 = CPyDict_SetItem(r72, r73, r71) |
| r75 = r74 >= 0 :: signed |
| r76 = 'Bar' |
| r77 = __main__.globals :: static |
| r78 = 'Foo' |
| r79 = CPyDict_GetItem(r77, r78) |
| r80 = __main__.globals :: static |
| r81 = 'NewType' |
| r82 = CPyDict_GetItem(r80, r81) |
| r83 = PyObject_CallFunctionObjArgs(r82, r76, r79, 0) |
| r84 = __main__.globals :: static |
| r85 = 'Bar' |
| r86 = CPyDict_SetItem(r84, r85, r83) |
| r87 = r86 >= 0 :: signed |
| r88 = PyList_New(3) |
| r89 = box(short_int, 2) |
| r90 = box(short_int, 4) |
| r91 = box(short_int, 6) |
| r92 = get_element_ptr r88 ob_item :: PyListObject |
| r93 = load_mem r92 :: ptr* |
| set_mem r93, r89 :: builtins.object* |
| r94 = r93 + WORD_SIZE*1 |
| set_mem r94, r90 :: builtins.object* |
| r95 = r93 + WORD_SIZE*2 |
| set_mem r95, r91 :: builtins.object* |
| keep_alive r88 |
| r96 = __main__.globals :: static |
| r97 = 'Bar' |
| r98 = CPyDict_GetItem(r96, r97) |
| r99 = PyObject_CallFunctionObjArgs(r98, r88, 0) |
| r100 = __main__.globals :: static |
| r101 = 'y' |
| r102 = CPyDict_SetItem(r100, r101, r99) |
| r103 = r102 >= 0 :: signed |
| return 1 |
| |
| [case testChainedConditional] |
| def g(x: int) -> int: |
| return x |
| def f(x: int, y: int, z: int) -> bool: |
| return g(x) < g(y) > g(z) |
| [out] |
| def g(x): |
| x :: int |
| L0: |
| return x |
| def f(x, y, z): |
| x, y, z, r0, r1 :: int |
| r2 :: native_int |
| r3 :: bit |
| r4 :: native_int |
| r5, r6, r7 :: bit |
| r8 :: bool |
| r9 :: bit |
| r10 :: bool |
| r11 :: int |
| r12 :: native_int |
| r13 :: bit |
| r14 :: native_int |
| r15, r16, r17 :: bit |
| r18 :: bool |
| r19 :: bit |
| L0: |
| r0 = g(x) |
| r1 = g(y) |
| r2 = r0 & 1 |
| r3 = r2 == 0 |
| r4 = r1 & 1 |
| r5 = r4 == 0 |
| r6 = r3 & r5 |
| if r6 goto L1 else goto L2 :: bool |
| L1: |
| r7 = r0 < r1 :: signed |
| r8 = r7 |
| goto L3 |
| L2: |
| r9 = CPyTagged_IsLt_(r0, r1) |
| r8 = r9 |
| L3: |
| if r8 goto L5 else goto L4 :: bool |
| L4: |
| r10 = r8 |
| goto L9 |
| L5: |
| r11 = g(z) |
| r12 = r1 & 1 |
| r13 = r12 == 0 |
| r14 = r11 & 1 |
| r15 = r14 == 0 |
| r16 = r13 & r15 |
| if r16 goto L6 else goto L7 :: bool |
| L6: |
| r17 = r1 > r11 :: signed |
| r18 = r17 |
| goto L8 |
| L7: |
| r19 = CPyTagged_IsLt_(r11, r1) |
| r18 = r19 |
| L8: |
| r10 = r18 |
| L9: |
| return r10 |
| |
| [case testEq] |
| class A: |
| def __eq__(self, x: object) -> bool: |
| return NotImplemented |
| [out] |
| def A.__eq__(self, x): |
| self :: __main__.A |
| x, r0 :: object |
| L0: |
| r0 = load_address _Py_NotImplementedStruct |
| return r0 |
| def A.__ne__(__mypyc_self__, rhs): |
| __mypyc_self__ :: __main__.A |
| rhs, r0, r1 :: object |
| r2 :: bit |
| r3 :: int32 |
| r4 :: bit |
| r5 :: bool |
| r6 :: object |
| L0: |
| r0 = __mypyc_self__.__eq__(rhs) |
| r1 = load_address _Py_NotImplementedStruct |
| r2 = r0 == r1 |
| if r2 goto L2 else goto L1 :: bool |
| L1: |
| r3 = PyObject_Not(r0) |
| r4 = r3 >= 0 :: signed |
| r5 = truncate r3: int32 to builtins.bool |
| r6 = box(bool, r5) |
| return r6 |
| L2: |
| return r1 |
| |
| [case testDecorators_toplevel] |
| from typing import Callable |
| |
| def a(f: Callable[[], None]) -> Callable[[], None]: |
| def g() -> None: |
| print('Entering') |
| f() |
| print('Exited') |
| return g |
| |
| def b(f: Callable[[], None]) -> Callable[[], None]: |
| def g() -> None: |
| print('---') |
| f() |
| print('---') |
| return g |
| |
| @a |
| @b |
| def c() -> None: |
| @a |
| @b |
| def d() -> None: |
| print('d') |
| print('c') |
| d() |
| |
| [out] |
| def g_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 g_a_obj.__call__(__mypyc_self__): |
| __mypyc_self__ :: __main__.g_a_obj |
| r0 :: __main__.a_env |
| r1, g :: object |
| r2 :: str |
| r3 :: object |
| r4 :: str |
| r5, r6, r7, r8 :: object |
| r9 :: str |
| r10 :: object |
| r11 :: str |
| r12, r13 :: object |
| L0: |
| r0 = __mypyc_self__.__mypyc_env__ |
| r1 = r0.g |
| g = r1 |
| r2 = 'Entering' |
| r3 = builtins :: module |
| r4 = 'print' |
| r5 = CPyObject_GetAttr(r3, r4) |
| r6 = PyObject_CallFunctionObjArgs(r5, r2, 0) |
| r7 = r0.f |
| r8 = PyObject_CallFunctionObjArgs(r7, 0) |
| r9 = 'Exited' |
| r10 = builtins :: module |
| r11 = 'print' |
| r12 = CPyObject_GetAttr(r10, r11) |
| r13 = PyObject_CallFunctionObjArgs(r12, r9, 0) |
| return 1 |
| def a(f): |
| f :: object |
| r0 :: __main__.a_env |
| r1 :: bool |
| r2 :: __main__.g_a_obj |
| r3, r4 :: bool |
| r5 :: object |
| L0: |
| r0 = a_env() |
| r0.f = f; r1 = is_error |
| r2 = g_a_obj() |
| r2.__mypyc_env__ = r0; r3 = is_error |
| r0.g = r2; r4 = is_error |
| r5 = r0.g |
| return r5 |
| def g_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 g_b_obj.__call__(__mypyc_self__): |
| __mypyc_self__ :: __main__.g_b_obj |
| r0 :: __main__.b_env |
| r1, g :: object |
| r2 :: str |
| r3 :: object |
| r4 :: str |
| r5, r6, r7, r8 :: object |
| r9 :: str |
| r10 :: object |
| r11 :: str |
| r12, r13 :: object |
| L0: |
| r0 = __mypyc_self__.__mypyc_env__ |
| r1 = r0.g |
| g = r1 |
| r2 = '---' |
| r3 = builtins :: module |
| r4 = 'print' |
| r5 = CPyObject_GetAttr(r3, r4) |
| r6 = PyObject_CallFunctionObjArgs(r5, r2, 0) |
| r7 = r0.f |
| r8 = PyObject_CallFunctionObjArgs(r7, 0) |
| r9 = '---' |
| r10 = builtins :: module |
| r11 = 'print' |
| r12 = CPyObject_GetAttr(r10, r11) |
| r13 = PyObject_CallFunctionObjArgs(r12, r9, 0) |
| return 1 |
| def b(f): |
| f :: object |
| r0 :: __main__.b_env |
| r1 :: bool |
| r2 :: __main__.g_b_obj |
| r3, r4 :: bool |
| r5 :: object |
| L0: |
| r0 = b_env() |
| r0.f = f; r1 = is_error |
| r2 = g_b_obj() |
| r2.__mypyc_env__ = r0; r3 = is_error |
| r0.g = r2; r4 = is_error |
| r5 = r0.g |
| return r5 |
| def d_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 d_c_obj.__call__(__mypyc_self__): |
| __mypyc_self__ :: __main__.d_c_obj |
| r0 :: __main__.c_env |
| r1, d :: object |
| r2 :: str |
| r3 :: object |
| r4 :: str |
| r5, r6 :: object |
| L0: |
| r0 = __mypyc_self__.__mypyc_env__ |
| r1 = r0.d |
| d = r1 |
| r2 = 'd' |
| r3 = builtins :: module |
| r4 = 'print' |
| r5 = CPyObject_GetAttr(r3, r4) |
| r6 = PyObject_CallFunctionObjArgs(r5, r2, 0) |
| return 1 |
| def c(): |
| r0 :: __main__.c_env |
| r1 :: __main__.d_c_obj |
| r2 :: bool |
| r3 :: dict |
| r4 :: str |
| r5, r6 :: object |
| r7 :: dict |
| r8 :: str |
| r9, r10 :: object |
| r11 :: bool |
| r12 :: dict |
| r13 :: str |
| r14 :: int32 |
| r15 :: bit |
| r16 :: str |
| r17 :: object |
| r18 :: str |
| r19, r20, r21, r22 :: object |
| L0: |
| r0 = c_env() |
| r1 = d_c_obj() |
| r1.__mypyc_env__ = r0; r2 = is_error |
| r3 = __main__.globals :: static |
| r4 = 'b' |
| r5 = CPyDict_GetItem(r3, r4) |
| r6 = PyObject_CallFunctionObjArgs(r5, r1, 0) |
| r7 = __main__.globals :: static |
| r8 = 'a' |
| r9 = CPyDict_GetItem(r7, r8) |
| r10 = PyObject_CallFunctionObjArgs(r9, r6, 0) |
| r0.d = r10; r11 = is_error |
| r12 = __main__.globals :: static |
| r13 = 'd' |
| r14 = CPyDict_SetItem(r12, r13, r10) |
| r15 = r14 >= 0 :: signed |
| r16 = 'c' |
| r17 = builtins :: module |
| r18 = 'print' |
| r19 = CPyObject_GetAttr(r17, r18) |
| r20 = PyObject_CallFunctionObjArgs(r19, r16, 0) |
| r21 = r0.d |
| r22 = PyObject_CallFunctionObjArgs(r21, 0) |
| return 1 |
| def __top_level__(): |
| r0, r1 :: object |
| r2 :: bit |
| r3 :: str |
| r4 :: object |
| r5 :: dict |
| r6 :: str |
| r7 :: list |
| r8, r9 :: ptr |
| r10 :: str |
| r11 :: object |
| r12, r13, r14 :: str |
| r15 :: object |
| r16 :: str |
| r17 :: int32 |
| r18 :: bit |
| r19 :: dict |
| r20 :: str |
| r21 :: object |
| r22 :: dict |
| r23 :: str |
| r24, r25 :: object |
| r26 :: dict |
| r27 :: str |
| r28, r29 :: object |
| r30 :: dict |
| r31 :: str |
| r32 :: int32 |
| r33 :: bit |
| L0: |
| r0 = builtins :: module |
| r1 = load_address _Py_NoneStruct |
| r2 = r0 != r1 |
| if r2 goto L2 else goto L1 :: bool |
| L1: |
| r3 = 'builtins' |
| r4 = PyImport_Import(r3) |
| builtins = r4 :: module |
| L2: |
| r5 = __main__.globals :: static |
| r6 = 'Callable' |
| r7 = PyList_New(1) |
| r8 = get_element_ptr r7 ob_item :: PyListObject |
| r9 = load_mem r8 :: ptr* |
| set_mem r9, r6 :: builtins.object* |
| keep_alive r7 |
| r10 = 'typing' |
| r11 = PyImport_ImportModuleLevelObject(r10, r5, 0, r7, 0) |
| typing = r11 :: module |
| r12 = 'typing' |
| r13 = 'Callable' |
| r14 = 'Callable' |
| r15 = CPyImport_ImportFrom(r11, r12, r13, r14) |
| r16 = 'Callable' |
| r17 = CPyDict_SetItem(r5, r16, r15) |
| r18 = r17 >= 0 :: signed |
| r19 = __main__.globals :: static |
| r20 = 'c' |
| r21 = CPyDict_GetItem(r19, r20) |
| r22 = __main__.globals :: static |
| r23 = 'b' |
| r24 = CPyDict_GetItem(r22, r23) |
| r25 = PyObject_CallFunctionObjArgs(r24, r21, 0) |
| r26 = __main__.globals :: static |
| r27 = 'a' |
| r28 = CPyDict_GetItem(r26, r27) |
| r29 = PyObject_CallFunctionObjArgs(r28, r25, 0) |
| r30 = __main__.globals :: static |
| r31 = 'c' |
| r32 = CPyDict_SetItem(r30, r31, r29) |
| r33 = r32 >= 0 :: signed |
| return 1 |
| |
| [case testDecoratorsSimple_toplevel] |
| from typing import Callable |
| |
| def a(f: Callable[[], None]) -> Callable[[], None]: |
| def g() -> None: |
| print('Entering') |
| f() |
| print('Exited') |
| return g |
| |
| [out] |
| def g_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 g_a_obj.__call__(__mypyc_self__): |
| __mypyc_self__ :: __main__.g_a_obj |
| r0 :: __main__.a_env |
| r1, g :: object |
| r2 :: str |
| r3 :: object |
| r4 :: str |
| r5, r6, r7, r8 :: object |
| r9 :: str |
| r10 :: object |
| r11 :: str |
| r12, r13 :: object |
| L0: |
| r0 = __mypyc_self__.__mypyc_env__ |
| r1 = r0.g |
| g = r1 |
| r2 = 'Entering' |
| r3 = builtins :: module |
| r4 = 'print' |
| r5 = CPyObject_GetAttr(r3, r4) |
| r6 = PyObject_CallFunctionObjArgs(r5, r2, 0) |
| r7 = r0.f |
| r8 = PyObject_CallFunctionObjArgs(r7, 0) |
| r9 = 'Exited' |
| r10 = builtins :: module |
| r11 = 'print' |
| r12 = CPyObject_GetAttr(r10, r11) |
| r13 = PyObject_CallFunctionObjArgs(r12, r9, 0) |
| return 1 |
| def a(f): |
| f :: object |
| r0 :: __main__.a_env |
| r1 :: bool |
| r2 :: __main__.g_a_obj |
| r3, r4 :: bool |
| r5 :: object |
| L0: |
| r0 = a_env() |
| r0.f = f; r1 = is_error |
| r2 = g_a_obj() |
| r2.__mypyc_env__ = r0; r3 = is_error |
| r0.g = r2; r4 = is_error |
| r5 = r0.g |
| return r5 |
| def __top_level__(): |
| r0, r1 :: object |
| r2 :: bit |
| r3 :: str |
| r4 :: object |
| r5 :: dict |
| r6 :: str |
| r7 :: list |
| r8, r9 :: ptr |
| r10 :: str |
| r11 :: object |
| r12, r13, r14 :: str |
| r15 :: object |
| r16 :: str |
| r17 :: int32 |
| r18 :: bit |
| L0: |
| r0 = builtins :: module |
| r1 = load_address _Py_NoneStruct |
| r2 = r0 != r1 |
| if r2 goto L2 else goto L1 :: bool |
| L1: |
| r3 = 'builtins' |
| r4 = PyImport_Import(r3) |
| builtins = r4 :: module |
| L2: |
| r5 = __main__.globals :: static |
| r6 = 'Callable' |
| r7 = PyList_New(1) |
| r8 = get_element_ptr r7 ob_item :: PyListObject |
| r9 = load_mem r8 :: ptr* |
| set_mem r9, r6 :: builtins.object* |
| keep_alive r7 |
| r10 = 'typing' |
| r11 = PyImport_ImportModuleLevelObject(r10, r5, 0, r7, 0) |
| typing = r11 :: module |
| r12 = 'typing' |
| r13 = 'Callable' |
| r14 = 'Callable' |
| r15 = CPyImport_ImportFrom(r11, r12, r13, r14) |
| r16 = 'Callable' |
| r17 = CPyDict_SetItem(r5, r16, r15) |
| r18 = r17 >= 0 :: signed |
| return 1 |
| |
| [case testAnyAllG] |
| from typing import Iterable |
| |
| def call_any(l: Iterable[int]) -> bool: |
| return any(i == 0 for i in l) |
| |
| def call_all(l: Iterable[int]) -> bool: |
| return all(i == 0 for i in l) |
| |
| [out] |
| def call_any(l): |
| l :: object |
| r0 :: bool |
| r1, r2 :: object |
| r3, i :: int |
| r4 :: native_int |
| r5, r6 :: bit |
| r7 :: bool |
| r8, r9 :: bit |
| L0: |
| r0 = 0 |
| r1 = PyObject_GetIter(l) |
| L1: |
| r2 = PyIter_Next(r1) |
| if is_error(r2) goto L9 else goto L2 |
| L2: |
| r3 = unbox(int, r2) |
| i = r3 |
| r4 = i & 1 |
| r5 = r4 == 0 |
| if r5 goto L3 else goto L4 :: bool |
| L3: |
| r6 = i == 0 |
| r7 = r6 |
| goto L5 |
| L4: |
| r8 = CPyTagged_IsEq_(i, 0) |
| r7 = r8 |
| L5: |
| if r7 goto L6 else goto L7 :: bool |
| L6: |
| r0 = 1 |
| goto L11 |
| L7: |
| L8: |
| goto L1 |
| L9: |
| r9 = CPy_NoErrOccured() |
| L10: |
| L11: |
| return r0 |
| def call_all(l): |
| l :: object |
| r0 :: bool |
| r1, r2 :: object |
| r3, i :: int |
| r4 :: native_int |
| r5, r6 :: bit |
| r7 :: bool |
| r8 :: bit |
| r9 :: bool |
| r10 :: bit |
| L0: |
| r0 = 1 |
| r1 = PyObject_GetIter(l) |
| L1: |
| r2 = PyIter_Next(r1) |
| if is_error(r2) goto L9 else goto L2 |
| L2: |
| r3 = unbox(int, r2) |
| i = r3 |
| r4 = i & 1 |
| r5 = r4 == 0 |
| if r5 goto L3 else goto L4 :: bool |
| L3: |
| r6 = i == 0 |
| r7 = r6 |
| goto L5 |
| L4: |
| r8 = CPyTagged_IsEq_(i, 0) |
| r7 = r8 |
| L5: |
| r9 = r7 ^ 1 |
| if r9 goto L6 else goto L7 :: bool |
| L6: |
| r0 = 0 |
| goto L11 |
| L7: |
| L8: |
| goto L1 |
| L9: |
| r10 = CPy_NoErrOccured() |
| L10: |
| L11: |
| return r0 |
| |
| [case testSum] |
| from typing import Callable, Iterable |
| |
| def call_sum(l: Iterable[int], comparison: Callable[[int], bool]) -> int: |
| return sum(comparison(x) for x in l) |
| |
| [out] |
| def call_sum(l, comparison): |
| l, comparison :: object |
| r0 :: int |
| r1, r2 :: object |
| r3, x :: int |
| r4, r5 :: object |
| r6 :: bool |
| r7 :: object |
| r8, r9 :: int |
| r10 :: bit |
| L0: |
| r0 = 0 |
| r1 = PyObject_GetIter(l) |
| L1: |
| r2 = PyIter_Next(r1) |
| if is_error(r2) goto L4 else goto L2 |
| L2: |
| r3 = unbox(int, r2) |
| x = r3 |
| r4 = box(int, x) |
| r5 = PyObject_CallFunctionObjArgs(comparison, r4, 0) |
| r6 = unbox(bool, r5) |
| r7 = box(bool, r6) |
| r8 = unbox(int, r7) |
| r9 = CPyTagged_Add(r0, r8) |
| r0 = r9 |
| L3: |
| goto L1 |
| L4: |
| r10 = CPy_NoErrOccured() |
| L5: |
| return r0 |
| |
| [case testSetAttr1] |
| from typing import Any, Dict, List |
| def lol(x: Any): |
| setattr(x, 'x', '5') |
| |
| [out] |
| def lol(x): |
| x :: object |
| r0, r1 :: str |
| r2 :: int32 |
| r3 :: bit |
| r4 :: object |
| L0: |
| r0 = 'x' |
| r1 = '5' |
| r2 = PyObject_SetAttr(x, r0, r1) |
| r3 = r2 >= 0 :: signed |
| r4 = box(None, 1) |
| return r4 |
| |
| [case testFinalModuleInt] |
| from typing import Final |
| |
| x: Final = 1 |
| y: Final = 2 |
| |
| def f(a: bool) -> int: |
| if a: |
| return x |
| else: |
| return y |
| [out] |
| def f(a): |
| a :: bool |
| L0: |
| if a goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 4 |
| L3: |
| unreachable |
| |
| [case testFinalModuleStr] |
| from typing import Final |
| |
| x: Final = 'x' |
| y: Final = 'y' |
| |
| def f(a: bool) -> str: |
| if a: |
| return x |
| else: |
| return y |
| [out] |
| def f(a): |
| a :: bool |
| r0, r1 :: str |
| L0: |
| if a goto L1 else goto L2 :: bool |
| L1: |
| r0 = 'x' |
| return r0 |
| L2: |
| r1 = 'y' |
| return r1 |
| L3: |
| unreachable |
| |
| [case testFinalModuleBool] |
| from typing import Final |
| |
| x: Final = True |
| y: Final = False |
| |
| def f(a: bool) -> bool: |
| if a: |
| return x |
| else: |
| return y |
| [out] |
| def f(a): |
| a :: bool |
| L0: |
| if a goto L1 else goto L2 :: bool |
| L1: |
| return 1 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| |
| [case testFinalClass] |
| from typing import Final |
| |
| class C: |
| x: Final = 1 |
| y: Final = 2 |
| |
| def f(a: bool) -> int: |
| if a: |
| return C.x |
| else: |
| return C.y |
| [out] |
| def C.__mypyc_defaults_setup(__mypyc_self__): |
| __mypyc_self__ :: __main__.C |
| r0, r1 :: bool |
| L0: |
| __mypyc_self__.x = 2; r0 = is_error |
| __mypyc_self__.y = 4; r1 = is_error |
| return 1 |
| def f(a): |
| a :: bool |
| L0: |
| if a goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 4 |
| L3: |
| unreachable |
| |
| [case testFinalStaticList] |
| from typing import Final |
| |
| x: Final = [1] |
| |
| def f() -> int: |
| return x[0] |
| [out] |
| def f(): |
| r0 :: list |
| r1 :: bool |
| r2 :: object |
| r3 :: int |
| L0: |
| r0 = __main__.x :: static |
| if is_error(r0) goto L1 else goto L2 |
| L1: |
| r1 = raise NameError('value for final name "x" was not set') |
| unreachable |
| L2: |
| r2 = CPyList_GetItemShort(r0, 0) |
| r3 = unbox(int, r2) |
| return r3 |
| |
| [case testFinalStaticTuple] |
| from typing import Final |
| |
| x: Final = (1, 2) |
| |
| def f() -> int: |
| return x[0] |
| [out] |
| def f(): |
| r0 :: tuple[int, int] |
| r1 :: bool |
| r2 :: int |
| L0: |
| r0 = __main__.x :: static |
| if is_error(r0) goto L1 else goto L2 |
| L1: |
| r1 = raise NameError('value for final name "x" was not set') |
| unreachable |
| L2: |
| r2 = r0[0] |
| return r2 |
| |
| [case testFinalStaticInt] |
| from typing import Final |
| |
| x: Final = 1 + 1 |
| |
| def f() -> int: |
| return x - 1 |
| [out] |
| def f(): |
| r0 :: int |
| r1 :: bool |
| r2 :: int |
| L0: |
| r0 = __main__.x :: static |
| if is_error(r0) goto L1 else goto L2 |
| L1: |
| r1 = raise NameError('value for final name "x" was not set') |
| unreachable |
| L2: |
| r2 = CPyTagged_Subtract(r0, 2) |
| return r2 |
| |
| [case testFinalRestrictedTypeVar] |
| from typing import TypeVar |
| if False: |
| from typing import Final |
| |
| FOO = 10 # type: Final |
| |
| Targ = TypeVar('Targ', int, str) |
| def foo(z: Targ) -> None: |
| FOO |
| [out] |
| def foo(z): |
| z :: object |
| L0: |
| return 1 |
| |
| [case testDirectlyCall__bool__] |
| class A: |
| def __bool__(self) -> bool: |
| return True |
| class B(A): |
| def __bool__(self) -> bool: |
| return False |
| |
| def lol(x: A) -> int: |
| if x: |
| return 1 |
| else: |
| return 0 |
| |
| [out] |
| def A.__bool__(self): |
| self :: __main__.A |
| L0: |
| return 1 |
| def B.__bool__(self): |
| self :: __main__.B |
| L0: |
| return 0 |
| def lol(x): |
| x :: __main__.A |
| r0 :: bool |
| L0: |
| r0 = x.__bool__() |
| if r0 goto L1 else goto L2 :: bool |
| L1: |
| return 2 |
| L2: |
| return 0 |
| L3: |
| unreachable |
| |
| [case testRevealType] |
| def f(x: int) -> None: |
| reveal_type(x) # type: ignore |
| [out] |
| def f(x): |
| x :: int |
| r0 :: object |
| r1 :: str |
| r2, r3, r4 :: object |
| L0: |
| r0 = builtins :: module |
| r1 = 'reveal_type' |
| r2 = CPyObject_GetAttr(r0, r1) |
| r3 = box(int, x) |
| r4 = PyObject_CallFunctionObjArgs(r2, r3, 0) |
| return 1 |
| |
| [case testCallCWithStrJoinMethod] |
| from typing import List |
| def f(x: str, y: List[str]) -> str: |
| return x.join(y) |
| [out] |
| def f(x, y): |
| x :: str |
| y :: list |
| r0 :: str |
| L0: |
| r0 = PyUnicode_Join(x, y) |
| return r0 |
| |
| [case testCallCWithToListFunction] |
| from typing import List, Iterable, Tuple, Dict |
| # generic object |
| def f(x: Iterable[int]) -> List[int]: |
| return list(x) |
| |
| # need coercing |
| def g(x: Tuple[int, int, int]) -> List[int]: |
| return list(x) |
| |
| # non-list object |
| def h(x: Dict[int, str]) -> List[int]: |
| return list(x) |
| |
| [out] |
| def f(x): |
| x :: object |
| r0 :: list |
| L0: |
| r0 = PySequence_List(x) |
| return r0 |
| def g(x): |
| x :: tuple[int, int, int] |
| r0 :: object |
| r1 :: list |
| L0: |
| r0 = box(tuple[int, int, int], x) |
| r1 = PySequence_List(r0) |
| return r1 |
| def h(x): |
| x :: dict |
| r0 :: list |
| L0: |
| r0 = PySequence_List(x) |
| return r0 |
| |
| [case testBoolFunction] |
| def f(x: object) -> bool: |
| return bool(x) |
| [out] |
| def f(x): |
| x :: object |
| r0 :: int32 |
| r1 :: bit |
| r2 :: bool |
| L0: |
| r0 = PyObject_IsTrue(x) |
| r1 = r0 >= 0 :: signed |
| r2 = truncate r0: int32 to builtins.bool |
| return r2 |
| |
| [case testLocalImportSubmodule] |
| def f() -> int: |
| import p.m |
| return p.x |
| [file p/__init__.py] |
| x = 1 |
| [file p/m.py] |
| [out] |
| def f(): |
| r0 :: dict |
| r1, r2 :: object |
| r3 :: bit |
| r4 :: str |
| r5 :: object |
| r6 :: dict |
| r7 :: str |
| r8 :: object |
| r9 :: str |
| r10 :: int32 |
| r11 :: bit |
| r12 :: dict |
| r13 :: str |
| r14 :: object |
| r15 :: str |
| r16 :: object |
| r17 :: int |
| L0: |
| r0 = __main__.globals :: static |
| r1 = p.m :: module |
| r2 = load_address _Py_NoneStruct |
| r3 = r1 != r2 |
| if r3 goto L2 else goto L1 :: bool |
| L1: |
| r4 = 'p.m' |
| r5 = PyImport_Import(r4) |
| p.m = r5 :: module |
| L2: |
| r6 = PyImport_GetModuleDict() |
| r7 = 'p' |
| r8 = CPyDict_GetItem(r6, r7) |
| r9 = 'p' |
| r10 = CPyDict_SetItem(r0, r9, r8) |
| r11 = r10 >= 0 :: signed |
| r12 = PyImport_GetModuleDict() |
| r13 = 'p' |
| r14 = CPyDict_GetItem(r12, r13) |
| r15 = 'x' |
| r16 = CPyObject_GetAttr(r14, r15) |
| r17 = unbox(int, r16) |
| return r17 |
| |
| [case testIsinstanceBool] |
| def f(x: object) -> bool: |
| return isinstance(x, bool) |
| [out] |
| def f(x): |
| x, r0 :: object |
| r1 :: int32 |
| r2 :: bit |
| r3 :: bool |
| L0: |
| r0 = load_address PyBool_Type |
| r1 = PyObject_IsInstance(x, r0) |
| r2 = r1 >= 0 :: signed |
| r3 = truncate r1: int32 to builtins.bool |
| return r3 |
| |
| [case testRangeObject] |
| def range_object() -> None: |
| r = range(4, 12, 2) |
| sum = 0 |
| for i in r: |
| sum += i |
| |
| def range_in_loop() -> None: |
| sum = 0 |
| for i in range(4, 12, 2): |
| sum += i |
| [out] |
| def range_object(): |
| r0, r1, r2, r3, r4 :: object |
| r5, r :: range |
| sum :: int |
| r6, r7 :: object |
| r8, i, r9 :: int |
| r10 :: bit |
| L0: |
| r0 = load_address PyRange_Type |
| r1 = box(short_int, 8) |
| r2 = box(short_int, 24) |
| r3 = box(short_int, 4) |
| r4 = PyObject_CallFunctionObjArgs(r0, r1, r2, r3, 0) |
| r5 = cast(range, r4) |
| r = r5 |
| sum = 0 |
| r6 = PyObject_GetIter(r) |
| L1: |
| r7 = PyIter_Next(r6) |
| if is_error(r7) goto L4 else goto L2 |
| L2: |
| r8 = unbox(int, r7) |
| i = r8 |
| r9 = CPyTagged_Add(sum, i) |
| sum = r9 |
| L3: |
| goto L1 |
| L4: |
| r10 = CPy_NoErrOccured() |
| L5: |
| return 1 |
| def range_in_loop(): |
| sum :: int |
| r0 :: short_int |
| i :: int |
| r1 :: bit |
| r2 :: int |
| r3 :: short_int |
| L0: |
| sum = 0 |
| r0 = 8 |
| i = r0 |
| L1: |
| r1 = r0 < 24 :: signed |
| if r1 goto L2 else goto L4 :: bool |
| L2: |
| r2 = CPyTagged_Add(sum, i) |
| sum = r2 |
| L3: |
| r3 = r0 + 4 |
| r0 = r3 |
| i = r3 |
| goto L1 |
| L4: |
| return 1 |
| [case testLocalRedefinition] |
| # mypy: allow-redefinition |
| def f() -> None: |
| i = 0 |
| i += 1 |
| i = "foo" |
| i += i |
| i = 0.0 |
| [out] |
| def f(): |
| i, r0 :: int |
| r1, i__redef__, r2 :: str |
| r3, i__redef____redef__ :: float |
| L0: |
| i = 0 |
| r0 = CPyTagged_Add(i, 2) |
| i = r0 |
| r1 = 'foo' |
| i__redef__ = r1 |
| r2 = CPyStr_Append(i__redef__, i__redef__) |
| i__redef__ = r2 |
| r3 = 0.0 |
| i__redef____redef__ = r3 |
| return 1 |