Commits

Armin Rigo committed d2f2a8c

Yay. Kill the special case 'indirect_call(instantiate, None)':
found out that we always have the correct list of graphs to put there.

Comments (0)

Files changed (7)

rpython/jit/codewriter/call.py

         else:
             assert op.opname == 'indirect_call'
             graphs = op.args[-1].value
-            if graphs is None:
-                # special case: handle the indirect call that goes to
-                # the 'instantiate' methods.  This check is a bit imprecise
-                # but it's not too bad if we mistake a random indirect call
-                # for the one to 'instantiate'.
-                from rpython.rtyper.lltypesystem import rclass
-                CALLTYPE = op.args[0].concretetype
-                if (op.opname == 'indirect_call' and len(op.args) == 2 and
-                    CALLTYPE == rclass.OBJECT_VTABLE.instantiate):
-                    graphs = list(self._graphs_of_all_instantiate())
-            #
             if graphs is not None:
                 result = []
                 for graph in graphs:
         # residual call case: we don't need to look into any graph
         return None
 
-    def _graphs_of_all_instantiate(self):
-        for vtable in self.rtyper.lltype2vtable.values():
-            if vtable.instantiate:
-                yield vtable.instantiate._obj.graph
-
     def guess_call_kind(self, op, is_candidate=None):
         if op.opname == 'direct_call':
             funcptr = op.args[0].value

rpython/jit/metainterp/test/test_ajit.py

         self.check_resops(call=2)
 
     def test_merge_guardclass_guardvalue(self):
-        from rpython.rlib.objectmodel import instantiate
         myjitdriver = JitDriver(greens = [], reds = ['x', 'l'])
 
         class A(object):
         self.check_resops(guard_class=0, guard_value=6)
 
     def test_merge_guardnonnull_guardclass(self):
-        from rpython.rlib.objectmodel import instantiate
         myjitdriver = JitDriver(greens = [], reds = ['x', 'l'])
 
         class A(object):
 
 
     def test_merge_guardnonnull_guardvalue(self):
-        from rpython.rlib.objectmodel import instantiate
         myjitdriver = JitDriver(greens = [], reds = ['x', 'l'])
 
         class A(object):
 
 
     def test_merge_guardnonnull_guardvalue_2(self):
-        from rpython.rlib.objectmodel import instantiate
         myjitdriver = JitDriver(greens = [], reds = ['x', 'l'])
 
         class A(object):
 
 
     def test_merge_guardnonnull_guardclass_guardvalue(self):
-        from rpython.rlib.objectmodel import instantiate
         myjitdriver = JitDriver(greens = [], reds = ['x', 'l'])
 
         class A(object):

rpython/rtyper/lltypesystem/rpbc.py

     # no __init__ here, AbstractClassesPBCRepr.__init__ is good enough
 
     def _instantiate_runtime_class(self, hop, vtypeptr, r_instance):
-        v_instantiate = hop.genop('getfield', [vtypeptr, hop.inputconst(Void, "instantiate")], resulttype=vtypeptr.concretetype.TO.instantiate)
-        possible_graphs = hop.inputconst(Void,
-            [desc.getclassdef(None).my_instantiate_graph for desc in self.s_pbc.descriptions]
-        )
-        v_inst = hop.genop('indirect_call', [v_instantiate, possible_graphs], resulttype=vtypeptr.concretetype.TO.instantiate.TO.RESULT)
+        graphs = []
+        for desc in self.s_pbc.descriptions:
+            classdef = desc.getclassdef(None)
+            assert hasattr(classdef, 'my_instantiate_graph')
+            graphs.append(classdef.my_instantiate_graph)
+        c_graphs = hop.inputconst(Void, graphs)
+        #
+        # "my_instantiate = typeptr.instantiate"
+        c_name = hop.inputconst(Void, 'instantiate')
+        v_instantiate = hop.genop('getfield', [vtypeptr, c_name],
+                                 resulttype = rclass.OBJECT_VTABLE.instantiate)
+        # "my_instantiate()"
+        v_inst = hop.genop('indirect_call', [v_instantiate, c_graphs],
+                           resulttype = rclass.OBJECTPTR)
         return hop.genop('cast_pointer', [v_inst], resulttype=r_instance)
 
     def getlowleveltype(self):

rpython/rtyper/rbuiltin.py

     assert isinstance(hop.args_r[0], rclass.InstanceRepr)
     return hop.args_r[0].rtype_isinstance(hop)
 
-def ll_instantiate(typeptr):   # NB. used by rpbc.ClassesPBCRepr as well
-    my_instantiate = typeptr.instantiate
-    return my_instantiate()
-
 def rtype_instantiate(hop):
     hop.exception_cannot_occur()
     s_class = hop.args_s[0]
     if len(s_class.descriptions) != 1:
         # instantiate() on a variable class
         vtypeptr, = hop.inputargs(rclass.get_type_repr(hop.rtyper))
-        v_inst = hop.gendirectcall(ll_instantiate, vtypeptr)
-        return hop.genop('cast_pointer', [v_inst],    # v_type implicit in r_result
-                         resulttype = hop.r_result.lowleveltype)
-
+        r_class = hop.args_r[0]
+        return r_class._instantiate_runtime_class(hop, vtypeptr,
+                                                  hop.r_result.lowleveltype)
     classdef = s_class.any_description().getuniqueclassdef()
     return rclass.rtype_new_instance(hop.rtyper, classdef, hop.llops)
 

rpython/translator/backendopt/gilanalysis.py

             return False
         else:
             return False
-
-    def analyze_instantiate_call(self, seen=None):
-        return False
                 
     def analyze_simple_operation(self, op, graphinfo):
         return False

rpython/translator/backendopt/graphanalyze.py

                         result, self.analyze_direct_call(graph, seen))
         return result
 
-    def analyze_instantiate_call(self, seen=None):
-        return self.top_result()
-
     def analyze_link(self, graph, link):
         return self.bottom_result()
 
     def compute_graph_info(self, graph):
         return None
 
-    def analyze(self, op, seen=None, graphinfo=None, block=None):
+    def analyze(self, op, seen=None, graphinfo=None):
         if op.opname == "direct_call":
             graph = get_graph(op.args[0], self.translator)
             if graph is None:
         elif op.opname == "indirect_call":
             graphs = op.args[-1].value
             if graphs is None:
-                if block is not None:
-                    v_func = op.args[0]
-                    for op1 in block.operations:
-                        if (v_func is op1.result and
-                            op1.opname == 'getfield' and
-                            op1.args[0].concretetype == rclass.CLASSTYPE and
-                            op1.args[1].value == 'instantiate'):
-                            x = self.analyze_instantiate_call(seen)
-                            if self.verbose and x:
-                                self.dump_info('analyze_instantiate(%s): %r' % (
-                                    graphs, x))
-                            return x
                 if self.verbose:
                     self.dump_info('%s to unknown' % (op,))
                 return self.top_result()
                 for op in block.operations:
                     result = self.add_to_result(
                         result,
-                        self.analyze(op, seen, graphinfo, block=block)
+                        self.analyze(op, seen, graphinfo)
                     )
                     if self.is_top_result(result):
                         break
             graphs = self.translator.graphs
         for graph in graphs:
             for block, op in graph.iterblockops():
-                self.analyze(op, block=block)
+                self.analyze(op)
 
 
 class Dependency(object):

rpython/translator/backendopt/test/test_writeanalyze.py

         assert not wa.analyze(op_call_m)
 
     def test_instantiate(self):
-        # instantiate is interesting, because it leads to one of the few cases of
-        # an indirect call without a list of graphs
         from rpython.rlib.objectmodel import instantiate
         class A:
             pass
         t, wa = self.translate(f, [int])
         fgraph = graphof(t, f)
         result = wa.analyze(fgraph.startblock.operations[0])
-        assert result is top_set
+        assert not result
 
     def test_llexternal(self):
         from rpython.rtyper.lltypesystem.rffi import llexternal