1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2  * vim: set ts=8 sts=2 et sw=2 tw=80:
3  */
4 /* This Source Code Form is subject to the terms of the Mozilla Public
5  * License, v. 2.0. If a copy of the MPL was not distributed with this
6  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 
8 #if defined(JS_SIMULATOR_ARM)
9 
10 #  include "jit/arm/Assembler-arm.h"
11 #  include "jit/arm/MoveEmitter-arm.h"
12 #  include "jit/arm/Simulator-arm.h"
13 #  include "jit/Linker.h"
14 #  include "jit/MacroAssembler.h"
15 #  include "jit/MoveResolver.h"
16 
17 #  include "jsapi-tests/tests.h"
18 
19 #  include "vm/Runtime.h"
20 
21 static const int LIFO_ALLOC_PRIMARY_CHUNK_SIZE = 4 * 1024;
22 
23 static constexpr js::jit::FloatRegister s0(0, js::jit::VFPRegister::Single);
24 static constexpr js::jit::FloatRegister s1(1, js::jit::VFPRegister::Single);
25 static constexpr js::jit::FloatRegister s2(2, js::jit::VFPRegister::Single);
26 static constexpr js::jit::FloatRegister s3(3, js::jit::VFPRegister::Single);
27 static constexpr js::jit::FloatRegister s4(4, js::jit::VFPRegister::Single);
28 static constexpr js::jit::FloatRegister s5(5, js::jit::VFPRegister::Single);
29 static constexpr js::jit::FloatRegister s6(6, js::jit::VFPRegister::Single);
30 static constexpr js::jit::FloatRegister s7(7, js::jit::VFPRegister::Single);
31 static constexpr js::jit::FloatRegister s8(8, js::jit::VFPRegister::Single);
32 static constexpr js::jit::FloatRegister s9(9, js::jit::VFPRegister::Single);
33 static constexpr js::jit::FloatRegister s10(10, js::jit::VFPRegister::Single);
34 static constexpr js::jit::FloatRegister s11(11, js::jit::VFPRegister::Single);
35 static constexpr js::jit::FloatRegister s12(12, js::jit::VFPRegister::Single);
36 static constexpr js::jit::FloatRegister s13(13, js::jit::VFPRegister::Single);
37 static constexpr js::jit::FloatRegister s14(14, js::jit::VFPRegister::Single);
38 static constexpr js::jit::FloatRegister s15(15, js::jit::VFPRegister::Single);
39 static constexpr js::jit::FloatRegister s16(16, js::jit::VFPRegister::Single);
40 static constexpr js::jit::FloatRegister s17(17, js::jit::VFPRegister::Single);
41 static constexpr js::jit::FloatRegister s18(18, js::jit::VFPRegister::Single);
42 static constexpr js::jit::FloatRegister s19(19, js::jit::VFPRegister::Single);
43 static constexpr js::jit::FloatRegister s20(20, js::jit::VFPRegister::Single);
44 static constexpr js::jit::FloatRegister s21(21, js::jit::VFPRegister::Single);
45 static constexpr js::jit::FloatRegister s22(22, js::jit::VFPRegister::Single);
46 static constexpr js::jit::FloatRegister s23(23, js::jit::VFPRegister::Single);
47 static constexpr js::jit::FloatRegister s24(24, js::jit::VFPRegister::Single);
48 static constexpr js::jit::FloatRegister s25(25, js::jit::VFPRegister::Single);
49 static constexpr js::jit::FloatRegister s26(26, js::jit::VFPRegister::Single);
50 static constexpr js::jit::FloatRegister s27(27, js::jit::VFPRegister::Single);
51 static constexpr js::jit::FloatRegister s28(28, js::jit::VFPRegister::Single);
52 static constexpr js::jit::FloatRegister s29(29, js::jit::VFPRegister::Single);
53 static constexpr js::jit::FloatRegister s30(30, js::jit::VFPRegister::Single);
54 static constexpr js::jit::FloatRegister s31(31, js::jit::VFPRegister::Single);
55 
linkAndAllocate(JSContext * cx,js::jit::MacroAssembler * masm)56 static js::jit::JitCode* linkAndAllocate(JSContext* cx,
57                                          js::jit::MacroAssembler* masm) {
58   using namespace js;
59   using namespace js::jit;
60   Linker l(*masm);
61   return l.newCode(cx, CodeKind::Ion);
62 }
63 
64 #  define TRY(x) \
65     if (!(x)) return false;
66 
BEGIN_TEST(testJitMoveEmitterCycles_simple)67 BEGIN_TEST(testJitMoveEmitterCycles_simple) {
68   using namespace js;
69   using namespace js::jit;
70   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
71   TempAllocator alloc(&lifo);
72   JitContext jc(cx, &alloc);
73   StackMacroAssembler masm;
74   AutoCreatedBy acb(masm, __func__);
75   MoveEmitter mover(masm);
76   MoveResolver mr;
77   mr.setAllocator(alloc);
78   Simulator* sim = Simulator::Current();
79   TRY(mr.addMove(MoveOperand(d0), MoveOperand(d2), MoveOp::DOUBLE));
80   sim->set_d_register_from_double(0, 2);
81   TRY(mr.addMove(MoveOperand(d3), MoveOperand(d1), MoveOp::DOUBLE));
82   sim->set_d_register_from_double(3, 1);
83   TRY(mr.addMove(MoveOperand(s4), MoveOperand(s0), MoveOp::FLOAT32));
84   sim->set_s_register_from_float(4, 0);
85   TRY(mr.addMove(MoveOperand(s5), MoveOperand(s6), MoveOp::FLOAT32));
86   sim->set_s_register_from_float(5, 6);
87   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s1), MoveOp::FLOAT32));
88   sim->set_s_register_from_float(2, 1);
89   TRY(mr.addMove(MoveOperand(s3), MoveOperand(s7), MoveOp::FLOAT32));
90   sim->set_s_register_from_float(3, 7);
91   // don't explode!
92   TRY(mr.resolve());
93   mover.emit(mr);
94   mover.finish();
95   masm.abiret();
96   JitCode* code = linkAndAllocate(cx, &masm);
97   sim->call(code->raw(), 1, 1);
98   float f;
99   double d;
100   sim->get_double_from_d_register(2, &d);
101   CHECK(d == 2);
102   sim->get_double_from_d_register(1, &d);
103   CHECK(int(d) == 1);
104   sim->get_float_from_s_register(0, &f);
105   CHECK(int(f) == 0);
106   sim->get_float_from_s_register(6, &f);
107   CHECK(int(f) == 6);
108   sim->get_float_from_s_register(1, &f);
109   CHECK(int(f) == 1);
110   sim->get_float_from_s_register(7, &f);
111   CHECK(int(f) == 7);
112   return true;
113 }
114 END_TEST(testJitMoveEmitterCycles_simple)
BEGIN_TEST(testJitMoveEmitterCycles_autogen)115 BEGIN_TEST(testJitMoveEmitterCycles_autogen) {
116   using namespace js;
117   using namespace js::jit;
118   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
119   TempAllocator alloc(&lifo);
120   JitContext jc(cx, &alloc);
121   StackMacroAssembler masm;
122   AutoCreatedBy acb(masm, __func__);
123   MoveEmitter mover(masm);
124   MoveResolver mr;
125   mr.setAllocator(alloc);
126   Simulator* sim = Simulator::Current();
127   TRY(mr.addMove(MoveOperand(d9), MoveOperand(d14), MoveOp::DOUBLE));
128   sim->set_d_register_from_double(9, 9);
129   TRY(mr.addMove(MoveOperand(s24), MoveOperand(s25), MoveOp::FLOAT32));
130   sim->set_s_register_from_float(24, 24);
131   TRY(mr.addMove(MoveOperand(d3), MoveOperand(d0), MoveOp::DOUBLE));
132   sim->set_d_register_from_double(3, 3);
133   TRY(mr.addMove(MoveOperand(s10), MoveOperand(s31), MoveOp::FLOAT32));
134   sim->set_s_register_from_float(10, 10);
135   TRY(mr.addMove(MoveOperand(d1), MoveOperand(d10), MoveOp::DOUBLE));
136   sim->set_d_register_from_double(1, 1);
137   TRY(mr.addMove(MoveOperand(s8), MoveOperand(s10), MoveOp::FLOAT32));
138   sim->set_s_register_from_float(8, 8);
139   TRY(mr.addMove(MoveOperand(d2), MoveOperand(d7), MoveOp::DOUBLE));
140   sim->set_d_register_from_double(2, 2);
141   TRY(mr.addMove(MoveOperand(s20), MoveOperand(s18), MoveOp::FLOAT32));
142   sim->set_s_register_from_float(20, 20);
143   TRY(mr.addMove(MoveOperand(s1), MoveOperand(s3), MoveOp::FLOAT32));
144   sim->set_s_register_from_float(1, 1);
145   TRY(mr.addMove(MoveOperand(s17), MoveOperand(s11), MoveOp::FLOAT32));
146   sim->set_s_register_from_float(17, 17);
147   TRY(mr.addMove(MoveOperand(s22), MoveOperand(s30), MoveOp::FLOAT32));
148   sim->set_s_register_from_float(22, 22);
149   TRY(mr.addMove(MoveOperand(s31), MoveOperand(s7), MoveOp::FLOAT32));
150   sim->set_s_register_from_float(31, 31);
151   TRY(mr.addMove(MoveOperand(d3), MoveOperand(d13), MoveOp::DOUBLE));
152   sim->set_d_register_from_double(3, 3);
153   TRY(mr.addMove(MoveOperand(d9), MoveOperand(d8), MoveOp::DOUBLE));
154   sim->set_d_register_from_double(9, 9);
155   TRY(mr.addMove(MoveOperand(s31), MoveOperand(s23), MoveOp::FLOAT32));
156   sim->set_s_register_from_float(31, 31);
157   TRY(mr.addMove(MoveOperand(s13), MoveOperand(s8), MoveOp::FLOAT32));
158   sim->set_s_register_from_float(13, 13);
159   TRY(mr.addMove(MoveOperand(s28), MoveOperand(s5), MoveOp::FLOAT32));
160   sim->set_s_register_from_float(28, 28);
161   TRY(mr.addMove(MoveOperand(s31), MoveOperand(s19), MoveOp::FLOAT32));
162   sim->set_s_register_from_float(31, 31);
163   TRY(mr.addMove(MoveOperand(s20), MoveOperand(s6), MoveOp::FLOAT32));
164   sim->set_s_register_from_float(20, 20);
165   TRY(mr.addMove(MoveOperand(s0), MoveOperand(s2), MoveOp::FLOAT32));
166   sim->set_s_register_from_float(0, 0);
167   TRY(mr.addMove(MoveOperand(d7), MoveOperand(d6), MoveOp::DOUBLE));
168   sim->set_d_register_from_double(7, 7);
169   TRY(mr.addMove(MoveOperand(s13), MoveOperand(s9), MoveOp::FLOAT32));
170   sim->set_s_register_from_float(13, 13);
171   TRY(mr.addMove(MoveOperand(s1), MoveOperand(s4), MoveOp::FLOAT32));
172   sim->set_s_register_from_float(1, 1);
173   TRY(mr.addMove(MoveOperand(s29), MoveOperand(s22), MoveOp::FLOAT32));
174   sim->set_s_register_from_float(29, 29);
175   TRY(mr.addMove(MoveOperand(s25), MoveOperand(s24), MoveOp::FLOAT32));
176   sim->set_s_register_from_float(25, 25);
177   // don't explode!
178   TRY(mr.resolve());
179   mover.emit(mr);
180   mover.finish();
181   masm.abiret();
182   JitCode* code = linkAndAllocate(cx, &masm);
183   sim->skipCalleeSavedRegsCheck = true;
184   sim->call(code->raw(), 1, 1);
185   double d;
186   float f;
187   sim->get_double_from_d_register(14, &d);
188   CHECK(int(d) == 9);
189   sim->get_float_from_s_register(25, &f);
190   CHECK(int(f) == 24);
191   sim->get_double_from_d_register(0, &d);
192   CHECK(int(d) == 3);
193   sim->get_float_from_s_register(31, &f);
194   CHECK(int(f) == 10);
195   sim->get_double_from_d_register(10, &d);
196   CHECK(int(d) == 1);
197   sim->get_float_from_s_register(10, &f);
198   CHECK(int(f) == 8);
199   sim->get_double_from_d_register(7, &d);
200   CHECK(int(d) == 2);
201   sim->get_float_from_s_register(18, &f);
202   CHECK(int(f) == 20);
203   sim->get_float_from_s_register(3, &f);
204   CHECK(int(f) == 1);
205   sim->get_float_from_s_register(11, &f);
206   CHECK(int(f) == 17);
207   sim->get_float_from_s_register(30, &f);
208   CHECK(int(f) == 22);
209   sim->get_float_from_s_register(7, &f);
210   CHECK(int(f) == 31);
211   sim->get_double_from_d_register(13, &d);
212   CHECK(int(d) == 3);
213   sim->get_double_from_d_register(8, &d);
214   CHECK(int(d) == 9);
215   sim->get_float_from_s_register(23, &f);
216   CHECK(int(f) == 31);
217   sim->get_float_from_s_register(8, &f);
218   CHECK(int(f) == 13);
219   sim->get_float_from_s_register(5, &f);
220   CHECK(int(f) == 28);
221   sim->get_float_from_s_register(19, &f);
222   CHECK(int(f) == 31);
223   sim->get_float_from_s_register(6, &f);
224   CHECK(int(f) == 20);
225   sim->get_float_from_s_register(2, &f);
226   CHECK(int(f) == 0);
227   sim->get_double_from_d_register(6, &d);
228   CHECK(int(d) == 7);
229   sim->get_float_from_s_register(9, &f);
230   CHECK(int(f) == 13);
231   sim->get_float_from_s_register(4, &f);
232   CHECK(int(f) == 1);
233   sim->get_float_from_s_register(22, &f);
234   CHECK(int(f) == 29);
235   sim->get_float_from_s_register(24, &f);
236   CHECK(int(f) == 25);
237   return true;
238 }
239 END_TEST(testJitMoveEmitterCycles_autogen)
240 
BEGIN_TEST(testJitMoveEmitterCycles_autogen2)241 BEGIN_TEST(testJitMoveEmitterCycles_autogen2) {
242   using namespace js;
243   using namespace js::jit;
244   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
245   TempAllocator alloc(&lifo);
246   JitContext jc(cx, &alloc);
247   StackMacroAssembler masm;
248   AutoCreatedBy acb(masm, __func__);
249   MoveEmitter mover(masm);
250   MoveResolver mr;
251   mr.setAllocator(alloc);
252   Simulator* sim = Simulator::Current();
253   TRY(mr.addMove(MoveOperand(d10), MoveOperand(d0), MoveOp::DOUBLE));
254   sim->set_d_register_from_double(10, 10);
255   TRY(mr.addMove(MoveOperand(s15), MoveOperand(s3), MoveOp::FLOAT32));
256   sim->set_s_register_from_float(15, 15);
257   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s28), MoveOp::FLOAT32));
258   sim->set_s_register_from_float(2, 2);
259   TRY(mr.addMove(MoveOperand(s30), MoveOperand(s25), MoveOp::FLOAT32));
260   sim->set_s_register_from_float(30, 30);
261   TRY(mr.addMove(MoveOperand(s16), MoveOperand(s2), MoveOp::FLOAT32));
262   sim->set_s_register_from_float(16, 16);
263   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s29), MoveOp::FLOAT32));
264   sim->set_s_register_from_float(2, 2);
265   TRY(mr.addMove(MoveOperand(s17), MoveOperand(s10), MoveOp::FLOAT32));
266   sim->set_s_register_from_float(17, 17);
267   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s19), MoveOp::FLOAT32));
268   sim->set_s_register_from_float(2, 2);
269   TRY(mr.addMove(MoveOperand(s9), MoveOperand(s26), MoveOp::FLOAT32));
270   sim->set_s_register_from_float(9, 9);
271   TRY(mr.addMove(MoveOperand(s1), MoveOperand(s23), MoveOp::FLOAT32));
272   sim->set_s_register_from_float(1, 1);
273   TRY(mr.addMove(MoveOperand(s8), MoveOperand(s6), MoveOp::FLOAT32));
274   sim->set_s_register_from_float(8, 8);
275   TRY(mr.addMove(MoveOperand(s24), MoveOperand(s16), MoveOp::FLOAT32));
276   sim->set_s_register_from_float(24, 24);
277   TRY(mr.addMove(MoveOperand(s19), MoveOperand(s4), MoveOp::FLOAT32));
278   sim->set_s_register_from_float(19, 19);
279   TRY(mr.addMove(MoveOperand(d5), MoveOperand(d6), MoveOp::DOUBLE));
280   sim->set_d_register_from_double(5, 5);
281   TRY(mr.addMove(MoveOperand(s18), MoveOperand(s15), MoveOp::FLOAT32));
282   sim->set_s_register_from_float(18, 18);
283   TRY(mr.addMove(MoveOperand(s23), MoveOperand(s30), MoveOp::FLOAT32));
284   sim->set_s_register_from_float(23, 23);
285   TRY(mr.addMove(MoveOperand(s27), MoveOperand(s17), MoveOp::FLOAT32));
286   sim->set_s_register_from_float(27, 27);
287   TRY(mr.addMove(MoveOperand(d3), MoveOperand(d4), MoveOp::DOUBLE));
288   sim->set_d_register_from_double(3, 3);
289   TRY(mr.addMove(MoveOperand(s14), MoveOperand(s27), MoveOp::FLOAT32));
290   sim->set_s_register_from_float(14, 14);
291   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s31), MoveOp::FLOAT32));
292   sim->set_s_register_from_float(2, 2);
293   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s24), MoveOp::FLOAT32));
294   sim->set_s_register_from_float(2, 2);
295   TRY(mr.addMove(MoveOperand(s31), MoveOperand(s11), MoveOp::FLOAT32));
296   sim->set_s_register_from_float(31, 31);
297   TRY(mr.addMove(MoveOperand(s0), MoveOperand(s18), MoveOp::FLOAT32));
298   sim->set_s_register_from_float(0, 0);
299   TRY(mr.addMove(MoveOperand(s24), MoveOperand(s7), MoveOp::FLOAT32));
300   sim->set_s_register_from_float(24, 24);
301   TRY(mr.addMove(MoveOperand(s0), MoveOperand(s21), MoveOp::FLOAT32));
302   sim->set_s_register_from_float(0, 0);
303   TRY(mr.addMove(MoveOperand(s27), MoveOperand(s20), MoveOp::FLOAT32));
304   sim->set_s_register_from_float(27, 27);
305   TRY(mr.addMove(MoveOperand(s14), MoveOperand(s5), MoveOp::FLOAT32));
306   sim->set_s_register_from_float(14, 14);
307   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s14), MoveOp::FLOAT32));
308   sim->set_s_register_from_float(2, 2);
309   TRY(mr.addMove(MoveOperand(s12), MoveOperand(s22), MoveOp::FLOAT32));
310   sim->set_s_register_from_float(12, 12);
311   // don't explode!
312   TRY(mr.resolve());
313   mover.emit(mr);
314   mover.finish();
315   masm.abiret();
316   JitCode* code = linkAndAllocate(cx, &masm);
317   sim->skipCalleeSavedRegsCheck = true;
318   sim->call(code->raw(), 1, 1);
319 
320   double d;
321   float f;
322   sim->get_double_from_d_register(0, &d);
323   CHECK(int(d) == 10);
324   sim->get_float_from_s_register(3, &f);
325   CHECK(int(f) == 15);
326   sim->get_float_from_s_register(28, &f);
327   CHECK(int(f) == 2);
328   sim->get_float_from_s_register(25, &f);
329   CHECK(int(f) == 30);
330   sim->get_float_from_s_register(2, &f);
331   CHECK(int(f) == 16);
332   sim->get_float_from_s_register(29, &f);
333   CHECK(int(f) == 2);
334   sim->get_float_from_s_register(10, &f);
335   CHECK(int(f) == 17);
336   sim->get_float_from_s_register(19, &f);
337   CHECK(int(f) == 2);
338   sim->get_float_from_s_register(26, &f);
339   CHECK(int(f) == 9);
340   sim->get_float_from_s_register(23, &f);
341   CHECK(int(f) == 1);
342   sim->get_float_from_s_register(6, &f);
343   CHECK(int(f) == 8);
344   sim->get_float_from_s_register(16, &f);
345   CHECK(int(f) == 24);
346   sim->get_float_from_s_register(4, &f);
347   CHECK(int(f) == 19);
348   sim->get_double_from_d_register(6, &d);
349   CHECK(int(d) == 5);
350   sim->get_float_from_s_register(15, &f);
351   CHECK(int(f) == 18);
352   sim->get_float_from_s_register(30, &f);
353   CHECK(int(f) == 23);
354   sim->get_float_from_s_register(17, &f);
355   CHECK(int(f) == 27);
356   sim->get_double_from_d_register(4, &d);
357   CHECK(int(d) == 3);
358   sim->get_float_from_s_register(27, &f);
359   CHECK(int(f) == 14);
360   sim->get_float_from_s_register(31, &f);
361   CHECK(int(f) == 2);
362   sim->get_float_from_s_register(24, &f);
363   CHECK(int(f) == 2);
364   sim->get_float_from_s_register(11, &f);
365   CHECK(int(f) == 31);
366   sim->get_float_from_s_register(18, &f);
367   CHECK(int(f) == 0);
368   sim->get_float_from_s_register(7, &f);
369   CHECK(int(f) == 24);
370   sim->get_float_from_s_register(21, &f);
371   CHECK(int(f) == 0);
372   sim->get_float_from_s_register(20, &f);
373   CHECK(int(f) == 27);
374   sim->get_float_from_s_register(5, &f);
375   CHECK(int(f) == 14);
376   sim->get_float_from_s_register(14, &f);
377   CHECK(int(f) == 2);
378   sim->get_float_from_s_register(22, &f);
379   CHECK(int(f) == 12);
380   return true;
381 }
382 END_TEST(testJitMoveEmitterCycles_autogen2)
383 
BEGIN_TEST(testJitMoveEmitterCycles_autogen3)384 BEGIN_TEST(testJitMoveEmitterCycles_autogen3) {
385   using namespace js;
386   using namespace js::jit;
387   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
388   TempAllocator alloc(&lifo);
389   JitContext jc(cx, &alloc);
390   StackMacroAssembler masm;
391   AutoCreatedBy acb(masm, __func__);
392   MoveEmitter mover(masm);
393   MoveResolver mr;
394   mr.setAllocator(alloc);
395   Simulator* sim = Simulator::Current();
396   TRY(mr.addMove(MoveOperand(s0), MoveOperand(s21), MoveOp::FLOAT32));
397   sim->set_s_register_from_float(0, 0);
398   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s26), MoveOp::FLOAT32));
399   sim->set_s_register_from_float(2, 2);
400   TRY(mr.addMove(MoveOperand(s19), MoveOperand(s20), MoveOp::FLOAT32));
401   sim->set_s_register_from_float(19, 19);
402   TRY(mr.addMove(MoveOperand(s4), MoveOperand(s24), MoveOp::FLOAT32));
403   sim->set_s_register_from_float(4, 4);
404   TRY(mr.addMove(MoveOperand(s22), MoveOperand(s9), MoveOp::FLOAT32));
405   sim->set_s_register_from_float(22, 22);
406   TRY(mr.addMove(MoveOperand(s5), MoveOperand(s28), MoveOp::FLOAT32));
407   sim->set_s_register_from_float(5, 5);
408   TRY(mr.addMove(MoveOperand(s15), MoveOperand(s7), MoveOp::FLOAT32));
409   sim->set_s_register_from_float(15, 15);
410   TRY(mr.addMove(MoveOperand(s26), MoveOperand(s14), MoveOp::FLOAT32));
411   sim->set_s_register_from_float(26, 26);
412   TRY(mr.addMove(MoveOperand(s13), MoveOperand(s30), MoveOp::FLOAT32));
413   sim->set_s_register_from_float(13, 13);
414   TRY(mr.addMove(MoveOperand(s26), MoveOperand(s22), MoveOp::FLOAT32));
415   sim->set_s_register_from_float(26, 26);
416   TRY(mr.addMove(MoveOperand(s21), MoveOperand(s6), MoveOp::FLOAT32));
417   sim->set_s_register_from_float(21, 21);
418   TRY(mr.addMove(MoveOperand(s23), MoveOperand(s31), MoveOp::FLOAT32));
419   sim->set_s_register_from_float(23, 23);
420   TRY(mr.addMove(MoveOperand(s7), MoveOperand(s12), MoveOp::FLOAT32));
421   sim->set_s_register_from_float(7, 7);
422   TRY(mr.addMove(MoveOperand(s14), MoveOperand(s10), MoveOp::FLOAT32));
423   sim->set_s_register_from_float(14, 14);
424   TRY(mr.addMove(MoveOperand(d12), MoveOperand(d8), MoveOp::DOUBLE));
425   sim->set_d_register_from_double(12, 12);
426   TRY(mr.addMove(MoveOperand(s5), MoveOperand(s1), MoveOp::FLOAT32));
427   sim->set_s_register_from_float(5, 5);
428   TRY(mr.addMove(MoveOperand(d12), MoveOperand(d2), MoveOp::DOUBLE));
429   sim->set_d_register_from_double(12, 12);
430   TRY(mr.addMove(MoveOperand(s3), MoveOperand(s8), MoveOp::FLOAT32));
431   sim->set_s_register_from_float(3, 3);
432   TRY(mr.addMove(MoveOperand(s14), MoveOperand(s0), MoveOp::FLOAT32));
433   sim->set_s_register_from_float(14, 14);
434   TRY(mr.addMove(MoveOperand(s28), MoveOperand(s29), MoveOp::FLOAT32));
435   sim->set_s_register_from_float(28, 28);
436   TRY(mr.addMove(MoveOperand(d12), MoveOperand(d9), MoveOp::DOUBLE));
437   sim->set_d_register_from_double(12, 12);
438   TRY(mr.addMove(MoveOperand(s29), MoveOperand(s2), MoveOp::FLOAT32));
439   sim->set_s_register_from_float(29, 29);
440   TRY(mr.addMove(MoveOperand(s22), MoveOperand(s27), MoveOp::FLOAT32));
441   sim->set_s_register_from_float(22, 22);
442   TRY(mr.addMove(MoveOperand(s19), MoveOperand(s3), MoveOp::FLOAT32));
443   sim->set_s_register_from_float(19, 19);
444   TRY(mr.addMove(MoveOperand(s21), MoveOperand(s11), MoveOp::FLOAT32));
445   sim->set_s_register_from_float(21, 21);
446   TRY(mr.addMove(MoveOperand(s22), MoveOperand(s13), MoveOp::FLOAT32));
447   sim->set_s_register_from_float(22, 22);
448   TRY(mr.addMove(MoveOperand(s29), MoveOperand(s25), MoveOp::FLOAT32));
449   sim->set_s_register_from_float(29, 29);
450   TRY(mr.addMove(MoveOperand(s29), MoveOperand(s15), MoveOp::FLOAT32));
451   sim->set_s_register_from_float(29, 29);
452   TRY(mr.addMove(MoveOperand(s16), MoveOperand(s23), MoveOp::FLOAT32));
453   sim->set_s_register_from_float(16, 16);
454   // don't explode!
455   TRY(mr.resolve());
456   mover.emit(mr);
457   mover.finish();
458   masm.abiret();
459   JitCode* code = linkAndAllocate(cx, &masm);
460   sim->skipCalleeSavedRegsCheck = true;
461   sim->call(code->raw(), 1, 1);
462 
463   float f;
464   double d;
465   sim->get_float_from_s_register(21, &f);
466   CHECK(int(f) == 0);
467   sim->get_float_from_s_register(26, &f);
468   CHECK(int(f) == 2);
469   sim->get_float_from_s_register(20, &f);
470   CHECK(int(f) == 19);
471   sim->get_float_from_s_register(24, &f);
472   CHECK(int(f) == 4);
473   sim->get_float_from_s_register(9, &f);
474   CHECK(int(f) == 22);
475   sim->get_float_from_s_register(28, &f);
476   CHECK(int(f) == 5);
477   sim->get_float_from_s_register(7, &f);
478   CHECK(int(f) == 15);
479   sim->get_float_from_s_register(14, &f);
480   CHECK(int(f) == 26);
481   sim->get_float_from_s_register(30, &f);
482   CHECK(int(f) == 13);
483   sim->get_float_from_s_register(22, &f);
484   CHECK(int(f) == 26);
485   sim->get_float_from_s_register(6, &f);
486   CHECK(int(f) == 21);
487   sim->get_float_from_s_register(31, &f);
488   CHECK(int(f) == 23);
489   sim->get_float_from_s_register(12, &f);
490   CHECK(int(f) == 7);
491   sim->get_float_from_s_register(10, &f);
492   CHECK(int(f) == 14);
493   sim->get_double_from_d_register(8, &d);
494   CHECK(int(d) == 12);
495   sim->get_float_from_s_register(1, &f);
496   CHECK(int(f) == 5);
497   sim->get_double_from_d_register(2, &d);
498   CHECK(int(d) == 12);
499   sim->get_float_from_s_register(8, &f);
500   CHECK(int(f) == 3);
501   sim->get_float_from_s_register(0, &f);
502   CHECK(int(f) == 14);
503   sim->get_float_from_s_register(29, &f);
504   CHECK(int(f) == 28);
505   sim->get_double_from_d_register(9, &d);
506   CHECK(int(d) == 12);
507   sim->get_float_from_s_register(2, &f);
508   CHECK(int(f) == 29);
509   sim->get_float_from_s_register(27, &f);
510   CHECK(int(f) == 22);
511   sim->get_float_from_s_register(3, &f);
512   CHECK(int(f) == 19);
513   sim->get_float_from_s_register(11, &f);
514   CHECK(int(f) == 21);
515   sim->get_float_from_s_register(13, &f);
516   CHECK(int(f) == 22);
517   sim->get_float_from_s_register(25, &f);
518   CHECK(int(f) == 29);
519   sim->get_float_from_s_register(15, &f);
520   CHECK(int(f) == 29);
521   sim->get_float_from_s_register(23, &f);
522   CHECK(int(f) == 16);
523   return true;
524 }
525 END_TEST(testJitMoveEmitterCycles_autogen3)
BEGIN_TEST(testJitMoveEmitterCycles_bug1299147_1)526 BEGIN_TEST(testJitMoveEmitterCycles_bug1299147_1) {
527   using namespace js;
528   using namespace js::jit;
529   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
530   TempAllocator alloc(&lifo);
531   JitContext jc(cx, &alloc);
532   StackMacroAssembler masm;
533   AutoCreatedBy acb(masm, __func__);
534   MoveEmitter mover(masm);
535   MoveResolver mr;
536   mr.setAllocator(alloc);
537   Simulator* sim = Simulator::Current();
538   // S2 -> S0
539   // S2 -> S6
540   // S3 -> S1
541   // S3 -> S7
542   // D0 -> D1
543   // D0 -> D2
544   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s0), MoveOp::FLOAT32));
545   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s6), MoveOp::FLOAT32));
546   sim->set_s_register_from_float(2, 2);
547   TRY(mr.addMove(MoveOperand(s3), MoveOperand(s1), MoveOp::FLOAT32));
548   TRY(mr.addMove(MoveOperand(s3), MoveOperand(s7), MoveOp::FLOAT32));
549   sim->set_s_register_from_float(3, 4);
550   TRY(mr.addMove(MoveOperand(d0), MoveOperand(d1), MoveOp::FLOAT32));
551   TRY(mr.addMove(MoveOperand(d0), MoveOperand(d2), MoveOp::FLOAT32));
552   sim->set_d_register_from_double(0, 1);
553   // don't explode!
554   TRY(mr.resolve());
555   mover.emit(mr);
556   mover.finish();
557   masm.abiret();
558   JitCode* code = linkAndAllocate(cx, &masm);
559   sim->call(code->raw(), 1, 1);
560   float f;
561   double d;
562   sim->get_double_from_d_register(1, &d);
563   CHECK(d == 1);
564   sim->get_double_from_d_register(2, &d);
565   CHECK(d == 1);
566   sim->get_float_from_s_register(0, &f);
567   CHECK(int(f) == 2);
568   sim->get_float_from_s_register(6, &f);
569   CHECK(int(f) == 2);
570   sim->get_float_from_s_register(1, &f);
571   CHECK(int(f) == 4);
572   sim->get_float_from_s_register(7, &f);
573   CHECK(int(f) == 4);
574   return true;
575 }
576 END_TEST(testJitMoveEmitterCycles_bug1299147_1)
BEGIN_TEST(testJitMoveEmitterCycles_bug1299147)577 BEGIN_TEST(testJitMoveEmitterCycles_bug1299147) {
578   using namespace js;
579   using namespace js::jit;
580   LifoAlloc lifo(LIFO_ALLOC_PRIMARY_CHUNK_SIZE);
581   TempAllocator alloc(&lifo);
582   JitContext jc(cx, &alloc);
583   StackMacroAssembler masm;
584   AutoCreatedBy acb(masm, __func__);
585   MoveEmitter mover(masm);
586   MoveResolver mr;
587   mr.setAllocator(alloc);
588   Simulator* sim = Simulator::Current();
589   // S2 -> S5
590   // S2 -> S6
591   // D0 -> D1
592   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s5), MoveOp::FLOAT32));
593   TRY(mr.addMove(MoveOperand(s2), MoveOperand(s6), MoveOp::FLOAT32));
594   sim->set_s_register_from_float(2, 2);
595   TRY(mr.addMove(MoveOperand(d0), MoveOperand(d1), MoveOp::FLOAT32));
596   sim->set_d_register_from_double(0, 1);
597   // don't explode!
598   TRY(mr.resolve());
599   mover.emit(mr);
600   mover.finish();
601   masm.abiret();
602   JitCode* code = linkAndAllocate(cx, &masm);
603   sim->call(code->raw(), 1, 1);
604   float f;
605   double d;
606   sim->get_double_from_d_register(1, &d);
607   CHECK(d == 1);
608   sim->get_float_from_s_register(5, &f);
609   CHECK(int(f) == 2);
610   sim->get_float_from_s_register(6, &f);
611   CHECK(int(f) == 2);
612   return true;
613 }
614 END_TEST(testJitMoveEmitterCycles_bug1299147)
615 
616 #endif  // JS_SIMULATOR_ARM
617