OLD | NEW |
1 //===- subzero/src/IceAssemblerARM32.cpp - Assembler for ARM32 --*- C++ -*-===// | 1 //===- subzero/src/IceAssemblerARM32.cpp - Assembler for ARM32 --*- C++ -*-===// |
2 // | 2 // |
3 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 3 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
4 // for details. All rights reserved. Use of this source code is governed by a | 4 // for details. All rights reserved. Use of this source code is governed by a |
5 // BSD-style license that can be found in the LICENSE file. | 5 // BSD-style license that can be found in the LICENSE file. |
6 // | 6 // |
7 // Modified by the Subzero authors. | 7 // Modified by the Subzero authors. |
8 // | 8 // |
9 //===----------------------------------------------------------------------===// | 9 //===----------------------------------------------------------------------===// |
10 // | 10 // |
(...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
263 Utils::IsInt(kBranchOffsetBits, Offset >> 2); | 263 Utils::IsInt(kBranchOffsetBits, Offset >> 2); |
264 } | 264 } |
265 | 265 |
266 } // end of anonymous namespace | 266 } // end of anonymous namespace |
267 | 267 |
268 namespace Ice { | 268 namespace Ice { |
269 namespace ARM32 { | 269 namespace ARM32 { |
270 | 270 |
271 size_t MoveRelocatableFixup::emit(GlobalContext *Ctx, | 271 size_t MoveRelocatableFixup::emit(GlobalContext *Ctx, |
272 const Assembler &Asm) const { | 272 const Assembler &Asm) const { |
273 static constexpr const size_t FixupSize = sizeof(IValueT); | |
274 if (!BuildDefs::dump()) | 273 if (!BuildDefs::dump()) |
275 return FixupSize; | 274 return InstARM32::InstSize; |
276 Ostream &Str = Ctx->getStrEmit(); | 275 Ostream &Str = Ctx->getStrEmit(); |
277 IValueT Inst = Asm.load<IValueT>(position()); | 276 IValueT Inst = Asm.load<IValueT>(position()); |
278 Str << "\tmov" << (kind() == llvm::ELF::R_ARM_MOVW_ABS_NC ? "w" : "t") << "\t" | 277 Str << "\tmov" << (kind() == llvm::ELF::R_ARM_MOVW_ABS_NC ? "w" : "t") << "\t" |
279 << RegARM32::RegNames[(Inst >> kRdShift) & 0xF] | 278 << RegARM32::RegNames[(Inst >> kRdShift) & 0xF] |
280 << ", #:" << (kind() == llvm::ELF::R_ARM_MOVW_ABS_NC ? "lower" : "upper") | 279 << ", #:" << (kind() == llvm::ELF::R_ARM_MOVW_ABS_NC ? "lower" : "upper") |
281 << "16:" << symbol(Ctx) << "\t@ .word " | 280 << "16:" << symbol(Ctx) << "\t@ .word " |
282 << llvm::format_hex_no_prefix(Inst, 8) << "\n"; | 281 << llvm::format_hex_no_prefix(Inst, 8) << "\n"; |
283 return FixupSize; | 282 return InstARM32::InstSize; |
284 } | 283 } |
285 | 284 |
286 MoveRelocatableFixup *AssemblerARM32::createMoveFixup(bool IsMovW, | 285 MoveRelocatableFixup *AssemblerARM32::createMoveFixup(bool IsMovW, |
287 const Constant *Value) { | 286 const Constant *Value) { |
288 MoveRelocatableFixup *F = | 287 MoveRelocatableFixup *F = |
289 new (allocate<MoveRelocatableFixup>()) MoveRelocatableFixup(); | 288 new (allocate<MoveRelocatableFixup>()) MoveRelocatableFixup(); |
290 F->set_kind(IsMovW ? llvm::ELF::R_ARM_MOVW_ABS_NC | 289 F->set_kind(IsMovW ? llvm::ELF::R_ARM_MOVW_ABS_NC |
291 : llvm::ELF::R_ARM_MOVT_ABS); | 290 : llvm::ELF::R_ARM_MOVT_ABS); |
292 F->set_value(Value); | 291 F->set_value(Value); |
293 Buffer.installFixup(F); | 292 Buffer.installFixup(F); |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
353 IOffsetT Position = L->getLinkPosition(); | 352 IOffsetT Position = L->getLinkPosition(); |
354 IOffsetT Dest = BoundPc - Position; | 353 IOffsetT Dest = BoundPc - Position; |
355 IValueT Inst = Buffer.load<IValueT>(Position); | 354 IValueT Inst = Buffer.load<IValueT>(Position); |
356 Buffer.store<IValueT>(Position, encodeBranchOffset(Dest, Inst)); | 355 Buffer.store<IValueT>(Position, encodeBranchOffset(Dest, Inst)); |
357 L->setPosition(decodeBranchOffset(Inst)); | 356 L->setPosition(decodeBranchOffset(Inst)); |
358 } | 357 } |
359 L->bindTo(BoundPc); | 358 L->bindTo(BoundPc); |
360 } | 359 } |
361 | 360 |
362 void AssemblerARM32::emitTextInst(const std::string &Text, SizeT InstSize) { | 361 void AssemblerARM32::emitTextInst(const std::string &Text, SizeT InstSize) { |
363 AssemblerBuffer::EnsureCapacity ensured(&Buffer); | |
364 AssemblerFixup *F = createTextFixup(Text, InstSize); | 362 AssemblerFixup *F = createTextFixup(Text, InstSize); |
365 emitFixup(F); | 363 emitFixup(F); |
366 for (SizeT I = 0; I < InstSize; ++I) | 364 for (SizeT I = 0; I < InstSize; ++I) { |
| 365 AssemblerBuffer::EnsureCapacity ensured(&Buffer); |
367 Buffer.emit<char>(0); | 366 Buffer.emit<char>(0); |
| 367 } |
368 } | 368 } |
369 | 369 |
370 void AssemblerARM32::emitType01(CondARM32::Cond Cond, IValueT Type, | 370 void AssemblerARM32::emitType01(CondARM32::Cond Cond, IValueT Type, |
371 IValueT Opcode, bool SetCc, IValueT Rn, | 371 IValueT Opcode, bool SetCc, IValueT Rn, |
372 IValueT Rd, IValueT Imm12) { | 372 IValueT Rd, IValueT Imm12) { |
373 if (!isGPRRegisterDefined(Rd) || !isConditionDefined(Cond)) | 373 if (!isGPRRegisterDefined(Rd) || !isConditionDefined(Cond)) |
374 return setNeedsTextFixup(); | 374 return setNeedsTextFixup(); |
375 AssemblerBuffer::EnsureCapacity ensured(&Buffer); | 375 AssemblerBuffer::EnsureCapacity ensured(&Buffer); |
376 const IValueT Encoding = (encodeCondition(Cond) << kConditionShift) | | 376 const IValueT Encoding = (encodeCondition(Cond) << kConditionShift) | |
377 (Type << kTypeShift) | (Opcode << kOpcodeShift) | | 377 (Type << kTypeShift) | (Opcode << kOpcodeShift) | |
378 (encodeBool(SetCc) << kSShift) | (Rn << kRnShift) | | 378 (encodeBool(SetCc) << kSShift) | (Rn << kRnShift) | |
379 (Rd << kRdShift) | Imm12; | 379 (Rd << kRdShift) | Imm12; |
380 emitInst(Encoding); | 380 emitInst(Encoding); |
381 } | 381 } |
382 | 382 |
383 void AssemblerARM32::emitType01(IValueT Opcode, const Operand *OpRd, | 383 void AssemblerARM32::emitType01(IValueT Opcode, const Operand *OpRd, |
384 const Operand *OpRn, const Operand *OpSrc1, | 384 const Operand *OpRn, const Operand *OpSrc1, |
385 bool SetFlags, CondARM32::Cond Cond, | 385 bool SetFlags, CondARM32::Cond Cond, |
386 Type01Checks RuleChecks) { | 386 Type01Checks RuleChecks) { |
387 IValueT Rd; | 387 IValueT Rd; |
388 if (decodeOperand(OpRd, Rd) != DecodedAsRegister) | 388 if (decodeOperand(OpRd, Rd) != DecodedAsRegister) |
389 return setNeedsTextFixup(); | 389 return setNeedsTextFixup(); |
390 IValueT Rn; | 390 IValueT Rn; |
391 if (decodeOperand(OpRn, Rn) != DecodedAsRegister) | 391 if (decodeOperand(OpRn, Rn) != DecodedAsRegister) |
392 return setNeedsTextFixup(); | 392 return setNeedsTextFixup(); |
393 emitType01(Opcode, Rd, Rn, OpSrc1, SetFlags, Cond, RuleChecks); | 393 emitType01(Opcode, Rd, Rn, OpSrc1, SetFlags, Cond, RuleChecks); |
394 } | 394 } |
395 | 395 |
396 void AssemblerARM32::emitType01(IValueT Opcode, IValueT Rd, | 396 void AssemblerARM32::emitType01(IValueT Opcode, IValueT Rd, IValueT Rn, |
397 IValueT Rn, const Operand *OpSrc1, | 397 const Operand *OpSrc1, bool SetFlags, |
398 bool SetFlags, CondARM32::Cond Cond, | 398 CondARM32::Cond Cond, Type01Checks RuleChecks) { |
399 Type01Checks RuleChecks) { | |
400 switch (RuleChecks) { | 399 switch (RuleChecks) { |
401 case NoChecks: | 400 case NoChecks: |
402 break; | 401 break; |
403 case RdIsPcAndSetFlags: | 402 case RdIsPcAndSetFlags: |
404 if (((Rd == RegARM32::Encoded_Reg_pc) && SetFlags)) | 403 if (((Rd == RegARM32::Encoded_Reg_pc) && SetFlags)) |
405 // Conditions of rule violated. | 404 // Conditions of rule violated. |
406 return setNeedsTextFixup(); | 405 return setNeedsTextFixup(); |
407 break; | 406 break; |
408 } | 407 } |
409 | 408 |
(...skipping 560 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
970 // tst<c> <Rn>, #<RotatedImm8> | 969 // tst<c> <Rn>, #<RotatedImm8> |
971 // | 970 // |
972 // cccc00110001nnnn0000iiiiiiiiiiii where cccc=Cond, nnnn=Rn, and | 971 // cccc00110001nnnn0000iiiiiiiiiiii where cccc=Cond, nnnn=Rn, and |
973 // iiiiiiiiiiii defines RotatedImm8. | 972 // iiiiiiiiiiii defines RotatedImm8. |
974 constexpr IValueT Opcode = B3; // ie. 1000 | 973 constexpr IValueT Opcode = B3; // ie. 1000 |
975 emitCompareOp(Opcode, OpRn, OpSrc1, Cond); | 974 emitCompareOp(Opcode, OpRn, OpSrc1, Cond); |
976 } | 975 } |
977 | 976 |
978 } // end of namespace ARM32 | 977 } // end of namespace ARM32 |
979 } // end of namespace Ice | 978 } // end of namespace Ice |
OLD | NEW |