1 /****************************************************************************
3 ** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: Nokia Corporation (qt-info@nokia.com)
7 ** This file is part of the QtDeclarative module of the Qt Toolkit.
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** GNU Lesser General Public License Usage
11 ** This file may be used under the terms of the GNU Lesser General Public
12 ** License version 2.1 as published by the Free Software Foundation and
13 ** appearing in the file LICENSE.LGPL included in the packaging of this
14 ** file. Please review the following information to ensure the GNU Lesser
15 ** General Public License version 2.1 requirements will be met:
16 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
18 ** In addition, as a special exception, Nokia gives you certain additional
19 ** rights. These rights are described in the Nokia Qt LGPL Exception
20 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
22 ** GNU General Public License Usage
23 ** Alternatively, this file may be used under the terms of the GNU General
24 ** Public License version 3.0 as published by the Free Software Foundation
25 ** and appearing in the file LICENSE.GPL included in the packaging of this
26 ** file. Please review the following information to ensure the GNU General
27 ** Public License version 3.0 requirements will be met:
28 ** http://www.gnu.org/copyleft/gpl.html.
31 ** Alternatively, this file may be used in accordance with the terms and
32 ** conditions contained in a signed written agreement between you and Nokia.
40 ****************************************************************************/
42 #ifndef QDECLARATIVECOMPILER_P_H
43 #define QDECLARATIVECOMPILER_P_H
49 // This file is not part of the Qt API. It exists purely as an
50 // implementation detail. This header file may change from version to
51 // version without notice, or even be removed.
56 #include "qdeclarative.h"
57 #include "qdeclarativeerror.h"
58 #include "private/qv8_p.h"
59 #include "private/qdeclarativeinstruction_p.h"
60 #include "private/qdeclarativeparser_p.h"
61 #include "private/qdeclarativeengine_p.h"
62 #include "private/qbitfield_p.h"
63 #include "private/qdeclarativepropertycache_p.h"
64 #include "private/qdeclarativeintegercache_p.h"
65 #include "private/qdeclarativetypenamecache_p.h"
66 #include "private/qdeclarativetypeloader_p.h"
68 #include <QtCore/qbytearray.h>
69 #include <QtCore/qset.h>
70 #include <QtCore/QCoreApplication>
74 class QDeclarativeEngine;
75 class QDeclarativeComponent;
76 class QDeclarativeContext;
77 class QDeclarativeContextData;
79 class Q_AUTOTEST_EXPORT QDeclarativeCompiledData : public QDeclarativeRefCount, public QDeclarativeCleanup
82 QDeclarativeCompiledData(QDeclarativeEngine *engine);
83 virtual ~QDeclarativeCompiledData();
87 QDeclarativeTypeNameCache *importCache;
92 : type(0), typePropertyCache(0), component(0) {}
95 QDeclarativeType *type;
96 QDeclarativePropertyCache *typePropertyCache;
97 QDeclarativeCompiledData *component;
99 QObject *createInstance(QDeclarativeContextData *, const QBitField &, QList<QDeclarativeError> *) const;
100 const QMetaObject *metaObject() const;
101 QDeclarativePropertyCache *propertyCache() const;
102 QDeclarativePropertyCache *createPropertyCache(QDeclarativeEngine *);
104 QList<TypeReference> types;
106 QList<v8::Persistent<v8::Array> > v8bindings;
108 const QMetaObject *root;
109 QAbstractDynamicMetaObject rootData;
110 QDeclarativePropertyCache *rootPropertyCache;
111 QList<QString> primitives;
112 QList<QByteArray> datas;
114 QList<QJSValue *> cachedClosures;
115 QList<QDeclarativePropertyCache *> propertyCaches;
116 QList<QDeclarativeIntegerCache *> contextCaches;
117 QList<QDeclarativeScriptData *> scripts;
120 void dumpInstructions();
122 int addInstruction(const QDeclarativeInstruction &instr);
123 int nextInstructionIndex();
124 QDeclarativeInstruction *instruction(int index);
127 virtual void clear(); // From QDeclarativeCleanup
130 void dump(QDeclarativeInstruction *, int idx = -1);
131 QDeclarativeCompiledData(const QDeclarativeCompiledData &other);
132 QDeclarativeCompiledData &operator=(const QDeclarativeCompiledData &other);
134 friend class QDeclarativeCompiler;
135 int pack(const char *, size_t);
137 int indexForString(const QString &);
138 int indexForByteArray(const QByteArray &);
139 int indexForUrl(const QUrl &);
142 namespace QDeclarativeCompilerTypes {
143 struct BindingContext
146 : stack(0), owner(0), object(0) {}
147 BindingContext(QDeclarativeParser::Object *o)
148 : stack(0), owner(0), object(o) {}
149 BindingContext incr() const {
150 BindingContext rv(object);
151 rv.stack = stack + 1;
154 bool isSubContext() const { return stack != 0; }
157 QDeclarativeParser::Object *object;
160 struct BindingReference : public QDeclarativePool::Class
162 BindingReference() : nextReference(0) {}
164 QDeclarativeParser::Variant expression;
165 QDeclarativeParser::Property *property;
166 QDeclarativeParser::Value *value;
168 enum DataType { QtScript, V4, V8 };
173 QString rewrittenExpression;
174 BindingContext bindingContext;
176 BindingReference *nextReference;
179 struct IdList : public QFieldList<QDeclarativeParser::Object,
180 &QDeclarativeParser::Object::nextIdObject>
182 QDeclarativeParser::Object *value(const QString &id) const {
183 for (QDeclarativeParser::Object *o = first(); o; o = next(o)) {
191 // Contains all the incremental compiler state about a component. As
192 // a single QML file can have multiple components defined, there may be
193 // more than one of these for each compile
194 struct ComponentCompileState : public QDeclarativePool::Class
196 ComponentCompileState()
197 : parserStatusCount(0), pushedProperties(0), nested(false), v8BindingProgramLine(-1), root(0) {}
200 int parserStatusCount;
201 int pushedProperties;
204 QByteArray compiledBindingData;
205 QString v8BindingProgram;
206 int v8BindingProgramLine;
207 int v8BindingProgramIndex;
209 typedef QDeclarativeCompilerTypes::BindingReference B;
210 typedef QFieldList<B, &B::nextReference> BindingReferenceList;
211 BindingReferenceList bindings;
212 typedef QDeclarativeParser::Object O;
213 typedef QFieldList<O, &O::nextAliasingObject> AliasingObjectsList;
214 AliasingObjectsList aliasingObjects;
215 QDeclarativeParser::Object *root;
219 class QMetaObjectBuilder;
220 class Q_AUTOTEST_EXPORT QDeclarativeCompiler
222 Q_DECLARE_TR_FUNCTIONS(QDeclarativeCompiler)
224 QDeclarativeCompiler(QDeclarativePool *);
226 bool compile(QDeclarativeEngine *, QDeclarativeTypeData *, QDeclarativeCompiledData *);
228 bool isError() const;
229 QList<QDeclarativeError> errors() const;
231 static bool isAttachedPropertyName(const QString &);
232 static bool isSignalPropertyName(const QString &);
233 static bool isAttachedPropertyName(const QStringRef &);
234 static bool isSignalPropertyName(const QStringRef &);
236 int evaluateEnum(const QByteArray& script) const; // for QDeclarativeCustomParser::evaluateEnum
237 const QMetaObject *resolveType(const QByteArray& name) const; // for QDeclarativeCustomParser::resolveType
238 int rewriteBinding(const QString& expression, const QString& name); // for QDeclarativeCustomParser::rewriteBinding
241 static void reset(QDeclarativeCompiledData *);
243 void compileTree(QDeclarativeParser::Object *tree);
246 bool buildObject(QDeclarativeParser::Object *obj, const QDeclarativeCompilerTypes::BindingContext &);
247 bool buildComponent(QDeclarativeParser::Object *obj, const QDeclarativeCompilerTypes::BindingContext &);
248 bool buildSubObject(QDeclarativeParser::Object *obj, const QDeclarativeCompilerTypes::BindingContext &);
249 bool buildSignal(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj,
250 const QDeclarativeCompilerTypes::BindingContext &);
251 bool buildProperty(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj,
252 const QDeclarativeCompilerTypes::BindingContext &);
253 bool buildPropertyInNamespace(QDeclarativeImportedNamespace *ns,
254 QDeclarativeParser::Property *prop,
255 QDeclarativeParser::Object *obj,
256 const QDeclarativeCompilerTypes::BindingContext &);
257 bool buildIdProperty(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj);
258 bool buildAttachedProperty(QDeclarativeParser::Property *prop,
259 QDeclarativeParser::Object *obj,
260 const QDeclarativeCompilerTypes::BindingContext &ctxt);
261 bool buildGroupedProperty(QDeclarativeParser::Property *prop,
262 QDeclarativeParser::Object *obj,
263 const QDeclarativeCompilerTypes::BindingContext &ctxt);
264 bool buildValueTypeProperty(QObject *type,
265 QDeclarativeParser::Object *obj,
266 QDeclarativeParser::Object *baseObj,
267 const QDeclarativeCompilerTypes::BindingContext &ctxt);
268 bool buildListProperty(QDeclarativeParser::Property *prop,
269 QDeclarativeParser::Object *obj,
270 const QDeclarativeCompilerTypes::BindingContext &ctxt);
271 bool buildScriptStringProperty(QDeclarativeParser::Property *prop,
272 QDeclarativeParser::Object *obj,
273 const QDeclarativeCompilerTypes::BindingContext &ctxt);
274 bool buildPropertyAssignment(QDeclarativeParser::Property *prop,
275 QDeclarativeParser::Object *obj,
276 const QDeclarativeCompilerTypes::BindingContext &ctxt);
277 bool buildPropertyObjectAssignment(QDeclarativeParser::Property *prop,
278 QDeclarativeParser::Object *obj,
279 QDeclarativeParser::Value *value,
280 const QDeclarativeCompilerTypes::BindingContext &ctxt);
281 bool buildPropertyOnAssignment(QDeclarativeParser::Property *prop,
282 QDeclarativeParser::Object *obj,
283 QDeclarativeParser::Object *baseObj,
284 QDeclarativeParser::Value *value,
285 const QDeclarativeCompilerTypes::BindingContext &ctxt);
286 bool buildPropertyLiteralAssignment(QDeclarativeParser::Property *prop,
287 QDeclarativeParser::Object *obj,
288 QDeclarativeParser::Value *value,
289 const QDeclarativeCompilerTypes::BindingContext &ctxt);
290 bool doesPropertyExist(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj);
291 bool testLiteralAssignment(QDeclarativeParser::Property *prop,
292 QDeclarativeParser::Value *value);
293 bool testQualifiedEnumAssignment(const QMetaProperty &prop,
294 QDeclarativeParser::Object *obj,
295 QDeclarativeParser::Value *value,
297 enum DynamicMetaMode { IgnoreAliases, ResolveAliases, ForceCreation };
298 bool mergeDynamicMetaProperties(QDeclarativeParser::Object *obj);
299 bool buildDynamicMeta(QDeclarativeParser::Object *obj, DynamicMetaMode mode);
300 bool checkDynamicMeta(QDeclarativeParser::Object *obj);
301 bool buildBinding(QDeclarativeParser::Value *, QDeclarativeParser::Property *prop,
302 const QDeclarativeCompilerTypes::BindingContext &ctxt);
303 bool buildComponentFromRoot(QDeclarativeParser::Object *obj, const QDeclarativeCompilerTypes::BindingContext &);
304 bool compileAlias(QFastMetaBuilder &,
306 QDeclarativeParser::Object *obj,
307 int propIndex, int aliasIndex,
308 QDeclarativeParser::Object::DynamicProperty &);
309 bool completeComponentBuild();
310 bool checkValidId(QDeclarativeParser::Value *, const QString &);
313 void genObject(QDeclarativeParser::Object *obj);
314 void genObjectBody(QDeclarativeParser::Object *obj);
315 void genValueTypeProperty(QDeclarativeParser::Object *obj,QDeclarativeParser::Property *);
316 void genComponent(QDeclarativeParser::Object *obj);
317 void genValueProperty(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj);
318 void genListProperty(QDeclarativeParser::Property *prop, QDeclarativeParser::Object *obj);
319 void genPropertyAssignment(QDeclarativeParser::Property *prop,
320 QDeclarativeParser::Object *obj,
321 QDeclarativeParser::Property *valueTypeProperty = 0);
322 void genLiteralAssignment(QDeclarativeParser::Property *prop,
323 QDeclarativeParser::Value *value);
324 void genBindingAssignment(QDeclarativeParser::Value *binding,
325 QDeclarativeParser::Property *prop,
326 QDeclarativeParser::Object *obj,
327 QDeclarativeParser::Property *valueTypeProperty = 0);
328 int genContextCache();
330 int genValueTypeData(QDeclarativeParser::Property *prop, QDeclarativeParser::Property *valueTypeProp);
331 int genPropertyData(QDeclarativeParser::Property *prop);
333 int componentTypeRef();
335 static QDeclarativeType *toQmlType(QDeclarativeParser::Object *from);
336 bool canCoerce(int to, QDeclarativeParser::Object *from);
338 QString elementName(QDeclarativeParser::Object *);
340 QStringList deferredProperties(QDeclarativeParser::Object *);
342 QDeclarativePropertyCache::Data *property(QDeclarativeParser::Object *, int);
343 QDeclarativePropertyCache::Data *property(QDeclarativeParser::Object *, const QStringRef &,
344 bool *notInRevision = 0);
345 QDeclarativePropertyCache::Data *signal(QDeclarativeParser::Object *, const QStringRef &,
346 bool *notInRevision = 0);
347 int indexOfProperty(QDeclarativeParser::Object *, const QStringRef &, bool *notInRevision = 0);
348 int indexOfProperty(QDeclarativeParser::Object *, const QString &, bool *notInRevision = 0);
349 int indexOfSignal(QDeclarativeParser::Object *, const QString &, bool *notInRevision = 0);
351 void addId(const QString &, QDeclarativeParser::Object *);
355 void addBindingReference(QDeclarativeCompilerTypes::BindingReference *);
357 QDeclarativeCompilerTypes::ComponentCompileState *compileState;
359 QDeclarativePool *pool;
361 QDeclarativeCompilerTypes::ComponentCompileState *componentState(QDeclarativeParser::Object *);
362 void saveComponentState();
364 QList<QDeclarativeError> exceptions;
365 QDeclarativeCompiledData *output;
366 QDeclarativeEngine *engine;
367 QDeclarativeEnginePrivate *enginePrivate;
368 QDeclarativeParser::Object *unitRoot;
369 QDeclarativeTypeData *unit;
372 // Compiler component statistics. Only collected if QML_COMPILER_STATS=1
375 ComponentStat() : ids(0), objects(0) {}
380 QList<QDeclarativeParser::LocationSpan> scriptBindings;
381 QList<QDeclarativeParser::LocationSpan> optimizedBindings;
384 struct ComponentStats : public QDeclarativePool::Class
386 ComponentStat componentStat;
387 QList<ComponentStat> savedComponentStats;
389 ComponentStats *componentStats;
394 #endif // QDECLARATIVECOMPILER_P_H