| OLD | NEW |
| 1 //===- subzero/src/IceAssemblerARM32.h - Assembler for ARM32 ----*- C++ -*-===// | 1 //===- subzero/src/IceAssemblerARM32.h - 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 21 matching lines...) Expand all Loading... |
| 32 #include "IceDefs.h" | 32 #include "IceDefs.h" |
| 33 #include "IceFixups.h" | 33 #include "IceFixups.h" |
| 34 #include "IceInstARM32.h" | 34 #include "IceInstARM32.h" |
| 35 #include "IceRegistersARM32.h" | 35 #include "IceRegistersARM32.h" |
| 36 #include "IceTargetLowering.h" | 36 #include "IceTargetLowering.h" |
| 37 | 37 |
| 38 namespace Ice { | 38 namespace Ice { |
| 39 namespace ARM32 { | 39 namespace ARM32 { |
| 40 | 40 |
| 41 class AssemblerARM32 : public Assembler { | 41 class AssemblerARM32 : public Assembler { |
| 42 AssemblerARM32() = delete; |
| 42 AssemblerARM32(const AssemblerARM32 &) = delete; | 43 AssemblerARM32(const AssemblerARM32 &) = delete; |
| 43 AssemblerARM32 &operator=(const AssemblerARM32 &) = delete; | 44 AssemblerARM32 &operator=(const AssemblerARM32 &) = delete; |
| 44 | 45 |
| 45 public: | 46 public: |
| 46 explicit AssemblerARM32(GlobalContext *Ctx, bool use_far_branches = false) | 47 explicit AssemblerARM32(GlobalContext *Ctx, bool use_far_branches = false) |
| 47 : Assembler(Asm_ARM32, Ctx) { | 48 : Assembler(Asm_ARM32, Ctx) { |
| 48 // TODO(kschimpf): Add mode if needed when branches are handled. | 49 // TODO(kschimpf): Add mode if needed when branches are handled. |
| 49 (void)use_far_branches; | 50 (void)use_far_branches; |
| 50 } | 51 } |
| 51 ~AssemblerARM32() override = default; | 52 ~AssemblerARM32() override { |
| 53 if (BuildDefs::asserts()) { |
| 54 for (const Label *Label : CfgNodeLabels) { |
| 55 Label->finalCheck(); |
| 56 } |
| 57 for (const Label *Label : LocalLabels) { |
| 58 Label->finalCheck(); |
| 59 } |
| 60 } |
| 61 } |
| 52 | 62 |
| 53 void alignFunction() override { | 63 void alignFunction() override { |
| 54 const SizeT Align = 1 << getBundleAlignLog2Bytes(); | 64 const SizeT Align = 1 << getBundleAlignLog2Bytes(); |
| 55 SizeT BytesNeeded = Utils::OffsetToAlignment(Buffer.getPosition(), Align); | 65 SizeT BytesNeeded = Utils::OffsetToAlignment(Buffer.getPosition(), Align); |
| 56 constexpr uint32_t UndefinedInst = 0xe7fedef0; // udf #60896 | 66 constexpr uint32_t UndefinedInst = 0xe7fedef0; // udf #60896 |
| 57 constexpr SizeT InstSize = sizeof(int32_t); | 67 constexpr SizeT InstSize = sizeof(int32_t); |
| 58 assert(BytesNeeded % InstSize == 0); | 68 assert(BytesNeeded % InstSize == 0); |
| 59 while (BytesNeeded > 0) { | 69 while (BytesNeeded > 0) { |
| 60 AssemblerBuffer::EnsureCapacity ensured(&Buffer); | 70 AssemblerBuffer::EnsureCapacity ensured(&Buffer); |
| 61 emitInst(UndefinedInst); | 71 emitInst(UndefinedInst); |
| (...skipping 15 matching lines...) Expand all Loading... |
| 77 void padWithNop(intptr_t Padding) override { | 87 void padWithNop(intptr_t Padding) override { |
| 78 (void)Padding; | 88 (void)Padding; |
| 79 llvm_unreachable("Not yet implemented."); | 89 llvm_unreachable("Not yet implemented."); |
| 80 } | 90 } |
| 81 | 91 |
| 82 Ice::Label *getCfgNodeLabel(SizeT NodeNumber) override { | 92 Ice::Label *getCfgNodeLabel(SizeT NodeNumber) override { |
| 83 assert(NodeNumber < CfgNodeLabels.size()); | 93 assert(NodeNumber < CfgNodeLabels.size()); |
| 84 return CfgNodeLabels[NodeNumber]; | 94 return CfgNodeLabels[NodeNumber]; |
| 85 } | 95 } |
| 86 | 96 |
| 87 void bindCfgNodeLabel(SizeT NodeNumber) override { | 97 void bindCfgNodeLabel(const CfgNode *Node) override; |
| 88 assert(!getPreliminary()); | 98 |
| 89 Label *L = getOrCreateCfgNodeLabel(NodeNumber); | 99 void bindLocalLabel(SizeT Number) { |
| 90 this->bind(L); | 100 Label *L = getOrCreateLocalLabel(Number); |
| 101 if (!getPreliminary()) |
| 102 this->bind(L); |
| 91 } | 103 } |
| 92 | 104 |
| 93 bool fixupIsPCRel(FixupKind Kind) const override { | 105 bool fixupIsPCRel(FixupKind Kind) const override { |
| 94 (void)Kind; | 106 (void)Kind; |
| 95 // TODO(kschimpf) Decide if we need this. | 107 // TODO(kschimpf) Decide if we need this. |
| 96 return false; | 108 return false; |
| 97 } | 109 } |
| 98 | 110 |
| 99 void bind(Label *label); | 111 void bind(Label *label); |
| 100 | 112 |
| (...skipping 12 matching lines...) Expand all Loading... |
| 113 | 125 |
| 114 void str(const Operand *OpRt, const Operand *OpAddress, CondARM32::Cond Cond); | 126 void str(const Operand *OpRt, const Operand *OpAddress, CondARM32::Cond Cond); |
| 115 | 127 |
| 116 void sub(const Operand *OpRd, const Operand *OpRn, const Operand *OpSrc1, | 128 void sub(const Operand *OpRd, const Operand *OpRn, const Operand *OpSrc1, |
| 117 bool SetFlags, CondARM32::Cond Cond); | 129 bool SetFlags, CondARM32::Cond Cond); |
| 118 | 130 |
| 119 static bool classof(const Assembler *Asm) { | 131 static bool classof(const Assembler *Asm) { |
| 120 return Asm->getKind() == Asm_ARM32; | 132 return Asm->getKind() == Asm_ARM32; |
| 121 } | 133 } |
| 122 | 134 |
| 123 void emitTextInst(const std::string &Text); | 135 void emitTextInst(const std::string &Text, SizeT InstSize = sizeof(uint32_t)); |
| 124 | 136 |
| 125 private: | 137 private: |
| 126 // A vector of pool-allocated x86 labels for CFG nodes. | 138 // A vector of pool-allocated x86 labels for CFG nodes. |
| 127 using LabelVector = std::vector<Label *>; | 139 using LabelVector = std::vector<Label *>; |
| 128 LabelVector CfgNodeLabels; | 140 LabelVector CfgNodeLabels; |
| 141 // A vector of pool-allocated x86 labels for Local labels. |
| 142 LabelVector LocalLabels; |
| 129 | 143 |
| 130 Label *getOrCreateLabel(SizeT Number, LabelVector &Labels); | 144 Label *getOrCreateLabel(SizeT Number, LabelVector &Labels); |
| 131 Label *getOrCreateCfgNodeLabel(SizeT NodeNumber) { | 145 Label *getOrCreateCfgNodeLabel(SizeT NodeNumber) { |
| 132 return getOrCreateLabel(NodeNumber, CfgNodeLabels); | 146 return getOrCreateLabel(NodeNumber, CfgNodeLabels); |
| 133 } | 147 } |
| 148 Label *getOrCreateLocalLabel(SizeT Number) { |
| 149 return getOrCreateLabel(Number, LocalLabels); |
| 150 } |
| 134 | 151 |
| 135 void emitInst(uint32_t Value) { Buffer.emit<uint32_t>(Value); } | 152 void emitInst(uint32_t Value) { Buffer.emit<uint32_t>(Value); } |
| 136 | 153 |
| 137 // Pattern cccctttoooosnnnnddddiiiiiiiiiiii where cccc=Cond, ttt=Type, | 154 // Pattern cccctttoooosnnnnddddiiiiiiiiiiii where cccc=Cond, ttt=Type, |
| 138 // oooo=Opcode, nnnn=Rn, dddd=Rd, iiiiiiiiiiii=imm12 (See ARM section A5.2.3). | 155 // oooo=Opcode, nnnn=Rn, dddd=Rd, iiiiiiiiiiii=imm12 (See ARM section A5.2.3). |
| 139 void emitType01(CondARM32::Cond Cond, uint32_t Type, uint32_t Opcode, | 156 void emitType01(CondARM32::Cond Cond, uint32_t Type, uint32_t Opcode, |
| 140 bool SetCc, uint32_t Rn, uint32_t Rd, uint32_t imm12); | 157 bool SetCc, uint32_t Rn, uint32_t Rd, uint32_t imm12); |
| 141 | 158 |
| 142 // Pattern ccccoooaabalnnnnttttaaaaaaaaaaaa where cccc=Cond, ooo=InstType, | 159 // Pattern ccccoooaabalnnnnttttaaaaaaaaaaaa where cccc=Cond, ooo=InstType, |
| 143 // l=isLoad, b=isByte, and aaa0a0aaaa0000aaaaaaaaaaaa=Address. Note that | 160 // l=isLoad, b=isByte, and aaa0a0aaaa0000aaaaaaaaaaaa=Address. Note that |
| 144 // Address is assumed to be defined by decodeAddress() in | 161 // Address is assumed to be defined by decodeAddress() in |
| 145 // IceAssemblerARM32.cpp. | 162 // IceAssemblerARM32.cpp. |
| 146 void emitMemOp(CondARM32::Cond Cond, uint32_t InstType, bool IsLoad, | 163 void emitMemOp(CondARM32::Cond Cond, uint32_t InstType, bool IsLoad, |
| 147 bool IsByte, uint32_t Rt, uint32_t Address); | 164 bool IsByte, uint32_t Rt, uint32_t Address); |
| 148 }; | 165 }; |
| 149 | 166 |
| 150 } // end of namespace ARM32 | 167 } // end of namespace ARM32 |
| 151 } // end of namespace Ice | 168 } // end of namespace Ice |
| 152 | 169 |
| 153 #endif // SUBZERO_SRC_ICEASSEMBLERARM32_H | 170 #endif // SUBZERO_SRC_ICEASSEMBLERARM32_H |
| OLD | NEW |