rsCpuScript.h revision f3213d7fd648da98bb3b03204eaf90f03c31926b
1/*
2 * Copyright (C) 2011-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#ifndef RSD_BCC_H
18#define RSD_BCC_H
19
20#include <rs_hal.h>
21#include <rsRuntime.h>
22
23#ifndef RS_COMPATIBILITY_LIB
24#include <utility>
25#endif
26
27#include "rsCpuCore.h"
28
29#include <vector>
30
31namespace bcc {
32    class BCCContext;
33    class RSCompilerDriver;
34}
35
36namespace bcinfo {
37    class MetadataExtractor;
38}
39
40namespace android {
41namespace renderscript {
42
43class SharedLibraryUtils {
44 public:
45#ifndef RS_COMPATIBILITY_LIB
46  static bool createSharedLibrary(const char* cacheDir, const char* resName);
47#endif
48
49  // Load the shared library referred to by cacheDir and resName. If we have
50  // already loaded this library, we instead create a new copy (in the
51  // cache dir) and then load that. We then immediately destroy the copy.
52  // This is required behavior to implement script instancing for the support
53  // library, since shared objects are loaded and de-duped by name only.
54
55  // For 64bit RS Support Lib, the shared lib path cannot be constructed from
56  // cacheDir, so nativeLibDir is needed to load shared libs.
57  static void* loadSharedLibrary(const char *cacheDir, const char *resName,
58                                 const char *nativeLibDir = nullptr);
59
60 private:
61  // Attempt to load the shared library from origName, but then fall back to
62  // creating a copy of the shared library if necessary (to ensure instancing).
63  // This function returns the dlopen()-ed handle if successful.
64  static void *loadSOHelper(const char *origName, const char *cacheDir,
65                            const char *resName);
66
67  static const char* LD_EXE_PATH;
68  static const char* RS_CACHE_DIR;
69};
70
71class ScriptExecutable {
72 public:
73  ScriptExecutable(Context* RSContext,
74                   std::vector<void*>& fieldAddress,
75                   std::vector<bool>& fieldIsObject,
76                   std::vector<InvokeFunc_t>& invokeFunctions,
77                   std::vector<ForEachFunc_t>& forEachFunctions,
78                   std::vector<uint32_t>& forEachSignatures,
79                   std::vector<const char *> &pragmaKeys,
80                   std::vector<const char *> &pragmaValues,
81                   bool isThreadable)
82                   : mIsThreadable(isThreadable), mRS(RSContext) {
83      mFieldAddress.swap(fieldAddress);
84      mFieldIsObject.swap(fieldIsObject);
85      mInvokeFunctions.swap(invokeFunctions);
86      mForEachFunctions.swap(forEachFunctions);
87      mForEachSignatures.swap(forEachSignatures);
88      mPragmaKeys.swap(pragmaKeys);
89      mPragmaValues.swap(pragmaValues);
90  }
91
92  ~ScriptExecutable() {
93      for (size_t i = 0; i < mFieldAddress.size(); ++i) {
94          if (mFieldIsObject[i]) {
95              if (mFieldAddress[i] != nullptr) {
96                  rs_object_base *obj_addr =
97                      reinterpret_cast<rs_object_base *>(mFieldAddress[i]);
98                  rsrClearObject(mRS, obj_addr);
99              }
100          }
101      }
102
103      for (size_t i = 0; i < mPragmaKeys.size(); ++i) {
104          delete [] mPragmaKeys[i];
105          delete [] mPragmaValues[i];
106      }
107  }
108
109  static ScriptExecutable*
110  createFromSharedObject(Context* RSContext, void* sharedObj);
111
112  size_t getExportedVariableCount() const { return mFieldAddress.size(); }
113  size_t getExportedFunctionCount() const { return mInvokeFunctions.size(); }
114  size_t getExportedForEachCount() const { return mForEachFunctions.size(); }
115  size_t getPragmaCount() const { return mPragmaKeys.size(); }
116
117  void* getFieldAddress(int slot) const { return mFieldAddress[slot]; }
118  bool getFieldIsObject(int slot) const { return mFieldIsObject[slot]; }
119  InvokeFunc_t getInvokeFunction(int slot) const { return mInvokeFunctions[slot]; }
120  ForEachFunc_t getForEachFunction(int slot) const { return mForEachFunctions[slot]; }
121  uint32_t getForEachSignature(int slot) const { return mForEachSignatures[slot]; }
122
123  const std::vector<const char *> & getPragmaKeys() const { return mPragmaKeys; }
124  const std::vector<const char *> & getPragmaValues() const { return mPragmaValues; }
125
126  bool getThreadable() const { return mIsThreadable; }
127
128 private:
129  std::vector<void*> mFieldAddress;
130  std::vector<bool> mFieldIsObject;
131  std::vector<InvokeFunc_t> mInvokeFunctions;
132  std::vector<ForEachFunc_t> mForEachFunctions;
133  std::vector<uint32_t> mForEachSignatures;
134  std::vector<const char *> mPragmaKeys;
135  std::vector<const char *> mPragmaValues;
136
137  bool mIsThreadable;
138
139  Context* mRS;
140};
141
142class RsdCpuScriptImpl : public RsdCpuReferenceImpl::CpuScript {
143public:
144    typedef void (*outer_foreach_t)(
145        const RsExpandKernelParams *,
146        uint32_t x1, uint32_t x2,
147        uint32_t outstep);
148
149    typedef void (* InvokeFunc_t)(void);
150    typedef void (* ForEachFunc_t)(void);
151    typedef int (* RootFunc_t)(void);
152#ifdef RS_COMPATIBILITY_LIB
153    typedef void (*WorkerCallback_t)(void *usr, uint32_t idx);
154#endif
155
156    bool init(char const *resName, char const *cacheDir,
157              uint8_t const *bitcode, size_t bitcodeSize, uint32_t flags,
158              char const *bccPluginName = nullptr);
159    virtual void populateScript(Script *);
160
161    virtual void invokeFunction(uint32_t slot, const void *params, size_t paramLength);
162    virtual int invokeRoot();
163    virtual void preLaunch(uint32_t slot, const Allocation ** ains,
164                           uint32_t inLen, Allocation * aout, const void * usr,
165                           uint32_t usrLen, const RsScriptCall *sc);
166    virtual void postLaunch(uint32_t slot, const Allocation ** ains,
167                            uint32_t inLen, Allocation * aout,
168                            const void * usr, uint32_t usrLen,
169                            const RsScriptCall *sc);
170
171    virtual void invokeForEach(uint32_t slot,
172                               const Allocation ** ains,
173                               uint32_t inLen,
174                               Allocation* aout,
175                               const void* usr,
176                               uint32_t usrLen,
177                               const RsScriptCall* sc);
178
179    virtual void invokeInit();
180    virtual void invokeFreeChildren();
181
182    virtual void setGlobalVar(uint32_t slot, const void *data, size_t dataLength);
183    virtual void getGlobalVar(uint32_t slot, void *data, size_t dataLength);
184    virtual void setGlobalVarWithElemDims(uint32_t slot, const void *data, size_t dataLength,
185                                  const Element *e, const uint32_t *dims, size_t dimLength);
186    virtual void setGlobalBind(uint32_t slot, Allocation *data);
187    virtual void setGlobalObj(uint32_t slot, ObjectBase *data);
188
189
190    virtual ~RsdCpuScriptImpl();
191    RsdCpuScriptImpl(RsdCpuReferenceImpl *ctx, const Script *s);
192
193    const Script * getScript() {return mScript;}
194
195    bool forEachMtlsSetup(const Allocation ** ains, uint32_t inLen,
196                          Allocation * aout, const void * usr, uint32_t usrLen,
197                          const RsScriptCall *sc, MTLaunchStruct *mtls);
198
199    virtual void forEachKernelSetup(uint32_t slot, MTLaunchStruct *mtls);
200
201
202    const RsdCpuReference::CpuSymbol * lookupSymbolMath(const char *sym);
203    static void * lookupRuntimeStub(void* pContext, char const* name);
204
205    virtual Allocation * getAllocationForPointer(const void *ptr) const;
206    bool storeRSInfoFromSO();
207
208protected:
209    RsdCpuReferenceImpl *mCtx;
210    const Script *mScript;
211    void *mScriptSO;
212
213#ifndef RS_COMPATIBILITY_LIB
214    // Returns the path to the core library we'll use.
215    const char* findCoreLib(const bcinfo::MetadataExtractor& bitCodeMetaData, const char* bitcode,
216                            size_t bitcodeSize);
217
218    bcc::RSCompilerDriver *mCompilerDriver;
219#endif
220
221    RootFunc_t mRoot;
222    RootFunc_t mRootExpand;
223    InvokeFunc_t mInit;
224    InvokeFunc_t mFreeChildren;
225    ScriptExecutable* mScriptExec;
226
227    Allocation **mBoundAllocs;
228    void * mIntrinsicData;
229    bool mIsThreadable;
230};
231
232Allocation * rsdScriptGetAllocationForPointer(
233                        const Context *dc,
234                        const Script *script,
235                        const void *);
236
237
238
239}
240
241}
242
243#endif
244