• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ART_COMPILER_UTILS_ARM_ASSEMBLER_ARM32_H_
18 #define ART_COMPILER_UTILS_ARM_ASSEMBLER_ARM32_H_
19 
20 #include <vector>
21 
22 #include "base/logging.h"
23 #include "constants_arm.h"
24 #include "utils/arm/managed_register_arm.h"
25 #include "utils/arm/assembler_arm.h"
26 #include "offsets.h"
27 #include "utils.h"
28 
29 namespace art {
30 namespace arm {
31 
32 class Arm32Assembler FINAL : public ArmAssembler {
33  public:
Arm32Assembler()34   Arm32Assembler() {
35   }
~Arm32Assembler()36   virtual ~Arm32Assembler() {}
37 
IsThumb()38   bool IsThumb() const OVERRIDE {
39     return false;
40   }
41 
42   // Data-processing instructions.
43   void and_(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
44 
45   void eor(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
46 
47   void sub(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
48   void subs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
49 
50   void rsb(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
51   void rsbs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
52 
53   void add(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
54 
55   void adds(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
56 
57   void adc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
58 
59   void sbc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
60 
61   void rsc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
62 
63   void tst(Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
64 
65   void teq(Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
66 
67   void cmp(Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
68 
69   void cmn(Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
70 
71   void orr(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
72   void orrs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
73 
74   void mov(Register rd, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
75   void movs(Register rd, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
76 
77   void bic(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
78 
79   void mvn(Register rd, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
80   void mvns(Register rd, const ShifterOperand& so, Condition cond = AL) OVERRIDE;
81 
82   // Miscellaneous data-processing instructions.
83   void clz(Register rd, Register rm, Condition cond = AL) OVERRIDE;
84   void movw(Register rd, uint16_t imm16, Condition cond = AL) OVERRIDE;
85   void movt(Register rd, uint16_t imm16, Condition cond = AL) OVERRIDE;
86 
87   // Multiply instructions.
88   void mul(Register rd, Register rn, Register rm, Condition cond = AL) OVERRIDE;
89   void mla(Register rd, Register rn, Register rm, Register ra,
90            Condition cond = AL) OVERRIDE;
91   void mls(Register rd, Register rn, Register rm, Register ra,
92            Condition cond = AL) OVERRIDE;
93   void umull(Register rd_lo, Register rd_hi, Register rn, Register rm,
94              Condition cond = AL) OVERRIDE;
95 
96   void sdiv(Register rd, Register rn, Register rm, Condition cond = AL) OVERRIDE;
97   void udiv(Register rd, Register rn, Register rm, Condition cond = AL) OVERRIDE;
98 
99   // Load/store instructions.
100   void ldr(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
101   void str(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
102 
103   void ldrb(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
104   void strb(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
105 
106   void ldrh(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
107   void strh(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
108 
109   void ldrsb(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
110   void ldrsh(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
111 
112   void ldrd(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
113   void strd(Register rd, const Address& ad, Condition cond = AL) OVERRIDE;
114 
115   void ldm(BlockAddressMode am, Register base,
116            RegList regs, Condition cond = AL) OVERRIDE;
117   void stm(BlockAddressMode am, Register base,
118            RegList regs, Condition cond = AL) OVERRIDE;
119 
120   void ldrex(Register rd, Register rn, Condition cond = AL) OVERRIDE;
121   void strex(Register rd, Register rt, Register rn, Condition cond = AL) OVERRIDE;
122 
123   // Miscellaneous instructions.
124   void clrex(Condition cond = AL) OVERRIDE;
125   void nop(Condition cond = AL) OVERRIDE;
126 
127   // Note that gdb sets breakpoints using the undefined instruction 0xe7f001f0.
128   void bkpt(uint16_t imm16) OVERRIDE;
129   void svc(uint32_t imm24) OVERRIDE;
130 
131   void cbz(Register rn, Label* target) OVERRIDE;
132   void cbnz(Register rn, Label* target) OVERRIDE;
133 
134   // Floating point instructions (VFPv3-D16 and VFPv3-D32 profiles).
135   void vmovsr(SRegister sn, Register rt, Condition cond = AL) OVERRIDE;
136   void vmovrs(Register rt, SRegister sn, Condition cond = AL) OVERRIDE;
137   void vmovsrr(SRegister sm, Register rt, Register rt2, Condition cond = AL) OVERRIDE;
138   void vmovrrs(Register rt, Register rt2, SRegister sm, Condition cond = AL) OVERRIDE;
139   void vmovdrr(DRegister dm, Register rt, Register rt2, Condition cond = AL) OVERRIDE;
140   void vmovrrd(Register rt, Register rt2, DRegister dm, Condition cond = AL) OVERRIDE;
141   void vmovs(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
142   void vmovd(DRegister dd, DRegister dm, Condition cond = AL) OVERRIDE;
143 
144   // Returns false if the immediate cannot be encoded.
145   bool vmovs(SRegister sd, float s_imm, Condition cond = AL) OVERRIDE;
146   bool vmovd(DRegister dd, double d_imm, Condition cond = AL) OVERRIDE;
147 
148   void vldrs(SRegister sd, const Address& ad, Condition cond = AL) OVERRIDE;
149   void vstrs(SRegister sd, const Address& ad, Condition cond = AL) OVERRIDE;
150   void vldrd(DRegister dd, const Address& ad, Condition cond = AL) OVERRIDE;
151   void vstrd(DRegister dd, const Address& ad, Condition cond = AL) OVERRIDE;
152 
153   void vadds(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
154   void vaddd(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
155   void vsubs(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
156   void vsubd(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
157   void vmuls(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
158   void vmuld(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
159   void vmlas(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
160   void vmlad(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
161   void vmlss(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
162   void vmlsd(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
163   void vdivs(SRegister sd, SRegister sn, SRegister sm, Condition cond = AL) OVERRIDE;
164   void vdivd(DRegister dd, DRegister dn, DRegister dm, Condition cond = AL) OVERRIDE;
165 
166   void vabss(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
167   void vabsd(DRegister dd, DRegister dm, Condition cond = AL) OVERRIDE;
168   void vnegs(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
169   void vnegd(DRegister dd, DRegister dm, Condition cond = AL) OVERRIDE;
170   void vsqrts(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
171   void vsqrtd(DRegister dd, DRegister dm, Condition cond = AL) OVERRIDE;
172 
173   void vcvtsd(SRegister sd, DRegister dm, Condition cond = AL) OVERRIDE;
174   void vcvtds(DRegister dd, SRegister sm, Condition cond = AL) OVERRIDE;
175   void vcvtis(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
176   void vcvtid(SRegister sd, DRegister dm, Condition cond = AL) OVERRIDE;
177   void vcvtsi(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
178   void vcvtdi(DRegister dd, SRegister sm, Condition cond = AL) OVERRIDE;
179   void vcvtus(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
180   void vcvtud(SRegister sd, DRegister dm, Condition cond = AL) OVERRIDE;
181   void vcvtsu(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
182   void vcvtdu(DRegister dd, SRegister sm, Condition cond = AL) OVERRIDE;
183 
184   void vcmps(SRegister sd, SRegister sm, Condition cond = AL) OVERRIDE;
185   void vcmpd(DRegister dd, DRegister dm, Condition cond = AL) OVERRIDE;
186   void vcmpsz(SRegister sd, Condition cond = AL) OVERRIDE;
187   void vcmpdz(DRegister dd, Condition cond = AL) OVERRIDE;
188   void vmstat(Condition cond = AL) OVERRIDE;  // VMRS APSR_nzcv, FPSCR
189 
190   void vpushs(SRegister reg, int nregs, Condition cond = AL) OVERRIDE;
191   void vpushd(DRegister reg, int nregs, Condition cond = AL) OVERRIDE;
192   void vpops(SRegister reg, int nregs, Condition cond = AL) OVERRIDE;
193   void vpopd(DRegister reg, int nregs, Condition cond = AL) OVERRIDE;
194 
195   // Branch instructions.
196   void b(Label* label, Condition cond = AL);
197   void bl(Label* label, Condition cond = AL);
198   void blx(Register rm, Condition cond = AL) OVERRIDE;
199   void bx(Register rm, Condition cond = AL) OVERRIDE;
200   void Lsl(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
201            Condition cond = AL) OVERRIDE;
202   void Lsr(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
203            Condition cond = AL) OVERRIDE;
204   void Asr(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
205            Condition cond = AL) OVERRIDE;
206   void Ror(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
207            Condition cond = AL) OVERRIDE;
208   void Rrx(Register rd, Register rm, bool setcc = false,
209            Condition cond = AL) OVERRIDE;
210 
211   void Lsl(Register rd, Register rm, Register rn, bool setcc = false,
212            Condition cond = AL) OVERRIDE;
213   void Lsr(Register rd, Register rm, Register rn, bool setcc = false,
214            Condition cond = AL) OVERRIDE;
215   void Asr(Register rd, Register rm, Register rn, bool setcc = false,
216            Condition cond = AL) OVERRIDE;
217   void Ror(Register rd, Register rm, Register rn, bool setcc = false,
218            Condition cond = AL) OVERRIDE;
219 
220   void Push(Register rd, Condition cond = AL) OVERRIDE;
221   void Pop(Register rd, Condition cond = AL) OVERRIDE;
222 
223   void PushList(RegList regs, Condition cond = AL) OVERRIDE;
224   void PopList(RegList regs, Condition cond = AL) OVERRIDE;
225 
226   void Mov(Register rd, Register rm, Condition cond = AL) OVERRIDE;
227 
228   void CompareAndBranchIfZero(Register r, Label* label) OVERRIDE;
229   void CompareAndBranchIfNonZero(Register r, Label* label) OVERRIDE;
230 
231 
232   // Macros.
233   // Add signed constant value to rd. May clobber IP.
234   void AddConstant(Register rd, int32_t value, Condition cond = AL) OVERRIDE;
235   void AddConstant(Register rd, Register rn, int32_t value,
236                    Condition cond = AL) OVERRIDE;
237   void AddConstantSetFlags(Register rd, Register rn, int32_t value,
238                            Condition cond = AL) OVERRIDE;
239   void AddConstantWithCarry(Register rd, Register rn, int32_t value,
240                             Condition cond = AL) {}
241 
242   // Load and Store. May clobber IP.
243   void LoadImmediate(Register rd, int32_t value, Condition cond = AL) OVERRIDE;
244   void LoadSImmediate(SRegister sd, float value, Condition cond = AL) {}
245   void LoadDImmediate(DRegister dd, double value,
246                       Register scratch, Condition cond = AL) {}
247   void MarkExceptionHandler(Label* label) OVERRIDE;
248   void LoadFromOffset(LoadOperandType type,
249                       Register reg,
250                       Register base,
251                       int32_t offset,
252                       Condition cond = AL) OVERRIDE;
253   void StoreToOffset(StoreOperandType type,
254                      Register reg,
255                      Register base,
256                      int32_t offset,
257                      Condition cond = AL) OVERRIDE;
258   void LoadSFromOffset(SRegister reg,
259                        Register base,
260                        int32_t offset,
261                        Condition cond = AL) OVERRIDE;
262   void StoreSToOffset(SRegister reg,
263                       Register base,
264                       int32_t offset,
265                       Condition cond = AL) OVERRIDE;
266   void LoadDFromOffset(DRegister reg,
267                        Register base,
268                        int32_t offset,
269                        Condition cond = AL) OVERRIDE;
270   void StoreDToOffset(DRegister reg,
271                       Register base,
272                       int32_t offset,
273                       Condition cond = AL) OVERRIDE;
274 
275 
276   static bool IsInstructionForExceptionHandling(uword pc);
277 
278   // Emit data (e.g. encoded instruction or immediate) to the
279   // instruction stream.
280   void Emit(int32_t value);
281   void Bind(Label* label) OVERRIDE;
282 
283   void MemoryBarrier(ManagedRegister scratch) OVERRIDE;
284 
285  private:
286   void EmitType01(Condition cond,
287                   int type,
288                   Opcode opcode,
289                   int set_cc,
290                   Register rn,
291                   Register rd,
292                   const ShifterOperand& so);
293 
294   void EmitType5(Condition cond, int offset, bool link);
295 
296   void EmitMemOp(Condition cond,
297                  bool load,
298                  bool byte,
299                  Register rd,
300                  const Address& ad);
301 
302   void EmitMemOpAddressMode3(Condition cond,
303                              int32_t mode,
304                              Register rd,
305                              const Address& ad);
306 
307   void EmitMultiMemOp(Condition cond,
308                       BlockAddressMode am,
309                       bool load,
310                       Register base,
311                       RegList regs);
312 
313   void EmitShiftImmediate(Condition cond,
314                           Shift opcode,
315                           Register rd,
316                           Register rm,
317                           const ShifterOperand& so);
318 
319   void EmitShiftRegister(Condition cond,
320                          Shift opcode,
321                          Register rd,
322                          Register rm,
323                          const ShifterOperand& so);
324 
325   void EmitMulOp(Condition cond,
326                  int32_t opcode,
327                  Register rd,
328                  Register rn,
329                  Register rm,
330                  Register rs);
331 
332   void EmitVFPsss(Condition cond,
333                   int32_t opcode,
334                   SRegister sd,
335                   SRegister sn,
336                   SRegister sm);
337 
338   void EmitVFPddd(Condition cond,
339                   int32_t opcode,
340                   DRegister dd,
341                   DRegister dn,
342                   DRegister dm);
343 
344   void EmitVFPsd(Condition cond,
345                  int32_t opcode,
346                  SRegister sd,
347                  DRegister dm);
348 
349   void EmitVFPds(Condition cond,
350                  int32_t opcode,
351                  DRegister dd,
352                  SRegister sm);
353 
354   void EmitVPushPop(uint32_t reg, int nregs, bool push, bool dbl, Condition cond);
355 
356   void EmitBranch(Condition cond, Label* label, bool link);
357   static int32_t EncodeBranchOffset(int offset, int32_t inst);
358   static int DecodeBranchOffset(int32_t inst);
359   int32_t EncodeTstOffset(int offset, int32_t inst);
360   int DecodeTstOffset(int32_t inst);
361 };
362 
363 }  // namespace arm
364 }  // namespace art
365 
366 #endif  // ART_COMPILER_UTILS_ARM_ASSEMBLER_ARM32_H_
367