|
From: Andreas A. <ar...@so...> - 2026-03-18 18:39:38
|
https://sourceware.org/cgit/valgrind/commit/?id=1d07a025cae9786d9733fcc4fa7cef08e010d73c commit 1d07a025cae9786d9733fcc4fa7cef08e010d73c Author: Andreas Arnez <ar...@li...> Date: Wed Mar 18 18:27:44 2026 +0100 s390x: Slightly optimize AND/OR/XOR with immediates In host_s390_defs.c, when generating code for AND, OR, or XOR with a 64-bit immediate value, two instructions are emitted: one for each 32-bit half of the full 64-bit value. In cases where the value only affects the low or the high half of the result, one of these instructions becomes a no-op. For these cases, just suppress the effective no-op instructions. Diff: --- VEX/priv/host_s390_defs.c | 36 +++++++++++++++++++++++++++--------- 1 file changed, 27 insertions(+), 9 deletions(-) diff --git a/VEX/priv/host_s390_defs.c b/VEX/priv/host_s390_defs.c index 8ff386cc4a..1495b26338 100644 --- a/VEX/priv/host_s390_defs.c +++ b/VEX/priv/host_s390_defs.c @@ -7517,17 +7517,35 @@ s390_insn_alu_emit(UChar *buf, const s390_insn *insn) return s390_emit_MSGR(buf, dst, R0); /* Do it in two steps: upper half [0:31] and lower half [32:63] */ - case S390_ALU_AND: - buf = s390_emit_NIHF(buf, dst, value >> 32); - return s390_emit_NILF(buf, dst, value & 0xFFFFFFFF); + case S390_ALU_AND: { + UInt high = value >> 32; + UInt low = value & 0xffffffff; + if (high != 0xffffffff) + buf = s390_emit_NIHF(buf, dst, high); + if (low != 0xffffffff) + buf = s390_emit_NILF(buf, dst, low); + return buf; + } - case S390_ALU_OR: - buf = s390_emit_OIHF(buf, dst, value >> 32); - return s390_emit_OILF(buf, dst, value & 0xFFFFFFFF); + case S390_ALU_OR: { + UInt high = value >> 32; + UInt low = value & 0xffffffff; + if (high != 0) + buf = s390_emit_OIHF(buf, dst, high); + if (low != 0) + buf = s390_emit_OILF(buf, dst, low); + return buf; + } - case S390_ALU_XOR: - buf = s390_emit_XIHF(buf, dst, value >> 32); - return s390_emit_XILF(buf, dst, value & 0xFFFFFFFF); + case S390_ALU_XOR: { + UInt high = value >> 32; + UInt low = value & 0xffffffff; + if (high != 0) + buf = s390_emit_XIHF(buf, dst, high); + if (low != 0) + buf = s390_emit_XILF(buf, dst, low); + return buf; + } /* No special considerations for long displacement here. Only the six least significant bits of VALUE will be taken; all other bits are |