@@ -4277,7 +4277,8 @@ struct BaseIndexOffset {
4277
4277
}
4278
4278
4279
4279
/// Parses tree in Ptr for base, index, offset addresses.
4280
- static BaseIndexOffset match(SDValue Ptr, SelectionDAG &DAG) {
4280
+ static BaseIndexOffset match(SDValue Ptr, SelectionDAG &DAG,
4281
+ int64_t PartialOffset = 0) {
4281
4282
bool IsIndexSignExt = false;
4282
4283
4283
4284
// Split up a folded GlobalAddress+Offset into its component parts.
@@ -4286,7 +4287,7 @@ struct BaseIndexOffset {
4286
4287
return BaseIndexOffset(DAG.getGlobalAddress(GA->getGlobal(),
4287
4288
SDLoc(GA),
4288
4289
GA->getValueType(0),
4289
- /*Offset=*/0 ,
4290
+ /*Offset=*/PartialOffset ,
4290
4291
/*isTargetGA=*/false,
4291
4292
GA->getTargetFlags()),
4292
4293
SDValue(),
@@ -4298,14 +4299,13 @@ struct BaseIndexOffset {
4298
4299
// instruction, then it could be just the BASE or everything else we don't
4299
4300
// know how to handle. Just use Ptr as BASE and give up.
4300
4301
if (Ptr->getOpcode() != ISD::ADD)
4301
- return BaseIndexOffset(Ptr, SDValue(), 0 , IsIndexSignExt);
4302
+ return BaseIndexOffset(Ptr, SDValue(), PartialOffset , IsIndexSignExt);
4302
4303
4303
4304
// We know that we have at least an ADD instruction. Try to pattern match
4304
4305
// the simple case of BASE + OFFSET.
4305
4306
if (isa<ConstantSDNode>(Ptr->getOperand(1))) {
4306
4307
int64_t Offset = cast<ConstantSDNode>(Ptr->getOperand(1))->getSExtValue();
4307
- return BaseIndexOffset(Ptr->getOperand(0), SDValue(), Offset,
4308
- IsIndexSignExt);
4308
+ return match(Ptr->getOperand(0), DAG, Offset + PartialOffset);
4309
4309
}
4310
4310
4311
4311
// Inside a loop the current BASE pointer is calculated using an ADD and a
@@ -4314,7 +4314,7 @@ struct BaseIndexOffset {
4314
4314
// (i64 mul (i64 %induction_var)
4315
4315
// (i64 %element_size)))
4316
4316
if (Ptr->getOperand(1)->getOpcode() == ISD::MUL)
4317
- return BaseIndexOffset(Ptr, SDValue(), 0 , IsIndexSignExt);
4317
+ return BaseIndexOffset(Ptr, SDValue(), PartialOffset , IsIndexSignExt);
4318
4318
4319
4319
// Look at Base + Index + Offset cases.
4320
4320
SDValue Base = Ptr->getOperand(0);
@@ -4328,14 +4328,14 @@ struct BaseIndexOffset {
4328
4328
4329
4329
// Either the case of Base + Index (no offset) or something else.
4330
4330
if (IndexOffset->getOpcode() != ISD::ADD)
4331
- return BaseIndexOffset(Base, IndexOffset, 0 , IsIndexSignExt);
4331
+ return BaseIndexOffset(Base, IndexOffset, PartialOffset , IsIndexSignExt);
4332
4332
4333
4333
// Now we have the case of Base + Index + offset.
4334
4334
SDValue Index = IndexOffset->getOperand(0);
4335
4335
SDValue Offset = IndexOffset->getOperand(1);
4336
4336
4337
4337
if (!isa<ConstantSDNode>(Offset))
4338
- return BaseIndexOffset(Ptr, SDValue(), 0 , IsIndexSignExt);
4338
+ return BaseIndexOffset(Ptr, SDValue(), PartialOffset , IsIndexSignExt);
4339
4339
4340
4340
// Ignore signextends.
4341
4341
if (Index->getOpcode() == ISD::SIGN_EXTEND) {
@@ -4344,7 +4344,7 @@ struct BaseIndexOffset {
4344
4344
} else IsIndexSignExt = false;
4345
4345
4346
4346
int64_t Off = cast<ConstantSDNode>(Offset)->getSExtValue();
4347
- return BaseIndexOffset(Base, Index, Off, IsIndexSignExt);
4347
+ return BaseIndexOffset(Base, Index, Off + PartialOffset , IsIndexSignExt);
4348
4348
}
4349
4349
};
4350
4350
} // namespace
0 commit comments