diff options
author | Stefan Behnel <stefan_ml@behnel.de> | 2018-12-12 20:25:00 +0100 |
---|---|---|
committer | Stefan Behnel <stefan_ml@behnel.de> | 2018-12-12 20:25:00 +0100 |
commit | ca688476359325dfcf1ec6239f51b500842f8293 (patch) | |
tree | 5a07a52ed44709fc9430141c8cfdf8e08a16b0a8 | |
parent | 62b6ba0ff7f706a32c6ca1316369010318c1278c (diff) | |
parent | cfa02c2765cfd8bcd2bf2b449fed2ef4ac87419a (diff) | |
download | cython-ca688476359325dfcf1ec6239f51b500842f8293.tar.gz |
Merge branch '0.29.x'
-rw-r--r-- | Cython/Compiler/Code.py | 12 | ||||
-rw-r--r-- | Cython/Compiler/ExprNodes.py | 32 |
2 files changed, 28 insertions, 16 deletions
diff --git a/Cython/Compiler/Code.py b/Cython/Compiler/Code.py index e7ccdc5ae..098988a3c 100644 --- a/Cython/Compiler/Code.py +++ b/Cython/Compiler/Code.py @@ -1133,6 +1133,7 @@ class GlobalState(object): self.num_const_index = {} self.py_constants = [] self.cached_cmethods = {} + self.initialised_constants = set() writer.set_global_state(self) self.rootwriter = writer @@ -1242,7 +1243,12 @@ class GlobalState(object): # constant handling at code generation time - def get_cached_constants_writer(self): + def get_cached_constants_writer(self, target=None): + if target is not None: + if target in self.initialised_constants: + # Return None on second/later calls to prevent duplicate creation code. + return None + self.initialised_constants.add(target) return self.parts['cached_constants'] def get_int_const(self, str_value, longness=False): @@ -1816,8 +1822,8 @@ class CCodeWriter(object): def intern_identifier(self, text): return self.get_py_string_const(text, identifier=True) - def get_cached_constants_writer(self): - return self.globalstate.get_cached_constants_writer() + def get_cached_constants_writer(self, target=None): + return self.globalstate.get_cached_constants_writer(target) # code generation diff --git a/Cython/Compiler/ExprNodes.py b/Cython/Compiler/ExprNodes.py index 65d903019..71aa853fd 100644 --- a/Cython/Compiler/ExprNodes.py +++ b/Cython/Compiler/ExprNodes.py @@ -1621,15 +1621,17 @@ class UnicodeNode(ConstNode): # decoded by the UTF-8 codec in Py3.3 self.result_code = code.get_py_const(py_object_type, 'ustring') data_cname = code.get_pyunicode_ptr_const(self.value) - code = code.get_cached_constants_writer() - code.mark_pos(self.pos) - code.putln( + const_code = code.get_cached_constants_writer(self.result_code) + if const_code is None: + return # already initialised + const_code.mark_pos(self.pos) + const_code.putln( "%s = PyUnicode_FromUnicode(%s, (sizeof(%s) / sizeof(Py_UNICODE))-1); %s" % ( self.result_code, data_cname, data_cname, code.error_goto_if_null(self.result_code, self.pos))) - code.put_error_if_neg( + const_code.put_error_if_neg( self.pos, "__Pyx_PyUnicode_READY(%s)" % self.result_code) else: self.result_code = code.get_py_string_const(self.value) @@ -5253,7 +5255,9 @@ class SliceNode(ExprNode): if self.is_literal: dedup_key = make_dedup_key(self.type, (self,)) self.result_code = code.get_py_const(py_object_type, 'slice', cleanup_level=2, dedup_key=dedup_key) - code = code.get_cached_constants_writer() + code = code.get_cached_constants_writer(self.result_code) + if code is None: + return # already initialised code.mark_pos(self.pos) code.putln( @@ -7988,14 +7992,14 @@ class TupleNode(SequenceNode): return if self.is_literal or self.is_partly_literal: - dedup_key = None - if self.is_literal: - dedup_key = make_dedup_key(self.type, self.args) + dedup_key = make_dedup_key(self.type, self.args) if self.is_literal else None tuple_target = code.get_py_const(py_object_type, 'tuple', cleanup_level=2, dedup_key=dedup_key) - const_code = code.get_cached_constants_writer() - const_code.mark_pos(self.pos) - self.generate_sequence_packing_code(const_code, tuple_target, plain=not self.is_literal) - const_code.put_giveref(tuple_target) + const_code = code.get_cached_constants_writer(tuple_target) + if const_code is not None: + # constant is not yet initialised + const_code.mark_pos(self.pos) + self.generate_sequence_packing_code(const_code, tuple_target, plain=not self.is_literal) + const_code.put_giveref(tuple_target) if self.is_literal: self.result_code = tuple_target else: @@ -9511,7 +9515,9 @@ class CodeObjectNode(ExprNode): if self.result_code is None: self.result_code = code.get_py_const(py_object_type, 'codeobj', cleanup_level=2) - code = code.get_cached_constants_writer() + code = code.get_cached_constants_writer(self.result_code) + if code is None: + return # already initialised code.mark_pos(self.pos) func = self.def_node func_name = code.get_py_string_const( |