Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion mypyc/codegen/emitclass.py
Original file line number Diff line number Diff line change
Expand Up @@ -299,7 +299,8 @@ def generate_class(cl: ClassIR, module: str, emitter: Emitter) -> None:
fields["tp_traverse"] = f"(traverseproc){name_prefix}_traverse"
fields["tp_clear"] = f"(inquiry){clear_name}"
# Populate .tp_finalize and generate a finalize method only if __del__ is defined for this class.
del_method = next((e.method for e in cl.vtable_entries if e.name == "__del__"), None)
# A decorated __del__ has no vtable entry, so it's looked up in the methods.
del_method = cl.get_method("__del__")
if del_method:
fields["tp_finalize"] = f"(destructor){finalize_name}"
if needs_getseters:
Expand Down
9 changes: 5 additions & 4 deletions mypyc/irbuild/vtable.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@

import itertools

from mypyc.common import UNDECORATED_PREFIX
from mypyc.ir.class_ir import ClassIR, VTableEntries, VTableMethod
from mypyc.sametype import is_same_method_signature

Expand Down Expand Up @@ -40,9 +39,11 @@ def compute_vtable(cls: ClassIR) -> None:

for t in [cls] + [t for t in all_traits if t is not cls]:
for fn in itertools.chain(t.methods.values()):
if fn.name.startswith(UNDECORATED_PREFIX):
# The undecorated function of a decorated override is only called by the
# decorator at runtime, never natively
if fn.name not in t.method_decls:
# Decorated methods aren't declared as native methods, since they are only
# called through the Python API, so they don't need an entry. This includes
# the undecorated function of a decorated override, which only the
# decorators call.
continue
# TODO: don't generate a new entry when we overload without changing the type
if fn == cls.get_method(fn.name, prefer_method=True):
Expand Down
57 changes: 57 additions & 0 deletions mypyc/test-data/irbuild-glue-methods.test
Original file line number Diff line number Diff line change
Expand Up @@ -509,3 +509,60 @@ L0:
r0 = ''
__mypyc_self__._x = r0
return 1

[case testNoGlueForOverrideOfDecoratedMethod_64bit]
from typing import TypeVar

T = TypeVar("T")

def dec(f: T) -> T:
return f

class Base:
@dec
def f(self) -> object:
return None

class Sub(Base):
def f(self) -> int:
return 1

def call_base(b: Base) -> object:
return b.f()

def call_sub(s: Sub) -> int:
return s.f()
[out]
def dec(f):
f :: object
L0:
return f
def Base.f(self):
self :: __main__.Base
r0 :: object
L0:
r0 = box(None, 1)
return r0
def Sub.f(self):
self :: __main__.Sub
L0:
return 2
def call_base(b):
b :: __main__.Base
r0 :: str
r1 :: object[1]
r2 :: object_ptr
r3 :: object
L0:
r0 = 'f'
r1 = [b]
r2 = load_address r1
r3 = PyObject_VectorcallMethod(r0, r2, 9223372036854775809, 0)
keep_alive b
return r3
def call_sub(s):
s :: __main__.Sub
r0 :: int
L0:
r0 = s.f()
return r0
Loading
Loading