[pypy-commit] pypy s390x-backend: added regalloc/assembler for int_neg, int_invert
plan_rich
noreply at buildbot.pypy.org
Thu Nov 12 13:54:23 EST 2015
Author: Richard Plangger <planrichi at gmail.com>
Branch: s390x-backend
Changeset: r80650:54d56775dc1e
Date: 2015-11-12 19:54 +0100
http://bitbucket.org/pypy/pypy/changeset/54d56775dc1e/
Log: added regalloc/assembler for int_neg, int_invert
diff --git a/rpython/jit/backend/zarch/helper/regalloc.py b/rpython/jit/backend/zarch/helper/regalloc.py
--- a/rpython/jit/backend/zarch/helper/regalloc.py
+++ b/rpython/jit/backend/zarch/helper/regalloc.py
@@ -118,9 +118,9 @@
self.free_op_vars()
return [l0, l1]
-def prepare_unary(self, op):
+def prepare_unary_op(self, op):
a0 = op.getarg(0)
- assert not a0.is_imm()
+ assert not isinstance(a0, ConstInt)
l0 = self.ensure_reg(a0)
self.force_result_in_reg(op, a0)
self.free_op_vars()
diff --git a/rpython/jit/backend/zarch/instructions.py b/rpython/jit/backend/zarch/instructions.py
--- a/rpython/jit/backend/zarch/instructions.py
+++ b/rpython/jit/backend/zarch/instructions.py
@@ -40,6 +40,7 @@
# invert & negative & absolute
'LPGR': ('rre', ['\xB9','\x00']),
'LNGR': ('rre', ['\xB9','\x01']),
+ 'LCGR': ('rre', ['\xB9','\x03']),
@@ -58,6 +59,7 @@
'CLGR': ('rre', ['\xB9','\x21']),
'CLG': ('rxy', ['\xE3','\x21']),
'CGHI': ('ri', ['\xA7','\x0F']),
+ 'CGFI': ('ril', ['\xC2','\x0E']),
}
logic_mnemonic_codes = {
diff --git a/rpython/jit/backend/zarch/opassembler.py b/rpython/jit/backend/zarch/opassembler.py
--- a/rpython/jit/backend/zarch/opassembler.py
+++ b/rpython/jit/backend/zarch/opassembler.py
@@ -3,8 +3,24 @@
from rpython.jit.backend.zarch.codebuilder import ZARCHGuardToken
import rpython.jit.backend.zarch.conditions as c
import rpython.jit.backend.zarch.registers as r
+import rpython.jit.backend.zarch.locations as l
from rpython.jit.backend.llsupport.gcmap import allocate_gcmap
+def flush_cc(asm, condition, result_loc):
+ # After emitting an instruction that leaves a boolean result in
+ # a condition code (cc), call this. In the common case, result_loc
+ # will be set to 'fp' by the regalloc, which in this case means
+ # "propagate it between this operation and the next guard by keeping
+ # it in the cc". In the uncommon case, result_loc is another
+ # register, and we emit a load from the cc into this register.
+ assert asm.guard_success_cc == c.cond_none
+ if result_loc is r.SPP:
+ asm.guard_success_cc = condition
+ else:
+ xxx
+ #asm.mc.MOV_ri(result_loc.value, 1, condition)
+ #asm.mc.MOV_ri(result_loc.value, 0, c.get_opposite_of(condition))
+
class IntOpAssembler(object):
_mixin_ = True
@@ -73,6 +89,26 @@
else:
self.mc.SGR(l0, l1)
+ def emit_int_invert(self, op, arglocs, regalloc):
+ l0 = arglocs[0]
+ assert not l0.is_imm()
+ self.mc.XG(l0, l.pool(self.pool.constant_64_ones))
+
+ def emit_int_neg(self, op, arglocs, regalloc):
+ l0 = arglocs[0]
+ self.mc.LNGR(l0, l0)
+
+ def emit_int_is_zero(self, op, arglocs, regalloc):
+ l0 = arglocs[0]
+ self.mc.CGHI(l0, l.imm(0))
+ flush_cc(self, l0, c.EQ)
+
+ def emit_int_is_true(self, op, arglocs, regalloc):
+ l0 = arglocs[0]
+ self.mc.CGHI(l0, l.imm(0))
+ flush_cc(self, l0, c.NE)
+
+
emit_int_and = gen_emit_rr_or_rpool("NGR", "NG")
emit_int_or = gen_emit_rr_or_rpool("OGR", "OG")
emit_int_xor = gen_emit_rr_or_rpool("XGR", "XG")
diff --git a/rpython/jit/backend/zarch/pool.py b/rpython/jit/backend/zarch/pool.py
--- a/rpython/jit/backend/zarch/pool.py
+++ b/rpython/jit/backend/zarch/pool.py
@@ -15,6 +15,8 @@
self.label_offset = 0
self.label_count = 0
self.offset_map = {}
+ self.constant_64_zeros = -1
+ self.constant_64_ones = -1
def ensure_can_hold_constants(self, asm, op):
if op.is_guard():
@@ -34,6 +36,8 @@
if descr not in asm.target_tokens_currently_compiling:
# this is a 'long' jump instead of a relative jump
self.offset_map[descr] = self.size
+ elif op.getopnum() == rop.INT_INVERT:
+ self.constant_64_ones = 1 # we need constant ones!!!
for arg in op.getarglist():
if arg.is_constant():
self.offset_map[arg] = self.size
@@ -71,13 +75,23 @@
self.pool_start = asm.mc.get_relative_pos()
for op in operations:
self.ensure_can_hold_constants(asm, op)
- if self.size == 0:
+ if self.size == 0 and written != 0:
# no pool needed!
return
assert self.size % 2 == 0
#if self.size % 2 == 1:
# self.size += 1
asm.mc.write('\xFF' * self.size)
+ written = 0
+ if self.constant_64_ones:
+ asm.mc.write('\xFF' * 8)
+ self.constant_64_ones = self.size
+ written += 8
+ if self.constant_64_zeros:
+ asm.mc.write('\x00' * 8)
+ self.constant_64_zeros = self.size
+ written += 8
+ self.size += written
print "pool with %d quad words" % (self.size // 8)
def overwrite_64(self, mc, index, value):
diff --git a/rpython/jit/backend/zarch/test/test_runner.py b/rpython/jit/backend/zarch/test/test_runner.py
--- a/rpython/jit/backend/zarch/test/test_runner.py
+++ b/rpython/jit/backend/zarch/test/test_runner.py
@@ -42,6 +42,16 @@
(-1,'i1 = int_lshift(i0, 1)', -2),
(-2**35,'i1 = int_lshift(i0, 1)', (-2**35)*2),
(2**64-1,'i1 = uint_rshift(i0, 2)', (2**64-1)//4),
+ (-1,'i1 = int_neg(i0)', -1),
+ (1,'i1 = int_neg(i0)', -1),
+ (2**63-1,'i1 = int_neg(i0)', -(2**63-1)),
+ (1,'i1 = int_invert(i0)', ~1),
+ (15,'i1 = int_invert(i0)', ~15),
+ (-1,'i1 = int_invert(i0)', ~(-1)),
+ (0,'i1 = int_is_zero(i0)', 1),
+ (50,'i1 = int_is_zero(i0)', 0),
+ (-1,'i1 = int_is_true(i0)', 1),
+ (0,'i1 = int_is_true(i0)', 0),
])
def test_int_arithmetic_and_logic(self, value, opcode, result):
loop = parse("""
More information about the pypy-commit
mailing list