Skip to content

Commit f24987a

Browse files
Add a null check for attribute promotion
1 parent d8994b0 commit f24987a

File tree

4 files changed

+51
-2
lines changed

4 files changed

+51
-2
lines changed

Lib/test/test_capi/test_opt.py

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2305,6 +2305,40 @@ def testfunc(n):
23052305
self.assertNotIn("_GUARD_TOS_INT", uops)
23062306
self.assertNotIn("_GUARD_NOS_INT", uops)
23072307

2308+
def test_attr_promotion_failure(self):
2309+
# We're not testing for any specific uops here, just
2310+
# testing it doesn't crash.
2311+
result = script_helper.run_python_until_end('-c', textwrap.dedent("""
2312+
import _testinternalcapi
2313+
import opcode
2314+
import _opcode
2315+
2316+
def get_first_executor(func):
2317+
code = func.__code__
2318+
co_code = code.co_code
2319+
for i in range(0, len(co_code), 2):
2320+
try:
2321+
return _opcode.get_executor(code, i)
2322+
except ValueError:
2323+
pass
2324+
return None
2325+
2326+
def get_opnames(ex):
2327+
return {item[0] for item in ex}
2328+
2329+
import email
2330+
2331+
def testfunc(n):
2332+
for _ in range(n):
2333+
email.jit_testing = None
2334+
prompt = email.jit_testing
2335+
del email.jit_testing
2336+
2337+
2338+
testfunc(_testinternalcapi.TIER2_THRESHOLD)
2339+
"""), PYTHON_JIT="1")
2340+
self.assertEqual(result[0].rc, 0, result)
2341+
23082342

23092343
def global_identity(x):
23102344
return x

Python/optimizer_analysis.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,10 @@ convert_global_to_const(_PyUOpInstruction *inst, PyObject *obj, bool pop)
103103
if ((int)index >= dict->ma_keys->dk_nentries) {
104104
return NULL;
105105
}
106+
PyDictKeysObject *keys = dict->ma_keys;
107+
if (keys->dk_version != inst->operand0) {
108+
return NULL;
109+
}
106110
PyObject *res = entries[index].me_value;
107111
if (res == NULL) {
108112
return NULL;

Python/optimizer_bytecodes.c

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -557,7 +557,13 @@ dummy_func(void) {
557557
PyDict_Watch(GLOBALS_WATCHER_ID, dict);
558558
_Py_BloomFilter_Add(dependencies, dict);
559559
PyObject *res = convert_global_to_const(this_instr, dict, true);
560-
attr = sym_new_const(ctx, res);
560+
if (res == NULL) {
561+
attr = sym_new_not_null(ctx);
562+
}
563+
else {
564+
attr = sym_new_const(ctx, res);
565+
}
566+
561567
}
562568
}
563569
}

Python/optimizer_cases.c.h

Lines changed: 6 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)