Chromium Code Reviews| Index: src/IceTargetLoweringX8632.cpp |
| diff --git a/src/IceTargetLoweringX8632.cpp b/src/IceTargetLoweringX8632.cpp |
| index 81973d06cd027df3c652d75c789e6d380ff6e352..9f34239f5a3c3d3206a6bfa09c1a8c6db1384dd0 100644 |
| --- a/src/IceTargetLoweringX8632.cpp |
| +++ b/src/IceTargetLoweringX8632.cpp |
| @@ -758,7 +758,7 @@ Operand *TargetX8632::loOperand(Operand *Operand) { |
| if (OperandX8632Mem *Mem = llvm::dyn_cast<OperandX8632Mem>(Operand)) { |
| return OperandX8632Mem::create(Func, IceType_i32, Mem->getBase(), |
| Mem->getOffset(), Mem->getIndex(), |
| - Mem->getShift()); |
| + Mem->getShift(), Mem->getSegmentRegister()); |
| } |
| llvm_unreachable("Unsupported operand type"); |
| return NULL; |
| @@ -788,7 +788,8 @@ Operand *TargetX8632::hiOperand(Operand *Operand) { |
| SymOffset->getName()); |
| } |
| return OperandX8632Mem::create(Func, IceType_i32, Mem->getBase(), Offset, |
| - Mem->getIndex(), Mem->getShift()); |
| + Mem->getIndex(), Mem->getShift(), |
| + Mem->getSegmentRegister()); |
| } |
| llvm_unreachable("Unsupported operand type"); |
| return NULL; |
| @@ -1764,6 +1765,86 @@ void TargetX8632::lowerIcmp(const InstIcmp *Inst) { |
| Context.insert(Label); |
| } |
| +void TargetX8632::lowerIntrinsicCall(const InstIntrinsicCall *Instr) { |
| + switch (Instr->getIntrinsicInfo().ID) { |
| + case AtomicCmpxchg: |
| + case AtomicFence: |
| + case AtomicFenceAll: |
| + case AtomicIsLockFree: |
| + case AtomicLoad: |
| + case AtomicRMW: |
| + case AtomicStore: |
| + case Bswap: |
| + case Ctlz: |
| + case Ctpop: |
| + case Cttz: |
| + Func->setError("Unhandled intrinsic"); |
| + return; |
| + case Longjmp: { |
| + InstCall *Call = makeHelperCall("longjmp", NULL, 2); |
| + Call->addArg(Instr->getSrc(1)); |
| + Call->addArg(Instr->getSrc(2)); |
| + lowerCall(Call); |
| + break; |
| + } |
| + case Memcpy: { |
| + // In the future, we could potentially emit an inline memcpy/memset, etc. |
| + // for intrinsic calls w/ a known length. |
| + InstCall *Call = makeHelperCall("memcpy", NULL, 3); |
| + Call->addArg(Instr->getSrc(1)); |
| + Call->addArg(Instr->getSrc(2)); |
| + Call->addArg(Instr->getSrc(3)); |
| + lowerCall(Call); |
| + break; |
| + } |
| + case Memmove: { |
| + InstCall *Call = makeHelperCall("memmove", NULL, 3); |
| + Call->addArg(Instr->getSrc(1)); |
| + Call->addArg(Instr->getSrc(2)); |
| + Call->addArg(Instr->getSrc(3)); |
| + lowerCall(Call); |
| + break; |
| + } |
| + case Memset: { |
| + InstCall *Call = makeHelperCall("memset", NULL, 3); |
| + Call->addArg(Instr->getSrc(1)); |
| + Call->addArg(Instr->getSrc(2)); |
|
jvoung (off chromium)
2014/06/12 05:48:30
Should this code be responsible for "widening" the
Jim Stichnoth
2014/06/12 17:04:44
The Subzero lowering code assumes the simplificati
jvoung (off chromium)
2014/06/16 20:51:58
Added a movzx for this case.
Was going to add a d
Jim Stichnoth
2014/06/16 23:05:15
Hmm, looks like those two tests are not valid PNaC
jvoung (off chromium)
2014/06/17 17:36:18
Ah right, I should have looked at what the test wa
|
| + Call->addArg(Instr->getSrc(3)); |
| + lowerCall(Call); |
| + break; |
| + } |
| + case NaClReadTP: { |
| + Constant *Zero = Ctx->getConstantInt(IceType_i32, 0); |
| + Operand *Src = OperandX8632Mem::create( |
| + Func, IceType_i32, NULL, Zero, NULL, 0, |
| + OperandX8632Mem::Reg_GS); |
| + Variable *Dest = Instr->getDest(); |
| + Variable *T = NULL; |
| + _mov(T, Src); |
| + _mov(Dest, T); |
| + break; |
| + } |
| + case Setjmp: { |
| + InstCall *Call = makeHelperCall("setjmp", Instr->getDest(), 1); |
| + Call->addArg(Instr->getSrc(1)); |
| + lowerCall(Call); |
| + break; |
| + } |
| + case Sqrt: |
| + case Stacksave: |
| + case Stackrestore: |
| + Func->setError("Unhandled intrinsic"); |
| + return; |
| + case Trap: |
| + _ud2(); |
| + break; |
| + case UnknownIntrinsic: |
| + Func->setError("Should not be lowering UnknownIntrinsic"); |
| + return; |
| + } |
| + return; |
| +} |
| + |
| namespace { |
| bool isAdd(const Inst *Inst) { |
| @@ -1774,7 +1855,7 @@ bool isAdd(const Inst *Inst) { |
| return false; |
| } |
| -void computeAddressOpt(Variable *&Base, Variable *&Index, int32_t &Shift, |
| +void computeAddressOpt(Variable *&Base, Variable *&Index, uint16_t &Shift, |
| int32_t &Offset) { |
| (void)Offset; // TODO: pattern-match for non-zero offsets. |
| if (Base == NULL) |
| @@ -1955,14 +2036,20 @@ void TargetX8632::doAddressOptLoad() { |
| Variable *Dest = Inst->getDest(); |
| Operand *Addr = Inst->getSrc(0); |
| Variable *Index = NULL; |
| - int32_t Shift = 0; |
| + uint16_t Shift = 0; |
| int32_t Offset = 0; // TODO: make Constant |
| + // At the ICE level, load instructions should not use the |
| + // segment registers, and computeAddressOpt only works at the level |
| + // of Variables and Constants, not other OperandX8632Mem, so there |
| + // should be no mention of segment registers there either. |
| + OperandX8632Mem::SegmentRegisters SegmentReg = |
| + OperandX8632Mem::DefaultSegment; |
| Variable *Base = llvm::dyn_cast<Variable>(Addr); |
| computeAddressOpt(Base, Index, Shift, Offset); |
| if (Base && Addr != Base) { |
| Constant *OffsetOp = Ctx->getConstantInt(IceType_i32, Offset); |
| Addr = OperandX8632Mem::create(Func, Dest->getType(), Base, OffsetOp, Index, |
| - Shift); |
| + Shift, SegmentReg); |
| Inst->setDeleted(); |
| Context.insert(InstLoad::create(Func, Dest, Addr)); |
| } |
| @@ -2071,14 +2158,20 @@ void TargetX8632::doAddressOptStore() { |
| Operand *Data = Inst->getData(); |
| Operand *Addr = Inst->getAddr(); |
| Variable *Index = NULL; |
| - int32_t Shift = 0; |
| + uint16_t Shift = 0; |
| int32_t Offset = 0; // TODO: make Constant |
| Variable *Base = llvm::dyn_cast<Variable>(Addr); |
| + // At the ICE level, load instructions should not use the |
| + // segment registers, and computeAddressOpt only works at the level |
| + // of Variables and Constants, not other OperandX8632Mem, so there |
| + // should be no mention of segment registers there either. |
| + OperandX8632Mem::SegmentRegisters SegmentReg = |
| + OperandX8632Mem::DefaultSegment; |
| computeAddressOpt(Base, Index, Shift, Offset); |
| if (Base && Addr != Base) { |
| Constant *OffsetOp = Ctx->getConstantInt(IceType_i32, Offset); |
| Addr = OperandX8632Mem::create(Func, Data->getType(), Base, OffsetOp, Index, |
| - Shift); |
| + Shift, SegmentReg); |
| Inst->setDeleted(); |
| Context.insert(InstStore::create(Func, Data, Addr)); |
| } |
| @@ -2139,7 +2232,8 @@ Operand *TargetX8632::legalize(Operand *From, LegalMask Allowed, |
| if (Base != RegBase || Index != RegIndex) { |
| From = |
| OperandX8632Mem::create(Func, Mem->getType(), RegBase, |
| - Mem->getOffset(), RegIndex, Mem->getShift()); |
| + Mem->getOffset(), RegIndex, Mem->getShift(), |
| + Mem->getSegmentRegister()); |
| } |
| if (!(Allowed & Legal_Mem)) { |