Author: Amaury Forgeot d'Arc <amaur...@gmail.com> Branch: py3k Changeset: r60410:792caad9d5ca Date: 2013-01-23 23:58 +0100 http://bitbucket.org/pypy/pypy/changeset/792caad9d5ca/
Log: hg merge default diff --git a/rpython/jit/codewriter/effectinfo.py b/rpython/jit/codewriter/effectinfo.py --- a/rpython/jit/codewriter/effectinfo.py +++ b/rpython/jit/codewriter/effectinfo.py @@ -79,9 +79,11 @@ OS_RAW_MALLOC_VARSIZE = 110 OS_RAW_FREE = 111 + OS_JIT_FORCE_VIRTUAL = 120 + # for debugging: _OS_CANRAISE = set([OS_NONE, OS_STR2UNICODE, OS_LIBFFI_CALL, - OS_RAW_MALLOC_VARSIZE]) + OS_RAW_MALLOC_VARSIZE, OS_JIT_FORCE_VIRTUAL]) def __new__(cls, readonly_descrs_fields, readonly_descrs_arrays, write_descrs_fields, write_descrs_arrays, diff --git a/rpython/jit/codewriter/jtransform.py b/rpython/jit/codewriter/jtransform.py --- a/rpython/jit/codewriter/jtransform.py +++ b/rpython/jit/codewriter/jtransform.py @@ -1393,6 +1393,8 @@ elif oopspec_name == 'jit.isvirtual': kind = getkind(args[0].concretetype) return SpaceOperation('%s_isvirtual' % kind, args, op.result) + elif oopspec_name == 'jit.force_virtual': + return self._handle_oopspec_call(op, args, EffectInfo.OS_JIT_FORCE_VIRTUAL, EffectInfo.EF_FORCES_VIRTUAL_OR_VIRTUALIZABLE) else: raise AssertionError("missing support for %r" % oopspec_name) diff --git a/rpython/jit/codewriter/support.py b/rpython/jit/codewriter/support.py --- a/rpython/jit/codewriter/support.py +++ b/rpython/jit/codewriter/support.py @@ -1,24 +1,24 @@ import sys -from rpython.rtyper.lltypesystem import lltype, rclass, rffi, llmemory -from rpython.rtyper.ootypesystem import ootype -from rpython.rtyper import rlist -from rpython.rtyper.lltypesystem import rstr as ll_rstr, rdict as ll_rdict -from rpython.rtyper.lltypesystem.module import ll_math -from rpython.rtyper.lltypesystem.lloperation import llop -from rpython.rtyper.ootypesystem import rdict as oo_rdict -from rpython.rtyper.llinterp import LLInterpreter -from rpython.rtyper.extregistry import ExtRegistryEntry -from rpython.translator.simplify import get_funcobj -from rpython.translator.unsimplify import split_block + +from rpython.annotator import model as annmodel +from rpython.annotator.policy import AnnotatorPolicy from rpython.flowspace.model import Variable, Constant -from rpython.translator.translator import TranslationContext -from rpython.annotator.policy import AnnotatorPolicy -from rpython.annotator import model as annmodel -from rpython.rtyper.annlowlevel import MixLevelHelperAnnotator from rpython.jit.metainterp.typesystem import deref from rpython.rlib import rgc -from rpython.rlib.jit import elidable +from rpython.rlib.jit import elidable, oopspec from rpython.rlib.rarithmetic import r_longlong, r_ulonglong, r_uint, intmask +from rpython.rtyper import rlist +from rpython.rtyper.annlowlevel import MixLevelHelperAnnotator +from rpython.rtyper.extregistry import ExtRegistryEntry +from rpython.rtyper.llinterp import LLInterpreter +from rpython.rtyper.lltypesystem import lltype, rclass, rffi, llmemory, rstr as ll_rstr, rdict as ll_rdict +from rpython.rtyper.lltypesystem.lloperation import llop +from rpython.rtyper.lltypesystem.module import ll_math +from rpython.rtyper.ootypesystem import ootype, rdict as oo_rdict +from rpython.translator.simplify import get_funcobj +from rpython.translator.translator import TranslationContext +from rpython.translator.unsimplify import split_block + def getargtypes(annotator, values): if values is None: # for backend tests producing stand-alone exe's @@ -213,10 +213,12 @@ _ll_5_list_ll_arraycopy = rgc.ll_arraycopy + @elidable def _ll_1_gc_identityhash(x): return lltype.identityhash(x) + # the following function should not be "@elidable": I can think of # a corner case in which id(const) is constant-folded, and then 'const' # disappears and is collected too early (possibly causing another object @@ -224,6 +226,8 @@ def _ll_1_gc_id(ptr): return llop.gc_id(lltype.Signed, ptr) + +@oopspec("jit.force_virtual(inst)") def _ll_1_jit_force_virtual(inst): return llop.jit_force_virtual(lltype.typeOf(inst), inst) diff --git a/rpython/jit/metainterp/history.py b/rpython/jit/metainterp/history.py --- a/rpython/jit/metainterp/history.py +++ b/rpython/jit/metainterp/history.py @@ -978,11 +978,9 @@ def get_all_jitcell_tokens(self): tokens = [t() for t in self.jitcell_token_wrefs] if None in tokens: - assert False, "get_all_jitcell_tokens will not work as "+\ - "loops have been freed" + assert False, ("get_all_jitcell_tokens will not work as " + "loops have been freed") return tokens - - def check_history(self, expected=None, **check): insns = {} diff --git a/rpython/jit/metainterp/optimizeopt/virtualize.py b/rpython/jit/metainterp/optimizeopt/virtualize.py --- a/rpython/jit/metainterp/optimizeopt/virtualize.py +++ b/rpython/jit/metainterp/optimizeopt/virtualize.py @@ -1,12 +1,13 @@ +from rpython.jit.codewriter.effectinfo import EffectInfo +from rpython.jit.metainterp.executor import execute from rpython.jit.codewriter.heaptracker import vtable2descr -from rpython.jit.metainterp.executor import execute from rpython.jit.metainterp.history import Const, ConstInt, BoxInt from rpython.jit.metainterp.optimizeopt import optimizer +from rpython.jit.metainterp.optimizeopt.optimizer import OptValue, REMOVED from rpython.jit.metainterp.optimizeopt.util import (make_dispatcher_method, descrlist_dict, sort_descrs) from rpython.jit.metainterp.resoperation import rop, ResOperation from rpython.rlib.objectmodel import we_are_translated -from rpython.jit.metainterp.optimizeopt.optimizer import OptValue class AbstractVirtualValue(optimizer.OptValue): @@ -386,6 +387,24 @@ self.make_equal_to(box, vvalue) return vvalue + def optimize_GUARD_NO_EXCEPTION(self, op): + if self.last_emitted_operation is REMOVED: + return + self.emit_operation(op) + + def optimize_GUARD_NOT_FORCED(self, op): + if self.last_emitted_operation is REMOVED: + return + self.emit_operation(op) + + def optimize_CALL_MAY_FORCE(self, op): + effectinfo = op.getdescr().get_extra_info() + oopspecindex = effectinfo.oopspecindex + if oopspecindex == EffectInfo.OS_JIT_FORCE_VIRTUAL: + if self._optimize_JIT_FORCE_VIRTUAL(op): + return + self.emit_operation(op) + def optimize_VIRTUAL_REF(self, op): indexbox = op.getarg(1) # @@ -429,7 +448,7 @@ # - set 'virtual_token' to TOKEN_NONE args = [op.getarg(0), ConstInt(vrefinfo.TOKEN_NONE)] seo(ResOperation(rop.SETFIELD_GC, args, None, - descr = vrefinfo.descr_virtual_token)) + descr=vrefinfo.descr_virtual_token)) # Note that in some cases the virtual in op.getarg(1) has been forced # already. This is fine. In that case, and *if* a residual # CALL_MAY_FORCE suddenly turns out to access it, then it will @@ -437,6 +456,20 @@ # will work too (but just be a little pointless, as the structure # was already forced). + def _optimize_JIT_FORCE_VIRTUAL(self, op): + vref = self.getvalue(op.getarg(1)) + vrefinfo = self.optimizer.metainterp_sd.virtualref_info + if vref.is_virtual(): + tokenvalue = vref.getfield(vrefinfo.descr_virtual_token, None) + if (tokenvalue is not None and tokenvalue.is_constant() and + tokenvalue.box.getint() == vrefinfo.TOKEN_NONE): + forcedvalue = vref.getfield(vrefinfo.descr_forced, None) + if forcedvalue is not None and not forcedvalue.is_null(): + self.make_equal_to(op.result, forcedvalue) + self.last_emitted_operation = REMOVED + return True + return False + def optimize_GETFIELD_GC(self, op): value = self.getvalue(op.getarg(0)) # If this is an immutable field (as indicated by op.is_always_pure()) diff --git a/rpython/jit/metainterp/test/support.py b/rpython/jit/metainterp/test/support.py --- a/rpython/jit/metainterp/test/support.py +++ b/rpython/jit/metainterp/test/support.py @@ -160,16 +160,17 @@ class JitMixin: basic = True + def check_resops(self, expected=None, **check): get_stats().check_resops(expected=expected, **check) + def check_simple_loop(self, expected=None, **check): get_stats().check_simple_loop(expected=expected, **check) - - def check_trace_count(self, count): # was check_loop_count # The number of traces compiled assert get_stats().compiled_count == count + def check_trace_count_at_most(self, count): assert get_stats().compiled_count <= count @@ -178,11 +179,12 @@ def check_target_token_count(self, count): tokens = get_stats().get_all_jitcell_tokens() - n = sum ([len(t.target_tokens) for t in tokens]) + n = sum([len(t.target_tokens) for t in tokens]) assert n == count def check_enter_count(self, count): assert get_stats().enter_count == count + def check_enter_count_at_most(self, count): assert get_stats().enter_count <= count @@ -192,6 +194,7 @@ def check_aborted_count(self, count): assert get_stats().aborted_count == count + def check_aborted_count_at_least(self, count): assert get_stats().aborted_count >= count diff --git a/rpython/jit/metainterp/test/test_virtualref.py b/rpython/jit/metainterp/test/test_virtualref.py --- a/rpython/jit/metainterp/test/test_virtualref.py +++ b/rpython/jit/metainterp/test/test_virtualref.py @@ -1,19 +1,20 @@ import py -from rpython.rtyper.lltypesystem import lltype, llmemory, lloperation + +from rpython.rtyper.lltypesystem import lltype, lloperation from rpython.rtyper.exceptiondata import UnknownException from rpython.rlib.jit import JitDriver, dont_look_inside, vref_None from rpython.rlib.jit import virtual_ref, virtual_ref_finish, InvalidVirtualRef from rpython.rlib.jit import non_virtual_ref from rpython.rlib.objectmodel import compute_unique_id -from rpython.jit.metainterp.test.support import LLJitMixin, OOJitMixin, _get_jitcodes +from rpython.jit.metainterp.test.support import LLJitMixin, _get_jitcodes from rpython.jit.metainterp.resoperation import rop from rpython.jit.metainterp.virtualref import VirtualRefInfo + debug_print = lloperation.llop.debug_print -class VRefTests: - +class VRefTests(object): def finish_setup_for_interp_operations(self): self.vrefinfo = VirtualRefInfo(self.warmrunnerstate) self.cw.setup_vrefinfo(self.vrefinfo) @@ -115,8 +116,8 @@ from rpython.jit.metainterp.resume import ResumeDataDirectReader cpu = self.metainterp.cpu cpu.get_latest_value_count = lambda df: len(guard_op.getfailargs()) - cpu.get_latest_value_int = lambda df,i:guard_op.getfailargs()[i].getint() - cpu.get_latest_value_ref = lambda df,i:guard_op.getfailargs()[i].getref_base() + cpu.get_latest_value_int = lambda df, i: guard_op.getfailargs()[i].getint() + cpu.get_latest_value_ref = lambda df, i: guard_op.getfailargs()[i].getref_base() cpu.clear_latest_values = lambda count: None class FakeMetaInterpSd: callinfocollection = None @@ -418,15 +419,18 @@ self.check_aborted_count(0) def test_jit_force_virtual_seen(self): - myjitdriver = JitDriver(greens = [], reds = ['n']) - # + myjitdriver = JitDriver(greens=[], reds=['n']) + A = lltype.GcArray(lltype.Signed) - class XY: + + class XY(object): pass - class ExCtx: + + class ExCtx(object): pass exctx = ExCtx() - # + escapes = [] + def f(n): while n > 0: myjitdriver.can_enter_jit(n=n) @@ -434,16 +438,16 @@ xy = XY() xy.n = n exctx.topframeref = vref = virtual_ref(xy) + escapes.append(xy) xy.next1 = lltype.malloc(A, 0) n = exctx.topframeref().n - 1 - xy.next1 = lltype.nullptr(A) exctx.topframeref = vref_None virtual_ref_finish(vref, xy) return 1 # res = self.meta_interp(f, [15]) assert res == 1 - self.check_resops(new_with_vtable=4, # vref, xy + self.check_resops(new_with_vtable=2, # xy new_array=2) # next1 self.check_aborted_count(0) @@ -656,6 +660,34 @@ res = self.meta_interp(f, [10]) assert res == 0 + def test_force_virtual_vref(self): + myjitdriver = JitDriver(greens=[], reds=['n', 'ec']) + + class ExecutionContext(object): + pass + + class Frame(object): + def __init__(self, x): + self.x = x + + def f(n): + ec = ExecutionContext() + while n > 0: + myjitdriver.jit_merge_point(n=n, ec=ec) + frame = Frame(1) + ec.topframeref = virtual_ref(frame) + n -= ec.topframeref().x + frame_vref = ec.topframeref + ec.topframeref = vref_None + virtual_ref_finish(frame_vref, frame) + return n + res = self.meta_interp(f, [10]) + assert res == 0 + self.check_resops({ + 'int_sub': 2, 'int_gt': 2, 'jump': 1, 'guard_true': 2, + 'force_token': 2, 'setfield_gc': 1 + }) + class TestLLtype(VRefTests, LLJitMixin): pass diff --git a/rpython/rlib/unicodedata/test/test_ucd.py b/rpython/rlib/unicodedata/test/test_ucd.py --- a/rpython/rlib/unicodedata/test/test_ucd.py +++ b/rpython/rlib/unicodedata/test/test_ucd.py @@ -1,9 +1,9 @@ +from rpython.rlib.runicode import code_to_unichr +from rpython.rlib.unicodedata import unicodedb_5_2_0 from rpython.rtyper.test.tool import BaseRtypingTest, LLRtypeMixin -from rpython.rlib.unicodedata import unicodedb_5_2_0 -from rpython.rlib.unicodedata.ucd import code_to_unichr + class TestTranslated(BaseRtypingTest, LLRtypeMixin): - def test_translated(self): def f(n): if n == 0: diff --git a/rpython/rlib/unicodedata/test/test_unicodedata.py b/rpython/rlib/unicodedata/test/test_unicodedata.py --- a/rpython/rlib/unicodedata/test/test_unicodedata.py +++ b/rpython/rlib/unicodedata/test/test_unicodedata.py @@ -1,11 +1,15 @@ +import random +import unicodedata + import py + from rpython.rlib.unicodedata import unicodedb_3_2_0, unicodedb_5_2_0 + class TestUnicodeData(object): def setup_class(cls): - import random, unicodedata if unicodedata.unidata_version != '5.2.0': - skip('Needs python with unicode 5.2.0 database.') + py.test.skip('Needs python with unicode 5.2.0 database.') seed = random.getrandbits(32) print "random seed: ", seed @@ -39,14 +43,12 @@ assert not unicodedb_5_2_0.isprintable(0xE0020) # TAG SPACE def test_compare_functions(self): - import unicodedata # CPython implementation - def getX(fun, code): try: return getattr(unicodedb_5_2_0, fun)(code) except KeyError: return -1 - + for code in range(0x10000): char = unichr(code) assert unicodedata.digit(char, -1) == getX('digit', code) @@ -83,5 +85,3 @@ assert unicodedb_5_2_0.lookup('BENZENE RING WITH CIRCLE') == 9187 py.test.raises(KeyError, unicodedb_3_2_0.lookup, 'BENZENE RING WITH CIRCLE') py.test.raises(KeyError, unicodedb_3_2_0.name, 9187) - - _______________________________________________ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit