blob: 139cb71df241037d8c7ab49d00d3f818954736b2 [file] [log] [blame]
Zonr Changc383a502010-10-12 01:52:08 +08001/*
Stephen Hines48b72bf2011-06-10 15:37:27 -07002 * Copyright 2010-2011, The Android Open Source Project
Zonr Changc383a502010-10-12 01:52:08 +08003 *
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
Stephen Hinese639eb52010-11-08 19:27:20 -080017#ifndef _FRAMEWORKS_COMPILE_SLANG_SLANG_RS_REFLECTION_H_ // NOLINT
18#define _FRAMEWORKS_COMPILE_SLANG_SLANG_RS_REFLECTION_H_
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070019
Shih-wei Liao462aefd2010-06-04 15:32:04 -070020#include <fstream>
21#include <iostream>
Stephen Hinese639eb52010-11-08 19:27:20 -080022#include <map>
Stephen Hines48b72bf2011-06-10 15:37:27 -070023#include <set>
Stephen Hinese639eb52010-11-08 19:27:20 -080024#include <string>
25#include <vector>
Shih-wei Liao462aefd2010-06-04 15:32:04 -070026
zonr6315f762010-10-05 15:35:14 +080027#include "llvm/ADT/StringExtras.h"
28
Stephen Hines6e6578a2011-02-07 18:05:48 -080029#include "slang_assert.h"
zonr6315f762010-10-05 15:35:14 +080030#include "slang_rs_export_type.h"
31
Shih-wei Liao462aefd2010-06-04 15:32:04 -070032namespace slang {
33
zonr6315f762010-10-05 15:35:14 +080034 class RSContext;
35 class RSExportVar;
36 class RSExportFunc;
Stephen Hines593a8942011-05-10 15:29:50 -070037 class RSExportForEach;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070038
39class RSReflection {
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070040 private:
41 const RSContext *mRSContext;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070042
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070043 std::string mLastError;
Stephen Hines4cc67fc2011-01-31 16:48:57 -080044 std::vector<std::string> *mGeneratedFileNames;
45
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070046 inline void setError(const std::string &Error) { mLastError = Error; }
Shih-wei Liao462aefd2010-06-04 15:32:04 -070047
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070048 class Context {
49 private:
50 static const char *const ApacheLicenseNote;
Victor Hsiehd8a0d182010-07-07 19:22:33 +080051
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070052 static const char *const Import[];
Shih-wei Liao462aefd2010-06-04 15:32:04 -070053
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070054 bool mVerbose;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070055
Shih-wei Liaob81c6a42010-10-10 14:15:00 -070056 std::string mOutputPathBase;
Zonr Chang8c6d9b22010-10-07 18:01:19 +080057
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070058 std::string mInputRSFile;
Ying Wang4e348442010-08-18 10:29:12 -070059
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070060 std::string mPackageName;
61 std::string mResourceId;
Stephen Hinesa9ae5ae2011-11-11 21:16:59 -080062 std::string mPaddingPrefix;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070063
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070064 std::string mClassName;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070065
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070066 std::string mLicenseNote;
Shih-wei Liaocecd11d2010-09-21 08:07:58 -070067
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070068 std::string mIndent;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070069
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070070 int mPaddingFieldIndex;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070071
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070072 int mNextExportVarSlot;
73 int mNextExportFuncSlot;
Stephen Hines593a8942011-05-10 15:29:50 -070074 int mNextExportForEachSlot;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070075
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070076 // A mapping from a field in a record type to its index in the rsType
77 // instance. Only used when generates TypeClass (ScriptField_*).
Stephen Hinese639eb52010-11-08 19:27:20 -080078 typedef std::map<const RSExportRecordType::Field*, unsigned>
79 FieldIndexMapTy;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070080 FieldIndexMapTy mFieldIndexMap;
81 // Field index of current processing TypeClass.
82 unsigned mFieldIndex;
Shih-wei Liao9c631ff2010-09-17 11:57:29 -070083
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070084 inline void clear() {
85 mClassName = "";
86 mIndent = "";
87 mPaddingFieldIndex = 1;
88 mNextExportVarSlot = 0;
89 mNextExportFuncSlot = 0;
Stephen Hines593a8942011-05-10 15:29:50 -070090 mNextExportForEachSlot = 0;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070091 return;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070092 }
93
Zonr Chang8c6d9b22010-10-07 18:01:19 +080094 bool openClassFile(const std::string &ClassName,
95 std::string &ErrorMsg);
96
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070097 public:
98 typedef enum {
99 AM_Public,
100 AM_Protected,
Alex Sakhartchouk38eca1a2011-08-25 10:47:52 -0700101 AM_Private,
102 AM_PublicSynchronized
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700103 } AccessModifier;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700104
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700105 bool mUseStdout;
106 mutable std::ofstream mOF;
107
Stephen Hines48b72bf2011-06-10 15:37:27 -0700108 std::set<std::string> mTypesToCheck;
109
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700110 static const char *AccessModifierStr(AccessModifier AM);
111
Shih-wei Liaob81c6a42010-10-10 14:15:00 -0700112 Context(const std::string &OutputPathBase,
Zonr Chang8c6d9b22010-10-07 18:01:19 +0800113 const std::string &InputRSFile,
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700114 const std::string &PackageName,
115 const std::string &ResourceId,
Stephen Hinesa9ae5ae2011-11-11 21:16:59 -0800116 const std::string &PaddingPrefix,
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700117 bool UseStdout)
118 : mVerbose(true),
Shih-wei Liaob81c6a42010-10-10 14:15:00 -0700119 mOutputPathBase(OutputPathBase),
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700120 mInputRSFile(InputRSFile),
121 mPackageName(PackageName),
122 mResourceId(ResourceId),
Stephen Hinesa9ae5ae2011-11-11 21:16:59 -0800123 mPaddingPrefix(PaddingPrefix),
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700124 mLicenseNote(ApacheLicenseNote),
125 mUseStdout(UseStdout) {
126 clear();
Zonr Chang66aa2992010-10-05 15:56:31 +0800127 resetFieldIndex();
128 clearFieldIndexMap();
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700129 return;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700130 }
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700131
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700132 inline std::ostream &out() const {
zonr6315f762010-10-05 15:35:14 +0800133 return ((mUseStdout) ? std::cout : mOF);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700134 }
135 inline std::ostream &indent() const {
136 out() << mIndent;
137 return out();
138 }
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700139
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700140 inline void incIndentLevel() {
141 mIndent.append(4, ' ');
142 return;
143 }
144
145 inline void decIndentLevel() {
Stephen Hines6e6578a2011-02-07 18:05:48 -0800146 slangAssert(getIndentLevel() > 0 && "No indent");
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700147 mIndent.erase(0, 4);
148 return;
149 }
150
Zonr Chang92b344a2010-10-05 20:39:03 +0800151 inline int getIndentLevel() { return (mIndent.length() >> 2); }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700152
Zonr Chang92b344a2010-10-05 20:39:03 +0800153 inline int getNextExportVarSlot() { return mNextExportVarSlot++; }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700154
Zonr Chang92b344a2010-10-05 20:39:03 +0800155 inline int getNextExportFuncSlot() { return mNextExportFuncSlot++; }
Stephen Hines593a8942011-05-10 15:29:50 -0700156 inline int getNextExportForEachSlot() { return mNextExportForEachSlot++; }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700157
158 // Will remove later due to field name information is not necessary for
159 // C-reflect-to-Java
160 inline std::string createPaddingField() {
Stephen Hinesa9ae5ae2011-11-11 21:16:59 -0800161 return mPaddingPrefix + llvm::itostr(mPaddingFieldIndex++);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700162 }
163
164 inline void setLicenseNote(const std::string &LicenseNote) {
165 mLicenseNote = LicenseNote;
166 }
167
168 bool startClass(AccessModifier AM,
169 bool IsStatic,
170 const std::string &ClassName,
171 const char *SuperClassName,
172 std::string &ErrorMsg);
173 void endClass();
174
175 void startFunction(AccessModifier AM,
176 bool IsStatic,
177 const char *ReturnType,
178 const std::string &FunctionName,
179 int Argc, ...);
180
181 typedef std::vector<std::pair<std::string, std::string> > ArgTy;
182 void startFunction(AccessModifier AM,
183 bool IsStatic,
184 const char *ReturnType,
185 const std::string &FunctionName,
186 const ArgTy &Args);
187 void endFunction();
188
189 void startBlock(bool ShouldIndent = false);
190 void endBlock();
191
192 inline const std::string &getPackageName() const { return mPackageName; }
193 inline const std::string &getClassName() const { return mClassName; }
194 inline const std::string &getResourceId() const { return mResourceId; }
195
196 void startTypeClass(const std::string &ClassName);
197 void endTypeClass();
198
Zonr Chang92b344a2010-10-05 20:39:03 +0800199 inline void incFieldIndex() { mFieldIndex++; }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700200
Zonr Chang92b344a2010-10-05 20:39:03 +0800201 inline void resetFieldIndex() { mFieldIndex = 0; }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700202
203 inline void addFieldIndexMapping(const RSExportRecordType::Field *F) {
Stephen Hines6e6578a2011-02-07 18:05:48 -0800204 slangAssert((mFieldIndexMap.find(F) == mFieldIndexMap.end()) &&
205 "Nested structure never occurs in C language.");
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700206 mFieldIndexMap.insert(std::make_pair(F, mFieldIndex));
207 }
208
209 inline unsigned getFieldIndex(const RSExportRecordType::Field *F) const {
210 FieldIndexMapTy::const_iterator I = mFieldIndexMap.find(F);
Stephen Hines6e6578a2011-02-07 18:05:48 -0800211 slangAssert((I != mFieldIndexMap.end()) &&
212 "Requesting field is out of scope.");
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700213 return I->second;
214 }
215
Zonr Chang92b344a2010-10-05 20:39:03 +0800216 inline void clearFieldIndexMap() { mFieldIndexMap.clear(); }
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700217 };
218
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700219 bool genScriptClass(Context &C,
220 const std::string &ClassName,
221 std::string &ErrorMsg);
222 void genScriptClassConstructor(Context &C);
223
Stephen Hines5d671782012-01-31 19:32:04 -0800224 static void genInitBoolExportVariable(Context &C,
225 const std::string &VarName,
226 const clang::APValue &Val);
227 static void genInitPrimitiveExportVariable(Context &C,
228 const std::string &VarName,
229 const clang::APValue &Val);
230 static void genInitExportVariable(Context &C,
231 const RSExportType *ET,
232 const std::string &VarName,
233 const clang::APValue &Val);
234 static void genInitValue(Context &C, const clang::APValue &Val);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700235 void genExportVariable(Context &C, const RSExportVar *EV);
236 void genPrimitiveTypeExportVariable(Context &C, const RSExportVar *EV);
237 void genPointerTypeExportVariable(Context &C, const RSExportVar *EV);
238 void genVectorTypeExportVariable(Context &C, const RSExportVar *EV);
Zonr Chang92b344a2010-10-05 20:39:03 +0800239 void genMatrixTypeExportVariable(Context &C, const RSExportVar *EV);
Zonr Chang2e1dba62010-10-05 22:20:11 +0800240 void genConstantArrayTypeExportVariable(Context &C, const RSExportVar *EV);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700241 void genRecordTypeExportVariable(Context &C, const RSExportVar *EV);
242 void genGetExportVariable(Context &C,
243 const std::string &TypeName,
244 const std::string &VarName);
245
246 void genExportFunction(Context &C,
247 const RSExportFunc *EF);
248
Stephen Hines593a8942011-05-10 15:29:50 -0700249 void genExportForEach(Context &C,
250 const RSExportForEach *EF);
251
Stephen Hines48b72bf2011-06-10 15:37:27 -0700252 static void genTypeCheck(Context &C,
253 const RSExportType *ET,
254 const char *VarName);
255
256 static void genTypeInstance(Context &C,
257 const RSExportType *ET);
Stephen Hinesb5a89fb2011-05-17 14:48:02 -0700258
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700259 bool genTypeClass(Context &C,
260 const RSExportRecordType *ERT,
261 std::string &ErrorMsg);
Zonr Chang2e1dba62010-10-05 22:20:11 +0800262 void genTypeItemClass(Context &C, const RSExportRecordType *ERT);
Zonr Chang92b344a2010-10-05 20:39:03 +0800263 void genTypeClassConstructor(Context &C, const RSExportRecordType *ERT);
264 void genTypeClassCopyToArray(Context &C, const RSExportRecordType *ERT);
Alex Sakhartchouk38eca1a2011-08-25 10:47:52 -0700265 void genTypeClassCopyToArrayLocal(Context &C, const RSExportRecordType *ERT);
Zonr Chang92b344a2010-10-05 20:39:03 +0800266 void genTypeClassItemSetter(Context &C, const RSExportRecordType *ERT);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700267 void genTypeClassItemGetter(Context &C, const RSExportRecordType *ERT);
268 void genTypeClassComponentSetter(Context &C, const RSExportRecordType *ERT);
269 void genTypeClassComponentGetter(Context &C, const RSExportRecordType *ERT);
270 void genTypeClassCopyAll(Context &C, const RSExportRecordType *ERT);
Zonr Changd42a4292010-10-17 02:38:43 +0800271 void genTypeClassResize(Context &C);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700272
273 void genBuildElement(Context &C,
Zonr Chang89273bd2010-10-14 20:57:38 +0800274 const char *ElementBuilderName,
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700275 const RSExportRecordType *ERT,
Zonr Chang89273bd2010-10-14 20:57:38 +0800276 const char *RenderScriptVar,
277 bool IsInline);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700278 void genAddElementToElementBuilder(Context &C,
279 const RSExportType *ERT,
280 const std::string &VarName,
281 const char *ElementBuilderName,
Zonr Chang89273bd2010-10-14 20:57:38 +0800282 const char *RenderScriptVar,
283 unsigned ArraySize);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700284 void genAddPaddingToElementBuiler(Context &C,
285 int PaddingSize,
286 const char *ElementBuilderName,
287 const char *RenderScriptVar);
288
289 bool genCreateFieldPacker(Context &C,
290 const RSExportType *T,
291 const char *FieldPackerName);
292 void genPackVarOfType(Context &C,
293 const RSExportType *T,
294 const char *VarName,
295 const char *FieldPackerName);
Zonr Chang2e1dba62010-10-05 22:20:11 +0800296 void genAllocateVarOfType(Context &C,
297 const RSExportType *T,
298 const std::string &VarName);
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700299 void genNewItemBufferIfNull(Context &C, const char *Index);
300 void genNewItemBufferPackerIfNull(Context &C);
301
302 public:
Stephen Hines4cc67fc2011-01-31 16:48:57 -0800303 explicit RSReflection(const RSContext *Context,
304 std::vector<std::string> *GeneratedFileNames)
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700305 : mRSContext(Context),
Stephen Hines4cc67fc2011-01-31 16:48:57 -0800306 mLastError(""),
307 mGeneratedFileNames(GeneratedFileNames) {
Stephen Hines6e6578a2011-02-07 18:05:48 -0800308 slangAssert(mGeneratedFileNames && "Must supply GeneratedFileNames");
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700309 return;
310 }
311
Shih-wei Liaob81c6a42010-10-10 14:15:00 -0700312 bool reflect(const std::string &OutputPathBase,
313 const std::string &OutputPackageName,
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700314 const std::string &InputFileName,
315 const std::string &OutputBCFileName);
316
317 inline const char *getLastError() const {
318 if (mLastError.empty())
319 return NULL;
320 else
321 return mLastError.c_str();
322 }
323}; // class RSReflection
324
325} // namespace slang
326
Stephen Hinese639eb52010-11-08 19:27:20 -0800327#endif // _FRAMEWORKS_COMPILE_SLANG_SLANG_RS_REFLECTION_H_ NOLINT