[pypy-commit] pypy vecopt2: working on packing instructions
plan_rich
noreply at buildbot.pypy.org
Tue May 5 09:45:20 CEST 2015
Author: Richard Plangger <rich at pasra.at>
Branch: vecopt2
Changeset: r77073:1047edfb7de1
Date: 2015-03-12 10:19 +0100
http://bitbucket.org/pypy/pypy/changeset/1047edfb7de1/
Log: working on packing instructions
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py b/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
--- a/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
+++ b/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
@@ -42,15 +42,23 @@
self._do_optimize_loop(loop, call_pure_results, export_state=True)
self.assert_equal(loop, expected_loop)
- def assert_unroll_loop_equals(self, loop, expected_loop, \
- unroll_factor = -1, call_pure_results=None):
+ def vec_optimizer(self, loop):
metainterp_sd = FakeMetaInterpStaticData(self.cpu)
jitdriver_sd = FakeJitDriverStaticData()
opt = OptVectorize(metainterp_sd, jitdriver_sd, loop, [])
+ return opt
+
+ def vec_optimizer_unrolled(self, loop, unroll_factor = -1):
+ opt = self.vec_optimizer(loop)
+ opt._gather_trace_information(loop)
if unroll_factor == -1:
- opt._gather_trace_information(loop)
unroll_factor = opt.get_estimated_unroll_factor()
opt.unroll_loop_iterations(loop, unroll_factor)
+ return opt
+
+ def assert_unroll_loop_equals(self, loop, expected_loop, \
+ unroll_factor = -1):
+ vec_optimizer = self.vec_optimizer(loop, unroll_factor)
self.assert_equal(loop, expected_loop)
def assert_def_use(self, graph, from_instr_index, to_instr_index):
@@ -171,49 +179,36 @@
"""
self.assert_unroll_loop_equals(self.parse_loop(ops), self.parse_loop(opt_ops), 2)
+ def test_estimate_unroll_factor_smallest_byte_zero(self):
+ ops = """
+ [p0,i0]
+ raw_load(p0,i0,descr=arraydescr2)
+ jump(p0,i0)
+ """
+ vopt = self.vec_optimizer(self.parse_loop(ops))
+ assert 0 == vopt.vec_info.smallest_type_bytes
+ assert 0 == vopt.get_estimated_unroll_factor()
+
+ def test_array_operation_indices_not_unrolled(self):
+ ops = """
+ [p0,i0]
+ raw_load(p0,i0,descr=arraydescr2)
+ jump(p0,i0)
+ """
+ vopt = self.vec_optimizer_unrolled(self.parse_loop(ops))
+ assert 1 in vopt.vec_info.array_ops
+ assert len(vopt.vec_info.array_ops) == 1
+
+ def test_array_operation_indices_unrolled_1(self):
+ ops = """
+ [p0,i0]
+ raw_load(p0,i0,descr=chararraydescr)
+ jump(p0,i0)
+ """
+ vopt = self.vec_optimizer_unrolled(self.parse_loop(ops),2)
+ assert 1 in vopt.vec_info.array_ops
+ assert 2 in vopt.vec_info.array_ops
+ assert len(vopt.vec_info.array_ops) == 2
+
class TestLLtype(BaseTestDependencyGraph, LLtypeMixin):
pass
-
-#class BaseTestVectorize(BaseTest):
-#
-# # vector instructions are not produced by the interpreter
-# # the optimization vectorize produces them
-# # load from from aligned memory example:
-# # vec = vec_aligned_raw_load(dst, index, sizeinbytes, descr)
-# # 'VEC_ALIGNED_RAW_LOAD/3d',
-# # store to aligned memory. example:
-# # vec_aligned_raw_store(dst, index, vector, sizeinbytes, descr)
-# # 'VEC_ALIGNED_RAW_STORE/4d',
-# # a list of operations on vectors
-# # add a vector: vec_int_add(v1, v2, 16)
-# # 'VEC_INT_ADD/3',
-#
-#class TestVectorize(BaseTestVectorize):
-#
-# def test_simple(self):
-# ops = """
-# [ia,ib,ic,i0]
-# ibi = raw_load(ib, i0, descr=arraydescr)
-# ici = raw_load(ic, i0, descr=arraydescr)
-# iai = int_add(ibi, ici)
-# raw_store(ia, i0, iai, descr=arraydescr)
-# i1 = int_add(i0,1)
-# ie = int_ge(i1,8)
-# guard_false(ie) [ia,ib,ic,i1]
-# jump(ia,ib,ic,i1)
-# """
-# expected = """
-# [ia,ib,ic,i0]
-# ibv = vec_raw_load(ib, i0, 16, descr=arraydescr)
-# icv = vec_raw_load(ic, i0, 16, descr=arraydescr)
-# iav = vec_int_add(ibi, ici, 16)
-# vec_raw_store(ia, i0, iai, 16, descr=arraydescr)
-# i1 = int_add(i0,4)
-# ie = int_ge(i1,8)
-# guard_false(ie) [ia,ib,ic,i1]
-# jump(ia,ib,ic,i1)
-# """
-# self.optimize_loop(ops, expected)
-#
-#class TestLLtype(TestVectorize, LLtypeMixin):
-# pass
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
@@ -25,7 +25,8 @@
def __init__(self, metainterp_sd, jitdriver_sd, loop, optimizations):
self.optimizer = VectorizeOptimizer(metainterp_sd, jitdriver_sd,
loop, optimizations)
- self.loop_vectorizer_checker = LoopVectorizeChecker()
+ self.vec_info = LoopVectorizeInfo()
+ self.memory_refs = []
self.vectorized = False
def _rename_arguments_ssa(self, rename_map, label_args, jump_args):
@@ -42,10 +43,12 @@
def unroll_loop_iterations(self, loop, unroll_factor):
label_op = loop.operations[0]
jump_op = loop.operations[-1]
- operations = [loop.operations[i] for i in range(1,len(loop.operations)-1)]
+ operations = [loop.operations[i].clone() for i in range(1,len(loop.operations)-1)]
loop.operations = []
- iterations = [[op.clone() for op in operations]]
+ op_index = len(operations) + 1
+
+ iterations = [operations]
label_op_args = [self.getvalue(box).get_key_box() for box in label_op.getarglist()]
values = [self.getvalue(box) for box in label_op.getarglist()]
#values[0].make_nonnull(self.optimizer)
@@ -75,7 +78,10 @@
except KeyError:
pass
+ self._op_index = op_index
iteration_ops.append(copied_op)
+ self.vec_info.inspect_operation(copied_op)
+ op_index += 1
# the jump arguments have been changed
# if label(iX) ... jump(i(X+1)) is called, at the next unrolled loop
@@ -102,13 +108,15 @@
def _gather_trace_information(self, loop):
for i,op in enumerate(loop.operations):
- self.loop_vectorizer_checker._op_index = i
- self.loop_vectorizer_checker.inspect_operation(op)
+ self.vec_info._op_index = i
+ self.vec_info.inspect_operation(op)
def get_estimated_unroll_factor(self, force_reg_bytes = -1):
""" force_reg_bytes used for testing """
# this optimization is not opaque, and needs info about the CPU
- byte_count = self.loop_vectorizer_checker.smallest_type_bytes
+ byte_count = self.vec_info.smallest_type_bytes
+ if byte_count == 0:
+ return 0
simd_vec_reg_bytes = 16 # TODO get from cpu
if force_reg_bytes > 0:
simd_vec_reg_bytes = force_reg_bytes
@@ -122,10 +130,7 @@
self._gather_trace_information(loop)
- for op in loop.operations:
- self.loop_vectorizer_checker.inspect_operation(op)
-
- byte_count = self.loop_vectorizer_checker.smallest_type_bytes
+ byte_count = self.vec_info.smallest_type_bytes
if byte_count == 0:
# stop, there is no chance to vectorize this trace
return loop
@@ -143,37 +148,37 @@
for more details.
"""
+ for i,operation in enumerate(loop.operations):
+
+ if operation.getopnum() == rop.RAW_LOAD:
+ # TODO while the loop is unrolled, build memory accesses
+ pass
+
# was not able to vectorize
return False
-
-
-class LoopVectorizeChecker(object):
+class LoopVectorizeInfo(object):
def __init__(self):
self.smallest_type_bytes = 0
self._op_index = 0
- self.mem_ref_indices = []
+ self.array_ops = []
- def add_memory_ref(self, i):
- self.mem_ref_indices.append(i)
-
- def count_RAW_LOAD(self, op):
- self.add_memory_ref(self._op_index)
+ def operation_RAW_LOAD(self, op):
descr = op.getdescr()
+ self.array_ops.append(self._op_index)
if not descr.is_array_of_pointers():
byte_count = descr.get_item_size_in_bytes()
if self.smallest_type_bytes == 0 \
or byte_count < self.smallest_type_bytes:
self.smallest_type_bytes = byte_count
- def default_count(self, operation):
+ def default_operation(self, operation):
pass
-dispatch_opt = make_dispatcher_method(LoopVectorizeChecker, 'count_',
- default=LoopVectorizeChecker.default_count)
-LoopVectorizeChecker.inspect_operation = dispatch_opt
-
+dispatch_opt = make_dispatcher_method(LoopVectorizeInfo, 'operation_',
+ default=LoopVectorizeInfo.default_operation)
+LoopVectorizeInfo.inspect_operation = dispatch_opt
class Pack(object):
""" A pack is a set of n statements that are:
@@ -194,11 +199,11 @@
Pack.__init__(self, [left_op, right_op])
-class MemoryAccess(object):
- def __init__(self, array, origin, offset):
+class MemoryRef(object):
+ def __init__(self, array, origin):
self.array = array
self.origin = origin
- self.offset = offset
+ self.offset = None
def is_adjacent_to(self, mem_acc):
if self.array == mem_acc.array:
More information about the pypy-commit
mailing list