From: Robert Bradshaw Date: Thu, 17 Jan 2008 13:27:06 +0000 (-0800) Subject: tp_new, etc. cleanup X-Git-Tag: 0.9.6.14~29^2~68 X-Git-Url: http://git.tremily.us/?a=commitdiff_plain;h=50bab2d6b251997f2d18ff7e882dc6d5e1740ac5;p=cython.git tp_new, etc. cleanup --- diff --git a/Cython/Compiler/ModuleNode.py b/Cython/Compiler/ModuleNode.py index 680304af..c9f60433 100644 --- a/Cython/Compiler/ModuleNode.py +++ b/Cython/Compiler/ModuleNode.py @@ -628,10 +628,8 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode): "%s;" % scope.parent_type.declaration_code("p")) if base_type: - entry = scope.parent_scope.lookup_here(scope.parent_type.base_type.name) - if scope.parent_scope is base_type.scope.parent_scope and entry.visibility != 'extern': - tp_new = TypeSlots.InternalMethodSlot("tp_new").slot_code(base_type.scope) - else: + tp_new = TypeSlots.get_base_slot_function(scope, tp_slot) + if tp_new is None: tp_new = "%s->tp_new" % base_type.typeptr_cname code.putln( "PyObject *o = %s(t, a, k);" % tp_new) @@ -691,10 +689,8 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode): for entry in py_attrs: code.put_xdecref("p->%s" % entry.cname, entry.type) if base_type: - entry = scope.parent_scope.lookup_here(scope.parent_type.base_type.name) - if scope.parent_scope is base_type.scope.parent_scope and entry.visibility != 'extern': - tp_dealloc = TypeSlots.InternalMethodSlot("tp_dealloc").slot_code(base_type.scope) - else: + tp_dealloc = TypeSlots.get_base_slot_function(scope, tp_slot) + if tp_dealloc is None: tp_dealloc = "%s->tp_dealloc" % base_type.typeptr_cname code.putln( "%s(o);" % tp_dealloc) @@ -747,10 +743,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode): self.generate_self_cast(scope, code) if base_type: # want to call it explicitly if possible so inlining can be performed - parent_slot = tp_slot.slot_code(base_type.scope) - entry = scope.parent_scope.lookup_here(scope.parent_type.base_type.name) - if scope.parent_scope is base_type.scope.parent_scope and parent_slot != '0' and entry.visibility != 'extern': - code.putln("e = %s(o, v, a); if (e) return e;" % parent_slot) + static_call = TypeSlots.get_base_slot_function(scope, tp_slot) + if static_call: + code.putln("e = %s(o, v, a); if (e) return e;" % static_call) else: code.putln("if (%s->tp_traverse) {" % base_type.typeptr_cname) code.putln( @@ -791,10 +786,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode): code.putln("PyObject* tmp;") if base_type: # want to call it explicitly if possible so inlining can be performed - parent_slot = tp_slot.slot_code(base_type.scope) - entry = scope.parent_scope.lookup_here(scope.parent_type.base_type.name) - if scope.parent_scope is base_type.scope.parent_scope and parent_slot != '0' and entry.visibility != 'extern': - code.putln("%s(o);" % parent_slot) + static_call = TypeSlots.get_base_slot_function(scope, tp_slot) + if static_call: + code.putln("%s(o);" % static_call) else: code.putln("if (%s->tp_clear) {" % base_type.typeptr_cname) code.putln("%s->tp_clear(o);" % base_type.typeptr_cname) diff --git a/Cython/Compiler/TypeSlots.py b/Cython/Compiler/TypeSlots.py index de94ab94..8b647bd1 100644 --- a/Cython/Compiler/TypeSlots.py +++ b/Cython/Compiler/TypeSlots.py @@ -397,6 +397,19 @@ def get_property_accessor_signature(name): # Return signature of accessor for an extension type # property, else None. return property_accessor_signatures.get(name) + +def get_base_slot_function(scope, slot): + # Returns the function implementing this slot in the baseclass. + # This is useful for enabling the compiler to optimize calls + # that recursively climb the class hierarchy. + base_type = scope.parent_type.base_type + if scope.parent_scope is base_type.scope.parent_scope: + parent_slot = slot.slot_code(base_type.scope) + if parent_slot != '0': + entry = scope.parent_scope.lookup_here(scope.parent_type.base_type.name) + if entry.visibility != 'extern': + return parent_slot + return None #------------------------------------------------------------------------------------------ #