• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 The SwiftShader Authors. All Rights Reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //    http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #include "Reactor.hpp"
16 
17 #include "gtest/gtest.h"
18 
19 using namespace sw;
20 
reference(int * p,int y)21 int reference(int *p, int y)
22 {
23 	int x = p[-1];
24 	int z = 4;
25 
26 	for(int i = 0; i < 10; i++)
27 	{
28 		z += (2 << i) - (i / 3);
29 	}
30 
31 	int sum = x + y + z;
32 
33 	return sum;
34 }
35 
TEST(SubzeroReactorTest,Sample)36 TEST(SubzeroReactorTest, Sample)
37 {
38 	Routine *routine = nullptr;
39 
40 	{
41 		Function<Int(Pointer<Int>, Int)> function;
42 		{
43 			Pointer<Int> p = function.Arg<0>();
44 			Int x = p[-1];
45 			Int y = function.Arg<1>();
46 			Int z = 4;
47 
48 			For(Int i = 0, i < 10, i++)
49 			{
50 				z += (2 << i) - (i / 3);
51 			}
52 
53 			Float4 v;
54 			v.z = As<Float>(z);
55 			z = As<Int>(Float(Float4(v.xzxx).y));
56 
57 			Int sum = x + y + z;
58 
59 			Return(sum);
60 		}
61 
62 		routine = function(L"one");
63 
64 		if(routine)
65 		{
66 			int (*callable)(int*, int) = (int(*)(int*,int))routine->getEntry();
67 			int one[2] = {1, 0};
68 			int result = callable(&one[1], 2);
69 			EXPECT_EQ(result, reference(&one[1], 2));
70 		}
71 	}
72 
73 	delete routine;
74 }
75 
TEST(SubzeroReactorTest,Uninitialized)76 TEST(SubzeroReactorTest, Uninitialized)
77 {
78 	Routine *routine = nullptr;
79 
80 	{
81 		Function<Int()> function;
82 		{
83 			Int a;
84 			Int z = 4;
85 			Int q;
86 			Int c;
87 			Int p;
88 			Bool b;
89 
90 			q += q;
91 
92 			If(b)
93 			{
94 				c = p;
95 			}
96 
97 			Return(a + z + q + c);
98 		}
99 
100 		routine = function(L"one");
101 
102 		if(routine)
103 		{
104 			int (*callable)() = (int(*)())routine->getEntry();
105 			int result = callable();
106 			EXPECT_EQ(result, result);   // Anything is fine, just don't crash
107 		}
108 	}
109 
110 	delete routine;
111 }
112 
TEST(SubzeroReactorTest,SubVectorLoadStore)113 TEST(SubzeroReactorTest, SubVectorLoadStore)
114 {
115 	Routine *routine = nullptr;
116 
117 	{
118 		Function<Int(Pointer<Byte>, Pointer<Byte>)> function;
119 		{
120 			Pointer<Byte> in = function.Arg<0>();
121 			Pointer<Byte> out = function.Arg<1>();
122 
123 			*Pointer<Int4>(out + 16 * 0)   = *Pointer<Int4>(in + 16 * 0);
124 			*Pointer<Short4>(out + 16 * 1) = *Pointer<Short4>(in + 16 * 1);
125 			*Pointer<Byte8>(out + 16 * 2)  = *Pointer<Byte8>(in + 16 * 2);
126 			*Pointer<Byte4>(out + 16 * 3)  = *Pointer<Byte4>(in + 16 * 3);
127 			*Pointer<Short2>(out + 16 * 4) = *Pointer<Short2>(in + 16 * 4);
128 
129 			Return(0);
130 		}
131 
132 		routine = function(L"one");
133 
134 		if(routine)
135 		{
136 			int8_t in[16 * 5] = {1,  2,  3,  4,  5,  6,  7,  8,  9,  10, 11, 12, 13, 14, 15, 16,
137 			                     17, 18, 19, 20, 21, 22, 23, 24,  0,  0,  0,  0,  0,  0,  0,  0,
138 			                     25, 26, 27, 28, 29, 30, 31, 32,  0,  0,  0,  0,  0,  0,  0,  0,
139 			                     33, 34, 35, 36,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
140 			                     37, 38, 39, 40,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0};
141 
142 			int8_t out[16 * 5] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
143 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
144 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
145 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
146 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};
147 
148 			int (*callable)(void*, void*) = (int(*)(void*,void*))routine->getEntry();
149 			callable(in, out);
150 
151 			for(int row = 0; row < 5; row++)
152 			{
153 				for(int col = 0; col < 16; col++)
154 				{
155 					int i = row * 16 + col;
156 
157 					if(in[i] ==  0)
158 					{
159 						EXPECT_EQ(out[i], -1) << "Row " << row << " column " << col <<  " not left untouched.";
160 					}
161 					else
162 					{
163 						EXPECT_EQ(out[i], in[i]) << "Row " << row << " column " << col << " not equal to input.";
164 					}
165 				}
166 			}
167 		}
168 	}
169 
170 	delete routine;
171 }
172 
TEST(SubzeroReactorTest,VectorConstant)173 TEST(SubzeroReactorTest, VectorConstant)
174 {
175 	Routine *routine = nullptr;
176 
177 	{
178 		Function<Int(Pointer<Byte>)> function;
179 		{
180 			Pointer<Byte> out = function.Arg<0>();
181 
182 			*Pointer<Int4>(out + 16 * 0) = Int4(0x04030201, 0x08070605, 0x0C0B0A09, 0x100F0E0D);
183 			*Pointer<Short4>(out + 16 * 1) = Short4(0x1211, 0x1413, 0x1615, 0x1817);
184 			*Pointer<Byte8>(out + 16 * 2) = Byte8(0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20);
185 			*Pointer<Int2>(out + 16 * 3) = Int2(0x24232221, 0x28272625);
186 
187 			Return(0);
188 		}
189 
190 		routine = function(L"one");
191 
192 		if(routine)
193 		{
194 			int8_t out[16 * 4] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
195 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
196 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
197 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};
198 
199 			int8_t exp[16 * 4] = {1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15, 16,
200 			                      17, 18, 19, 20, 21, 22, 23, 24, -1, -1, -1, -1, -1, -1, -1, -1,
201 			                      25, 26, 27, 28, 29, 30, 31, 32, -1, -1, -1, -1, -1, -1, -1, -1,
202 			                      33, 34, 35, 36, 37, 38, 39, 40, -1, -1, -1, -1, -1, -1, -1, -1};
203 
204 			int(*callable)(void*) = (int(*)(void*))routine->getEntry();
205 			callable(out);
206 
207 			for(int row = 0; row < 4; row++)
208 			{
209 				for(int col = 0; col < 16; col++)
210 				{
211 					int i = row * 16 + col;
212 
213 					EXPECT_EQ(out[i], exp[i]);
214 				}
215 			}
216 		}
217 	}
218 
219 	delete routine;
220 }
221 
TEST(SubzeroReactorTest,Concatenate)222 TEST(SubzeroReactorTest, Concatenate)
223 {
224 	Routine *routine = nullptr;
225 
226 	{
227 		Function<Int(Pointer<Byte>)> function;
228 		{
229 			Pointer<Byte> out = function.Arg<0>();
230 
231 			*Pointer<Int4>(out + 16 * 0)   = Int4(Int2(0x04030201, 0x08070605), Int2(0x0C0B0A09, 0x100F0E0D));
232 			*Pointer<Short8>(out + 16 * 1) = Short8(Short4(0x0201, 0x0403, 0x0605, 0x0807), Short4(0x0A09, 0x0C0B, 0x0E0D, 0x100F));
233 
234 			Return(0);
235 		}
236 
237 		routine = function(L"one");
238 
239 		if(routine)
240 		{
241 			int8_t ref[16 * 5] = {1,  2,  3,  4,  5,  6,  7,  8,  9,  10, 11, 12, 13, 14, 15, 16,
242 			                      1,  2,  3,  4,  5,  6,  7,  8,  9,  10, 11, 12, 13, 14, 15, 16};
243 
244 			int8_t out[16 * 5] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
245 			                      -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};
246 
247 			int (*callable)(void*) = (int(*)(void*))routine->getEntry();
248 			callable(out);
249 
250 			for(int row = 0; row < 2; row++)
251 			{
252 				for(int col = 0; col < 16; col++)
253 				{
254 					int i = row * 16 + col;
255 
256 					EXPECT_EQ(out[i], ref[i]) << "Row " << row << " column " << col << " not equal to reference.";
257 				}
258 			}
259 		}
260 	}
261 
262 	delete routine;
263 }
264 
TEST(SubzeroReactorTest,Swizzle)265 TEST(SubzeroReactorTest, Swizzle)
266 {
267 	Routine *routine = nullptr;
268 
269 	{
270 		Function<Int(Pointer<Byte>)> function;
271 		{
272 			Pointer<Byte> out = function.Arg<0>();
273 
274 			for(int i = 0; i < 256; i++)
275 			{
276 				*Pointer<Float4>(out + 16 * i) = Swizzle(Float4(1.0f, 2.0f, 3.0f, 4.0f), i);
277 			}
278 
279 			for(int i = 0; i < 256; i++)
280 			{
281 				*Pointer<Float4>(out + 16 * (256 + i)) = ShuffleLowHigh(Float4(1.0f, 2.0f, 3.0f, 4.0f), Float4(5.0f, 6.0f, 7.0f, 8.0f), i);
282 			}
283 
284 			*Pointer<Float4>(out + 16 * (512 + 0)) = UnpackLow(Float4(1.0f, 2.0f, 3.0f, 4.0f), Float4(5.0f, 6.0f, 7.0f, 8.0f));
285 			*Pointer<Float4>(out + 16 * (512 + 1)) = UnpackHigh(Float4(1.0f, 2.0f, 3.0f, 4.0f), Float4(5.0f, 6.0f, 7.0f, 8.0f));
286 			*Pointer<Int2>(out + 16 * (512 + 2)) = UnpackLow(Short4(1, 2, 3, 4), Short4(5, 6, 7, 8));
287 			*Pointer<Int2>(out + 16 * (512 + 3)) = UnpackHigh(Short4(1, 2, 3, 4), Short4(5, 6, 7, 8));
288 			*Pointer<Short4>(out + 16 * (512 + 4)) = UnpackLow(Byte8(1, 2, 3, 4, 5, 6, 7, 8), Byte8(9, 10, 11, 12, 13, 14, 15, 16));
289 			*Pointer<Short4>(out + 16 * (512 + 5)) = UnpackHigh(Byte8(1, 2, 3, 4, 5, 6, 7, 8), Byte8(9, 10, 11, 12, 13, 14, 15, 16));
290 
291 			Return(0);
292 		}
293 
294 		routine = function(L"one");
295 
296 		if(routine)
297 		{
298 			struct
299 			{
300 				float f[256 + 256 + 2][4];
301 				int i[4][4];
302 			} out;
303 
304 			memset(&out, 0, sizeof(out));
305 
306 			int(*callable)(void*) = (int(*)(void*))routine->getEntry();
307 			callable(&out);
308 
309 			for(int i = 0; i < 256; i++)
310 			{
311 				EXPECT_EQ(out.f[i][0], float((i >> 0) & 0x03) + 1.0f);
312 				EXPECT_EQ(out.f[i][1], float((i >> 2) & 0x03) + 1.0f);
313 				EXPECT_EQ(out.f[i][2], float((i >> 4) & 0x03) + 1.0f);
314 				EXPECT_EQ(out.f[i][3], float((i >> 6) & 0x03) + 1.0f);
315 			}
316 
317 			for(int i = 0; i < 256; i++)
318 			{
319 				EXPECT_EQ(out.f[256 + i][0], float((i >> 0) & 0x03) + 1.0f);
320 				EXPECT_EQ(out.f[256 + i][1], float((i >> 2) & 0x03) + 1.0f);
321 				EXPECT_EQ(out.f[256 + i][2], float((i >> 4) & 0x03) + 5.0f);
322 				EXPECT_EQ(out.f[256 + i][3], float((i >> 6) & 0x03) + 5.0f);
323 			}
324 
325 			EXPECT_EQ(out.f[512 + 0][0], 1.0f);
326 			EXPECT_EQ(out.f[512 + 0][1], 5.0f);
327 			EXPECT_EQ(out.f[512 + 0][2], 2.0f);
328 			EXPECT_EQ(out.f[512 + 0][3], 6.0f);
329 
330 			EXPECT_EQ(out.f[512 + 1][0], 3.0f);
331 			EXPECT_EQ(out.f[512 + 1][1], 7.0f);
332 			EXPECT_EQ(out.f[512 + 1][2], 4.0f);
333 			EXPECT_EQ(out.f[512 + 1][3], 8.0f);
334 
335 			EXPECT_EQ(out.i[0][0], 0x00050001);
336 			EXPECT_EQ(out.i[0][1], 0x00060002);
337 			EXPECT_EQ(out.i[0][2], 0x00000000);
338 			EXPECT_EQ(out.i[0][3], 0x00000000);
339 
340 			EXPECT_EQ(out.i[1][0], 0x00070003);
341 			EXPECT_EQ(out.i[1][1], 0x00080004);
342 			EXPECT_EQ(out.i[1][2], 0x00000000);
343 			EXPECT_EQ(out.i[1][3], 0x00000000);
344 
345 			EXPECT_EQ(out.i[2][0], 0x0A020901);
346 			EXPECT_EQ(out.i[2][1], 0x0C040B03);
347 			EXPECT_EQ(out.i[2][2], 0x00000000);
348 			EXPECT_EQ(out.i[2][3], 0x00000000);
349 
350 			EXPECT_EQ(out.i[3][0], 0x0E060D05);
351 			EXPECT_EQ(out.i[3][1], 0x10080F07);
352 			EXPECT_EQ(out.i[3][2], 0x00000000);
353 			EXPECT_EQ(out.i[3][3], 0x00000000);
354 		}
355 	}
356 
357 	delete routine;
358 }
359 
TEST(SubzeroReactorTest,Branching)360 TEST(SubzeroReactorTest, Branching)
361 {
362 	Routine *routine = nullptr;
363 
364 	{
365 		Function<Int(Void)> function;
366 		{
367 			Int x = 0;
368 
369 			For(Int i = 0, i < 8, i++)
370 			{
371 				If(i < 2)
372 				{
373 					x += 1;
374 				}
375 				Else If(i < 4)
376 				{
377 					x += 10;
378 				}
379 				Else If(i < 6)
380 				{
381 					x += 100;
382 				}
383 				Else
384 				{
385 					x += 1000;
386 				}
387 
388 				For(Int i = 0, i < 5, i++)
389 					x += 10000;
390 			}
391 
392 			For(Int i = 0, i < 10, i++)
393 				for(int i = 0; i < 10; i++)
394 					For(Int i = 0, i < 10, i++)
395 					{
396 						x += 1000000;
397 					}
398 
399 			For(Int i = 0, i < 2, i++)
400 				If(x == 1000402222)
401 				{
402 					If(x != 1000402222)
403 						x += 1000000000;
404 				}
405 				Else
406 					x = -5;
407 
408 			Return(x);
409 		}
410 
411 		routine = function(L"one");
412 
413 		if(routine)
414 		{
415 			int(*callable)() = (int(*)())routine->getEntry();
416 			int result = callable();
417 
418 			EXPECT_EQ(result, 1000402222);
419 		}
420 	}
421 
422 	delete routine;
423 }
424 
TEST(SubzeroReactorTest,MinMax)425 TEST(SubzeroReactorTest, MinMax)
426 {
427 	Routine *routine = nullptr;
428 
429 	{
430 		Function<Int(Pointer<Byte>)> function;
431 		{
432 			Pointer<Byte> out = function.Arg<0>();
433 
434 			*Pointer<Float4>(out + 16 * 0) = Min(Float4(1.0f, 0.0f, -0.0f, +0.0f), Float4(0.0f, 1.0f, +0.0f, -0.0f));
435 			*Pointer<Float4>(out + 16 * 1) = Max(Float4(1.0f, 0.0f, -0.0f, +0.0f), Float4(0.0f, 1.0f, +0.0f, -0.0f));
436 
437 			*Pointer<Int4>(out + 16 * 2) = Min(Int4(1, 0, -1, -0), Int4(0, 1, 0, +0));
438 			*Pointer<Int4>(out + 16 * 3) = Max(Int4(1, 0, -1, -0), Int4(0, 1, 0, +0));
439 			*Pointer<UInt4>(out + 16 * 4) = Min(UInt4(1, 0, -1, -0), UInt4(0, 1, 0, +0));
440 			*Pointer<UInt4>(out + 16 * 5) = Max(UInt4(1, 0, -1, -0), UInt4(0, 1, 0, +0));
441 
442 			*Pointer<Short4>(out + 16 * 6) = Min(Short4(1, 0, -1, -0), Short4(0, 1, 0, +0));
443 			*Pointer<Short4>(out + 16 * 7) = Max(Short4(1, 0, -1, -0), Short4(0, 1, 0, +0));
444 			*Pointer<UShort4>(out + 16 * 8) = Min(UShort4(1, 0, -1, -0), UShort4(0, 1, 0, +0));
445 			*Pointer<UShort4>(out + 16 * 9) = Max(UShort4(1, 0, -1, -0), UShort4(0, 1, 0, +0));
446 
447 			Return(0);
448 		}
449 
450 		routine = function(L"one");
451 
452 		if(routine)
453 		{
454 			int out[10][4];
455 
456 			memset(&out, 0, sizeof(out));
457 
458 			int(*callable)(void*) = (int(*)(void*))routine->getEntry();
459 			callable(&out);
460 
461 			EXPECT_EQ(out[0][0], 0x00000000);
462 			EXPECT_EQ(out[0][1], 0x00000000);
463 			EXPECT_EQ(out[0][2], 0x00000000);
464 			EXPECT_EQ(out[0][3], 0x80000000);
465 
466 			EXPECT_EQ(out[1][0], 0x3F800000);
467 			EXPECT_EQ(out[1][1], 0x3F800000);
468 			EXPECT_EQ(out[1][2], 0x00000000);
469 			EXPECT_EQ(out[1][3], 0x80000000);
470 
471 			EXPECT_EQ(out[2][0], 0x00000000);
472 			EXPECT_EQ(out[2][1], 0x00000000);
473 			EXPECT_EQ(out[2][2], 0xFFFFFFFF);
474 			EXPECT_EQ(out[2][3], 0x00000000);
475 
476 			EXPECT_EQ(out[3][0], 0x00000001);
477 			EXPECT_EQ(out[3][1], 0x00000001);
478 			EXPECT_EQ(out[3][2], 0x00000000);
479 			EXPECT_EQ(out[3][3], 0x00000000);
480 
481 			EXPECT_EQ(out[4][0], 0x00000000);
482 			EXPECT_EQ(out[4][1], 0x00000000);
483 			EXPECT_EQ(out[4][2], 0x00000000);
484 			EXPECT_EQ(out[4][3], 0x00000000);
485 
486 			EXPECT_EQ(out[5][0], 0x00000001);
487 			EXPECT_EQ(out[5][1], 0x00000001);
488 			EXPECT_EQ(out[5][2], 0xFFFFFFFF);
489 			EXPECT_EQ(out[5][3], 0x00000000);
490 
491 			EXPECT_EQ(out[6][0], 0x00000000);
492 			EXPECT_EQ(out[6][1], 0x0000FFFF);
493 			EXPECT_EQ(out[6][2], 0x00000000);
494 			EXPECT_EQ(out[6][3], 0x00000000);
495 
496 			EXPECT_EQ(out[7][0], 0x00010001);
497 			EXPECT_EQ(out[7][1], 0x00000000);
498 			EXPECT_EQ(out[7][2], 0x00000000);
499 			EXPECT_EQ(out[7][3], 0x00000000);
500 
501 			EXPECT_EQ(out[8][0], 0x00000000);
502 			EXPECT_EQ(out[8][1], 0x00000000);
503 			EXPECT_EQ(out[8][2], 0x00000000);
504 			EXPECT_EQ(out[8][3], 0x00000000);
505 
506 			EXPECT_EQ(out[9][0], 0x00010001);
507 			EXPECT_EQ(out[9][1], 0x0000FFFF);
508 			EXPECT_EQ(out[9][2], 0x00000000);
509 			EXPECT_EQ(out[9][3], 0x00000000);
510 		}
511 	}
512 
513 	delete routine;
514 }
515 
TEST(SubzeroReactorTest,NotNeg)516 TEST(SubzeroReactorTest, NotNeg)
517 {
518 	Routine *routine = nullptr;
519 
520 	{
521 		Function<Int(Pointer<Byte>)> function;
522 		{
523 			Pointer<Byte> out = function.Arg<0>();
524 
525 			*Pointer<Int>(out + 16 * 0) = ~Int(0x55555555);
526 			*Pointer<Short>(out + 16 * 1) = ~Short(0x5555);
527 			*Pointer<Int4>(out + 16 * 2) = ~Int4(0x55555555, 0xAAAAAAAA, 0x00000000, 0xFFFFFFFF);
528 			*Pointer<Short4>(out + 16 * 3) = ~Short4(0x5555, 0xAAAA, 0x0000, 0xFFFF);
529 
530 			*Pointer<Int>(out + 16 * 4) = -Int(0x55555555);
531 			*Pointer<Short>(out + 16 * 5) = -Short(0x5555);
532 			*Pointer<Int4>(out + 16 * 6) = -Int4(0x55555555, 0xAAAAAAAA, 0x00000000, 0xFFFFFFFF);
533 			*Pointer<Short4>(out + 16 * 7) = -Short4(0x5555, 0xAAAA, 0x0000, 0xFFFF);
534 
535 			*Pointer<Float4>(out + 16 * 8) = -Float4(1.0f, -1.0f, 0.0f, -0.0f);
536 
537 			Return(0);
538 		}
539 
540 		routine = function(L"one");
541 
542 		if(routine)
543 		{
544 			int out[10][4];
545 
546 			memset(&out, 0, sizeof(out));
547 
548 			int(*callable)(void*) = (int(*)(void*))routine->getEntry();
549 			callable(&out);
550 
551 			EXPECT_EQ(out[0][0], 0xAAAAAAAA);
552 			EXPECT_EQ(out[0][1], 0x00000000);
553 			EXPECT_EQ(out[0][2], 0x00000000);
554 			EXPECT_EQ(out[0][3], 0x00000000);
555 
556 			EXPECT_EQ(out[1][0], 0x0000AAAA);
557 			EXPECT_EQ(out[1][1], 0x00000000);
558 			EXPECT_EQ(out[1][2], 0x00000000);
559 			EXPECT_EQ(out[1][3], 0x00000000);
560 
561 			EXPECT_EQ(out[2][0], 0xAAAAAAAA);
562 			EXPECT_EQ(out[2][1], 0x55555555);
563 			EXPECT_EQ(out[2][2], 0xFFFFFFFF);
564 			EXPECT_EQ(out[2][3], 0x00000000);
565 
566 			EXPECT_EQ(out[3][0], 0x5555AAAA);
567 			EXPECT_EQ(out[3][1], 0x0000FFFF);
568 			EXPECT_EQ(out[3][2], 0x00000000);
569 			EXPECT_EQ(out[3][3], 0x00000000);
570 
571 			EXPECT_EQ(out[4][0], 0xAAAAAAAB);
572 			EXPECT_EQ(out[4][1], 0x00000000);
573 			EXPECT_EQ(out[4][2], 0x00000000);
574 			EXPECT_EQ(out[4][3], 0x00000000);
575 
576 			EXPECT_EQ(out[5][0], 0x0000AAAB);
577 			EXPECT_EQ(out[5][1], 0x00000000);
578 			EXPECT_EQ(out[5][2], 0x00000000);
579 			EXPECT_EQ(out[5][3], 0x00000000);
580 
581 			EXPECT_EQ(out[6][0], 0xAAAAAAAB);
582 			EXPECT_EQ(out[6][1], 0x55555556);
583 			EXPECT_EQ(out[6][2], 0x00000000);
584 			EXPECT_EQ(out[6][3], 0x00000001);
585 
586 			EXPECT_EQ(out[7][0], 0x5556AAAB);
587 			EXPECT_EQ(out[7][1], 0x00010000);
588 			EXPECT_EQ(out[7][2], 0x00000000);
589 			EXPECT_EQ(out[7][3], 0x00000000);
590 
591 			EXPECT_EQ(out[8][0], 0xBF800000);
592 			EXPECT_EQ(out[8][1], 0x3F800000);
593 			EXPECT_EQ(out[8][2], 0x80000000);
594 			EXPECT_EQ(out[8][3], 0x00000000);
595 		}
596 	}
597 
598 	delete routine;
599 }
600 
TEST(SubzeroReactorTest,VectorCompare)601 TEST(SubzeroReactorTest, VectorCompare)
602 {
603 	Routine *routine = nullptr;
604 
605 	{
606 		Function<Int(Pointer<Byte>)> function;
607 		{
608 			Pointer<Byte> out = function.Arg<0>();
609 
610 			*Pointer<Int4>(out + 16 * 0) = CmpEQ(Float4(1.0f, 1.0f, -0.0f, +0.0f), Float4(0.0f, 1.0f, +0.0f, -0.0f));
611 			*Pointer<Int4>(out + 16 * 1) = CmpEQ(Int4(1, 0, -1, -0), Int4(0, 1, 0, +0));
612 			*Pointer<Byte8>(out + 16 * 2) = CmpEQ(SByte8(1, 2, 3, 4, 5, 6, 7, 8), SByte8(7, 6, 5, 4, 3, 2, 1, 0));
613 
614 			*Pointer<Int4>(out + 16 * 3) = CmpNLT(Float4(1.0f, 1.0f, -0.0f, +0.0f), Float4(0.0f, 1.0f, +0.0f, -0.0f));
615 			*Pointer<Int4>(out + 16 * 4) = CmpNLT(Int4(1, 0, -1, -0), Int4(0, 1, 0, +0));
616 			*Pointer<Byte8>(out + 16 * 5) = CmpGT(SByte8(1, 2, 3, 4, 5, 6, 7, 8), SByte8(7, 6, 5, 4, 3, 2, 1, 0));
617 
618 			Return(0);
619 		}
620 
621 		routine = function(L"one");
622 
623 		if(routine)
624 		{
625 			int out[6][4];
626 
627 			memset(&out, 0, sizeof(out));
628 
629 			int(*callable)(void*) = (int(*)(void*))routine->getEntry();
630 			callable(&out);
631 
632 			EXPECT_EQ(out[0][0], 0x00000000);
633 			EXPECT_EQ(out[0][1], 0xFFFFFFFF);
634 			EXPECT_EQ(out[0][2], 0xFFFFFFFF);
635 			EXPECT_EQ(out[0][3], 0xFFFFFFFF);
636 
637 			EXPECT_EQ(out[1][0], 0x00000000);
638 			EXPECT_EQ(out[1][1], 0x00000000);
639 			EXPECT_EQ(out[1][2], 0x00000000);
640 			EXPECT_EQ(out[1][3], 0xFFFFFFFF);
641 
642 			EXPECT_EQ(out[2][0], 0xFF000000);
643 			EXPECT_EQ(out[2][1], 0x00000000);
644 
645 			EXPECT_EQ(out[3][0], 0xFFFFFFFF);
646 			EXPECT_EQ(out[3][1], 0xFFFFFFFF);
647 			EXPECT_EQ(out[3][2], 0xFFFFFFFF);
648 			EXPECT_EQ(out[3][3], 0xFFFFFFFF);
649 
650 			EXPECT_EQ(out[4][0], 0xFFFFFFFF);
651 			EXPECT_EQ(out[4][1], 0x00000000);
652 			EXPECT_EQ(out[4][2], 0x00000000);
653 			EXPECT_EQ(out[4][3], 0xFFFFFFFF);
654 
655 			EXPECT_EQ(out[5][0], 0x00000000);
656 			EXPECT_EQ(out[5][1], 0xFFFFFFFF);
657 		}
658 	}
659 
660 	delete routine;
661 }
662 
main(int argc,char ** argv)663 int main(int argc, char **argv)
664 {
665 	::testing::InitGoogleTest(&argc, argv);
666 	return RUN_ALL_TESTS();
667 }
668