[pypy-commit] pypy unroll-if-alt: Generate COPY{STR, UNICODE}CONTENT resops for copy_{string, unicode}contents calls. And optimize away those ops which have lengthboxes of 0.
alex_gaynor
noreply at buildbot.pypy.org
Fri Jul 29 23:36:50 CEST 2011
Author: Alex Gaynor <alex.gaynor at gmail.com>
Branch: unroll-if-alt
Changeset: r46098:16f06b5f8a48
Date: 2011-07-29 14:37 -0700
http://bitbucket.org/pypy/pypy/changeset/16f06b5f8a48/
Log: Generate COPY{STR,UNICODE}CONTENT resops for
copy_{string,unicode}contents calls. And optimize away those ops
which have lengthboxes of 0.
diff --git a/pypy/jit/backend/llsupport/llmodel.py b/pypy/jit/backend/llsupport/llmodel.py
--- a/pypy/jit/backend/llsupport/llmodel.py
+++ b/pypy/jit/backend/llsupport/llmodel.py
@@ -496,6 +496,16 @@
u = lltype.cast_opaque_ptr(lltype.Ptr(rstr.UNICODE), string)
u.chars[index] = unichr(newvalue)
+ def bh_copystrcontent(self, src, dst, srcstart, dststart, length):
+ src = lltype.cast_opaque_ptr(lltype.Ptr(rstr.STR), src)
+ dst = lltype.cast_opaque_ptr(lltype.Ptr(rstr.STR), dst)
+ rstr.copy_string_contents(src, dst, srcstart, dststart, length)
+
+ def bh_copyunicodecontent(self, src, dst, srcstart, dststart, length):
+ src = lltype.cast_opaque_ptr(lltype.Ptr(rstr.UNICODE), src)
+ dst = lltype.cast_opaque_ptr(lltype.Ptr(rstr.UNICODE), dst)
+ rstr.copy_unicode_contents(src, dst, srcstart, dststart, length)
+
def bh_call_i(self, func, calldescr, args_i, args_r, args_f):
assert isinstance(calldescr, BaseIntCallDescr)
if not we_are_translated():
diff --git a/pypy/jit/codewriter/jtransform.py b/pypy/jit/codewriter/jtransform.py
--- a/pypy/jit/codewriter/jtransform.py
+++ b/pypy/jit/codewriter/jtransform.py
@@ -1331,6 +1331,14 @@
else:
assert 0, "args[0].concretetype must be STR or UNICODE"
#
+ if oopspec_name == 'stroruni.copy_contents':
+ if SoU.TO == rstr.STR:
+ new_op = 'copystrcontent'
+ elif SoU.TO == rstr.UNICODE:
+ new_op = 'copyunicodecontent'
+ else:
+ assert 0
+ return SpaceOperation(new_op, args, op.result)
if oopspec_name == "stroruni.equal":
for otherindex, othername, argtypes, resulttype in [
(EffectInfo.OS_STREQ_SLICE_CHECKNULL,
diff --git a/pypy/jit/metainterp/blackhole.py b/pypy/jit/metainterp/blackhole.py
--- a/pypy/jit/metainterp/blackhole.py
+++ b/pypy/jit/metainterp/blackhole.py
@@ -1216,6 +1216,9 @@
@arguments("cpu", "r", "i", "i")
def bhimpl_strsetitem(cpu, string, index, newchr):
cpu.bh_strsetitem(string, index, newchr)
+ @arguments("cpu", "r", "r", "i", "i", "i")
+ def bhimpl_copystrcontent(cpu, src, dst, srcstart, dststart, length):
+ cpu.bh_copystrcontent(src, dst, srcstart, dststart, length)
@arguments("cpu", "i", returns="r")
def bhimpl_newunicode(cpu, length):
@@ -1229,6 +1232,9 @@
@arguments("cpu", "r", "i", "i")
def bhimpl_unicodesetitem(cpu, unicode, index, newchr):
cpu.bh_unicodesetitem(unicode, index, newchr)
+ @arguments("cpu", "r", "r", "i", "i", "i")
+ def bhimpl_copyunicodecontent(cpu, src, dst, srcstart, dststart, length):
+ cpu.bh_copyunicodecontent(src, dst, srcstart, dststart, length)
@arguments(returns=(longlong.is_64_bit and "i" or "f"))
def bhimpl_ll_read_timestamp():
diff --git a/pypy/jit/metainterp/optimizeopt/test/test_optimizebasic.py b/pypy/jit/metainterp/optimizeopt/test/test_optimizebasic.py
--- a/pypy/jit/metainterp/optimizeopt/test/test_optimizebasic.py
+++ b/pypy/jit/metainterp/optimizeopt/test/test_optimizebasic.py
@@ -4621,6 +4621,22 @@
"""
self.optimize_strunicode_loop(ops, expected)
+ def test_empty_copystrunicontent(self):
+ ops = """
+ [p0, p1, i0, i2, i3]
+ i4 = int_eq(i3, 0)
+ guard_true(i4) []
+ copystrcontent(p0, p1, i0, i2, i3)
+ jump(p0, p1, i0, i2, i3)
+ """
+ expected = """
+ [p0, p1, i0, i2, i3]
+ i4 = int_eq(i3, 0)
+ guard_true(i4) []
+ jump(p0, p1, i0, i2, 0)
+ """
+ self.optimize_strunicode_loop(ops, expected)
+
class TestLLtype(BaseTestOptimizeBasic, LLtypeMixin):
pass
diff --git a/pypy/jit/metainterp/optimizeopt/vstring.py b/pypy/jit/metainterp/optimizeopt/vstring.py
--- a/pypy/jit/metainterp/optimizeopt/vstring.py
+++ b/pypy/jit/metainterp/optimizeopt/vstring.py
@@ -296,7 +296,7 @@
def copy_str_content(optimizer, srcbox, targetbox,
- srcoffsetbox, offsetbox, lengthbox, mode):
+ srcoffsetbox, offsetbox, lengthbox, mode, need_next_offset=True):
if isinstance(srcbox, ConstPtr) and isinstance(srcoffsetbox, Const):
M = 5
else:
@@ -313,7 +313,10 @@
None))
offsetbox = _int_add(optimizer, offsetbox, CONST_1)
else:
- nextoffsetbox = _int_add(optimizer, offsetbox, lengthbox)
+ if need_next_offset:
+ nextoffsetbox = _int_add(optimizer, offsetbox, lengthbox)
+ else:
+ nextoffsetbox = None
op = ResOperation(mode.COPYSTRCONTENT, [srcbox, targetbox,
srcoffsetbox, offsetbox,
lengthbox], None)
@@ -451,6 +454,20 @@
lengthbox = value.getstrlen(self.optimizer, mode)
self.make_equal_to(op.result, self.getvalue(lengthbox))
+ def optimize_COPYSTRCONTENT(self, op):
+ self._optimize_COPYSTRCONTENT(op, mode_string)
+ def optimize_COPYUNICODECONTENT(self, op):
+ self._optimize_COPYSTRCONTENT(op, mode_unicode)
+
+ def _optimize_COPYSTRCONTENT(self, op, mode):
+ # args: src dst srcstart dststart length
+ src = self.getvalue(op.getarg(0))
+ dst = self.getvalue(op.getarg(1))
+ srcstart = self.getvalue(op.getarg(2))
+ dststart = self.getvalue(op.getarg(3))
+ length = self.getvalue(op.getarg(4))
+ copy_str_content(self.optimizer, src.box, dst.box, srcstart.box, dststart.box, length.box, mode, need_next_offset=False)
+
def optimize_CALL(self, op):
# dispatch based on 'oopspecindex' to a method that handles
# specifically the given oopspec call. For non-oopspec calls,
diff --git a/pypy/jit/metainterp/pyjitpl.py b/pypy/jit/metainterp/pyjitpl.py
--- a/pypy/jit/metainterp/pyjitpl.py
+++ b/pypy/jit/metainterp/pyjitpl.py
@@ -853,6 +853,14 @@
def opimpl_newunicode(self, lengthbox):
return self.execute(rop.NEWUNICODE, lengthbox)
+ @arguments("box", "box", "box", "box", "box")
+ def opimpl_copystrcontent(self, srcbox, dstbox, srcstartbox, dststartbox, lengthbox):
+ return self.execute(rop.COPYSTRCONTENT, srcbox, dstbox, srcstartbox, dststartbox, lengthbox)
+
+ @arguments("box", "box", "box", "box", "box")
+ def opimpl_copyunicodecontent(self, srcbox, dstbox, srcstartbox, dststartbox, lengthbox):
+ return self.execute(rop.COPYUNICODECONTENT, srcbox, dstbox, srcstartbox, dststartbox, lengthbox)
+
## @FixME #arguments("descr", "varargs")
## def opimpl_residual_oosend_canraise(self, methdescr, varargs):
## return self.execute_varargs(rop.OOSEND, varargs, descr=methdescr,
diff --git a/pypy/rpython/lltypesystem/rstr.py b/pypy/rpython/lltypesystem/rstr.py
--- a/pypy/rpython/lltypesystem/rstr.py
+++ b/pypy/rpython/lltypesystem/rstr.py
@@ -68,8 +68,8 @@
dst = llmemory.cast_ptr_to_adr(dst) + _str_ofs(dststart)
llmemory.raw_memcopy(src, dst, llmemory.sizeof(CHAR_TP) * length)
copy_string_contents._always_inline_ = True
- #copy_string_contents.oopspec = (
- # '%s.copy_contents(src, dst, srcstart, dststart, length)' % name)
+ copy_string_contents.oopspec = (
+ 'stroruni.copy_contents(src, dst, srcstart, dststart, length)')
return func_with_new_name(copy_string_contents, 'copy_%s_contents' % name)
copy_string_contents = _new_copy_contents_fun(STR, Char, 'string')
More information about the pypy-commit
mailing list