Skip to content

Commit c39f5e7

Browse files
advait-dixitJukkaL
authored andcommitted
[mypyc] Fixing condition for handling user-defined __del__ (#19188)
Fixes #19175. Conditions for generating and invoking `del` method were not consistent. As things currently stand, this pull request fixes the crash. However, for classes that derive from Python built-ins, user-defined `__del__` will not be invoked.
1 parent 0a4f284 commit c39f5e7

File tree

2 files changed

+24
-3
lines changed

2 files changed

+24
-3
lines changed

mypyc/codegen/emitclass.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -304,9 +304,6 @@ def emit_line() -> None:
304304
emit_line()
305305
generate_dealloc_for_class(cl, dealloc_name, clear_name, bool(del_method), emitter)
306306
emit_line()
307-
if del_method:
308-
generate_finalize_for_class(del_method, finalize_name, emitter)
309-
emit_line()
310307

311308
if cl.allow_interpreted_subclasses:
312309
shadow_vtable_name: str | None = generate_vtables(
@@ -317,6 +314,9 @@ def emit_line() -> None:
317314
shadow_vtable_name = None
318315
vtable_name = generate_vtables(cl, vtable_setup_name, vtable_name, emitter, shadow=False)
319316
emit_line()
317+
if del_method:
318+
generate_finalize_for_class(del_method, finalize_name, emitter)
319+
emit_line()
320320
if needs_getseters:
321321
generate_getseter_declarations(cl, emitter)
322322
emit_line()

mypyc/test-data/run-classes.test

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2754,6 +2754,21 @@ def test_function():
27542754
assert(isinstance(d.fitem, ForwardDefinedClass))
27552755
assert(isinstance(d.fitems, ForwardDefinedClass))
27562756

2757+
[case testDelForDictSubclass-xfail]
2758+
# The crash in issue mypy#19175 is fixed.
2759+
# But, for classes that derive from built-in Python classes, user-defined __del__ method is not
2760+
# being invoked.
2761+
class DictSubclass(dict):
2762+
def __del__(self):
2763+
print("deleting DictSubclass...")
2764+
2765+
[file driver.py]
2766+
import native
2767+
native.DictSubclass()
2768+
2769+
[out]
2770+
deleting DictSubclass...
2771+
27572772
[case testDel]
27582773
class A:
27592774
def __del__(self):
@@ -2774,6 +2789,12 @@ class C(B):
27742789
class D(A):
27752790
pass
27762791

2792+
# Just make sure that this class compiles (see issue mypy#19175). testDelForDictSubclass tests for
2793+
# correct output.
2794+
class NormDict(dict):
2795+
def __del__(self) -> None:
2796+
pass
2797+
27772798
[file driver.py]
27782799
import native
27792800
native.C()

0 commit comments

Comments
 (0)