blob: e571e72402dc0c96d819e85a09e2f8e51c4fbe2f [file] [log] [blame]
Roland Levillain1a28fc42014-11-13 18:03:06 +00001/*
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#include "assembler_thumb2.h"
18
19#include "base/stl_util.h"
20#include "utils/assembler_test.h"
21
22namespace art {
23
24class AssemblerThumb2Test : public AssemblerTest<arm::Thumb2Assembler,
Andreas Gampe851df202014-11-12 14:05:46 -080025 arm::Register, arm::SRegister,
26 uint32_t> {
Roland Levillain1a28fc42014-11-13 18:03:06 +000027 protected:
28 std::string GetArchitectureString() OVERRIDE {
29 return "arm";
30 }
31
32 std::string GetAssemblerParameters() OVERRIDE {
Andreas Gampe513ea0c2015-02-02 13:17:52 -080033 return " -march=armv7-a -mcpu=cortex-a15 -mfpu=neon -mthumb";
34 }
35
36 const char* GetAssemblyHeader() OVERRIDE {
37 return kThumb2AssemblyHeader;
Roland Levillain1a28fc42014-11-13 18:03:06 +000038 }
39
40 std::string GetDisassembleParameters() OVERRIDE {
Andreas Gampe513ea0c2015-02-02 13:17:52 -080041 return " -D -bbinary -marm --disassembler-options=force-thumb --no-show-raw-insn";
Roland Levillain1a28fc42014-11-13 18:03:06 +000042 }
43
44 void SetUpHelpers() OVERRIDE {
45 if (registers_.size() == 0) {
46 registers_.insert(end(registers_),
47 { // NOLINT(whitespace/braces)
48 new arm::Register(arm::R0),
49 new arm::Register(arm::R1),
50 new arm::Register(arm::R2),
51 new arm::Register(arm::R3),
52 new arm::Register(arm::R4),
53 new arm::Register(arm::R5),
54 new arm::Register(arm::R6),
55 new arm::Register(arm::R7),
56 new arm::Register(arm::R8),
57 new arm::Register(arm::R9),
58 new arm::Register(arm::R10),
59 new arm::Register(arm::R11),
60 new arm::Register(arm::R12),
61 new arm::Register(arm::R13),
62 new arm::Register(arm::R14),
63 new arm::Register(arm::R15)
64 });
65 }
66 }
67
68 void TearDown() OVERRIDE {
69 AssemblerTest::TearDown();
70 STLDeleteElements(&registers_);
71 }
72
73 std::vector<arm::Register*> GetRegisters() OVERRIDE {
74 return registers_;
75 }
76
77 uint32_t CreateImmediate(int64_t imm_value) OVERRIDE {
78 return imm_value;
79 }
80
81 private:
82 std::vector<arm::Register*> registers_;
Andreas Gampe513ea0c2015-02-02 13:17:52 -080083
84 static constexpr const char* kThumb2AssemblyHeader = ".syntax unified\n.thumb\n";
Roland Levillain1a28fc42014-11-13 18:03:06 +000085};
86
87
88TEST_F(AssemblerThumb2Test, Toolchain) {
89 EXPECT_TRUE(CheckTools());
90}
91
92
93TEST_F(AssemblerThumb2Test, Sbfx) {
94 GetAssembler()->sbfx(arm::R0, arm::R1, 0, 1);
95 GetAssembler()->sbfx(arm::R0, arm::R1, 0, 8);
96 GetAssembler()->sbfx(arm::R0, arm::R1, 0, 16);
97 GetAssembler()->sbfx(arm::R0, arm::R1, 0, 32);
98
99 GetAssembler()->sbfx(arm::R0, arm::R1, 8, 1);
100 GetAssembler()->sbfx(arm::R0, arm::R1, 8, 8);
101 GetAssembler()->sbfx(arm::R0, arm::R1, 8, 16);
102 GetAssembler()->sbfx(arm::R0, arm::R1, 8, 24);
103
104 GetAssembler()->sbfx(arm::R0, arm::R1, 16, 1);
105 GetAssembler()->sbfx(arm::R0, arm::R1, 16, 8);
106 GetAssembler()->sbfx(arm::R0, arm::R1, 16, 16);
107
108 GetAssembler()->sbfx(arm::R0, arm::R1, 31, 1);
109
110 const char* expected =
111 "sbfx r0, r1, #0, #1\n"
112 "sbfx r0, r1, #0, #8\n"
113 "sbfx r0, r1, #0, #16\n"
114 "sbfx r0, r1, #0, #32\n"
115
116 "sbfx r0, r1, #8, #1\n"
117 "sbfx r0, r1, #8, #8\n"
118 "sbfx r0, r1, #8, #16\n"
119 "sbfx r0, r1, #8, #24\n"
120
121 "sbfx r0, r1, #16, #1\n"
122 "sbfx r0, r1, #16, #8\n"
123 "sbfx r0, r1, #16, #16\n"
124
125 "sbfx r0, r1, #31, #1\n";
126 DriverStr(expected, "sbfx");
127}
128
Roland Levillain981e4542014-11-14 11:47:14 +0000129TEST_F(AssemblerThumb2Test, Ubfx) {
130 GetAssembler()->ubfx(arm::R0, arm::R1, 0, 1);
131 GetAssembler()->ubfx(arm::R0, arm::R1, 0, 8);
132 GetAssembler()->ubfx(arm::R0, arm::R1, 0, 16);
133 GetAssembler()->ubfx(arm::R0, arm::R1, 0, 32);
134
135 GetAssembler()->ubfx(arm::R0, arm::R1, 8, 1);
136 GetAssembler()->ubfx(arm::R0, arm::R1, 8, 8);
137 GetAssembler()->ubfx(arm::R0, arm::R1, 8, 16);
138 GetAssembler()->ubfx(arm::R0, arm::R1, 8, 24);
139
140 GetAssembler()->ubfx(arm::R0, arm::R1, 16, 1);
141 GetAssembler()->ubfx(arm::R0, arm::R1, 16, 8);
142 GetAssembler()->ubfx(arm::R0, arm::R1, 16, 16);
143
144 GetAssembler()->ubfx(arm::R0, arm::R1, 31, 1);
145
146 const char* expected =
147 "ubfx r0, r1, #0, #1\n"
148 "ubfx r0, r1, #0, #8\n"
149 "ubfx r0, r1, #0, #16\n"
150 "ubfx r0, r1, #0, #32\n"
151
152 "ubfx r0, r1, #8, #1\n"
153 "ubfx r0, r1, #8, #8\n"
154 "ubfx r0, r1, #8, #16\n"
155 "ubfx r0, r1, #8, #24\n"
156
157 "ubfx r0, r1, #16, #1\n"
158 "ubfx r0, r1, #16, #8\n"
159 "ubfx r0, r1, #16, #16\n"
160
161 "ubfx r0, r1, #31, #1\n";
162 DriverStr(expected, "ubfx");
163}
164
Calin Juravleddb7df22014-11-25 20:56:51 +0000165TEST_F(AssemblerThumb2Test, Vmstat) {
166 GetAssembler()->vmstat();
167
168 const char* expected = "vmrs APSR_nzcv, FPSCR\n";
169
170 DriverStr(expected, "vmrs");
171}
172
Calin Juravle52c48962014-12-16 17:02:57 +0000173TEST_F(AssemblerThumb2Test, ldrexd) {
174 GetAssembler()->ldrexd(arm::R0, arm::R1, arm::R0);
175 GetAssembler()->ldrexd(arm::R0, arm::R1, arm::R1);
176 GetAssembler()->ldrexd(arm::R0, arm::R1, arm::R2);
177 GetAssembler()->ldrexd(arm::R5, arm::R3, arm::R7);
178
179 const char* expected =
180 "ldrexd r0, r1, [r0]\n"
181 "ldrexd r0, r1, [r1]\n"
182 "ldrexd r0, r1, [r2]\n"
183 "ldrexd r5, r3, [r7]\n";
184 DriverStr(expected, "ldrexd");
185}
186
187TEST_F(AssemblerThumb2Test, strexd) {
188 GetAssembler()->strexd(arm::R9, arm::R0, arm::R1, arm::R0);
189 GetAssembler()->strexd(arm::R9, arm::R0, arm::R1, arm::R1);
190 GetAssembler()->strexd(arm::R9, arm::R0, arm::R1, arm::R2);
191 GetAssembler()->strexd(arm::R9, arm::R5, arm::R3, arm::R7);
192
193 const char* expected =
194 "strexd r9, r0, r1, [r0]\n"
195 "strexd r9, r0, r1, [r1]\n"
196 "strexd r9, r0, r1, [r2]\n"
197 "strexd r9, r5, r3, [r7]\n";
198 DriverStr(expected, "strexd");
199}
200
Andreas Gampe513ea0c2015-02-02 13:17:52 -0800201TEST_F(AssemblerThumb2Test, eor) {
202#define __ GetAssembler()->
203 __ eor(arm::R1, arm::R1, arm::ShifterOperand(arm::R0));
204 __ eor(arm::R1, arm::R0, arm::ShifterOperand(arm::R1));
205 __ eor(arm::R1, arm::R8, arm::ShifterOperand(arm::R0));
206 __ eor(arm::R8, arm::R1, arm::ShifterOperand(arm::R0));
207 __ eor(arm::R1, arm::R0, arm::ShifterOperand(arm::R8));
208
209 const char* expected =
210 "eors r1, r0\n"
211 "eor r1, r0, r1\n"
212 "eor r1, r8, r0\n"
213 "eor r8, r1, r0\n"
214 "eor r1, r0, r8\n";
215 DriverStr(expected, "abs");
216}
217
Roland Levillain1a28fc42014-11-13 18:03:06 +0000218} // namespace art