1 /*
2  * Copyright (C) 2016 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 // Don't edit this file!  It is auto-generated by frameworks/rs/api/generate.sh.
18 
19 package android.renderscript.cts;
20 
21 import android.renderscript.Allocation;
22 import android.renderscript.RSRuntimeException;
23 import android.renderscript.Element;
24 import android.renderscript.cts.Target;
25 
26 import java.util.Arrays;
27 
28 public class TestMad extends RSBaseCompute {
29 
30     private ScriptC_TestMad script;
31     private ScriptC_TestMadRelaxed scriptRelaxed;
32 
33     @Override
setUp()34     protected void setUp() throws Exception {
35         super.setUp();
36         script = new ScriptC_TestMad(mRS);
37         scriptRelaxed = new ScriptC_TestMadRelaxed(mRS);
38     }
39 
40     @Override
tearDown()41     protected void tearDown() throws Exception {
42         script.destroy();
43         scriptRelaxed.destroy();
44         super.tearDown();
45     }
46 
47     public class ArgumentsFloatFloatFloatFloat {
48         public float inMultiplicand1;
49         public float inMultiplicand2;
50         public float inOffset;
51         public Target.Floaty out;
52     }
53 
checkMadFloatFloatFloatFloat()54     private void checkMadFloatFloatFloatFloat() {
55         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 1, 0x2a4461e340b4de48l, false);
56         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 1, 0x2a4461e340b4de49l, false);
57         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 1, 0xcea3b86dc50ce0fcl, false);
58         try {
59             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 1), INPUTSIZE);
60             script.set_gAllocInMultiplicand2(inMultiplicand2);
61             script.set_gAllocInOffset(inOffset);
62             script.forEach_testMadFloatFloatFloatFloat(inMultiplicand1, out);
63             verifyResultsMadFloatFloatFloatFloat(inMultiplicand1, inMultiplicand2, inOffset, out, false);
64             out.destroy();
65         } catch (Exception e) {
66             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloatFloatFloatFloat: " + e.toString());
67         }
68         try {
69             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 1), INPUTSIZE);
70             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
71             scriptRelaxed.set_gAllocInOffset(inOffset);
72             scriptRelaxed.forEach_testMadFloatFloatFloatFloat(inMultiplicand1, out);
73             verifyResultsMadFloatFloatFloatFloat(inMultiplicand1, inMultiplicand2, inOffset, out, true);
74             out.destroy();
75         } catch (Exception e) {
76             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloatFloatFloatFloat: " + e.toString());
77         }
78         inMultiplicand1.destroy();
79         inMultiplicand2.destroy();
80         inOffset.destroy();
81     }
82 
verifyResultsMadFloatFloatFloatFloat(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)83     private void verifyResultsMadFloatFloatFloatFloat(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
84         float[] arrayInMultiplicand1 = new float[INPUTSIZE * 1];
85         Arrays.fill(arrayInMultiplicand1, (float) 42);
86         inMultiplicand1.copyTo(arrayInMultiplicand1);
87         float[] arrayInMultiplicand2 = new float[INPUTSIZE * 1];
88         Arrays.fill(arrayInMultiplicand2, (float) 42);
89         inMultiplicand2.copyTo(arrayInMultiplicand2);
90         float[] arrayInOffset = new float[INPUTSIZE * 1];
91         Arrays.fill(arrayInOffset, (float) 42);
92         inOffset.copyTo(arrayInOffset);
93         float[] arrayOut = new float[INPUTSIZE * 1];
94         Arrays.fill(arrayOut, (float) 42);
95         out.copyTo(arrayOut);
96         StringBuilder message = new StringBuilder();
97         boolean errorFound = false;
98         for (int i = 0; i < INPUTSIZE; i++) {
99             for (int j = 0; j < 1 ; j++) {
100                 // Extract the inputs.
101                 ArgumentsFloatFloatFloatFloat args = new ArgumentsFloatFloatFloatFloat();
102                 args.inMultiplicand1 = arrayInMultiplicand1[i];
103                 args.inMultiplicand2 = arrayInMultiplicand2[i];
104                 args.inOffset = arrayInOffset[i];
105                 // Figure out what the outputs should have been.
106                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.FLOAT, relaxed);
107                 CoreMathVerifier.computeMad(args, target);
108                 // Validate the outputs.
109                 boolean valid = true;
110                 if (!args.out.couldBe(arrayOut[i * 1 + j])) {
111                     valid = false;
112                 }
113                 if (!valid) {
114                     if (!errorFound) {
115                         errorFound = true;
116                         message.append("Input inMultiplicand1: ");
117                         appendVariableToMessage(message, args.inMultiplicand1);
118                         message.append("\n");
119                         message.append("Input inMultiplicand2: ");
120                         appendVariableToMessage(message, args.inMultiplicand2);
121                         message.append("\n");
122                         message.append("Input inOffset: ");
123                         appendVariableToMessage(message, args.inOffset);
124                         message.append("\n");
125                         message.append("Expected output out: ");
126                         appendVariableToMessage(message, args.out);
127                         message.append("\n");
128                         message.append("Actual   output out: ");
129                         appendVariableToMessage(message, arrayOut[i * 1 + j]);
130                         if (!args.out.couldBe(arrayOut[i * 1 + j])) {
131                             message.append(" FAIL");
132                         }
133                         message.append("\n");
134                         message.append("Errors at");
135                     }
136                     message.append(" [");
137                     message.append(Integer.toString(i));
138                     message.append(", ");
139                     message.append(Integer.toString(j));
140                     message.append("]");
141                 }
142             }
143         }
144         assertFalse("Incorrect output for checkMadFloatFloatFloatFloat" +
145                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
146     }
147 
checkMadFloat2Float2Float2Float2()148     private void checkMadFloat2Float2Float2Float2() {
149         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 2, 0xdfffb28a8a5fd7c0l, false);
150         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 2, 0xdfffb28a8a5fd7c1l, false);
151         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 2, 0x3da8592f318f8924l, false);
152         try {
153             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 2), INPUTSIZE);
154             script.set_gAllocInMultiplicand2(inMultiplicand2);
155             script.set_gAllocInOffset(inOffset);
156             script.forEach_testMadFloat2Float2Float2Float2(inMultiplicand1, out);
157             verifyResultsMadFloat2Float2Float2Float2(inMultiplicand1, inMultiplicand2, inOffset, out, false);
158             out.destroy();
159         } catch (Exception e) {
160             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat2Float2Float2Float2: " + e.toString());
161         }
162         try {
163             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 2), INPUTSIZE);
164             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
165             scriptRelaxed.set_gAllocInOffset(inOffset);
166             scriptRelaxed.forEach_testMadFloat2Float2Float2Float2(inMultiplicand1, out);
167             verifyResultsMadFloat2Float2Float2Float2(inMultiplicand1, inMultiplicand2, inOffset, out, true);
168             out.destroy();
169         } catch (Exception e) {
170             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat2Float2Float2Float2: " + e.toString());
171         }
172         inMultiplicand1.destroy();
173         inMultiplicand2.destroy();
174         inOffset.destroy();
175     }
176 
verifyResultsMadFloat2Float2Float2Float2(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)177     private void verifyResultsMadFloat2Float2Float2Float2(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
178         float[] arrayInMultiplicand1 = new float[INPUTSIZE * 2];
179         Arrays.fill(arrayInMultiplicand1, (float) 42);
180         inMultiplicand1.copyTo(arrayInMultiplicand1);
181         float[] arrayInMultiplicand2 = new float[INPUTSIZE * 2];
182         Arrays.fill(arrayInMultiplicand2, (float) 42);
183         inMultiplicand2.copyTo(arrayInMultiplicand2);
184         float[] arrayInOffset = new float[INPUTSIZE * 2];
185         Arrays.fill(arrayInOffset, (float) 42);
186         inOffset.copyTo(arrayInOffset);
187         float[] arrayOut = new float[INPUTSIZE * 2];
188         Arrays.fill(arrayOut, (float) 42);
189         out.copyTo(arrayOut);
190         StringBuilder message = new StringBuilder();
191         boolean errorFound = false;
192         for (int i = 0; i < INPUTSIZE; i++) {
193             for (int j = 0; j < 2 ; j++) {
194                 // Extract the inputs.
195                 ArgumentsFloatFloatFloatFloat args = new ArgumentsFloatFloatFloatFloat();
196                 args.inMultiplicand1 = arrayInMultiplicand1[i * 2 + j];
197                 args.inMultiplicand2 = arrayInMultiplicand2[i * 2 + j];
198                 args.inOffset = arrayInOffset[i * 2 + j];
199                 // Figure out what the outputs should have been.
200                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.FLOAT, relaxed);
201                 CoreMathVerifier.computeMad(args, target);
202                 // Validate the outputs.
203                 boolean valid = true;
204                 if (!args.out.couldBe(arrayOut[i * 2 + j])) {
205                     valid = false;
206                 }
207                 if (!valid) {
208                     if (!errorFound) {
209                         errorFound = true;
210                         message.append("Input inMultiplicand1: ");
211                         appendVariableToMessage(message, args.inMultiplicand1);
212                         message.append("\n");
213                         message.append("Input inMultiplicand2: ");
214                         appendVariableToMessage(message, args.inMultiplicand2);
215                         message.append("\n");
216                         message.append("Input inOffset: ");
217                         appendVariableToMessage(message, args.inOffset);
218                         message.append("\n");
219                         message.append("Expected output out: ");
220                         appendVariableToMessage(message, args.out);
221                         message.append("\n");
222                         message.append("Actual   output out: ");
223                         appendVariableToMessage(message, arrayOut[i * 2 + j]);
224                         if (!args.out.couldBe(arrayOut[i * 2 + j])) {
225                             message.append(" FAIL");
226                         }
227                         message.append("\n");
228                         message.append("Errors at");
229                     }
230                     message.append(" [");
231                     message.append(Integer.toString(i));
232                     message.append(", ");
233                     message.append(Integer.toString(j));
234                     message.append("]");
235                 }
236             }
237         }
238         assertFalse("Incorrect output for checkMadFloat2Float2Float2Float2" +
239                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
240     }
241 
checkMadFloat3Float3Float3Float3()242     private void checkMadFloat3Float3Float3Float3() {
243         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 3, 0xdd6226bde1551f1cl, false);
244         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 3, 0xdd6226bde1551f1dl, false);
245         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 3, 0x117f5b0bfb77d218l, false);
246         try {
247             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 3), INPUTSIZE);
248             script.set_gAllocInMultiplicand2(inMultiplicand2);
249             script.set_gAllocInOffset(inOffset);
250             script.forEach_testMadFloat3Float3Float3Float3(inMultiplicand1, out);
251             verifyResultsMadFloat3Float3Float3Float3(inMultiplicand1, inMultiplicand2, inOffset, out, false);
252             out.destroy();
253         } catch (Exception e) {
254             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat3Float3Float3Float3: " + e.toString());
255         }
256         try {
257             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 3), INPUTSIZE);
258             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
259             scriptRelaxed.set_gAllocInOffset(inOffset);
260             scriptRelaxed.forEach_testMadFloat3Float3Float3Float3(inMultiplicand1, out);
261             verifyResultsMadFloat3Float3Float3Float3(inMultiplicand1, inMultiplicand2, inOffset, out, true);
262             out.destroy();
263         } catch (Exception e) {
264             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat3Float3Float3Float3: " + e.toString());
265         }
266         inMultiplicand1.destroy();
267         inMultiplicand2.destroy();
268         inOffset.destroy();
269     }
270 
verifyResultsMadFloat3Float3Float3Float3(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)271     private void verifyResultsMadFloat3Float3Float3Float3(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
272         float[] arrayInMultiplicand1 = new float[INPUTSIZE * 4];
273         Arrays.fill(arrayInMultiplicand1, (float) 42);
274         inMultiplicand1.copyTo(arrayInMultiplicand1);
275         float[] arrayInMultiplicand2 = new float[INPUTSIZE * 4];
276         Arrays.fill(arrayInMultiplicand2, (float) 42);
277         inMultiplicand2.copyTo(arrayInMultiplicand2);
278         float[] arrayInOffset = new float[INPUTSIZE * 4];
279         Arrays.fill(arrayInOffset, (float) 42);
280         inOffset.copyTo(arrayInOffset);
281         float[] arrayOut = new float[INPUTSIZE * 4];
282         Arrays.fill(arrayOut, (float) 42);
283         out.copyTo(arrayOut);
284         StringBuilder message = new StringBuilder();
285         boolean errorFound = false;
286         for (int i = 0; i < INPUTSIZE; i++) {
287             for (int j = 0; j < 3 ; j++) {
288                 // Extract the inputs.
289                 ArgumentsFloatFloatFloatFloat args = new ArgumentsFloatFloatFloatFloat();
290                 args.inMultiplicand1 = arrayInMultiplicand1[i * 4 + j];
291                 args.inMultiplicand2 = arrayInMultiplicand2[i * 4 + j];
292                 args.inOffset = arrayInOffset[i * 4 + j];
293                 // Figure out what the outputs should have been.
294                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.FLOAT, relaxed);
295                 CoreMathVerifier.computeMad(args, target);
296                 // Validate the outputs.
297                 boolean valid = true;
298                 if (!args.out.couldBe(arrayOut[i * 4 + j])) {
299                     valid = false;
300                 }
301                 if (!valid) {
302                     if (!errorFound) {
303                         errorFound = true;
304                         message.append("Input inMultiplicand1: ");
305                         appendVariableToMessage(message, args.inMultiplicand1);
306                         message.append("\n");
307                         message.append("Input inMultiplicand2: ");
308                         appendVariableToMessage(message, args.inMultiplicand2);
309                         message.append("\n");
310                         message.append("Input inOffset: ");
311                         appendVariableToMessage(message, args.inOffset);
312                         message.append("\n");
313                         message.append("Expected output out: ");
314                         appendVariableToMessage(message, args.out);
315                         message.append("\n");
316                         message.append("Actual   output out: ");
317                         appendVariableToMessage(message, arrayOut[i * 4 + j]);
318                         if (!args.out.couldBe(arrayOut[i * 4 + j])) {
319                             message.append(" FAIL");
320                         }
321                         message.append("\n");
322                         message.append("Errors at");
323                     }
324                     message.append(" [");
325                     message.append(Integer.toString(i));
326                     message.append(", ");
327                     message.append(Integer.toString(j));
328                     message.append("]");
329                 }
330             }
331         }
332         assertFalse("Incorrect output for checkMadFloat3Float3Float3Float3" +
333                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
334     }
335 
checkMadFloat4Float4Float4Float4()336     private void checkMadFloat4Float4Float4Float4() {
337         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 4, 0xdac49af1384a6678l, false);
338         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 4, 0xdac49af1384a6679l, false);
339         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_32, 4, 0xe5565ce8c5601b0cl, false);
340         try {
341             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 4), INPUTSIZE);
342             script.set_gAllocInMultiplicand2(inMultiplicand2);
343             script.set_gAllocInOffset(inOffset);
344             script.forEach_testMadFloat4Float4Float4Float4(inMultiplicand1, out);
345             verifyResultsMadFloat4Float4Float4Float4(inMultiplicand1, inMultiplicand2, inOffset, out, false);
346             out.destroy();
347         } catch (Exception e) {
348             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat4Float4Float4Float4: " + e.toString());
349         }
350         try {
351             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_32, 4), INPUTSIZE);
352             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
353             scriptRelaxed.set_gAllocInOffset(inOffset);
354             scriptRelaxed.forEach_testMadFloat4Float4Float4Float4(inMultiplicand1, out);
355             verifyResultsMadFloat4Float4Float4Float4(inMultiplicand1, inMultiplicand2, inOffset, out, true);
356             out.destroy();
357         } catch (Exception e) {
358             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadFloat4Float4Float4Float4: " + e.toString());
359         }
360         inMultiplicand1.destroy();
361         inMultiplicand2.destroy();
362         inOffset.destroy();
363     }
364 
verifyResultsMadFloat4Float4Float4Float4(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)365     private void verifyResultsMadFloat4Float4Float4Float4(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
366         float[] arrayInMultiplicand1 = new float[INPUTSIZE * 4];
367         Arrays.fill(arrayInMultiplicand1, (float) 42);
368         inMultiplicand1.copyTo(arrayInMultiplicand1);
369         float[] arrayInMultiplicand2 = new float[INPUTSIZE * 4];
370         Arrays.fill(arrayInMultiplicand2, (float) 42);
371         inMultiplicand2.copyTo(arrayInMultiplicand2);
372         float[] arrayInOffset = new float[INPUTSIZE * 4];
373         Arrays.fill(arrayInOffset, (float) 42);
374         inOffset.copyTo(arrayInOffset);
375         float[] arrayOut = new float[INPUTSIZE * 4];
376         Arrays.fill(arrayOut, (float) 42);
377         out.copyTo(arrayOut);
378         StringBuilder message = new StringBuilder();
379         boolean errorFound = false;
380         for (int i = 0; i < INPUTSIZE; i++) {
381             for (int j = 0; j < 4 ; j++) {
382                 // Extract the inputs.
383                 ArgumentsFloatFloatFloatFloat args = new ArgumentsFloatFloatFloatFloat();
384                 args.inMultiplicand1 = arrayInMultiplicand1[i * 4 + j];
385                 args.inMultiplicand2 = arrayInMultiplicand2[i * 4 + j];
386                 args.inOffset = arrayInOffset[i * 4 + j];
387                 // Figure out what the outputs should have been.
388                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.FLOAT, relaxed);
389                 CoreMathVerifier.computeMad(args, target);
390                 // Validate the outputs.
391                 boolean valid = true;
392                 if (!args.out.couldBe(arrayOut[i * 4 + j])) {
393                     valid = false;
394                 }
395                 if (!valid) {
396                     if (!errorFound) {
397                         errorFound = true;
398                         message.append("Input inMultiplicand1: ");
399                         appendVariableToMessage(message, args.inMultiplicand1);
400                         message.append("\n");
401                         message.append("Input inMultiplicand2: ");
402                         appendVariableToMessage(message, args.inMultiplicand2);
403                         message.append("\n");
404                         message.append("Input inOffset: ");
405                         appendVariableToMessage(message, args.inOffset);
406                         message.append("\n");
407                         message.append("Expected output out: ");
408                         appendVariableToMessage(message, args.out);
409                         message.append("\n");
410                         message.append("Actual   output out: ");
411                         appendVariableToMessage(message, arrayOut[i * 4 + j]);
412                         if (!args.out.couldBe(arrayOut[i * 4 + j])) {
413                             message.append(" FAIL");
414                         }
415                         message.append("\n");
416                         message.append("Errors at");
417                     }
418                     message.append(" [");
419                     message.append(Integer.toString(i));
420                     message.append(", ");
421                     message.append(Integer.toString(j));
422                     message.append("]");
423                 }
424             }
425         }
426         assertFalse("Incorrect output for checkMadFloat4Float4Float4Float4" +
427                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
428     }
429 
430     public class ArgumentsHalfHalfHalfHalf {
431         public short inMultiplicand1;
432         public double inMultiplicand1Double;
433         public short inMultiplicand2;
434         public double inMultiplicand2Double;
435         public short inOffset;
436         public double inOffsetDouble;
437         public Target.Floaty out;
438     }
439 
checkMadHalfHalfHalfHalf()440     private void checkMadHalfHalfHalfHalf() {
441         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 1, 0x2983a5ddcfbe7d2cl, false);
442         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 1, 0x2983a5ddcfbe7d2dl, false);
443         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 1, 0xc76d350bfd6cfcc8l, false);
444         try {
445             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 1), INPUTSIZE);
446             script.set_gAllocInMultiplicand2(inMultiplicand2);
447             script.set_gAllocInOffset(inOffset);
448             script.forEach_testMadHalfHalfHalfHalf(inMultiplicand1, out);
449             verifyResultsMadHalfHalfHalfHalf(inMultiplicand1, inMultiplicand2, inOffset, out, false);
450             out.destroy();
451         } catch (Exception e) {
452             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalfHalfHalfHalf: " + e.toString());
453         }
454         try {
455             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 1), INPUTSIZE);
456             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
457             scriptRelaxed.set_gAllocInOffset(inOffset);
458             scriptRelaxed.forEach_testMadHalfHalfHalfHalf(inMultiplicand1, out);
459             verifyResultsMadHalfHalfHalfHalf(inMultiplicand1, inMultiplicand2, inOffset, out, true);
460             out.destroy();
461         } catch (Exception e) {
462             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalfHalfHalfHalf: " + e.toString());
463         }
464         inMultiplicand1.destroy();
465         inMultiplicand2.destroy();
466         inOffset.destroy();
467     }
468 
verifyResultsMadHalfHalfHalfHalf(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)469     private void verifyResultsMadHalfHalfHalfHalf(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
470         short[] arrayInMultiplicand1 = new short[INPUTSIZE * 1];
471         Arrays.fill(arrayInMultiplicand1, (short) 42);
472         inMultiplicand1.copyTo(arrayInMultiplicand1);
473         short[] arrayInMultiplicand2 = new short[INPUTSIZE * 1];
474         Arrays.fill(arrayInMultiplicand2, (short) 42);
475         inMultiplicand2.copyTo(arrayInMultiplicand2);
476         short[] arrayInOffset = new short[INPUTSIZE * 1];
477         Arrays.fill(arrayInOffset, (short) 42);
478         inOffset.copyTo(arrayInOffset);
479         short[] arrayOut = new short[INPUTSIZE * 1];
480         Arrays.fill(arrayOut, (short) 42);
481         out.copyTo(arrayOut);
482         StringBuilder message = new StringBuilder();
483         boolean errorFound = false;
484         for (int i = 0; i < INPUTSIZE; i++) {
485             for (int j = 0; j < 1 ; j++) {
486                 // Extract the inputs.
487                 ArgumentsHalfHalfHalfHalf args = new ArgumentsHalfHalfHalfHalf();
488                 args.inMultiplicand1 = arrayInMultiplicand1[i];
489                 args.inMultiplicand1Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand1);
490                 args.inMultiplicand2 = arrayInMultiplicand2[i];
491                 args.inMultiplicand2Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand2);
492                 args.inOffset = arrayInOffset[i];
493                 args.inOffsetDouble = Float16Utils.convertFloat16ToDouble(args.inOffset);
494                 // Figure out what the outputs should have been.
495                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.HALF, relaxed);
496                 CoreMathVerifier.computeMad(args, target);
497                 // Validate the outputs.
498                 boolean valid = true;
499                 if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 1 + j]))) {
500                     valid = false;
501                 }
502                 if (!valid) {
503                     if (!errorFound) {
504                         errorFound = true;
505                         message.append("Input inMultiplicand1: ");
506                         appendVariableToMessage(message, args.inMultiplicand1);
507                         message.append("\n");
508                         message.append("Input inMultiplicand2: ");
509                         appendVariableToMessage(message, args.inMultiplicand2);
510                         message.append("\n");
511                         message.append("Input inOffset: ");
512                         appendVariableToMessage(message, args.inOffset);
513                         message.append("\n");
514                         message.append("Expected output out: ");
515                         appendVariableToMessage(message, args.out);
516                         message.append("\n");
517                         message.append("Actual   output out: ");
518                         appendVariableToMessage(message, arrayOut[i * 1 + j]);
519                         message.append("\n");
520                         message.append("Actual   output out (in double): ");
521                         appendVariableToMessage(message, Float16Utils.convertFloat16ToDouble(arrayOut[i * 1 + j]));
522                         if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 1 + j]))) {
523                             message.append(" FAIL");
524                         }
525                         message.append("\n");
526                         message.append("Errors at");
527                     }
528                     message.append(" [");
529                     message.append(Integer.toString(i));
530                     message.append(", ");
531                     message.append(Integer.toString(j));
532                     message.append("]");
533                 }
534             }
535         }
536         assertFalse("Incorrect output for checkMadHalfHalfHalfHalf" +
537                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
538     }
539 
checkMadHalf2Half2Half2Half2()540     private void checkMadHalf2Half2Half2Half2() {
541         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 2, 0x448f565ee9fc79e0l, false);
542         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 2, 0x448f565ee9fc79e1l, false);
543         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 2, 0x340ae370deb2c084l, false);
544         try {
545             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 2), INPUTSIZE);
546             script.set_gAllocInMultiplicand2(inMultiplicand2);
547             script.set_gAllocInOffset(inOffset);
548             script.forEach_testMadHalf2Half2Half2Half2(inMultiplicand1, out);
549             verifyResultsMadHalf2Half2Half2Half2(inMultiplicand1, inMultiplicand2, inOffset, out, false);
550             out.destroy();
551         } catch (Exception e) {
552             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf2Half2Half2Half2: " + e.toString());
553         }
554         try {
555             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 2), INPUTSIZE);
556             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
557             scriptRelaxed.set_gAllocInOffset(inOffset);
558             scriptRelaxed.forEach_testMadHalf2Half2Half2Half2(inMultiplicand1, out);
559             verifyResultsMadHalf2Half2Half2Half2(inMultiplicand1, inMultiplicand2, inOffset, out, true);
560             out.destroy();
561         } catch (Exception e) {
562             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf2Half2Half2Half2: " + e.toString());
563         }
564         inMultiplicand1.destroy();
565         inMultiplicand2.destroy();
566         inOffset.destroy();
567     }
568 
verifyResultsMadHalf2Half2Half2Half2(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)569     private void verifyResultsMadHalf2Half2Half2Half2(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
570         short[] arrayInMultiplicand1 = new short[INPUTSIZE * 2];
571         Arrays.fill(arrayInMultiplicand1, (short) 42);
572         inMultiplicand1.copyTo(arrayInMultiplicand1);
573         short[] arrayInMultiplicand2 = new short[INPUTSIZE * 2];
574         Arrays.fill(arrayInMultiplicand2, (short) 42);
575         inMultiplicand2.copyTo(arrayInMultiplicand2);
576         short[] arrayInOffset = new short[INPUTSIZE * 2];
577         Arrays.fill(arrayInOffset, (short) 42);
578         inOffset.copyTo(arrayInOffset);
579         short[] arrayOut = new short[INPUTSIZE * 2];
580         Arrays.fill(arrayOut, (short) 42);
581         out.copyTo(arrayOut);
582         StringBuilder message = new StringBuilder();
583         boolean errorFound = false;
584         for (int i = 0; i < INPUTSIZE; i++) {
585             for (int j = 0; j < 2 ; j++) {
586                 // Extract the inputs.
587                 ArgumentsHalfHalfHalfHalf args = new ArgumentsHalfHalfHalfHalf();
588                 args.inMultiplicand1 = arrayInMultiplicand1[i * 2 + j];
589                 args.inMultiplicand1Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand1);
590                 args.inMultiplicand2 = arrayInMultiplicand2[i * 2 + j];
591                 args.inMultiplicand2Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand2);
592                 args.inOffset = arrayInOffset[i * 2 + j];
593                 args.inOffsetDouble = Float16Utils.convertFloat16ToDouble(args.inOffset);
594                 // Figure out what the outputs should have been.
595                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.HALF, relaxed);
596                 CoreMathVerifier.computeMad(args, target);
597                 // Validate the outputs.
598                 boolean valid = true;
599                 if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 2 + j]))) {
600                     valid = false;
601                 }
602                 if (!valid) {
603                     if (!errorFound) {
604                         errorFound = true;
605                         message.append("Input inMultiplicand1: ");
606                         appendVariableToMessage(message, args.inMultiplicand1);
607                         message.append("\n");
608                         message.append("Input inMultiplicand2: ");
609                         appendVariableToMessage(message, args.inMultiplicand2);
610                         message.append("\n");
611                         message.append("Input inOffset: ");
612                         appendVariableToMessage(message, args.inOffset);
613                         message.append("\n");
614                         message.append("Expected output out: ");
615                         appendVariableToMessage(message, args.out);
616                         message.append("\n");
617                         message.append("Actual   output out: ");
618                         appendVariableToMessage(message, arrayOut[i * 2 + j]);
619                         message.append("\n");
620                         message.append("Actual   output out (in double): ");
621                         appendVariableToMessage(message, Float16Utils.convertFloat16ToDouble(arrayOut[i * 2 + j]));
622                         if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 2 + j]))) {
623                             message.append(" FAIL");
624                         }
625                         message.append("\n");
626                         message.append("Errors at");
627                     }
628                     message.append(" [");
629                     message.append(Integer.toString(i));
630                     message.append(", ");
631                     message.append(Integer.toString(j));
632                     message.append("]");
633                 }
634             }
635         }
636         assertFalse("Incorrect output for checkMadHalf2Half2Half2Half2" +
637                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
638     }
639 
checkMadHalf3Half3Half3Half3()640     private void checkMadHalf3Half3Half3Half3() {
641         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 3, 0xf9ed0ccd5500128l, false);
642         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 3, 0xf9ed0ccd5500129l, false);
643         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 3, 0x191ee58a2979209cl, false);
644         try {
645             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 3), INPUTSIZE);
646             script.set_gAllocInMultiplicand2(inMultiplicand2);
647             script.set_gAllocInOffset(inOffset);
648             script.forEach_testMadHalf3Half3Half3Half3(inMultiplicand1, out);
649             verifyResultsMadHalf3Half3Half3Half3(inMultiplicand1, inMultiplicand2, inOffset, out, false);
650             out.destroy();
651         } catch (Exception e) {
652             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf3Half3Half3Half3: " + e.toString());
653         }
654         try {
655             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 3), INPUTSIZE);
656             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
657             scriptRelaxed.set_gAllocInOffset(inOffset);
658             scriptRelaxed.forEach_testMadHalf3Half3Half3Half3(inMultiplicand1, out);
659             verifyResultsMadHalf3Half3Half3Half3(inMultiplicand1, inMultiplicand2, inOffset, out, true);
660             out.destroy();
661         } catch (Exception e) {
662             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf3Half3Half3Half3: " + e.toString());
663         }
664         inMultiplicand1.destroy();
665         inMultiplicand2.destroy();
666         inOffset.destroy();
667     }
668 
verifyResultsMadHalf3Half3Half3Half3(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)669     private void verifyResultsMadHalf3Half3Half3Half3(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
670         short[] arrayInMultiplicand1 = new short[INPUTSIZE * 4];
671         Arrays.fill(arrayInMultiplicand1, (short) 42);
672         inMultiplicand1.copyTo(arrayInMultiplicand1);
673         short[] arrayInMultiplicand2 = new short[INPUTSIZE * 4];
674         Arrays.fill(arrayInMultiplicand2, (short) 42);
675         inMultiplicand2.copyTo(arrayInMultiplicand2);
676         short[] arrayInOffset = new short[INPUTSIZE * 4];
677         Arrays.fill(arrayInOffset, (short) 42);
678         inOffset.copyTo(arrayInOffset);
679         short[] arrayOut = new short[INPUTSIZE * 4];
680         Arrays.fill(arrayOut, (short) 42);
681         out.copyTo(arrayOut);
682         StringBuilder message = new StringBuilder();
683         boolean errorFound = false;
684         for (int i = 0; i < INPUTSIZE; i++) {
685             for (int j = 0; j < 3 ; j++) {
686                 // Extract the inputs.
687                 ArgumentsHalfHalfHalfHalf args = new ArgumentsHalfHalfHalfHalf();
688                 args.inMultiplicand1 = arrayInMultiplicand1[i * 4 + j];
689                 args.inMultiplicand1Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand1);
690                 args.inMultiplicand2 = arrayInMultiplicand2[i * 4 + j];
691                 args.inMultiplicand2Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand2);
692                 args.inOffset = arrayInOffset[i * 4 + j];
693                 args.inOffsetDouble = Float16Utils.convertFloat16ToDouble(args.inOffset);
694                 // Figure out what the outputs should have been.
695                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.HALF, relaxed);
696                 CoreMathVerifier.computeMad(args, target);
697                 // Validate the outputs.
698                 boolean valid = true;
699                 if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]))) {
700                     valid = false;
701                 }
702                 if (!valid) {
703                     if (!errorFound) {
704                         errorFound = true;
705                         message.append("Input inMultiplicand1: ");
706                         appendVariableToMessage(message, args.inMultiplicand1);
707                         message.append("\n");
708                         message.append("Input inMultiplicand2: ");
709                         appendVariableToMessage(message, args.inMultiplicand2);
710                         message.append("\n");
711                         message.append("Input inOffset: ");
712                         appendVariableToMessage(message, args.inOffset);
713                         message.append("\n");
714                         message.append("Expected output out: ");
715                         appendVariableToMessage(message, args.out);
716                         message.append("\n");
717                         message.append("Actual   output out: ");
718                         appendVariableToMessage(message, arrayOut[i * 4 + j]);
719                         message.append("\n");
720                         message.append("Actual   output out (in double): ");
721                         appendVariableToMessage(message, Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]));
722                         if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]))) {
723                             message.append(" FAIL");
724                         }
725                         message.append("\n");
726                         message.append("Errors at");
727                     }
728                     message.append(" [");
729                     message.append(Integer.toString(i));
730                     message.append(", ");
731                     message.append(Integer.toString(j));
732                     message.append("]");
733                 }
734             }
735         }
736         assertFalse("Incorrect output for checkMadHalf3Half3Half3Half3" +
737                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
738     }
739 
checkMadHalf4Half4Half4Half4()740     private void checkMadHalf4Half4Half4Half4() {
741         Allocation inMultiplicand1 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 4, 0xdaae4b3ac0a38870l, false);
742         Allocation inMultiplicand2 = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 4, 0xdaae4b3ac0a38871l, false);
743         Allocation inOffset = createRandomAllocation(mRS, Element.DataType.FLOAT_16, 4, 0xfe32e7a3743f80b4l, false);
744         try {
745             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 4), INPUTSIZE);
746             script.set_gAllocInMultiplicand2(inMultiplicand2);
747             script.set_gAllocInOffset(inOffset);
748             script.forEach_testMadHalf4Half4Half4Half4(inMultiplicand1, out);
749             verifyResultsMadHalf4Half4Half4Half4(inMultiplicand1, inMultiplicand2, inOffset, out, false);
750             out.destroy();
751         } catch (Exception e) {
752             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf4Half4Half4Half4: " + e.toString());
753         }
754         try {
755             Allocation out = Allocation.createSized(mRS, getElement(mRS, Element.DataType.FLOAT_16, 4), INPUTSIZE);
756             scriptRelaxed.set_gAllocInMultiplicand2(inMultiplicand2);
757             scriptRelaxed.set_gAllocInOffset(inOffset);
758             scriptRelaxed.forEach_testMadHalf4Half4Half4Half4(inMultiplicand1, out);
759             verifyResultsMadHalf4Half4Half4Half4(inMultiplicand1, inMultiplicand2, inOffset, out, true);
760             out.destroy();
761         } catch (Exception e) {
762             throw new RSRuntimeException("RenderScript. Can't invoke forEach_testMadHalf4Half4Half4Half4: " + e.toString());
763         }
764         inMultiplicand1.destroy();
765         inMultiplicand2.destroy();
766         inOffset.destroy();
767     }
768 
verifyResultsMadHalf4Half4Half4Half4(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed)769     private void verifyResultsMadHalf4Half4Half4Half4(Allocation inMultiplicand1, Allocation inMultiplicand2, Allocation inOffset, Allocation out, boolean relaxed) {
770         short[] arrayInMultiplicand1 = new short[INPUTSIZE * 4];
771         Arrays.fill(arrayInMultiplicand1, (short) 42);
772         inMultiplicand1.copyTo(arrayInMultiplicand1);
773         short[] arrayInMultiplicand2 = new short[INPUTSIZE * 4];
774         Arrays.fill(arrayInMultiplicand2, (short) 42);
775         inMultiplicand2.copyTo(arrayInMultiplicand2);
776         short[] arrayInOffset = new short[INPUTSIZE * 4];
777         Arrays.fill(arrayInOffset, (short) 42);
778         inOffset.copyTo(arrayInOffset);
779         short[] arrayOut = new short[INPUTSIZE * 4];
780         Arrays.fill(arrayOut, (short) 42);
781         out.copyTo(arrayOut);
782         StringBuilder message = new StringBuilder();
783         boolean errorFound = false;
784         for (int i = 0; i < INPUTSIZE; i++) {
785             for (int j = 0; j < 4 ; j++) {
786                 // Extract the inputs.
787                 ArgumentsHalfHalfHalfHalf args = new ArgumentsHalfHalfHalfHalf();
788                 args.inMultiplicand1 = arrayInMultiplicand1[i * 4 + j];
789                 args.inMultiplicand1Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand1);
790                 args.inMultiplicand2 = arrayInMultiplicand2[i * 4 + j];
791                 args.inMultiplicand2Double = Float16Utils.convertFloat16ToDouble(args.inMultiplicand2);
792                 args.inOffset = arrayInOffset[i * 4 + j];
793                 args.inOffsetDouble = Float16Utils.convertFloat16ToDouble(args.inOffset);
794                 // Figure out what the outputs should have been.
795                 Target target = new Target(Target.FunctionType.NORMAL, Target.ReturnType.HALF, relaxed);
796                 CoreMathVerifier.computeMad(args, target);
797                 // Validate the outputs.
798                 boolean valid = true;
799                 if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]))) {
800                     valid = false;
801                 }
802                 if (!valid) {
803                     if (!errorFound) {
804                         errorFound = true;
805                         message.append("Input inMultiplicand1: ");
806                         appendVariableToMessage(message, args.inMultiplicand1);
807                         message.append("\n");
808                         message.append("Input inMultiplicand2: ");
809                         appendVariableToMessage(message, args.inMultiplicand2);
810                         message.append("\n");
811                         message.append("Input inOffset: ");
812                         appendVariableToMessage(message, args.inOffset);
813                         message.append("\n");
814                         message.append("Expected output out: ");
815                         appendVariableToMessage(message, args.out);
816                         message.append("\n");
817                         message.append("Actual   output out: ");
818                         appendVariableToMessage(message, arrayOut[i * 4 + j]);
819                         message.append("\n");
820                         message.append("Actual   output out (in double): ");
821                         appendVariableToMessage(message, Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]));
822                         if (!args.out.couldBe(Float16Utils.convertFloat16ToDouble(arrayOut[i * 4 + j]))) {
823                             message.append(" FAIL");
824                         }
825                         message.append("\n");
826                         message.append("Errors at");
827                     }
828                     message.append(" [");
829                     message.append(Integer.toString(i));
830                     message.append(", ");
831                     message.append(Integer.toString(j));
832                     message.append("]");
833                 }
834             }
835         }
836         assertFalse("Incorrect output for checkMadHalf4Half4Half4Half4" +
837                 (relaxed ? "_relaxed" : "") + ":\n" + message.toString(), errorFound);
838     }
839 
testMad()840     public void testMad() {
841         checkMadFloatFloatFloatFloat();
842         checkMadFloat2Float2Float2Float2();
843         checkMadFloat3Float3Float3Float3();
844         checkMadFloat4Float4Float4Float4();
845         checkMadHalfHalfHalfHalf();
846         checkMadHalf2Half2Half2Half2();
847         checkMadHalf3Half3Half3Half3();
848         checkMadHalf4Half4Half4Half4();
849     }
850 }
851