Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(874)

Side by Side Diff: test/cctest/test-macro-assembler-arm.cc

Issue 2546933002: [Turbofan] Add ARM NEON instructions for implementing SIMD. (Closed)
Patch Set: Fourth review comments. Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « test/cctest/test-disasm-arm.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 24 matching lines...) Expand all
35 #include "src/arm/macro-assembler-arm.h" 35 #include "src/arm/macro-assembler-arm.h"
36 #include "src/arm/simulator-arm.h" 36 #include "src/arm/simulator-arm.h"
37 37
38 38
39 using namespace v8::internal; 39 using namespace v8::internal;
40 40
41 typedef void* (*F)(int x, int y, int p2, int p3, int p4); 41 typedef void* (*F)(int x, int y, int p2, int p3, int p4);
42 42
43 #define __ masm-> 43 #define __ masm->
44 44
45 typedef Object* (*F3)(void* p0, int p1, int p2, int p3, int p4);
45 typedef int (*F5)(void*, void*, void*, void*, void*); 46 typedef int (*F5)(void*, void*, void*, void*, void*);
46 47
47 48
48 TEST(LoadAndStoreWithRepresentation) { 49 TEST(LoadAndStoreWithRepresentation) {
49 // Allocate an executable page of memory. 50 // Allocate an executable page of memory.
50 size_t actual_size; 51 size_t actual_size;
51 byte* buffer = static_cast<byte*>(v8::base::OS::Allocate( 52 byte* buffer = static_cast<byte*>(v8::base::OS::Allocate(
52 Assembler::kMinimalBufferSize, &actual_size, true)); 53 Assembler::kMinimalBufferSize, &actual_size, true));
53 CHECK(buffer); 54 CHECK(buffer);
54 Isolate* isolate = CcTest::i_isolate(); 55 Isolate* isolate = CcTest::i_isolate();
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after
127 CodeDesc desc; 128 CodeDesc desc;
128 masm->GetCode(&desc); 129 masm->GetCode(&desc);
129 Handle<Code> code = isolate->factory()->NewCode( 130 Handle<Code> code = isolate->factory()->NewCode(
130 desc, Code::ComputeFlags(Code::STUB), Handle<Code>()); 131 desc, Code::ComputeFlags(Code::STUB), Handle<Code>());
131 132
132 // Call the function from C++. 133 // Call the function from C++.
133 F5 f = FUNCTION_CAST<F5>(code->entry()); 134 F5 f = FUNCTION_CAST<F5>(code->entry());
134 CHECK(!CALL_GENERATED_CODE(isolate, f, 0, 0, 0, 0, 0)); 135 CHECK(!CALL_GENERATED_CODE(isolate, f, 0, 0, 0, 0, 0));
135 } 136 }
136 137
138 TEST(ExtractLane) {
139 if (!CpuFeatures::IsSupported(NEON)) return;
140
141 // Allocate an executable page of memory.
142 size_t actual_size;
143 byte* buffer = static_cast<byte*>(v8::base::OS::Allocate(
144 Assembler::kMinimalBufferSize, &actual_size, true));
145 CHECK(buffer);
146 Isolate* isolate = CcTest::i_isolate();
147 HandleScope handles(isolate);
148 MacroAssembler assembler(isolate, buffer, static_cast<int>(actual_size),
149 v8::internal::CodeObjectRequired::kYes);
150 MacroAssembler* masm = &assembler; // Create a pointer for the __ macro.
151
152 typedef struct {
153 int32_t i32x4_low[4];
154 int32_t i32x4_high[4];
155 int32_t i16x8_low[8];
156 int32_t i16x8_high[8];
157 int32_t i8x16_low[16];
158 int32_t i8x16_high[16];
159 int32_t f32x4_low[4];
160 int32_t f32x4_high[4];
161 } T;
162 T t;
163
164 __ stm(db_w, sp, r4.bit() | r5.bit() | lr.bit());
165
166 for (int i = 0; i < 4; i++) {
167 __ mov(r4, Operand(i));
168 __ vdup(Neon32, q1, r4);
169 __ ExtractLane(r5, q1, NeonS32, i);
170 __ str(r5, MemOperand(r0, offsetof(T, i32x4_low) + 4 * i));
171 SwVfpRegister si = SwVfpRegister::from_code(i);
172 __ ExtractLane(si, q1, r4, i);
173 __ vstr(si, r0, offsetof(T, f32x4_low) + 4 * i);
174 }
175
176 for (int i = 0; i < 8; i++) {
177 __ mov(r4, Operand(i));
178 __ vdup(Neon16, q1, r4);
179 __ ExtractLane(r5, q1, NeonS16, i);
180 __ str(r5, MemOperand(r0, offsetof(T, i16x8_low) + 4 * i));
181 }
182
183 for (int i = 0; i < 16; i++) {
184 __ mov(r4, Operand(i));
185 __ vdup(Neon8, q1, r4);
186 __ ExtractLane(r5, q1, NeonS8, i);
187 __ str(r5, MemOperand(r0, offsetof(T, i8x16_low) + 4 * i));
188 }
189
190 if (CpuFeatures::IsSupported(VFP32DREGS)) {
191 for (int i = 0; i < 4; i++) {
192 __ mov(r4, Operand(-i));
193 __ vdup(Neon32, q15, r4);
194 __ ExtractLane(r5, q15, NeonS32, i);
195 __ str(r5, MemOperand(r0, offsetof(T, i32x4_high) + 4 * i));
196 SwVfpRegister si = SwVfpRegister::from_code(i);
197 __ ExtractLane(si, q15, r4, i);
198 __ vstr(si, r0, offsetof(T, f32x4_high) + 4 * i);
199 }
200
201 for (int i = 0; i < 8; i++) {
202 __ mov(r4, Operand(-i));
203 __ vdup(Neon16, q15, r4);
204 __ ExtractLane(r5, q15, NeonS16, i);
205 __ str(r5, MemOperand(r0, offsetof(T, i16x8_high) + 4 * i));
206 }
207
208 for (int i = 0; i < 16; i++) {
209 __ mov(r4, Operand(-i));
210 __ vdup(Neon8, q15, r4);
211 __ ExtractLane(r5, q15, NeonS8, i);
212 __ str(r5, MemOperand(r0, offsetof(T, i8x16_high) + 4 * i));
213 }
214 }
215
216 __ ldm(ia_w, sp, r4.bit() | r5.bit() | pc.bit());
217
218 CodeDesc desc;
219 masm->GetCode(&desc);
220 Handle<Code> code = isolate->factory()->NewCode(
221 desc, Code::ComputeFlags(Code::STUB), Handle<Code>());
222 #ifdef DEBUG
223 OFStream os(stdout);
224 code->Print(os);
225 #endif
226 F3 f = FUNCTION_CAST<F3>(code->entry());
227 Object* dummy = CALL_GENERATED_CODE(isolate, f, &t, 0, 0, 0, 0);
228 USE(dummy);
229 for (int i = 0; i < 4; i++) {
230 CHECK_EQ(i, t.i32x4_low[i]);
231 CHECK_EQ(i, t.f32x4_low[i]);
232 }
233 for (int i = 0; i < 8; i++) {
234 CHECK_EQ(i, t.i16x8_low[i]);
235 }
236 for (int i = 0; i < 16; i++) {
237 CHECK_EQ(i, t.i8x16_low[i]);
238 }
239 if (CpuFeatures::IsSupported(VFP32DREGS)) {
240 for (int i = 0; i < 4; i++) {
241 CHECK_EQ(-i, t.i32x4_high[i]);
242 CHECK_EQ(-i, t.f32x4_high[i]);
243 }
244 for (int i = 0; i < 8; i++) {
245 CHECK_EQ(-i, t.i16x8_high[i]);
246 }
247 for (int i = 0; i < 16; i++) {
248 CHECK_EQ(-i, t.i8x16_high[i]);
249 }
250 }
251 }
252
253 TEST(ReplaceLane) {
254 if (!CpuFeatures::IsSupported(NEON)) return;
255
256 // Allocate an executable page of memory.
257 size_t actual_size;
258 byte* buffer = static_cast<byte*>(v8::base::OS::Allocate(
259 Assembler::kMinimalBufferSize, &actual_size, true));
260 CHECK(buffer);
261 Isolate* isolate = CcTest::i_isolate();
262 HandleScope handles(isolate);
263 MacroAssembler assembler(isolate, buffer, static_cast<int>(actual_size),
264 v8::internal::CodeObjectRequired::kYes);
265 MacroAssembler* masm = &assembler; // Create a pointer for the __ macro.
266
267 typedef struct {
268 int32_t i32x4_low[4];
269 int32_t i32x4_high[4];
270 int16_t i16x8_low[8];
271 int16_t i16x8_high[8];
272 int8_t i8x16_low[16];
273 int8_t i8x16_high[16];
274 int32_t f32x4_low[4];
275 int32_t f32x4_high[4];
276 } T;
277 T t;
278
279 __ stm(db_w, sp, r4.bit() | r5.bit() | r6.bit() | r7.bit() | lr.bit());
280
281 const Register kScratch = r5;
282
283 __ veor(q0, q0, q0); // Zero
284 __ veor(q1, q1, q1); // Zero
285 for (int i = 0; i < 4; i++) {
286 __ mov(r4, Operand(i));
287 __ ReplaceLane(q0, q0, r4, NeonS32, i);
288 SwVfpRegister si = SwVfpRegister::from_code(i);
289 __ vmov(si, r4);
290 __ ReplaceLane(q1, q1, si, kScratch, i);
291 }
292 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i32x4_low))));
293 __ vst1(Neon8, NeonListOperand(q0), NeonMemOperand(r4));
294 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, f32x4_low))));
295 __ vst1(Neon8, NeonListOperand(q1), NeonMemOperand(r4));
296
297 __ veor(q0, q0, q0); // Zero
298 for (int i = 0; i < 8; i++) {
299 __ mov(r4, Operand(i));
300 __ ReplaceLane(q0, q0, r4, NeonS16, i);
301 }
302 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i16x8_low))));
303 __ vst1(Neon8, NeonListOperand(q0), NeonMemOperand(r4));
304
305 __ veor(q0, q0, q0); // Zero
306 for (int i = 0; i < 16; i++) {
307 __ mov(r4, Operand(i));
308 __ ReplaceLane(q0, q0, r4, NeonS8, i);
309 }
310 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i8x16_low))));
311 __ vst1(Neon8, NeonListOperand(q0), NeonMemOperand(r4));
312
313 if (CpuFeatures::IsSupported(VFP32DREGS)) {
314 __ veor(q14, q14, q14); // Zero
315 __ veor(q15, q15, q15); // Zero
316 for (int i = 0; i < 4; i++) {
317 __ mov(r4, Operand(-i));
318 __ ReplaceLane(q14, q14, r4, NeonS32, i);
319 SwVfpRegister si = SwVfpRegister::from_code(i);
320 __ vmov(si, r4);
321 __ ReplaceLane(q15, q15, si, kScratch, i);
322 }
323 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i32x4_high))));
324 __ vst1(Neon8, NeonListOperand(q14), NeonMemOperand(r4));
325 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, f32x4_high))));
326 __ vst1(Neon8, NeonListOperand(q15), NeonMemOperand(r4));
327
328 __ veor(q14, q14, q14); // Zero
329 for (int i = 0; i < 8; i++) {
330 __ mov(r4, Operand(-i));
331 __ ReplaceLane(q14, q14, r4, NeonS16, i);
332 }
333 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i16x8_high))));
334 __ vst1(Neon8, NeonListOperand(q14), NeonMemOperand(r4));
335
336 __ veor(q14, q14, q14); // Zero
337 for (int i = 0; i < 16; i++) {
338 __ mov(r4, Operand(-i));
339 __ ReplaceLane(q14, q14, r4, NeonS8, i);
340 }
341 __ add(r4, r0, Operand(static_cast<int32_t>(offsetof(T, i8x16_high))));
342 __ vst1(Neon8, NeonListOperand(q14), NeonMemOperand(r4));
343 }
344
345 __ ldm(ia_w, sp, r4.bit() | r5.bit() | r6.bit() | r7.bit() | pc.bit());
346
347 CodeDesc desc;
348 masm->GetCode(&desc);
349 Handle<Code> code = isolate->factory()->NewCode(
350 desc, Code::ComputeFlags(Code::STUB), Handle<Code>());
351 #ifdef DEBUG
352 OFStream os(stdout);
353 code->Print(os);
354 #endif
355 F3 f = FUNCTION_CAST<F3>(code->entry());
356 Object* dummy = CALL_GENERATED_CODE(isolate, f, &t, 0, 0, 0, 0);
357 USE(dummy);
358 for (int i = 0; i < 4; i++) {
359 CHECK_EQ(i, t.i32x4_low[i]);
360 CHECK_EQ(i, t.f32x4_low[i]);
361 }
362 for (int i = 0; i < 8; i++) {
363 CHECK_EQ(i, t.i16x8_low[i]);
364 }
365 for (int i = 0; i < 16; i++) {
366 CHECK_EQ(i, t.i8x16_low[i]);
367 }
368 if (CpuFeatures::IsSupported(VFP32DREGS)) {
369 for (int i = 0; i < 4; i++) {
370 CHECK_EQ(-i, t.i32x4_high[i]);
371 CHECK_EQ(-i, t.f32x4_high[i]);
372 }
373 for (int i = 0; i < 8; i++) {
374 CHECK_EQ(-i, t.i16x8_high[i]);
375 }
376 for (int i = 0; i < 16; i++) {
377 CHECK_EQ(-i, t.i8x16_high[i]);
378 }
379 }
380 }
381
137 #undef __ 382 #undef __
OLDNEW
« no previous file with comments | « test/cctest/test-disasm-arm.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698