aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp')
-rw-r--r--llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp16
1 files changed, 14 insertions, 2 deletions
diff --git a/llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp b/llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp
index ca5ca7257bab..4a9ea69d101c 100644
--- a/llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZSelectionDAGInfo.cpp
@@ -81,11 +81,12 @@ SDValue SystemZSelectionDAGInfo::EmitTargetCodeForMemset(
if (IsVolatile)
return SDValue();
+ auto *CByte = dyn_cast<ConstantSDNode>(Byte);
if (auto *CSize = dyn_cast<ConstantSDNode>(Size)) {
uint64_t Bytes = CSize->getZExtValue();
if (Bytes == 0)
return SDValue();
- if (auto *CByte = dyn_cast<ConstantSDNode>(Byte)) {
+ if (CByte) {
// Handle cases that can be done using at most two of
// MVI, MVHI, MVHHI and MVGHI. The latter two can only be
// used if ByteVal is all zeros or all ones; in other casees,
@@ -125,7 +126,6 @@ SDValue SystemZSelectionDAGInfo::EmitTargetCodeForMemset(
assert(Bytes >= 2 && "Should have dealt with 0- and 1-byte cases already");
// Handle the special case of a memset of 0, which can use XC.
- auto *CByte = dyn_cast<ConstantSDNode>(Byte);
if (CByte && CByte->getZExtValue() == 0)
return emitMemMem(DAG, DL, SystemZISD::XC, SystemZISD::XC_LOOP,
Chain, Dst, Dst, Bytes);
@@ -138,6 +138,18 @@ SDValue SystemZSelectionDAGInfo::EmitTargetCodeForMemset(
return emitMemMem(DAG, DL, SystemZISD::MVC, SystemZISD::MVC_LOOP,
Chain, DstPlus1, Dst, Bytes - 1);
}
+
+ // Variable length
+ if (CByte && CByte->getZExtValue() == 0) {
+ // Handle the special case of a variable length memset of 0 with XC.
+ SDValue LenMinus1 = DAG.getNode(ISD::ADD, DL, MVT::i64,
+ DAG.getZExtOrTrunc(Size, DL, MVT::i64),
+ DAG.getConstant(-1, DL, MVT::i64));
+ SDValue TripC = DAG.getNode(ISD::SRL, DL, MVT::i64, LenMinus1,
+ DAG.getConstant(8, DL, MVT::i64));
+ return DAG.getNode(SystemZISD::XC_LOOP, DL, MVT::Other, Chain, Dst, Dst,
+ LenMinus1, TripC);
+ }
return SDValue();
}