• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2012 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 package androidx.renderscript;
18 
19 import android.util.SparseArray;
20 
21 /**
22  * The parent class for all executable scripts. This should not be used by
23  * applications.
24  **/
25 public class Script extends BaseObj {
26     /**
27      * Determine if Incremental Intrinsic Support is needed
28      *
29      */
30     private boolean mUseIncSupp;
setIncSupp(boolean useInc)31     protected void setIncSupp(boolean useInc) {
32         mUseIncSupp = useInc;
33     }
isIncSupp()34     protected boolean isIncSupp() {
35         return mUseIncSupp;
36     }
37     /**
38      * An allocation for the compat context will be created when needed
39      * e.g. foreach(ain, aout), setVar(ain);
40      *
41      */
getDummyAlloc(Allocation ain)42     long getDummyAlloc(Allocation ain) {
43         long dInElement = 0;
44         long dInType = 0;
45         long dummyAlloc = 0;
46         if (ain != null) {
47             Type inType = ain.getType();
48             dInElement = inType.getElement().getDummyElement(mRS);
49             dInType = inType.getDummyType(mRS, dInElement);
50             int xBytesSize = inType.getX() * inType.getElement().getBytesSize();
51             dummyAlloc = mRS.nIncAllocationCreateTyped(ain.getID(mRS), dInType, xBytesSize);
52             ain.setIncAllocID(dummyAlloc);
53         }
54 
55         return dummyAlloc;
56     }
57     /**
58      * KernelID is an identifier for a Script + root function pair. It is used
59      * as an identifier for ScriptGroup creation.
60      *
61      * This class should not be directly created. Instead use the method in the
62      * reflected or intrinsic code "getKernelID_funcname()".
63      *
64      */
65     public static final class KernelID extends BaseObj {
66         android.renderscript.Script.KernelID mN;
67         Script mScript;
68         int mSlot;
69         int mSig;
KernelID(long id, RenderScript rs, Script s, int slot, int sig)70         KernelID(long id, RenderScript rs, Script s, int slot, int sig) {
71             super(id, rs);
72             mScript = s;
73             mSlot = slot;
74             mSig = sig;
75         }
76     }
77 
78     private final SparseArray<KernelID> mKIDs = new SparseArray<KernelID>();
79     /**
80      * Only to be used by generated reflected classes.
81      *
82      *
83      * @param slot
84      * @param sig
85      * @param ein
86      * @param eout
87      *
88      * @return KernelID
89      */
createKernelID(int slot, int sig, Element ein, Element eout)90     protected KernelID createKernelID(int slot, int sig, Element ein, Element eout) {
91         KernelID k = mKIDs.get(slot);
92         if (k != null) {
93             return k;
94         }
95 
96         long id = mRS.nScriptKernelIDCreate(getID(mRS), slot, sig, mUseIncSupp);
97         if (id == 0) {
98             throw new RSDriverException("Failed to create KernelID");
99         }
100 
101         k = new KernelID(id, mRS, this, slot, sig);
102 
103         mKIDs.put(slot, k);
104         return k;
105     }
106 
107     /**
108      * InvokeID is an identifier for a invoke function. It is used
109      * as an identifier for ScriptGroup creation.
110      *
111      * This class should not be directly created. Instead use the method in the
112      * reflected or intrinsic code "getInvokeID_funcname()".
113      *
114      */
115     public static final class InvokeID extends BaseObj {
116         Script mScript;
117         int mSlot;
InvokeID(long id, RenderScript rs, Script s, int slot)118         InvokeID(long id, RenderScript rs, Script s, int slot) {
119             super(id, rs);
120             mScript = s;
121             mSlot = slot;
122         }
123     }
124 
125     private final SparseArray<InvokeID> mIIDs = new SparseArray<InvokeID>();
126     /**
127      * Only to be used by generated reflected classes.
128      */
createInvokeID(int slot)129     protected InvokeID createInvokeID(int slot) {
130         InvokeID i = mIIDs.get(slot);
131         if (i != null) {
132             return i;
133         }
134 
135         long id = mRS.nScriptInvokeIDCreate(getID(mRS), slot);
136         if (id == 0) {
137             throw new RSDriverException("Failed to create KernelID");
138         }
139 
140         i = new InvokeID(id, mRS, this, slot);
141         mIIDs.put(slot, i);
142         return i;
143     }
144 
145     /**
146      * FieldID is an identifier for a Script + exported field pair. It is used
147      * as an identifier for ScriptGroup creation.
148      *
149      * This class should not be directly created. Instead use the method in the
150      * reflected or intrinsic code "getFieldID_funcname()".
151      *
152      */
153     public static final class FieldID extends BaseObj {
154         android.renderscript.Script.FieldID mN;
155         Script mScript;
156         int mSlot;
FieldID(long id, RenderScript rs, Script s, int slot)157         FieldID(long id, RenderScript rs, Script s, int slot) {
158             super(id, rs);
159             mScript = s;
160             mSlot = slot;
161         }
162     }
163 
164     private final SparseArray<FieldID> mFIDs = new SparseArray();
165     /**
166      * Only to be used by generated reflected classes.
167      *
168      * @param slot
169      * @param e
170      *
171      * @return FieldID
172      */
createFieldID(int slot, Element e)173     protected FieldID createFieldID(int slot, Element e) {
174         FieldID f = mFIDs.get(slot);
175         if (f != null) {
176             return f;
177         }
178 
179         long id = mRS.nScriptFieldIDCreate(getID(mRS), slot, mUseIncSupp);
180         if (id == 0) {
181             throw new RSDriverException("Failed to create FieldID");
182         }
183 
184         f = new FieldID(id, mRS, this, slot);
185         mFIDs.put(slot, f);
186         return f;
187     }
188 
189     /**
190      * Only intended for use by generated reflected code.
191      *
192      * @param slot
193      */
invoke(int slot)194     protected void invoke(int slot) {
195         mRS.nScriptInvoke(getID(mRS), slot, mUseIncSupp);
196     }
197 
198     /**
199      * Only intended for use by generated reflected code.
200      *
201      * @param slot
202      * @param v
203      */
invoke(int slot, FieldPacker v)204     protected void invoke(int slot, FieldPacker v) {
205         if (v != null) {
206             mRS.nScriptInvokeV(getID(mRS), slot, v.getData(), mUseIncSupp);
207         } else {
208             mRS.nScriptInvoke(getID(mRS), slot, mUseIncSupp);
209         }
210     }
211 
212     /**
213      * Only intended for use by generated reflected code.
214      *
215      * @param va
216      * @param slot
217      */
bindAllocation(Allocation va, int slot)218     public void bindAllocation(Allocation va, int slot) {
219         mRS.validate();
220         if (va != null) {
221             mRS.nScriptBindAllocation(getID(mRS), va.getID(mRS), slot, mUseIncSupp);
222         } else {
223             mRS.nScriptBindAllocation(getID(mRS), 0, slot, mUseIncSupp);
224         }
225     }
226 
setTimeZone(String timeZone)227     public void setTimeZone(String timeZone) {
228         mRS.validate();
229         try {
230             mRS.nScriptSetTimeZone(getID(mRS), timeZone.getBytes("UTF-8"), mUseIncSupp);
231         } catch (java.io.UnsupportedEncodingException e) {
232             throw new RuntimeException(e);
233         }
234     }
235 
236 
237     /**
238      * Only intended for use by generated reflected code.
239      *
240      * @param slot
241      * @param ain
242      * @param aout
243      * @param v
244      */
forEach(int slot, Allocation ain, Allocation aout, FieldPacker v)245     protected void forEach(int slot, Allocation ain, Allocation aout, FieldPacker v) {
246         if (ain == null && aout == null) {
247             throw new RSIllegalArgumentException(
248                 "At least one of ain or aout is required to be non-null.");
249         }
250         long in_id = 0;
251         long out_id = 0;
252         if (ain != null) {
253             in_id = ain.getID(mRS);
254         }
255         if (aout != null) {
256             out_id = aout.getID(mRS);
257         }
258 
259         byte[] params = null;
260         if (v != null) {
261             params = v.getData();
262         }
263 
264         if (mUseIncSupp) {
265             long ainInc = getDummyAlloc(ain);
266             long aoutInc = getDummyAlloc(aout);
267             mRS.nScriptForEach(getID(mRS), slot, ainInc, aoutInc, params, mUseIncSupp);
268         } else {
269             mRS.nScriptForEach(getID(mRS), slot, in_id, out_id, params, mUseIncSupp);
270         }
271     }
272 
273     /**
274      * Only intended for use by generated reflected code.
275      *
276      * @param slot
277      * @param ain
278      * @param aout
279      * @param v
280      * @param sc
281      */
forEach(int slot, Allocation ain, Allocation aout, FieldPacker v, LaunchOptions sc)282     protected void forEach(int slot, Allocation ain, Allocation aout, FieldPacker v, LaunchOptions sc) {
283         if (ain == null && aout == null) {
284             throw new RSIllegalArgumentException(
285                 "At least one of ain or aout is required to be non-null.");
286         }
287 
288         if (sc == null) {
289             forEach(slot, ain, aout, v);
290             return;
291         }
292         long in_id = 0;
293         long out_id = 0;
294         if (ain != null) {
295             in_id = ain.getID(mRS);
296         }
297         if (aout != null) {
298             out_id = aout.getID(mRS);
299         }
300 
301         byte[] params = null;
302         if (v != null) {
303             params = v.getData();
304         }
305         if (mUseIncSupp) {
306             long ainInc = getDummyAlloc(ain);
307             long aoutInc = getDummyAlloc(aout);
308             mRS.nScriptForEachClipped(getID(mRS), slot, ainInc, aoutInc, params, sc.xstart, sc.xend, sc.ystart, sc.yend, sc.zstart, sc.zend, mUseIncSupp);
309         } else {
310             mRS.nScriptForEachClipped(getID(mRS), slot, in_id, out_id, params, sc.xstart, sc.xend, sc.ystart, sc.yend, sc.zstart, sc.zend, mUseIncSupp);
311         }
312     }
313 
Script(long id, RenderScript rs)314     Script(long id, RenderScript rs) {
315         super(id, rs);
316         mUseIncSupp = false;
317     }
318 
319     /**
320      * Only intended for use by generated reflected code.
321      *
322      * @hide
323      */
forEach(int slot, Allocation[] ains, Allocation aout, FieldPacker v)324     protected void forEach(int slot, Allocation[] ains, Allocation aout,
325                            FieldPacker v) {
326         forEach(slot, ains, aout, v, null);
327     }
328 
329     /**
330      * Only intended for use by generated reflected code.
331      *
332      * @hide
333      */
forEach(int slot, Allocation[] ains, Allocation aout, FieldPacker v, LaunchOptions sc)334     protected void forEach(int slot, Allocation[] ains, Allocation aout,
335                            FieldPacker v, LaunchOptions sc) {
336         // TODO: Is this necessary if nScriptForEach calls validate as well?
337         mRS.validate();
338         if (ains != null) {
339             for (Allocation ain : ains) {
340                 mRS.validateObject(ain);
341             }
342         }
343         mRS.validateObject(aout);
344 
345         if (ains == null && aout == null) {
346             throw new RSIllegalArgumentException(
347                 "At least one of ain or aout is required to be non-null.");
348         }
349 
350         long[] in_ids;
351         if (ains != null) {
352             in_ids = new long[ains.length];
353             for (int index = 0; index < ains.length; ++index) {
354                 in_ids[index] = ains[index].getID(mRS);
355             }
356         } else {
357             in_ids = null;
358         }
359 
360         long out_id = 0;
361         if (aout != null) {
362             out_id = aout.getID(mRS);
363         }
364 
365         byte[] params = null;
366         if (v != null) {
367             params = v.getData();
368         }
369 
370         int[] limits = null;
371         if (sc != null) {
372             limits = new int[6];
373 
374             limits[0] = sc.xstart;
375             limits[1] = sc.xend;
376             limits[2] = sc.ystart;
377             limits[3] = sc.yend;
378             limits[4] = sc.zstart;
379             limits[5] = sc.zend;
380         }
381 
382         mRS.nScriptForEach(getID(mRS), slot, in_ids, out_id, params, limits);
383     }
384 
385     /**
386      * Only intended for use by generated reflected code.  (General reduction)
387      *
388      * @hide
389      */
reduce(int slot, Allocation[] ains, Allocation aout, LaunchOptions sc)390     protected void reduce(int slot, Allocation[] ains, Allocation aout, LaunchOptions sc) {
391         mRS.validate();
392         if (ains == null || ains.length < 1) {
393             throw new RSIllegalArgumentException(
394                 "At least one input is required.");
395         }
396         if (aout == null) {
397             throw new RSIllegalArgumentException(
398                 "aout is required to be non-null.");
399         }
400         for (Allocation ain : ains) {
401             mRS.validateObject(ain);
402         }
403 
404         long[] in_ids = new long[ains.length];
405         for (int index = 0; index < ains.length; ++index) {
406             in_ids[index] = ains[index].getID(mRS);
407         }
408         long out_id = aout.getID(mRS);
409 
410         int[] limits = null;
411         if (sc != null) {
412             limits = new int[6];
413 
414             limits[0] = sc.xstart;
415             limits[1] = sc.xend;
416             limits[2] = sc.ystart;
417             limits[3] = sc.yend;
418             limits[4] = sc.zstart;
419             limits[5] = sc.zend;
420         }
421 
422         mRS.nScriptReduce(getID(mRS), slot, in_ids, out_id, limits);
423     }
424 
425     /**
426      * Only intended for use by generated reflected code.
427      *
428      * @param index
429      * @param v
430      */
setVar(int index, float v)431     public void setVar(int index, float v) {
432         mRS.nScriptSetVarF(getID(mRS), index, v, mUseIncSupp);
433     }
434 
435     /**
436      * Only intended for use by generated reflected code.
437      *
438      * @param index
439      * @param v
440      */
setVar(int index, double v)441     public void setVar(int index, double v) {
442         mRS.nScriptSetVarD(getID(mRS), index, v, mUseIncSupp);
443     }
444 
445     /**
446      * Only intended for use by generated reflected code.
447      *
448      * @param index
449      * @param v
450      */
setVar(int index, int v)451     public void setVar(int index, int v) {
452         mRS.nScriptSetVarI(getID(mRS), index, v, mUseIncSupp);
453     }
454 
455     /**
456      * Only intended for use by generated reflected code.
457      *
458      * @param index
459      * @param v
460      */
setVar(int index, long v)461     public void setVar(int index, long v) {
462         mRS.nScriptSetVarJ(getID(mRS), index, v, mUseIncSupp);
463     }
464 
465     /**
466      * Only intended for use by generated reflected code.
467      *
468      * @param index
469      * @param v
470      */
setVar(int index, boolean v)471     public void setVar(int index, boolean v) {
472         mRS.nScriptSetVarI(getID(mRS), index, v ? 1 : 0, mUseIncSupp);
473     }
474 
475     /**
476      * Only intended for use by generated reflected code.
477      *
478      * @param index
479      * @param o
480      */
setVar(int index, BaseObj o)481     public void setVar(int index, BaseObj o) {
482         if (mUseIncSupp) {
483             long oInc = getDummyAlloc((Allocation)o);
484             mRS.nScriptSetVarObj(getID(mRS), index, (o == null) ? 0 : oInc, mUseIncSupp);
485         } else {
486             mRS.nScriptSetVarObj(getID(mRS), index, (o == null) ? 0 : o.getID(mRS), mUseIncSupp);
487         }
488     }
489 
490     /**
491      * Only intended for use by generated reflected code.
492      *
493      * @param index
494      * @param v
495      */
setVar(int index, FieldPacker v)496     public void setVar(int index, FieldPacker v) {
497         mRS.nScriptSetVarV(getID(mRS), index, v.getData(), mUseIncSupp);
498     }
499 
500     /**
501      * Only intended for use by generated reflected code.
502      *
503      * @param index
504      * @param v
505      * @param e
506      * @param dims
507      */
setVar(int index, FieldPacker v, Element e, int[] dims)508     public void setVar(int index, FieldPacker v, Element e, int[] dims) {
509         if (mUseIncSupp) {
510             long dElement = e.getDummyElement(mRS);
511             mRS.nScriptSetVarVE(getID(mRS), index, v.getData(), dElement, dims, mUseIncSupp);
512         } else {
513             mRS.nScriptSetVarVE(getID(mRS), index, v.getData(), e.getID(mRS), dims, mUseIncSupp);
514         }
515     }
516 
517     /**
518      * Only intended for use by generated reflected code.
519      *
520      */
521     public static class Builder {
522         RenderScript mRS;
523 
Builder(RenderScript rs)524         Builder(RenderScript rs) {
525             mRS = rs;
526         }
527     }
528 
529 
530     /**
531      * Only intended for use by generated reflected code.
532      *
533      */
534     public static class FieldBase {
535         protected Element mElement;
536         protected Allocation mAllocation;
537 
init(RenderScript rs, int dimx)538         protected void init(RenderScript rs, int dimx) {
539             mAllocation = Allocation.createSized(rs, mElement, dimx, Allocation.USAGE_SCRIPT);
540         }
541 
init(RenderScript rs, int dimx, int usages)542         protected void init(RenderScript rs, int dimx, int usages) {
543             mAllocation = Allocation.createSized(rs, mElement, dimx, Allocation.USAGE_SCRIPT | usages);
544         }
545 
FieldBase()546         protected FieldBase() {
547         }
548 
getElement()549         public Element getElement() {
550             return mElement;
551         }
552 
getType()553         public Type getType() {
554             return mAllocation.getType();
555         }
556 
getAllocation()557         public Allocation getAllocation() {
558             return mAllocation;
559         }
560 
561         //@Override
updateAllocation()562         public void updateAllocation() {
563         }
564     }
565 
566 
567     /**
568      * Class for specifying the specifics about how a kernel will be
569      * launched.
570      *
571      * This class can specify a potential range of cells on which to
572      * run a kernel.  If no set is called for a dimension then this
573      * class will have no impact on that dimension when the kernel
574      * is executed.
575      *
576      * The forEach kernel launch will operate over the intersection of
577      * the dimensions.
578      *
579      * Example:
580      * LaunchOptions with setX(5, 15)
581      * Allocation with dimension X=10, Y=10
582      * The resulting forEach run would execute over:
583      * x = 5 to 9 (inclusive) and
584      * y = 0 to 9 (inclusive).
585      *
586      */
587     public static final class LaunchOptions {
588         private int xstart = 0;
589         private int ystart = 0;
590         private int xend = 0;
591         private int yend = 0;
592         private int zstart = 0;
593         private int zend = 0;
594         private int strategy;
595 
596         /**
597          * Set the X range. xstartArg is the lowest coordinate of the range,
598          * and xendArg-1 is the highest coordinate of the range.
599          *
600          * @param xstartArg Must be >= 0
601          * @param xendArg Must be > xstartArg
602          *
603          * @return LaunchOptions
604          */
setX(int xstartArg, int xendArg)605         public LaunchOptions setX(int xstartArg, int xendArg) {
606             if (xstartArg < 0 || xendArg <= xstartArg) {
607                 throw new RSIllegalArgumentException("Invalid dimensions");
608             }
609             xstart = xstartArg;
610             xend = xendArg;
611             return this;
612         }
613 
614         /**
615          * Set the Y range. ystartArg is the lowest coordinate of the range,
616          * and yendArg-1 is the highest coordinate of the range.
617          *
618          * @param ystartArg Must be >= 0
619          * @param yendArg Must be > ystartArg
620          *
621          * @return LaunchOptions
622          */
setY(int ystartArg, int yendArg)623         public LaunchOptions setY(int ystartArg, int yendArg) {
624             if (ystartArg < 0 || yendArg <= ystartArg) {
625                 throw new RSIllegalArgumentException("Invalid dimensions");
626             }
627             ystart = ystartArg;
628             yend = yendArg;
629             return this;
630         }
631 
632         /**
633          * Set the Z range. zstartArg is the lowest coordinate of the range,
634          * and zendArg-1 is the highest coordinate of the range.
635          *
636          * @param zstartArg Must be >= 0
637          * @param zendArg Must be > zstartArg
638          *
639          * @return LaunchOptions
640          */
setZ(int zstartArg, int zendArg)641         public LaunchOptions setZ(int zstartArg, int zendArg) {
642             if (zstartArg < 0 || zendArg <= zstartArg) {
643                 throw new RSIllegalArgumentException("Invalid dimensions");
644             }
645             zstart = zstartArg;
646             zend = zendArg;
647             return this;
648         }
649 
650 
651         /**
652          * Returns the current X start
653          *
654          * @return int current value
655          */
getXStart()656         public int getXStart() {
657             return xstart;
658         }
659         /**
660          * Returns the current X end
661          *
662          * @return int current value
663          */
getXEnd()664         public int getXEnd() {
665             return xend;
666         }
667         /**
668          * Returns the current Y start
669          *
670          * @return int current value
671          */
getYStart()672         public int getYStart() {
673             return ystart;
674         }
675         /**
676          * Returns the current Y end
677          *
678          * @return int current value
679          */
getYEnd()680         public int getYEnd() {
681             return yend;
682         }
683         /**
684          * Returns the current Z start
685          *
686          * @return int current value
687          */
getZStart()688         public int getZStart() {
689             return zstart;
690         }
691         /**
692          * Returns the current Z end
693          *
694          * @return int current value
695          */
getZEnd()696         public int getZEnd() {
697             return zend;
698         }
699 
700     }
701 }
702