OSDN Git Service

Limit loop init scope to till end of loop.
[android-x86/external-swiftshader.git] / src / Reactor / Main.cpp
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
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
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
76 TEST(SubzeroReactorTest, SubVectorLoadStore)
77 {
78         Routine *routine = nullptr;
79
80         {
81                 Function<Int(Pointer<Byte>, Pointer<Byte>)> function;
82                 {
83                         Pointer<Byte> in = function.Arg<0>();
84                         Pointer<Byte> out = function.Arg<1>();
85
86                         *Pointer<Int4>(out + 16 * 0)   = *Pointer<Int4>(in + 16 * 0);
87                         *Pointer<Short4>(out + 16 * 1) = *Pointer<Short4>(in + 16 * 1);
88                         *Pointer<Byte8>(out + 16 * 2)  = *Pointer<Byte8>(in + 16 * 2);
89                         *Pointer<Byte4>(out + 16 * 3)  = *Pointer<Byte4>(in + 16 * 3);
90                         *Pointer<Short2>(out + 16 * 4) = *Pointer<Short2>(in + 16 * 4);
91    
92                         Return(0);
93                 }
94
95                 routine = function(L"one");
96
97                 if(routine)
98                 {
99                         int8_t in[16 * 5] = {1,  2,  3,  4,  5,  6,  7,  8,  9,  10, 11, 12, 13, 14, 15, 16,
100                                              17, 18, 19, 20, 21, 22, 23, 24,  0,  0,  0,  0,  0,  0,  0,  0,
101                                              25, 26, 27, 28, 29, 30, 31, 32,  0,  0,  0,  0,  0,  0,  0,  0,
102                                              33, 34, 35, 36,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
103                                              37, 38, 39, 40,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0};
104
105                         int8_t out[16 * 5] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
106                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
107                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
108                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
109                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};
110                 
111                         int (*callable)(void*, void*) = (int(*)(void*,void*))routine->getEntry();
112                         callable(in, out);
113
114                         for(int row = 0; row < 5; row++)
115                         {
116                                 for(int col = 0; col < 16; col++)
117                                 {
118                                         int i = row * 16 + col;
119
120                                         if(in[i] ==  0)
121                                         {
122                                                 EXPECT_EQ(out[i], -1) << "Row " << row << " column " << col <<  " not left untouched.";
123                                         }
124                                         else
125                                         {
126                                                 EXPECT_EQ(out[i], in[i]) << "Row " << row << " column " << col << " not equal to input.";
127                                         }
128                                 }
129                         }
130                 }
131         }
132
133         delete routine;
134 }
135
136 TEST(SubzeroReactorTest, VectorConstant)
137 {
138         Routine *routine = nullptr;
139
140         {
141                 Function<Int(Pointer<Byte>)> function;
142                 {
143                         Pointer<Byte> out = function.Arg<0>();
144
145                         *Pointer<Int4>(out + 16 * 0) = Int4(0x04030201, 0x08070605, 0x0C0B0A09, 0x100F0E0D);
146                         *Pointer<Short4>(out + 16 * 1) = Short4(0x1211, 0x1413, 0x1615, 0x1817);
147                         *Pointer<Byte8>(out + 16 * 2) = Byte8(0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20);
148                         *Pointer<Int2>(out + 16 * 3) = Int2(0x24232221, 0x28272625);
149
150                         Return(0);
151                 }
152
153                 routine = function(L"one");
154
155                 if(routine)
156                 {
157                         int8_t out[16 * 4] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
158                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
159                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
160                                               -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};
161
162                         int8_t exp[16 * 4] = {1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15, 16,
163                                               17, 18, 19, 20, 21, 22, 23, 24, -1, -1, -1, -1, -1, -1, -1, -1,
164                                               25, 26, 27, 28, 29, 30, 31, 32, -1, -1, -1, -1, -1, -1, -1, -1,
165                                               33, 34, 35, 36, 37, 38, 39, 40, -1, -1, -1, -1, -1, -1, -1, -1};
166
167                         int(*callable)(void*) = (int(*)(void*))routine->getEntry();
168                         callable(out);
169
170                         for(int row = 0; row < 4; row++)
171                         {
172                                 for(int col = 0; col < 16; col++)
173                                 {
174                                         int i = row * 16 + col;
175
176                                         EXPECT_EQ(out[i], exp[i]);
177                                 }
178                         }
179                 }
180         }
181
182         delete routine;
183 }
184
185 TEST(SubzeroReactorTest, Swizzle)
186 {
187         Routine *routine = nullptr;
188
189         {
190                 Function<Int(Pointer<Byte>)> function;
191                 {
192                         Pointer<Byte> out = function.Arg<0>();
193
194                         for(int i = 0; i < 256; i++)
195                         {
196                                 *Pointer<Float4>(out + 16 * i) = Swizzle(Float4(1.0f, 2.0f, 3.0f, 4.0f), i);
197                         }
198
199                         for(int i = 0; i < 256; i++)
200                         {
201                                 *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);
202                         }
203
204                         *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));
205                         *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));
206
207                         Return(0);
208                 }
209
210                 routine = function(L"one");
211
212                 if(routine)
213                 {
214                         float out[256 + 256 + 2][4];
215                         memset(out, 0, sizeof(out));
216
217                         float exp[256 + 256 + 2][4];
218
219                         for(int i = 0; i < 256; i++)
220                         {
221                                 exp[i][0] = float((i >> 0) & 0x03) + 1.0f;
222                                 exp[i][1] = float((i >> 2) & 0x03) + 1.0f;
223                                 exp[i][2] = float((i >> 4) & 0x03) + 1.0f;
224                                 exp[i][3] = float((i >> 6) & 0x03) + 1.0f;
225                         }
226
227                         for(int i = 0; i < 256; i++)
228                         {
229                                 exp[256 + i][0] = float((i >> 0) & 0x03) + 1.0f;
230                                 exp[256 + i][1] = float((i >> 2) & 0x03) + 1.0f;
231                                 exp[256 + i][2] = float((i >> 4) & 0x03) + 5.0f;
232                                 exp[256 + i][3] = float((i >> 6) & 0x03) + 5.0f;
233                         }
234
235                         exp[512 + 0][0] = 1.0f;
236                         exp[512 + 0][1] = 5.0f;
237                         exp[512 + 0][2] = 2.0f;
238                         exp[512 + 0][3] = 6.0f;
239
240                         exp[512 + 1][0] = 3.0f;
241                         exp[512 + 1][1] = 7.0f;
242                         exp[512 + 1][2] = 4.0f;
243                         exp[512 + 1][3] = 8.0f;
244
245                         int(*callable)(void*) = (int(*)(void*))routine->getEntry();
246                         callable(out);
247
248                         for(int i = 0; i < 256 + 256 + 2; i++)
249                         {
250                                 EXPECT_EQ(out[i][0], exp[i][0]);
251                                 EXPECT_EQ(out[i][1], exp[i][1]);
252                                 EXPECT_EQ(out[i][2], exp[i][2]);
253                                 EXPECT_EQ(out[i][3], exp[i][3]);
254                         }
255                 }
256         }
257
258         delete routine;
259 }
260
261 TEST(SubzeroReactorTest, Branching)
262 {
263         Routine *routine = nullptr;
264
265         {
266                 Function<Int(Void)> function;
267                 {
268                         Int x = 0;
269
270                         For(Int i = 0, i < 8, i++)
271                         {
272                                 If(i < 2)
273                                 {
274                                         x += 1;
275                                 }
276                                 Else If(i < 4)
277                                 {
278                                         x += 10;
279                                 }
280                                 Else If(i < 6)
281                                 {
282                                         x += 100;
283                                 }
284                                 Else
285                                 {
286                                         x += 1000;
287                                 }
288
289                                 For(Int i = 0, i < 5, i++)
290                                         x += 10000;
291                         }
292
293                         For(Int i = 0, i < 10, i++)
294                                 for(int i = 0; i < 10; i++)
295                                         For(Int i = 0, i < 10, i++)
296                                         {
297                                                 x += 1000000;
298                                         }
299
300                         For(Int i = 0, i < 2, i++)
301                                 If(x == 1000402222)
302                                 {
303                                         If(x != 1000402222)
304                                                 x += 1000000000;
305                                 }
306                                 Else
307                                         x = -5;
308
309                         Return(x);
310                 }
311
312                 routine = function(L"one");
313
314                 if(routine)
315                 {
316                         int(*callable)() = (int(*)())routine->getEntry();
317                         int result = callable();
318
319                         EXPECT_EQ(result, 1000402222);
320                 }
321         }
322
323         delete routine;
324 }
325
326 int main(int argc, char **argv)
327 {
328         ::testing::InitGoogleTest(&argc, argv);
329         return RUN_ALL_TESTS();
330 }