| OLD | NEW |
| 1 //===- subzero/src/IceInstARM32.cpp - ARM32 instruction implementation ----===// | 1 //===- subzero/src/IceInstARM32.cpp - ARM32 instruction implementation ----===// |
| 2 // | 2 // |
| 3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
| 4 // | 4 // |
| 5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
| 6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
| 7 // | 7 // |
| 8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
| 9 // | 9 // |
| 10 // This file implements the InstARM32 and OperandARM32 classes, | 10 // This file implements the InstARM32 and OperandARM32 classes, |
| (...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 146 if (!BuildDefs::dump()) | 146 if (!BuildDefs::dump()) |
| 147 return; | 147 return; |
| 148 Ostream &Str = Func->getContext()->getStrEmit(); | 148 Ostream &Str = Func->getContext()->getStrEmit(); |
| 149 assert(Inst->getSrcSize() == 2); | 149 assert(Inst->getSrcSize() == 2); |
| 150 Str << "\t" << Opcode << Inst->getPredicate() << "\t"; | 150 Str << "\t" << Opcode << Inst->getPredicate() << "\t"; |
| 151 Inst->getSrc(0)->emit(Func); | 151 Inst->getSrc(0)->emit(Func); |
| 152 Str << ", "; | 152 Str << ", "; |
| 153 Inst->getSrc(1)->emit(Func); | 153 Inst->getSrc(1)->emit(Func); |
| 154 } | 154 } |
| 155 | 155 |
| 156 OperandARM32Mem::OperandARM32Mem(Cfg * /* Func */, Type Ty, Variable *Base, | 156 OperandARM32Mem::OperandARM32Mem(Cfg * /* Func */, Type Ty, Variable *MyBase, |
| 157 ConstantInteger32 *ImmOffset, AddrMode Mode) | 157 ConstantInteger32 *MyImmOffset, |
| 158 : OperandARM32(kMem, Ty), Base(Base), ImmOffset(ImmOffset), Index(nullptr), | 158 AddrMode MyMode) |
| 159 ShiftOp(kNoShift), ShiftAmt(0), Mode(Mode) { | 159 : OperandARM32(kMem, Ty), Base(MyBase), ImmOffset(MyImmOffset), |
| 160 Index(nullptr), ShiftOp(kNoShift), ShiftAmt(0), Mode(MyMode) { |
| 160 // The Neg modes are only needed for Reg +/- Reg. | 161 // The Neg modes are only needed for Reg +/- Reg. |
| 161 assert(!isNegAddrMode()); | 162 assert(!isNegAddrMode()); |
| 162 NumVars = 1; | 163 NumVars = 1; |
| 163 Vars = &this->Base; | 164 Vars = &this->Base; |
| 164 } | 165 } |
| 165 | 166 |
| 166 OperandARM32Mem::OperandARM32Mem(Cfg *Func, Type Ty, Variable *Base, | 167 OperandARM32Mem::OperandARM32Mem(Cfg *Func, Type Ty, Variable *MyBase, |
| 167 Variable *Index, ShiftKind ShiftOp, | 168 Variable *MyIndex, ShiftKind MyShiftOp, |
| 168 uint16_t ShiftAmt, AddrMode Mode) | 169 uint16_t MyShiftAmt, AddrMode MyMode) |
| 169 : OperandARM32(kMem, Ty), Base(Base), ImmOffset(0), Index(Index), | 170 : OperandARM32(kMem, Ty), Base(MyBase), ImmOffset(0), Index(MyIndex), |
| 170 ShiftOp(ShiftOp), ShiftAmt(ShiftAmt), Mode(Mode) { | 171 ShiftOp(MyShiftOp), ShiftAmt(MyShiftAmt), Mode(MyMode) { |
| 171 NumVars = 2; | 172 NumVars = 2; |
| 172 Vars = Func->allocateArrayOf<Variable *>(2); | 173 Vars = Func->allocateArrayOf<Variable *>(2); |
| 173 Vars[0] = Base; | 174 Vars[0] = Base; |
| 174 Vars[1] = Index; | 175 Vars[1] = Index; |
| 175 } | 176 } |
| 176 | 177 |
| 177 bool OperandARM32Mem::canHoldOffset(Type Ty, bool SignExt, int32_t Offset) { | 178 bool OperandARM32Mem::canHoldOffset(Type Ty, bool SignExt, int32_t Offset) { |
| 178 int32_t Bits = SignExt ? TypeARM32Attributes[Ty].SExtAddrOffsetBits | 179 int32_t Bits = SignExt ? TypeARM32Attributes[Ty].SExtAddrOffsetBits |
| 179 : TypeARM32Attributes[Ty].ZExtAddrOffsetBits; | 180 : TypeARM32Attributes[Ty].ZExtAddrOffsetBits; |
| 180 if (Bits == 0) | 181 if (Bits == 0) |
| 181 return Offset == 0; | 182 return Offset == 0; |
| 182 // Note that encodings for offsets are sign-magnitude for ARM, so we check | 183 // Note that encodings for offsets are sign-magnitude for ARM, so we check |
| 183 // with IsAbsoluteUint(). | 184 // with IsAbsoluteUint(). |
| 184 if (isScalarFloatingType(Ty)) | 185 if (isScalarFloatingType(Ty)) |
| 185 return Utils::IsAligned(Offset, 4) && Utils::IsAbsoluteUint(Bits, Offset); | 186 return Utils::IsAligned(Offset, 4) && Utils::IsAbsoluteUint(Bits, Offset); |
| 186 return Utils::IsAbsoluteUint(Bits, Offset); | 187 return Utils::IsAbsoluteUint(Bits, Offset); |
| 187 } | 188 } |
| 188 | 189 |
| 189 OperandARM32FlexImm::OperandARM32FlexImm(Cfg * /* Func */, Type Ty, | 190 OperandARM32FlexImm::OperandARM32FlexImm(Cfg * /* Func */, Type Ty, |
| 190 uint32_t Imm, uint32_t RotateAmt) | 191 uint32_t MyImm, uint32_t MyRotateAmt) |
| 191 : OperandARM32Flex(kFlexImm, Ty), Imm(Imm), RotateAmt(RotateAmt) { | 192 : OperandARM32Flex(kFlexImm, Ty), Imm(MyImm), RotateAmt(MyRotateAmt) { |
| 192 NumVars = 0; | 193 NumVars = 0; |
| 193 Vars = nullptr; | 194 Vars = nullptr; |
| 194 } | 195 } |
| 195 | 196 |
| 196 bool OperandARM32FlexImm::canHoldImm(uint32_t Immediate, uint32_t *RotateAmt, | 197 bool OperandARM32FlexImm::canHoldImm(uint32_t Immediate, uint32_t *RotateAmt, |
| 197 uint32_t *Immed_8) { | 198 uint32_t *Immed_8) { |
| 198 // Avoid the more expensive test for frequent small immediate values. | 199 // Avoid the more expensive test for frequent small immediate values. |
| 199 if (Immediate <= 0xFF) { | 200 if (Immediate <= 0xFF) { |
| 200 *RotateAmt = 0; | 201 *RotateAmt = 0; |
| 201 *Immed_8 = Immediate; | 202 *Immed_8 = Immediate; |
| 202 return true; | 203 return true; |
| 203 } | 204 } |
| 204 // Note that immediate must be unsigned for the test to work correctly. | 205 // Note that immediate must be unsigned for the test to work correctly. |
| 205 for (int Rot = 1; Rot < 16; Rot++) { | 206 for (int Rot = 1; Rot < 16; Rot++) { |
| 206 uint32_t Imm8 = Utils::rotateLeft32(Immediate, 2 * Rot); | 207 uint32_t Imm8 = Utils::rotateLeft32(Immediate, 2 * Rot); |
| 207 if (Imm8 <= 0xFF) { | 208 if (Imm8 <= 0xFF) { |
| 208 *RotateAmt = Rot; | 209 *RotateAmt = Rot; |
| 209 *Immed_8 = Imm8; | 210 *Immed_8 = Imm8; |
| 210 return true; | 211 return true; |
| 211 } | 212 } |
| 212 } | 213 } |
| 213 return false; | 214 return false; |
| 214 } | 215 } |
| 215 | 216 |
| 216 OperandARM32FlexReg::OperandARM32FlexReg(Cfg *Func, Type Ty, Variable *Reg, | 217 OperandARM32FlexReg::OperandARM32FlexReg(Cfg *Func, Type Ty, Variable *MyReg, |
| 217 ShiftKind ShiftOp, Operand *ShiftAmt) | 218 ShiftKind MyShiftOp, |
| 218 : OperandARM32Flex(kFlexReg, Ty), Reg(Reg), ShiftOp(ShiftOp), | 219 Operand *MyShiftAmt) |
| 219 ShiftAmt(ShiftAmt) { | 220 : OperandARM32Flex(kFlexReg, Ty), Reg(MyReg), ShiftOp(MyShiftOp), |
| 221 ShiftAmt(MyShiftAmt) { |
| 220 NumVars = 1; | 222 NumVars = 1; |
| 221 Variable *ShiftVar = llvm::dyn_cast_or_null<Variable>(ShiftAmt); | 223 Variable *ShiftVar = llvm::dyn_cast_or_null<Variable>(ShiftAmt); |
| 222 if (ShiftVar) | 224 if (ShiftVar) |
| 223 ++NumVars; | 225 ++NumVars; |
| 224 Vars = Func->allocateArrayOf<Variable *>(NumVars); | 226 Vars = Func->allocateArrayOf<Variable *>(NumVars); |
| 225 Vars[0] = Reg; | 227 Vars[0] = Reg; |
| 226 if (ShiftVar) | 228 if (ShiftVar) |
| 227 Vars[1] = ShiftVar; | 229 Vars[1] = ShiftVar; |
| 228 } | 230 } |
| 229 | 231 |
| 230 InstARM32AdjustStack::InstARM32AdjustStack(Cfg *Func, Variable *SP, | 232 InstARM32AdjustStack::InstARM32AdjustStack(Cfg *Func, Variable *SP, |
| 231 SizeT Amount, Operand *SrcAmount) | 233 SizeT MyAmount, Operand *SrcAmount) |
| 232 : InstARM32(Func, InstARM32::Adjuststack, 2, SP), Amount(Amount) { | 234 : InstARM32(Func, InstARM32::Adjuststack, 2, SP), Amount(MyAmount) { |
| 233 addSource(SP); | 235 addSource(SP); |
| 234 addSource(SrcAmount); | 236 addSource(SrcAmount); |
| 235 } | 237 } |
| 236 | 238 |
| 237 InstARM32Br::InstARM32Br(Cfg *Func, const CfgNode *TargetTrue, | 239 InstARM32Br::InstARM32Br(Cfg *Func, const CfgNode *MyTargetTrue, |
| 238 const CfgNode *TargetFalse, | 240 const CfgNode *MyTargetFalse, |
| 239 const InstARM32Label *Label, CondARM32::Cond Pred) | 241 const InstARM32Label *MyLabel, CondARM32::Cond Pred) |
| 240 : InstARM32Pred(Func, InstARM32::Br, 0, nullptr, Pred), | 242 : InstARM32Pred(Func, InstARM32::Br, 0, nullptr, Pred), |
| 241 TargetTrue(TargetTrue), TargetFalse(TargetFalse), Label(Label) {} | 243 TargetTrue(MyTargetTrue), TargetFalse(MyTargetFalse), Label(MyLabel) {} |
| 242 | 244 |
| 243 bool InstARM32Br::optimizeBranch(const CfgNode *NextNode) { | 245 bool InstARM32Br::optimizeBranch(const CfgNode *NextNode) { |
| 244 // If there is no next block, then there can be no fallthrough to | 246 // If there is no next block, then there can be no fallthrough to |
| 245 // optimize. | 247 // optimize. |
| 246 if (NextNode == nullptr) | 248 if (NextNode == nullptr) |
| 247 return false; | 249 return false; |
| 248 // Intra-block conditional branches can't be optimized. | 250 // Intra-block conditional branches can't be optimized. |
| 249 if (Label) | 251 if (Label) |
| 250 return false; | 252 return false; |
| 251 // If there is no fallthrough node, such as a non-default case label | 253 // If there is no fallthrough node, such as a non-default case label |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 303 IceString InstARM32Label::getName(const Cfg *Func) const { | 305 IceString InstARM32Label::getName(const Cfg *Func) const { |
| 304 return ".L" + Func->getFunctionName() + "$local$__" + std::to_string(Number); | 306 return ".L" + Func->getFunctionName() + "$local$__" + std::to_string(Number); |
| 305 } | 307 } |
| 306 | 308 |
| 307 InstARM32Ldr::InstARM32Ldr(Cfg *Func, Variable *Dest, OperandARM32Mem *Mem, | 309 InstARM32Ldr::InstARM32Ldr(Cfg *Func, Variable *Dest, OperandARM32Mem *Mem, |
| 308 CondARM32::Cond Predicate) | 310 CondARM32::Cond Predicate) |
| 309 : InstARM32Pred(Func, InstARM32::Ldr, 1, Dest, Predicate) { | 311 : InstARM32Pred(Func, InstARM32::Ldr, 1, Dest, Predicate) { |
| 310 addSource(Mem); | 312 addSource(Mem); |
| 311 } | 313 } |
| 312 | 314 |
| 313 InstARM32Pop::InstARM32Pop(Cfg *Func, const VarList &Dests) | 315 InstARM32Pop::InstARM32Pop(Cfg *Func, const VarList &MyDests) |
| 314 : InstARM32(Func, InstARM32::Pop, 0, nullptr), Dests(Dests) { | 316 : InstARM32(Func, InstARM32::Pop, 0, nullptr), Dests(MyDests) { |
| 315 // Track modifications to Dests separately via FakeDefs. | 317 // Track modifications to Dests separately via FakeDefs. |
| 316 // Also, a pop instruction affects the stack pointer and so it should not | 318 // Also, a pop instruction affects the stack pointer and so it should not |
| 317 // be allowed to be automatically dead-code eliminated. This is automatic | 319 // be allowed to be automatically dead-code eliminated. This is automatic |
| 318 // since we leave the Dest as nullptr. | 320 // since we leave the Dest as nullptr. |
| 319 } | 321 } |
| 320 | 322 |
| 321 InstARM32Push::InstARM32Push(Cfg *Func, const VarList &Srcs) | 323 InstARM32Push::InstARM32Push(Cfg *Func, const VarList &Srcs) |
| 322 : InstARM32(Func, InstARM32::Push, Srcs.size(), nullptr) { | 324 : InstARM32(Func, InstARM32::Push, Srcs.size(), nullptr) { |
| 323 for (Variable *Source : Srcs) | 325 for (Variable *Source : Srcs) |
| 324 addSource(Source); | 326 addSource(Source); |
| 325 } | 327 } |
| 326 | 328 |
| 327 InstARM32Ret::InstARM32Ret(Cfg *Func, Variable *LR, Variable *Source) | 329 InstARM32Ret::InstARM32Ret(Cfg *Func, Variable *LR, Variable *Source) |
| 328 : InstARM32(Func, InstARM32::Ret, Source ? 2 : 1, nullptr) { | 330 : InstARM32(Func, InstARM32::Ret, Source ? 2 : 1, nullptr) { |
| 329 addSource(LR); | 331 addSource(LR); |
| 330 if (Source) | 332 if (Source) |
| 331 addSource(Source); | 333 addSource(Source); |
| 332 } | 334 } |
| 333 | 335 |
| 334 InstARM32Str::InstARM32Str(Cfg *Func, Variable *Value, OperandARM32Mem *Mem, | 336 InstARM32Str::InstARM32Str(Cfg *Func, Variable *Value, OperandARM32Mem *Mem, |
| 335 CondARM32::Cond Predicate) | 337 CondARM32::Cond Predicate) |
| 336 : InstARM32Pred(Func, InstARM32::Str, 2, nullptr, Predicate) { | 338 : InstARM32Pred(Func, InstARM32::Str, 2, nullptr, Predicate) { |
| 337 addSource(Value); | 339 addSource(Value); |
| 338 addSource(Mem); | 340 addSource(Mem); |
| 339 } | 341 } |
| 340 | 342 |
| 341 InstARM32Trap::InstARM32Trap(Cfg *Func) | 343 InstARM32Trap::InstARM32Trap(Cfg *Func) |
| 342 : InstARM32(Func, InstARM32::Trap, 0, nullptr) {} | 344 : InstARM32(Func, InstARM32::Trap, 0, nullptr) {} |
| 343 | 345 |
| 344 InstARM32Umull::InstARM32Umull(Cfg *Func, Variable *DestLo, Variable *DestHi, | 346 InstARM32Umull::InstARM32Umull(Cfg *Func, Variable *DestLo, Variable *MyDestHi, |
| 345 Variable *Src0, Variable *Src1, | 347 Variable *Src0, Variable *Src1, |
| 346 CondARM32::Cond Predicate) | 348 CondARM32::Cond Predicate) |
| 347 : InstARM32Pred(Func, InstARM32::Umull, 2, DestLo, Predicate), | 349 : InstARM32Pred(Func, InstARM32::Umull, 2, DestLo, Predicate), |
| 348 // DestHi is expected to have a FakeDef inserted by the lowering code. | 350 // DestHi is expected to have a FakeDef inserted by the lowering code. |
| 349 DestHi(DestHi) { | 351 DestHi(MyDestHi) { |
| 350 addSource(Src0); | 352 addSource(Src0); |
| 351 addSource(Src1); | 353 addSource(Src1); |
| 352 } | 354 } |
| 353 | 355 |
| 354 // ======================== Dump routines ======================== // | 356 // ======================== Dump routines ======================== // |
| 355 | 357 |
| 356 // Two-addr ops | 358 // Two-addr ops |
| 357 template <> const char *InstARM32Movt::Opcode = "movt"; | 359 template <> const char *InstARM32Movt::Opcode = "movt"; |
| 358 // Unary ops | 360 // Unary ops |
| 359 template <> const char *InstARM32Movw::Opcode = "movw"; | 361 template <> const char *InstARM32Movw::Opcode = "movw"; |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 393 Inst::dump(Func); | 395 Inst::dump(Func); |
| 394 } | 396 } |
| 395 | 397 |
| 396 template <> void InstARM32Mov::emit(const Cfg *Func) const { | 398 template <> void InstARM32Mov::emit(const Cfg *Func) const { |
| 397 if (!BuildDefs::dump()) | 399 if (!BuildDefs::dump()) |
| 398 return; | 400 return; |
| 399 Ostream &Str = Func->getContext()->getStrEmit(); | 401 Ostream &Str = Func->getContext()->getStrEmit(); |
| 400 assert(getSrcSize() == 1); | 402 assert(getSrcSize() == 1); |
| 401 Variable *Dest = getDest(); | 403 Variable *Dest = getDest(); |
| 402 if (Dest->hasReg()) { | 404 if (Dest->hasReg()) { |
| 403 IceString Opcode = "mov"; | 405 IceString MyOpcode = "mov"; |
| 404 Operand *Src0 = getSrc(0); | 406 Operand *Src0 = getSrc(0); |
| 405 if (const auto *Src0V = llvm::dyn_cast<Variable>(Src0)) { | 407 if (const auto *Src0V = llvm::dyn_cast<Variable>(Src0)) { |
| 406 if (!Src0V->hasReg()) { | 408 if (!Src0V->hasReg()) { |
| 407 Opcode = IceString("ldr"); // Always use the whole stack slot. | 409 MyOpcode = IceString("ldr"); // Always use the whole stack slot. |
| 408 } | 410 } |
| 409 } else { | 411 } else { |
| 410 if (llvm::isa<OperandARM32Mem>(Src0)) | 412 if (llvm::isa<OperandARM32Mem>(Src0)) |
| 411 Opcode = IceString("ldr") + getWidthString(Dest->getType()); | 413 MyOpcode = IceString("ldr") + getWidthString(Dest->getType()); |
| 412 } | 414 } |
| 413 Str << "\t" << Opcode << getPredicate() << "\t"; | 415 Str << "\t" << MyOpcode << getPredicate() << "\t"; |
| 414 getDest()->emit(Func); | 416 getDest()->emit(Func); |
| 415 Str << ", "; | 417 Str << ", "; |
| 416 getSrc(0)->emit(Func); | 418 getSrc(0)->emit(Func); |
| 417 } else { | 419 } else { |
| 418 Variable *Src0 = llvm::cast<Variable>(getSrc(0)); | 420 Variable *Src0 = llvm::cast<Variable>(getSrc(0)); |
| 419 assert(Src0->hasReg()); | 421 assert(Src0->hasReg()); |
| 420 Str << "\t" | 422 Str << "\t" |
| 421 << "str" << getPredicate() << "\t"; | 423 << "str" << getPredicate() << "\t"; |
| 422 Src0->emit(Func); | 424 Src0->emit(Func); |
| 423 Str << ", "; | 425 Str << ", "; |
| (...skipping 464 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 888 } else { | 890 } else { |
| 889 getOffset()->dump(Func, Str); | 891 getOffset()->dump(Func, Str); |
| 890 } | 892 } |
| 891 Str << "] AddrMode==" << getAddrMode(); | 893 Str << "] AddrMode==" << getAddrMode(); |
| 892 } | 894 } |
| 893 | 895 |
| 894 void OperandARM32FlexImm::emit(const Cfg *Func) const { | 896 void OperandARM32FlexImm::emit(const Cfg *Func) const { |
| 895 if (!BuildDefs::dump()) | 897 if (!BuildDefs::dump()) |
| 896 return; | 898 return; |
| 897 Ostream &Str = Func->getContext()->getStrEmit(); | 899 Ostream &Str = Func->getContext()->getStrEmit(); |
| 898 uint32_t Imm = getImm(); | 900 Str << "#" << Utils::rotateRight32(getImm(), 2 * getRotateAmt()); |
| 899 uint32_t RotateAmt = getRotateAmt(); | |
| 900 Str << "#" << Utils::rotateRight32(Imm, 2 * RotateAmt); | |
| 901 } | 901 } |
| 902 | 902 |
| 903 void OperandARM32FlexImm::dump(const Cfg * /* Func */, Ostream &Str) const { | 903 void OperandARM32FlexImm::dump(const Cfg * /* Func */, Ostream &Str) const { |
| 904 if (!BuildDefs::dump()) | 904 if (!BuildDefs::dump()) |
| 905 return; | 905 return; |
| 906 uint32_t Imm = getImm(); | 906 Str << "#(" << getImm() << " ror 2*" << getRotateAmt() << ")"; |
| 907 uint32_t RotateAmt = getRotateAmt(); | |
| 908 Str << "#(" << Imm << " ror 2*" << RotateAmt << ")"; | |
| 909 } | 907 } |
| 910 | 908 |
| 911 void OperandARM32FlexReg::emit(const Cfg *Func) const { | 909 void OperandARM32FlexReg::emit(const Cfg *Func) const { |
| 912 if (!BuildDefs::dump()) | 910 if (!BuildDefs::dump()) |
| 913 return; | 911 return; |
| 914 Ostream &Str = Func->getContext()->getStrEmit(); | 912 Ostream &Str = Func->getContext()->getStrEmit(); |
| 915 getReg()->emit(Func); | 913 getReg()->emit(Func); |
| 916 if (getShiftOp() != kNoShift) { | 914 if (getShiftOp() != kNoShift) { |
| 917 Str << ", " << InstARM32ShiftAttributes[getShiftOp()].EmitString << " "; | 915 Str << ", " << InstARM32ShiftAttributes[getShiftOp()].EmitString << " "; |
| 918 getShiftAmt()->emit(Func); | 916 getShiftAmt()->emit(Func); |
| 919 } | 917 } |
| 920 } | 918 } |
| 921 | 919 |
| 922 void OperandARM32FlexReg::dump(const Cfg *Func, Ostream &Str) const { | 920 void OperandARM32FlexReg::dump(const Cfg *Func, Ostream &Str) const { |
| 923 if (!BuildDefs::dump()) | 921 if (!BuildDefs::dump()) |
| 924 return; | 922 return; |
| 925 Variable *Reg = getReg(); | |
| 926 if (Func) | 923 if (Func) |
| 927 Reg->dump(Func); | 924 Reg->dump(Func); |
| 928 else | 925 else |
| 929 Reg->dump(Str); | 926 Reg->dump(Str); |
| 930 if (getShiftOp() != kNoShift) { | 927 if (getShiftOp() != kNoShift) { |
| 931 Str << ", " << InstARM32ShiftAttributes[getShiftOp()].EmitString << " "; | 928 Str << ", " << InstARM32ShiftAttributes[getShiftOp()].EmitString << " "; |
| 932 if (Func) | 929 if (Func) |
| 933 getShiftAmt()->dump(Func); | 930 getShiftAmt()->dump(Func); |
| 934 else | 931 else |
| 935 getShiftAmt()->dump(Str); | 932 getShiftAmt()->dump(Str); |
| 936 } | 933 } |
| 937 } | 934 } |
| 938 | 935 |
| 939 } // end of namespace Ice | 936 } // end of namespace Ice |
| OLD | NEW |