Author: Armin Rigo <ar...@tunes.org> Branch: py3.5 Changeset: r88822:806213151c0a Date: 2016-12-02 16:20 +0100 http://bitbucket.org/pypy/pypy/changeset/806213151c0a/
Log: implement LOAD_CLASSDEREF diff --git a/pypy/interpreter/astcompiler/assemble.py b/pypy/interpreter/astcompiler/assemble.py --- a/pypy/interpreter/astcompiler/assemble.py +++ b/pypy/interpreter/astcompiler/assemble.py @@ -682,12 +682,11 @@ ops.JUMP_IF_FALSE_OR_POP: 0, ops.POP_JUMP_IF_TRUE: -1, ops.POP_JUMP_IF_FALSE: -1, - # TODO ops.JUMP_IF_NOT_DEBUG: 0, # TODO ops.BUILD_LIST_FROM_ARG: 1, - # TODO + ops.LOAD_CLASSDEREF: 1, } diff --git a/pypy/interpreter/astcompiler/codegen.py b/pypy/interpreter/astcompiler/codegen.py --- a/pypy/interpreter/astcompiler/codegen.py +++ b/pypy/interpreter/astcompiler/codegen.py @@ -243,6 +243,8 @@ op = name_ops_fast(ctx) elif scope == symtable.SCOPE_FREE: op = name_ops_deref(ctx) + if op == ops.LOAD_DEREF and isinstance(self, ClassCodeGenerator): + op = ops.LOAD_CLASSDEREF container = self.free_vars elif scope == symtable.SCOPE_CELL: op = name_ops_deref(ctx) diff --git a/pypy/interpreter/astcompiler/test/test_compiler.py b/pypy/interpreter/astcompiler/test/test_compiler.py --- a/pypy/interpreter/astcompiler/test/test_compiler.py +++ b/pypy/interpreter/astcompiler/test/test_compiler.py @@ -1151,6 +1151,17 @@ assert e.value.msg == ( "'await' expressions in comprehensions are not supported") + def test_load_classderef(self): + source = """if 1: + def f(): + x = 42 + class X: + locals()["x"] = 43 + y = x + return X.y + """ + yield self.st, source, "f()", 43 + class AppTestCompiler: diff --git a/pypy/interpreter/pyopcode.py b/pypy/interpreter/pyopcode.py --- a/pypy/interpreter/pyopcode.py +++ b/pypy/interpreter/pyopcode.py @@ -348,6 +348,8 @@ self.LOAD_CONST(oparg, next_instr) elif opcode == opcodedesc.LOAD_DEREF.index: self.LOAD_DEREF(oparg, next_instr) + elif opcode == opcodedesc.LOAD_CLASSDEREF.index: + self.LOAD_CLASSDEREF(oparg, next_instr) elif opcode == opcodedesc.LOAD_FAST.index: self.LOAD_FAST(oparg, next_instr) elif opcode == opcodedesc.LOAD_GLOBAL.index: @@ -521,6 +523,18 @@ else: self.pushvalue(w_value) + def LOAD_CLASSDEREF(self, varindex, next_instr): + # like LOAD_DEREF but used in class bodies + space = self.space + i = varindex - len(self.pycode.co_cellvars) + assert i >= 0 + name = self.pycode.co_freevars[i] + w_value = space.finditem(self.debugdata.w_locals, space.wrap(name)) + if w_value is None: + self.LOAD_DEREF(varindex, next_instr) + else: + self.pushvalue(w_value) + def STORE_DEREF(self, varindex, next_instr): # nested scopes: access a variable through its cell object w_newvalue = self.popvalue() _______________________________________________ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit