def transform_func_to_jitcode(self, func, values, type_system='lltype'): """For testing.""" rtyper = support.annotate(func, values, type_system=type_system) graph = rtyper.annotator.translator.graphs[0] jitcode = JitCode("test") self.transform_graph_to_jitcode(graph, jitcode, True) return jitcode
def test_find_all_graphs(): def g(x): return x + 2 def f(x): return g(x) + 1 rtyper = support.annotate(f, [7]) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cc = CallControl(jitdrivers_sd=[jitdriver_sd]) res = cc.find_all_graphs(FakePolicy()) funcs = set([graph.func for graph in res]) assert funcs == set([f, g])
def test_int_abs(): def f(n): return abs(n) rtyper = support.annotate(f, [35]) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cw = CodeWriter(FakeCPU(rtyper), [jitdriver_sd]) cw.find_all_graphs(FakePolicy()) cw.make_jitcodes(verbose=True) # s = jitdriver_sd.mainjitcode.dump() assert "inline_call_ir_i <JitCode '_ll_1_int_abs__Signed'>" in s
def test_access_directly_but_not_seen(): class X: _virtualizable2_ = ["a"] def h(x, y): w = 0 for i in range(y): w += 4 return w def f(y): x = jit.hint(X(), access_directly=True) h(x, y) rtyper = support.annotate(f, [3]) h_graph = rtyper.annotator.translator.graphs[1] assert h_graph.func is h py.test.raises(ValueError, JitPolicy().look_inside_graph, h_graph)
def test_find_all_graphs_without_g(): def g(x): return x + 2 def f(x): return g(x) + 1 rtyper = support.annotate(f, [7]) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cc = CallControl(jitdrivers_sd=[jitdriver_sd]) class CustomFakePolicy: def look_inside_graph(self, graph): assert graph.name == 'g' return False res = cc.find_all_graphs(CustomFakePolicy()) funcs = [graph.func for graph in res] assert funcs == [f]
def test_random_effects_on_stacklet_switch(): from pypy.jit.backend.llgraph.runner import LLtypeCPU from pypy.rlib._rffi_stacklet import switch, thread_handle, handle @jit.dont_look_inside def f(): switch(rffi.cast(thread_handle, 0), rffi.cast(handle, 0)) rtyper = support.annotate(f, []) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cc = CallControl(LLtypeCPU(rtyper), jitdrivers_sd=[jitdriver_sd]) res = cc.find_all_graphs(FakePolicy()) [f_graph] = [x for x in res if x.func is f] [block, _] = list(f_graph.iterblocks()) op = block.operations[-1] call_descr = cc.getcalldescr(op) assert call_descr.extrainfo.has_random_effects()
def test_instantiate(): class A1: id = 651 class A2(A1): id = 652 class B1: id = 661 class B2(B1): id = 662 def dont_look(n): return n + 1 def f(n): if n > 5: x, y = A1, B1 else: x, y = A2, B2 return x().id + y().id + dont_look(n) rtyper = support.annotate(f, [35]) maingraph = rtyper.annotator.translator.graphs[0] cw = CodeWriter(FakeCPU(rtyper), [FakeJitDriverSD(maingraph)]) cw.find_all_graphs(FakePolicy()) cw.make_jitcodes(verbose=True) # assert len(cw.assembler.indirectcalltargets) == 4 names = [jitcode.name for jitcode in cw.assembler.indirectcalltargets] for expected in ["A1", "A2", "B1", "B2"]: for name in names: if name.startswith("instantiate_") and name.endswith(expected): break else: assert 0, "missing instantiate_*_%s in:\n%r" % (expected, names) # print cw.assembler.list_of_addr2name names = dict.fromkeys([value for key, value in cw.assembler.list_of_addr2name]) assert "A1" in names assert "B1" in names assert "A2" in names assert "B2" in names assert "dont_look" in names
def test_releases_gil_analyzer(): from pypy.jit.backend.llgraph.runner import LLtypeCPU T = rffi.CArrayPtr(rffi.TIME_T) external = rffi.llexternal("time", [T], rffi.TIME_T, threadsafe=True) @jit.dont_look_inside def f(): return external(lltype.nullptr(T.TO)) rtyper = support.annotate(f, []) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cc = CallControl(LLtypeCPU(rtyper), jitdrivers_sd=[jitdriver_sd]) res = cc.find_all_graphs(FakePolicy()) [f_graph] = [x for x in res if x.func is f] [block, _] = list(f_graph.iterblocks()) [op] = block.operations call_descr = cc.getcalldescr(op) assert call_descr.extrainfo.has_random_effects()
def test_raw_malloc_and_access(): TP = rffi.CArray(lltype.Signed) def f(n): a = lltype.malloc(TP, n, flavor="raw") a[0] = n res = a[0] lltype.free(a, flavor="raw") return res rtyper = support.annotate(f, [35]) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cw = CodeWriter(FakeCPU(rtyper), [jitdriver_sd]) cw.find_all_graphs(FakePolicy()) cw.make_jitcodes(verbose=True) # s = jitdriver_sd.mainjitcode.dump() assert "residual_call_ir_i $<* fn _ll_1_raw_malloc__Signed>" in s assert "setarrayitem_raw_i" in s assert "getarrayitem_raw_i" in s assert "residual_call_ir_v $<* fn _ll_1_raw_free__arrayPtr>" in s
def test_call(): def ggg(x): return x * 2 def fff(a, b): return ggg(b) - ggg(a) rtyper = support.annotate(fff, [35, 42]) jitdriver_sd = FakeJitDriverSD(rtyper.annotator.translator.graphs[0]) cw = CodeWriter(FakeCPU(rtyper), [jitdriver_sd]) cw.find_all_graphs(FakePolicy()) cw.make_jitcodes(verbose=True) jitcode = jitdriver_sd.mainjitcode print jitcode.dump() [jitcode2] = cw.assembler.descrs print jitcode2.dump() assert jitcode is not jitcode2 assert jitcode.name == "fff" assert jitcode2.name == "ggg" assert "ggg" in jitcode.dump() assert lltype.typeOf(jitcode2.fnaddr) == llmemory.Address assert isinstance(jitcode2.calldescr, FakeCallDescr)
def test_instantiate_with_unreasonable_attr(): # It is possible to have in real code the instantiate() function for # a class be dont-look-inside. This is caused by the code that # initialize the instance attributes: if one attribute has a strange # type, the whole function is disabled. Check that it still works. class MyFakePolicy: def look_inside_graph(self, graph): name = graph.name return not (name.startswith("instantiate_") and name.endswith("A2")) class A1: pass class A2(A1): pass def f(n): if n > 5: x = A1 else: x = A2 x() rtyper = support.annotate(f, [35]) maingraph = rtyper.annotator.translator.graphs[0] cw = CodeWriter(FakeCPU(rtyper), [FakeJitDriverSD(maingraph)]) cw.find_all_graphs(MyFakePolicy()) cw.make_jitcodes(verbose=True) # names = [jitcode.name for jitcode in cw.assembler.indirectcalltargets] assert len(names) == 1 assert names[0].startswith("instantiate_") and names[0].endswith("A1") # print cw.assembler.list_of_addr2name names = dict.fromkeys([value for key, value in cw.assembler.list_of_addr2name]) assert "A1" in names assert "A2" in names
def setup_class(cls): from pypy.jit.metainterp.typesystem import llhelper from pypy.jit.codewriter.support import annotate from pypy.jit.metainterp.warmspot import WarmRunnerDesc from pypy.rpython.lltypesystem.rclass import OBJECT, OBJECT_VTABLE from pypy.rpython.lltypesystem import lltype, llmemory exc_vtable = lltype.malloc(OBJECT_VTABLE, immortal=True) cls.exc_vtable = exc_vtable class FakeLoopToken: def __init__(self, no): self.no = no self.generation = 0 class FakeFailDescr(object): def __init__(self, looptoken): assert isinstance(looptoken, FakeLoopToken) self.looptoken = looptoken def handle_fail(self, metainterp_sd, jitdrivers_sd): no = self.looptoken.no if no == 0: raise metainterp_sd.warmrunnerdesc.DoneWithThisFrameInt(3) if no == 1: raise metainterp_sd.warmrunnerdesc.ContinueRunningNormally( [0], [], [], [1], [], []) if no == 3: exc = lltype.malloc(OBJECT) exc.typeptr = exc_vtable raise metainterp_sd.warmrunnerdesc.ExitFrameWithExceptionRef( metainterp_sd.cpu, lltype.cast_opaque_ptr(llmemory.GCREF, exc)) return self.looptoken class FakeDescr: def as_vtable_size_descr(self): return self class FakeCPU(object): supports_floats = False supports_longlong = False ts = llhelper translate_support_code = False stats = "stats" def get_fail_descr_number(self, d): return -1 def __init__(self, *args, **kwds): pass def nodescr(self, *args, **kwds): return FakeDescr() fielddescrof = nodescr calldescrof = nodescr sizeof = nodescr def get_fail_descr_from_number(self, no): return FakeFailDescr(FakeLoopToken(no)) def execute_token(self, token): assert token.no == 2 return FakeFailDescr(FakeLoopToken(1)) driver = JitDriver(reds = ['red'], greens = ['green']) def f(green): red = 0 while red < 10: driver.can_enter_jit(red=red, green=green) driver.jit_merge_point(red=red, green=green) red += 1 return red rtyper = annotate(f, [0]) FakeCPU.rtyper = rtyper translator = rtyper.annotator.translator translator.config.translation.gc = 'hybrid' cls.desc = WarmRunnerDesc(translator, CPUClass=FakeCPU)
def make_graphs(self, func, values, type_system='lltype'): self.rtyper = support.annotate(func, values, type_system=type_system) return self.rtyper.annotator.translator.graphs
def setup_class(cls): from pypy.jit.metainterp.typesystem import llhelper from pypy.jit.codewriter.support import annotate from pypy.jit.metainterp.warmspot import WarmRunnerDesc from pypy.rpython.lltypesystem.rclass import OBJECT, OBJECT_VTABLE from pypy.rpython.lltypesystem import lltype, llmemory exc_vtable = lltype.malloc(OBJECT_VTABLE, immortal=True) cls.exc_vtable = exc_vtable class FakeFailDescr(object): def __init__(self, no): self.no = no def handle_fail(self, metainterp_sd, jitdrivers_sd): no = self.no if no == 0: raise metainterp_sd.warmrunnerdesc.DoneWithThisFrameInt(3) if no == 1: raise metainterp_sd.warmrunnerdesc.ContinueRunningNormally( [0], [], [], [1], [], []) if no == 3: exc = lltype.malloc(OBJECT) exc.typeptr = exc_vtable raise metainterp_sd.warmrunnerdesc.ExitFrameWithExceptionRef( metainterp_sd.cpu, lltype.cast_opaque_ptr(llmemory.GCREF, exc)) assert 0 class FakeDescr: def as_vtable_size_descr(self): return self class FakeCPU(object): supports_floats = False supports_longlong = False supports_singlefloats = False ts = llhelper translate_support_code = False stats = "stats" def get_fail_descr_number(self, d): return -1 def __init__(self, *args, **kwds): pass def nodescr(self, *args, **kwds): return FakeDescr() fielddescrof = nodescr calldescrof = nodescr sizeof = nodescr def get_fail_descr_from_number(self, no): return FakeFailDescr(no) def make_execute_token(self, *ARGS): return "not callable" driver = JitDriver(reds=['red'], greens=['green']) def f(green): red = 0 while red < 10: driver.can_enter_jit(red=red, green=green) driver.jit_merge_point(red=red, green=green) red += 1 return red rtyper = annotate(f, [0]) FakeCPU.rtyper = rtyper translator = rtyper.annotator.translator translator.config.translation.gc = 'hybrid' cls.desc = WarmRunnerDesc(translator, CPUClass=FakeCPU)
def _get_jitcodes(testself, CPUClass, func, values, type_system, supports_longlong=False, translationoptions={}, **kwds): from pypy.jit.codewriter import support class FakeJitCell(object): __product_token = None def get_procedure_token(self): return self.__product_token def set_procedure_token(self, token): self.__product_token = token class FakeWarmRunnerState(object): def attach_procedure_to_interp(self, greenkey, procedure_token): cell = self.jit_cell_at_key(greenkey) cell.set_procedure_token(procedure_token) def helper_func(self, FUNCPTR, func): from pypy.rpython.annlowlevel import llhelper return llhelper(FUNCPTR, func) def get_location_str(self, args): return 'location' def jit_cell_at_key(self, greenkey): assert greenkey == [] return self._cell _cell = FakeJitCell() trace_limit = sys.maxint enable_opts = ALL_OPTS_DICT func._jit_unroll_safe_ = True rtyper = support.annotate(func, values, type_system=type_system, translationoptions=translationoptions) graphs = rtyper.annotator.translator.graphs testself.all_graphs = graphs result_kind = history.getkind(graphs[0].getreturnvar().concretetype)[0] class FakeJitDriverSD: num_green_args = 0 portal_graph = graphs[0] virtualizable_info = None greenfield_info = None result_type = result_kind portal_runner_ptr = "???" stats = history.Stats() cpu = CPUClass(rtyper, stats, None, False) cw = codewriter.CodeWriter(cpu, [FakeJitDriverSD()]) cw.debug = True testself.cw = cw policy = JitPolicy() policy.set_supports_floats(True) policy.set_supports_longlong(supports_longlong) cw.find_all_graphs(policy) # testself.warmrunnerstate = FakeWarmRunnerState() testself.warmrunnerstate.cpu = cpu FakeJitDriverSD.warmstate = testself.warmrunnerstate if hasattr(testself, 'finish_setup_for_interp_operations'): testself.finish_setup_for_interp_operations() # cw.make_jitcodes(verbose=True)
def _get_jitcodes(testself, CPUClass, func, values, type_system, supports_longlong=False, **kwds): from pypy.jit.codewriter import support class FakeJitCell(object): __compiled_merge_points = [] def get_compiled_merge_points(self): return self.__compiled_merge_points[:] def set_compiled_merge_points(self, lst): self.__compiled_merge_points = lst class FakeWarmRunnerState(object): def attach_unoptimized_bridge_from_interp(self, greenkey, newloop): pass def helper_func(self, FUNCPTR, func): from pypy.rpython.annlowlevel import llhelper return llhelper(FUNCPTR, func) def get_location_str(self, args): return 'location' def jit_cell_at_key(self, greenkey): assert greenkey == [] return self._cell _cell = FakeJitCell() trace_limit = sys.maxint enable_opts = ALL_OPTS_DICT func._jit_unroll_safe_ = True rtyper = support.annotate(func, values, type_system=type_system) graphs = rtyper.annotator.translator.graphs testself.all_graphs = graphs result_kind = history.getkind(graphs[0].getreturnvar().concretetype)[0] class FakeJitDriverSD: num_green_args = 0 portal_graph = graphs[0] virtualizable_info = None greenfield_info = None result_type = result_kind portal_runner_ptr = "???" on_compile = lambda *args: None on_compile_bridge = lambda *args: None stats = history.Stats() cpu = CPUClass(rtyper, stats, None, False) cw = codewriter.CodeWriter(cpu, [FakeJitDriverSD()]) cw.debug = True testself.cw = cw policy = JitPolicy() policy.set_supports_floats(True) policy.set_supports_longlong(supports_longlong) cw.find_all_graphs(policy) # testself.warmrunnerstate = FakeWarmRunnerState() testself.warmrunnerstate.cpu = cpu FakeJitDriverSD.warmstate = testself.warmrunnerstate if hasattr(testself, 'finish_setup_for_interp_operations'): testself.finish_setup_for_interp_operations() # cw.make_jitcodes(verbose=True)