Author: Richard Plangger <[email protected]>
Branch: vecopt-merge
Changeset: r79252:fc31b6dcacc8
Date: 2015-08-27 13:10 +0200
http://bitbucket.org/pypy/pypy/changeset/fc31b6dcacc8/
Log: extending test cases for memory references
diff --git a/rpython/jit/metainterp/optimizeopt/dependency.py
b/rpython/jit/metainterp/optimizeopt/dependency.py
--- a/rpython/jit/metainterp/optimizeopt/dependency.py
+++ b/rpython/jit/metainterp/optimizeopt/dependency.py
@@ -934,11 +934,11 @@
""" IndexVar is an AbstractValue only to ensure that a box can be assigned
to the same variable as an index var.
"""
- def __init__(self, var):
+ def __init__(self, var, coeff_mul=1, coeff_div=1, constant=0):
self.var = var
- self.coefficient_mul = 1
- self.coefficient_div = 1
- self.constant = 0
+ self.coefficient_mul = coeff_mul
+ self.coefficient_div = coeff_div
+ self.constant = constant
# saves the next modification that uses a variable
self.next_nonconst = None
self.current_end = None
@@ -990,7 +990,7 @@
def same_variable(self, other):
assert isinstance(other, IndexVar)
- return other.var == self.var
+ return other.var is self.var
def diff(self, other):
""" calculates the difference as a second parameter """
@@ -1060,9 +1060,8 @@
if self.is_identity():
return 'IndexVar(%s+%s)' % (self.var, repr(self.next_nonconst))
- return 'IndexVar((%s*(%s/%s)+%s) + %s)' % (self.var,
self.coefficient_mul,
- self.coefficient_div,
self.constant,
- repr(self.next_nonconst))
+ return 'IndexVar((%s*(%s/%s)+%s))' % (self.var, self.coefficient_mul,
+ self.coefficient_div,
self.constant)
class MemoryRef(object):
""" a memory reference to an array object. IntegralForwardModification is
able
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_dependency.py
b/rpython/jit/metainterp/optimizeopt/test/test_dependency.py
--- a/rpython/jit/metainterp/optimizeopt/test/test_dependency.py
+++ b/rpython/jit/metainterp/optimizeopt/test/test_dependency.py
@@ -7,20 +7,11 @@
from rpython.jit.metainterp.optimizeopt.dependency import (DependencyGraph,
Dependency,
IndexVar, MemoryRef, Node)
from rpython.jit.metainterp.resoperation import rop, ResOperation
+from rpython.jit.backend.llgraph.runner import ArrayDescr
+from rpython.rtyper.lltypesystem import rffi
+from rpython.rtyper.lltypesystem import lltype
from rpython.conftest import option
-class FakeNode(Node):
- def __init__(self, i):
- Node.__init__(self, None, i)
- pass
-
- def __repr__(self):
- return "n%d" % self.opidx
-
-class FakeDependencyGraph(DependencyGraph):
- def __init__(self):
- pass
-
class DependencyBaseTest(BaseTest):
def setup_method(self, method):
@@ -138,6 +129,48 @@
return self.last_graph.memory_refs[node]
class BaseTestDependencyGraph(DependencyBaseTest):
+
+ def test_index_var_basic(self):
+ b = FakeBox()
+ i = IndexVar(b,1,1,0)
+ j = IndexVar(b,1,1,0)
+ assert i.is_identity()
+ assert not i.less(j)
+ assert i.same_variable(j)
+ assert i.diff(j) == 0
+
+ def test_index_var_diff(self):
+ b = FakeBox()
+ i = IndexVar(b,4,2,0)
+ j = IndexVar(b,1,1,1)
+ assert not i.is_identity()
+ assert not j.is_identity()
+ assert i.diff(j) == 1
+
+ def test_memoryref_basic(self):
+ i = FakeBox()
+ a = FakeBox()
+ m1 = memoryref(a, i, (1,1,0))
+ m2 = memoryref(a, i, (1,1,0))
+ assert m1.match(m2)
+
+ @py.test.mark.parametrize('coeff1,coeff2,adja,alias',
+ [((1,1,0), (1,1,0), False, True),
+ ((4,2,0), (8,4,0), False, True),
+ ((4,2,0), (8,2,0), False, True),
+ ((4,2,1), (8,4,0), True, False),
+ ])
+ def test_memoryref_adjacent_alias(self, coeff1,
+ coeff2, adja,
+ alias):
+ i = FakeBox()
+ a = FakeBox()
+ m1 = memoryref(a, i, coeff1)
+ m2 = memoryref(a, i, coeff2)
+ assert m1.is_adjacent_after(m2) == adja
+ assert m2.is_adjacent_after(m1) == adja
+ assert m1.indices_can_alias(m2) == alias
+
def test_dependency_empty(self):
ops = """
[] # 0: 1
@@ -511,6 +544,49 @@
assert cycle is not None
assert cycle == [n1,n3,n4]
+class FakeMemoryRefResOp(object):
+ def __init__(self, array, descr):
+ self.array = array
+ self.descr = descr
+ def getarg(self, index):
+ return self.array
+ def getdescr(self):
+ return self.descr
+
+FLOAT = ArrayDescr(lltype.Float)
+SFLOAT = ArrayDescr(lltype.SingleFloat)
+CHAR = ArrayDescr(rffi.r_signedchar)
+UCHAR = ArrayDescr(rffi.r_uchar)
+SHORT = ArrayDescr(rffi.r_short)
+USHORT = ArrayDescr(rffi.r_ushort)
+INT = ArrayDescr(rffi.r_int)
+UINT = ArrayDescr(rffi.r_uint)
+LONG = ArrayDescr(rffi.r_longlong)
+ULONG = ArrayDescr(rffi.r_ulonglong)
+
+def memoryref(array, var, mod=(1,1,0), descr=None, raw=False):
+ if descr is None:
+ descr = FLOAT
+ mul, div, off = mod
+ op = FakeMemoryRefResOp(array, descr)
+ return MemoryRef(op,
+ IndexVar(var, mul, div, off),
+ raw)
+
+class FakeBox(object):
+ pass
+
+class FakeNode(Node):
+ def __init__(self, i):
+ Node.__init__(self, None, i)
+ pass
+
+ def __repr__(self):
+ return "n%d" % self.opidx
+
+class FakeDependencyGraph(DependencyGraph):
+ def __init__(self):
+ pass
class TestLLtype(BaseTestDependencyGraph, LLtypeMixin):
diff --git a/rpython/jit/metainterp/optimizeopt/vectorize.py
b/rpython/jit/metainterp/optimizeopt/vectorize.py
--- a/rpython/jit/metainterp/optimizeopt/vectorize.py
+++ b/rpython/jit/metainterp/optimizeopt/vectorize.py
@@ -326,6 +326,8 @@
if memref_a.is_adjacent_to(memref_b):
pair = self.packset.can_be_packed(node_a, node_b,
None, False)
if pair:
+ if node_a.op.getopnum() == rop.GETARRAYITEM_RAW:
+ print "found", memref_a.index_var,
memref_b.index_var
self.packset.add_pack(pair)
def extend_packset(self):
diff --git a/rpython/jit/metainterp/test/test_vectorize.py
b/rpython/jit/metainterp/test/test_vectorize.py
--- a/rpython/jit/metainterp/test/test_vectorize.py
+++ b/rpython/jit/metainterp/test/test_vectorize.py
@@ -13,6 +13,11 @@
from rpython.rlib.rawstorage import (alloc_raw_storage, raw_storage_setitem,
free_raw_storage, raw_storage_getitem)
+def malloc(T,n):
+ return lltype.malloc(T, n, flavor='raw', zero=True)
+def free(mem):
+ lltype.free(mem, flavor='raw')
+
class VectorizeTests:
enable_opts =
'intbounds:rewrite:virtualize:string:earlyforce:pure:heap:unroll'
@@ -289,8 +294,8 @@
myjitdriver = JitDriver(greens = [],
reds = 'auto')
def f(d, v1, v2):
- a = [v1] * d
- b = [v2] * d
+ a = [v1] * i
+ b = [v2] * i
i = 0
while i < len(a):
myjitdriver.jit_merge_point()
@@ -305,6 +310,31 @@
# return 69.999 ... instead of 70, (v1+v2)*i == 70.0
assert res == f(i,v1,v2) == sum([v1+v2]*i)
+ @py.test.mark.parametrize('size',[12])
+ def test_body_multiple_accesses(self, size):
+ myjitdriver = JitDriver(greens = [], reds = 'auto')
+ T = lltype.Array(rffi.CHAR, hints={'nolength': True})
+ def f(size):
+ vector_a = malloc(T, size)
+ vector_b = malloc(T, size)
+ i = 0
+ while i < size:
+ myjitdriver.jit_merge_point()
+ # should unroll and group them correctly
+ c1 = vector_a[i]
+ c2 = vector_a[i+1]
+ c3 = vector_a[i+2]
+ #
+ vector_b[i] = c1
+ vector_b[i+1] = c2
+ vector_b[i+2] = c3
+ i += 3
+ free(vector_a)
+ free(vector_b)
+ return 0
+ res = self.meta_interp(f, [size], vec_all=True)
+ assert res == f(size)
+
class VectorizeLLtypeTests(VectorizeTests):
pass
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit