104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross/*
204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * Copyright (C) 2016 The Android Open Source Project
304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross *
404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * Licensed under the Apache License, Version 2.0 (the "License");
504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * you may not use this file except in compliance with the License.
604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * You may obtain a copy of the License at
704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross *
804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross *      http://www.apache.org/licenses/LICENSE-2.0
904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross *
1004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * Unless required by applicable law or agreed to in writing, software
1104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * distributed under the License is distributed on an "AS IS" BASIS,
1204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * See the License for the specific language governing permissions and
1404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * limitations under the License.
1504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross */
1604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
1704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross/* Same as UT_reduce_backward.java, except this test case exercises
1804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * pragmas before the functions (forward reference), and the other
1904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * test case exercises the pragmas after the functions (backward
2004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross * reference).
2104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross */
2204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
2304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grosspackage com.android.rs.test_compat;
2404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
2504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport android.content.Context;
2604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport android.content.res.Resources;
2704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport android.support.v8.renderscript.*;
2804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport android.util.Log;
2904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport java.lang.Float;
3004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grossimport java.util.Random;
3104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
3204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Grosspublic class UT_reduce extends UnitTest {
3304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private static final String TAG = "reduce";
3404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
3504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    protected UT_reduce(RSTestCore rstc, Resources res, Context ctx) {
3604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        super(rstc, "reduce", ctx);
3704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
3804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
3904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private byte[] createInputArrayByte(int len, int seed) {
4004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        byte[] array = new byte[len];
4104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        (new Random(seed)).nextBytes(array);
4204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return array;
4304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
4404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
4504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private float[] createInputArrayFloat(int len, int seed) {
4604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Random rand = new Random(seed);
4704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        float[] array = new float[len];
4804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 0; i < len; ++i)
4904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            array[i] = rand.nextFloat();
5004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return array;
5104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
5204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
5304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private int[] createInputArrayInt(int len, int seed) {
5404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Random rand = new Random(seed);
5504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] array = new int[len];
5604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 0; i < len; ++i)
5704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            array[i] = rand.nextInt();
5804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return array;
5904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
6004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
6104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private int[] createInputArrayInt(int len, int seed, int eltRange) {
6204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Random rand = new Random(seed);
6304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] array = new int[len];
6404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 0; i < len; ++i)
6504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            array[i] = rand.nextInt(eltRange);
6604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return array;
6704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
6804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
6904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private <T extends Number> boolean result(String testName, T javaRslt, T rsRslt) {
7004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final boolean success = javaRslt.equals(rsRslt);
7104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG,
7204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                testName + ": java " + javaRslt + ", rs " + rsRslt + ": " +
7304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                (success ? "PASSED" : "FAILED"));
7404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return success;
7504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
7604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
7704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean result(String testName, Int2 javaRslt, Int2 rsRslt) {
7804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final boolean success = (javaRslt.x == rsRslt.x) && (javaRslt.y == rsRslt.y);
7904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG,
8004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                testName +
8104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                ": java (" + javaRslt.x + ", " + javaRslt.y + ")" +
8204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                ", rs (" + rsRslt.x + ", " + rsRslt.y + ")" +
8304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                ": " + (success ? "PASSED" : "FAILED"));
8404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return success;
8504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
8604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
8704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
8804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
8904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private int addint(int[] input) {
9004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int rslt = 0;
9104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int idx = 0; idx < input.length; ++idx)
9204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            rslt += input[idx];
9304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return rslt;
9404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
9504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
9604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean addint1D(RenderScript RS, ScriptC_reduce s) {
9704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int[] input = createInputArrayInt(100000, 0, 1 << 13);
9804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
9904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int javaRslt = addint(input);
10004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int rsRslt = s.reduce_addint(input).get();
10104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
10204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return result("addint1D", javaRslt, rsRslt);
10304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
10404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
10504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean addint2D(RenderScript RS, ScriptC_reduce s) {
10604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int dimX = 450, dimY = 225;
10704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
10804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int[] inputArray = createInputArrayInt(dimX * dimY, 1, 1 << 13);
10904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Type.Builder typeBuilder = new Type.Builder(RS, Element.I32(RS));
11004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        typeBuilder.setX(dimX).setY(dimY);
11104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Allocation inputAllocation = Allocation.createTyped(RS, typeBuilder.create());
11204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputAllocation.copy2DRangeFrom(0, 0, dimX, dimY, inputArray);
11304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
11404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int javaRslt = addint(inputArray);
11504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int rsRslt = s.reduce_addint(inputAllocation).get();
11604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
11704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return result("addint2D", javaRslt, rsRslt);
11804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
11904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
12004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
12104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
12204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private Int2 findMinAndMax(float[] input) {
12304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        float minVal = Float.POSITIVE_INFINITY;
12404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int minIdx = -1;
12504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        float maxVal = Float.NEGATIVE_INFINITY;
12604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int maxIdx = -1;
12704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
12804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int idx = 0; idx < input.length; ++idx) {
12904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            if (input[idx] < minVal) {
13004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                minVal = input[idx];
13104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                minIdx = idx;
13204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            }
13304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            if (input[idx] > maxVal) {
13404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                maxVal = input[idx];
13504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                maxIdx = idx;
13604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            }
13704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        }
13804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
13904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return new Int2(minIdx, maxIdx);
14004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
14104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
14204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean findMinAndMax(RenderScript RS, ScriptC_reduce s) {
14304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final float[] input = createInputArrayFloat(100000, 4);
14404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
14504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int2 javaRslt = findMinAndMax(input);
14604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int2 rsRslt = s.reduce_findMinAndMax(input).get();
14704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
14804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return result("findMinAndMax", javaRslt, rsRslt);
14904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
15004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
15104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
15204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
15304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean fz(RenderScript RS, ScriptC_reduce s) {
15404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int inputLen = 100000;
15504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] input = createInputArrayInt(inputLen, 5);
15604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        // just in case we got unlucky
15704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        input[(new Random(6)).nextInt(inputLen)] = 0;
15804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
15904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int rsRslt = s.reduce_fz(input).get();
16004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
16104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final boolean success = (input[rsRslt] == 0);
16204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG,
16304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                "fz: input[" + rsRslt + "] == " + input[rsRslt] + ": " +
16404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                (success ? "PASSED" : "FAILED"));
16504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return success;
16604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
16704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
16804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
16904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
17004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean fz2(RenderScript RS, ScriptC_reduce s) {
17104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int dimX = 225, dimY = 450;
17204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int inputLen = dimX * dimY;
17304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
17404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] inputArray = createInputArrayInt(inputLen, 7);
17504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        // just in case we got unlucky
17604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputArray[(new Random(8)).nextInt(inputLen)] = 0;
17704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
17804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Type.Builder typeBuilder = new Type.Builder(RS, Element.I32(RS));
17904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        typeBuilder.setX(dimX).setY(dimY);
18004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Allocation inputAllocation = Allocation.createTyped(RS, typeBuilder.create());
18104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputAllocation.copy2DRangeFrom(0, 0, dimX, dimY, inputArray);
18204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
18304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int2 rsRslt = s.reduce_fz2(inputAllocation).get();
18404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
18504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int cellVal = inputArray[rsRslt.x + dimX * rsRslt.y];
18604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final boolean success = (cellVal == 0);
18704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG,
18804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                "fz2: input[" + rsRslt.x + ", " + rsRslt.y + "] == " + cellVal + ": " +
18904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                (success ? "PASSED" : "FAILED"));
19004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return success;
19104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
19204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
19304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
19404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
19504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean fz3(RenderScript RS, ScriptC_reduce s) {
19604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int dimX = 59, dimY = 48, dimZ = 37;
19704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int inputLen = dimX * dimY * dimZ;
19804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
19904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] inputArray = createInputArrayInt(inputLen, 9);
20004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        // just in case we got unlucky
20104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputArray[(new Random(10)).nextInt(inputLen)] = 0;
20204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
20304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Type.Builder typeBuilder = new Type.Builder(RS, Element.I32(RS));
20404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        typeBuilder.setX(dimX).setY(dimY).setZ(dimZ);
20504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Allocation inputAllocation = Allocation.createTyped(RS, typeBuilder.create());
20604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputAllocation.copy3DRangeFrom(0, 0, 0, dimX, dimY, dimZ, inputArray);
20704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
20804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int3 rsRslt = s.reduce_fz3(inputAllocation).get();
20904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
21004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final int cellVal = inputArray[rsRslt.x + dimX * rsRslt.y + dimX * dimY * rsRslt.z];
21104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final boolean success = (cellVal == 0);
21204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG,
21304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                "fz3: input[" + rsRslt.x + ", " + rsRslt.y + ", " + rsRslt.z + "] == " + cellVal + ": " +
21404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                (success ? "PASSED" : "FAILED"));
21504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return success;
21604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
21704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
21804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
21904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
22004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private static final int histogramBucketCount = 256;
22104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
22204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private long[] histogram(RenderScript RS, final byte[] inputArray) {
22304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Allocation inputAllocation = Allocation.createSized(RS, Element.U8(RS), inputArray.length);
22404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        inputAllocation.copyFrom(inputArray);
22504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
22604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Allocation outputAllocation = Allocation.createSized(RS, Element.U32(RS), histogramBucketCount);
22704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
22804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        ScriptIntrinsicHistogram scriptHsg = ScriptIntrinsicHistogram.create(RS, Element.U8(RS));
22904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        scriptHsg.setOutput(outputAllocation);
23004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        scriptHsg.forEach(inputAllocation);
23104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
23204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int[] outputArrayMistyped = new int[histogramBucketCount];
23304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        outputAllocation.copyTo(outputArrayMistyped);
23404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
23504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        long[] outputArray = new long[histogramBucketCount];
23604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 0; i < histogramBucketCount; ++i)
23704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            outputArray[i] = outputArrayMistyped[i] & (long)0xffffffff;
23804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return outputArray;
23904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
24004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
24104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean histogram(RenderScript RS, ScriptC_reduce s) {
24204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final byte[] inputArray = createInputArrayByte(100000, 11);
24304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
24404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final long[] javaRslt = histogram(RS, inputArray);
24504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        _RS_ASSERT("javaRslt unexpected length: " + javaRslt.length, javaRslt.length == histogramBucketCount);
24604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final long[] rsRslt = s.reduce_histogram(inputArray).get();
24704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        _RS_ASSERT("rsRslt unexpected length: " + rsRslt.length, rsRslt.length == histogramBucketCount);
24804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
24904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 0; i < histogramBucketCount; ++i) {
25004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            if (javaRslt[i] != rsRslt[i]) {
25104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                Log.i(TAG,
25204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                        "histogram[" + i + "]: java " + javaRslt[i] + ", rs " + rsRslt[i] + ": FAILED");
25304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross                return false;
25404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            }
25504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        }
25604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
25704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG, "histogram: PASSED");
25804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return true;
25904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
26004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
26104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    //-----------------------------------------------------------------
26204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
26304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private Int2 mode(RenderScript RS, final byte[] inputArray) {
26404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        long[] hsg = histogram(RS, inputArray);
26504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
26604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        int modeIdx = 0;
26704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        for (int i = 1; i < hsg.length; ++i)
26804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            if (hsg[i] > hsg[modeIdx]) modeIdx =i;
26904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return new Int2(modeIdx, (int)hsg[modeIdx]);
27004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
27104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
27204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    private boolean mode(RenderScript RS, ScriptC_reduce s) {
27304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final byte[] inputArray = createInputArrayByte(100000, 12);
27404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
27504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int2 javaRslt = mode(RS, inputArray);
27604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        final Int2 rsRslt = s.reduce_mode(inputArray).get();
27704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
27804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        return result("mode", javaRslt, rsRslt);
27904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
28004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
28104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    ///////////////////////////////////////////////////////////////////
28204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
28304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    public void run() {
28404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        RenderScript pRS = RenderScript.create(mCtx);
28504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        ScriptC_reduce s = new ScriptC_reduce(pRS);
28604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        s.set_negInf(Float.NEGATIVE_INFINITY);
28704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        s.set_posInf(Float.POSITIVE_INFINITY);
28804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
28904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        boolean pass = true;
29004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= addint1D(pRS, s);
29104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= addint2D(pRS, s);
29204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= findMinAndMax(pRS, s);
29304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= fz(pRS, s);
29404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= fz2(pRS, s);
29504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= fz3(pRS, s);
29604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= histogram(pRS, s);
29704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pass &= mode(pRS, s);
29804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
29904cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pRS.finish();
30004cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        pRS.destroy();
30104cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross
30204cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        Log.i(TAG, pass ? "PASSED" : "FAILED");
30304cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        if (pass)
30404cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            passTest();
30504cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross        else
30604cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross            failTest();
30704cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross    }
30804cf3e4c1caad17bcd89c3fbe15260ac63c3704fDavid Gross}
309