7#include <private/qjsvalue_p.h>
8#include <private/qqmlbuiltinfunctions_p.h>
9#include <private/qqmlcomponent_p.h>
10#include <private/qqmldirdata_p.h>
11#include <private/qqmlengine_p.h>
12#include <private/qqmlfinalizer_p.h>
13#include <private/qqmlloggingcategorybase_p.h>
14#include <private/qqmlmetatype_p.h>
15#include <private/qqmlmetatypedata_p.h>
16#include <private/qqmltype_p_p.h>
17#include <private/qqmltypemodule_p.h>
18#include <private/qqmltypewrapper_p.h>
19#include <private/qqmlvaluetypewrapper_p.h>
20#include <private/qv4alloca_p.h>
21#include <private/qv4dateobject_p.h>
22#include <private/qv4errorobject_p.h>
23#include <private/qv4identifiertable_p.h>
24#include <private/qv4lookup_p.h>
25#include <private/qv4qobjectwrapper_p.h>
27#include <QtQml/qqmlprivate.h>
29#include <QtCore/qmutex.h>
30#include <QtCore/qmetasequence.h>
35
36
37
38
39
40
41
42
43
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
63 QQmlData *data = QQmlData::get(object);
67 || !data->context->engine()
68 || data->deferredData.isEmpty()
69 || data->wasDeleted(object)) {
73 if (!data->propertyCache)
74 data->propertyCache = QQmlMetaType::propertyCache(object->metaObject());
76 QQmlEnginePrivate *ep = QQmlEnginePrivate::get(data->context->engine());
78 QQmlComponentPrivate::DeferredState state;
79 QQmlComponentPrivate::beginDeferred(ep, object, &state);
82 data->releaseDeferredData();
84 QQmlComponentPrivate::completeDeferred(ep, &state);
89 return QQmlEngine::contextForObject(obj);
94 QQmlData *data = QQmlData::get(obj);
95 if (!data || !data->context)
97 return data->context->engine();
101 QObject *object,
bool create)
106 QObject *rv = data->hasExtendedData() ? data->attachedProperties()->value(pf) : 0;
113 data->attachedProperties()->insert(pf, rv);
119 const QMetaObject *attachedMetaObject)
121 QQmlEngine *engine = object ? qmlEngine(object) :
nullptr;
122 return QQmlMetaType::attachedPropertiesFunc(
123 engine ? QQmlTypeLoader::get(engine) :
nullptr, attachedMetaObject);
131 QQmlData *data = QQmlData::get(object, createIfMissing);
138 return resolveAttachedProperties(func, data, object, createIfMissing);
142
143
144
145
146
147
148
149QObject *qmlExtendedObject(QObject *base)
151 return QQmlPrivate::qmlExtendedObject(base, 0);
154QObject *QQmlPrivate::qmlExtendedObject(QObject *object,
int index)
159 void *result =
nullptr;
160 QObjectPrivate *d = QObjectPrivate::get(object);
164 const int id = d->metaObject->metaCall(
165 object, QMetaObject::CustomCall,
166 QQmlProxyMetaObject::extensionObjectId(index), &result);
167 if (id != QQmlProxyMetaObject::extensionObjectId(index))
170 return static_cast<QObject *>(result);
173void QQmlPrivate::qmlRegistrationWarning(
174 QQmlPrivate::QmlRegistrationWarning warning, QMetaType metaType)
177 case UnconstructibleType:
180 <<
" is neither a default constructible QObject, nor a default- "
181 <<
"and copy-constructible Q_GADGET, nor a QObject marked as uncreatable.\n"
182 <<
"You should not use it as a QML type.";
184 case UnconstructibleSingleton:
186 <<
"Singleton" << metaType.name()
187 <<
"needs to be a concrete class with either a default constructor"
188 <<
"or, when adding a default constructor is infeasible, a public static"
189 <<
"create(QQmlEngine *, QJSEngine *) method.";
191 case NonQObjectWithAtached:
194 <<
"is not a QObject, but has attached properties. This won't work.";
199QMetaType QQmlPrivate::compositeMetaType(
200 QV4::ExecutableCompilationUnit *unit,
int elementNameId)
202 return QQmlTypePrivate::visibleQmlTypeByName(unit, elementNameId).typeId();
205QMetaType QQmlPrivate::compositeMetaType(
206 QV4::ExecutableCompilationUnit *unit,
const QString &elementName)
208 return QQmlTypePrivate::visibleQmlTypeByName(
209 unit->baseCompilationUnit(), elementName, unit->engine->typeLoader())
213QMetaType QQmlPrivate::compositeListMetaType(
214 QV4::ExecutableCompilationUnit *unit,
int elementNameId)
216 return QQmlTypePrivate::visibleQmlTypeByName(unit, elementNameId).qListTypeId();
219QMetaType QQmlPrivate::compositeListMetaType(
220 QV4::ExecutableCompilationUnit *unit,
const QString &elementName)
222 return QQmlTypePrivate::visibleQmlTypeByName(
223 unit->baseCompilationUnit(), elementName, unit->engine->typeLoader())
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267int qmlRegisterUncreatableMetaObject(
const QMetaObject &staticMetaObject,
268 const char *uri,
int versionMajor,
269 int versionMinor,
const char *qmlName,
270 const QString& reason)
272 QQmlPrivate::RegisterType type = {
273 QQmlPrivate::RegisterType::CurrentVersion,
282 uri, QTypeRevision::fromVersion(versionMajor, versionMinor), qmlName, &staticMetaObject,
284 QQmlAttachedPropertiesFunc(),
294 QTypeRevision::zero(),
296 QQmlPrivate::ValueTypeCreationMethod::None
299 return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
303
304
305
306
307
308
309
310
311
312
313
314void qmlClearTypeRegistrations()
316 QQmlMetaType::clearTypeRegistrations();
317 QQmlEnginePrivate::baseModulesUninitialized =
true;
318 qmlClearEnginePlugins();
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
351 return QQmlMetaType::protectModule(QString::fromUtf8(uri),
352 QTypeRevision::fromMajorVersion(majVersion));
356
357
358
359
360
361
362
363
364
365
369 QQmlMetaType::registerModule(uri, QTypeRevision::fromVersion(versionMajor, versionMinor));
374 if (importMajor == QQmlModuleImportAuto)
375 return QQmlDirParser::Import(uri, QTypeRevision(), QQmlDirParser::Import::Auto);
376 else if (importMajor == QQmlModuleImportLatest)
377 return QQmlDirParser::Import(uri, QTypeRevision(), QQmlDirParser::Import::Default);
378 else if (importMinor == QQmlModuleImportLatest)
379 return QQmlDirParser::Import(uri, QTypeRevision::fromMajorVersion(importMajor), QQmlDirParser::Import::Default);
380 return QQmlDirParser::Import(uri, QTypeRevision::fromVersion(importMajor, importMinor), QQmlDirParser::Import::Default);
385 return moduleMajor == QQmlModuleImportModuleAny
387 : QTypeRevision::fromMajorVersion(moduleMajor);
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
451 const char *import,
int importMajor,
int importMinor)
453 QQmlMetaType::registerModuleImport(
454 QString::fromUtf8(uri), resolveModuleVersion(moduleMajor),
455 resolveImport(QString::fromUtf8(import), importMajor, importMinor));
460
461
462
463
464
465
466
467
468
469
471 const char *import,
int importMajor,
int importMinor)
473 QQmlMetaType::unregisterModuleImport(
474 QString::fromUtf8(uri), resolveModuleVersion(moduleMajor),
475 resolveImport(QString::fromUtf8(import), importMajor, importMinor));
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502int qmlTypeId(
const char *uri,
int versionMajor,
int versionMinor,
const char *qmlName)
504 auto revision = QTypeRevision::fromVersion(versionMajor, versionMinor);
505 int id = QQmlMetaType::typeId(uri, revision, qmlName);
509
510
511
512
513
515 QQmlTypeLoader *typeLoader = QQmlTypeLoader::get(&engine);
516 auto loadHelper = QQml::makeRefPointer<LoadHelper>(
517 typeLoader, uri, qmlName, QQmlTypeLoader::Synchronous);
518 const QQmlType type = loadHelper->type();
519 if (type.availableInVersion(revision))
529 error.setDescription(QStringLiteral(
"The registered singleton has already been deleted. "
530 "Ensure that it outlives the engine."));
531 QQmlEnginePrivate::get(engine)->warning(engine, error);
535 if (engine->thread() != instance->thread()) {
537 error.setDescription(QStringLiteral(
"Registered object must live in the same thread "
538 "as the engine it was registered with"));
539 QQmlEnginePrivate::get(engine)->warning(engine, error);
547#if QT_DEPRECATED_SINCE(6
, 3
)
548QObject *QQmlPrivate::SingletonFunctor::operator()(QQmlEngine *qeng, QJSEngine *)
550 if (!checkSingletonInstance(qeng, m_object))
555 error.setDescription(QStringLiteral(
"Singleton registered by registerSingletonInstance "
556 "must only be accessed from one engine"));
557 QQmlEnginePrivate::get(qeng)->warning(qeng, error);
561 alreadyCalled =
true;
562 QJSEngine::setObjectOwnership(m_object, QQmlEngine::CppOwnership);
567QObject *QQmlPrivate::SingletonInstanceFunctor::operator()(QQmlEngine *qeng, QJSEngine *)
569 if (!checkSingletonInstance(qeng, m_object))
574 QJSEngine::setObjectOwnership(m_object, QQmlEngine::CppOwnership);
575 }
else if (m_engine != qeng) {
577 error.setDescription(QLatin1String(
"Singleton registered by registerSingletonInstance must only be accessed from one engine"));
578 QQmlEnginePrivate::get(qeng)->warning(qeng, error);
587 QList<QTypeRevision> revisions;
590 const int propertyOffset = metaObject->propertyOffset();
591 const int propertyCount = metaObject->propertyCount();
592 for (
int coreIndex = propertyOffset, propertyEnd = propertyOffset + propertyCount;
593 coreIndex < propertyEnd; ++coreIndex) {
594 const QMetaProperty property = metaObject->property(coreIndex);
595 if (
int revision = property.revision())
596 revisions.append(QTypeRevision::fromEncodedVersion(revision));
598 const int methodOffset = metaObject->methodOffset();
599 const int methodCount = metaObject->methodCount();
600 for (
int methodIndex = methodOffset, methodEnd = methodOffset + methodCount;
601 methodIndex < methodEnd; ++methodIndex) {
602 const QMetaMethod method = metaObject->method(methodIndex);
603 if (
int revision = method.revision())
604 revisions.append(QTypeRevision::fromEncodedVersion(revision));
608 if (
const QMetaObject *superMeta = metaObject->superClass())
609 revisions += availableRevisions(superMeta);
614template<
typename Registration>
616 QTypeRevision defaultVersion)
618 const quint8 majorVersion = revision.hasMajorVersion() ? revision.majorVersion()
619 : defaultVersion.majorVersion();
620 registration->version = revision.hasMinorVersion()
621 ? QTypeRevision::fromVersion(majorVersion, revision.minorVersion())
622 : QTypeRevision::fromMajorVersion(majorVersion);
623 registration->revision = revision;
628 auto revisions = availableRevisions(metaObject);
629 revisions.append(added);
633static void uniqueRevisions(QList<QTypeRevision> *revisions, QTypeRevision defaultVersion,
636 bool revisionsHaveMajorVersions =
false;
639 const QList<QTypeRevision> origRevisions = *revisions;
640 for (QTypeRevision revision : origRevisions) {
642 if (revision.hasMajorVersion()) {
643 revisionsHaveMajorVersions =
true;
644 if (revision.majorVersion() < defaultVersion.majorVersion())
645 revisions->append(QTypeRevision::fromVersion(revision.majorVersion(), 254));
649 if (revisionsHaveMajorVersions) {
650 if (!added.hasMajorVersion()) {
652 revisions->append(QTypeRevision::fromVersion(defaultVersion.majorVersion(),
653 added.minorVersion()));
654 }
else if (added.majorVersion() < defaultVersion.majorVersion()) {
656 revisions->append(QTypeRevision::fromVersion(defaultVersion.majorVersion(), 0));
660 std::sort(revisions->begin(), revisions->end());
661 const auto it = std::unique(revisions->begin(), revisions->end());
662 revisions->erase(it, revisions->end());
666 const QQmlPrivate::RegisterSingletonType &type)
668 QQmlType::SingletonInstanceInfo::Ptr siinfo = QQmlType::SingletonInstanceInfo::create();
669 siinfo->scriptCallback = type.scriptApi;
670 siinfo->qobjectCallback = type.qObjectApi;
671 siinfo->typeName = type.typeName;
672 return QQmlType::SingletonInstanceInfo::ConstPtr(
673 siinfo.take(), QQmlType::SingletonInstanceInfo::ConstPtr::Adopt);
677 const QQmlPrivate::RegisterCompositeSingletonType &type)
679 QQmlType::SingletonInstanceInfo::Ptr siinfo = QQmlType::SingletonInstanceInfo::create();
680 siinfo->url = QQmlMetaType::normalizedUrl(type.url);
681 siinfo->typeName = type.typeName;
682 return QQmlType::SingletonInstanceInfo::ConstPtr(
683 siinfo.take(), QQmlType::SingletonInstanceInfo::ConstPtr::Adopt);
688 if (!dtype.isValid())
691 QQmlMetaType::registerUndeletableType(dtype);
692 return dtype.index();
695using ElementNames = QVarLengthArray<
const char *, 8>;
698 Q_ASSERT(metaObject);
699 const char *key =
"QML.Element";
701 const int offset = metaObject->classInfoOffset();
702 const int start = metaObject->classInfoCount() + offset - 1;
704 ElementNames elementNames;
706 for (
int i = start; i >= offset; --i) {
707 const QMetaClassInfo classInfo = metaObject->classInfo(i);
708 if (qstrcmp(key, classInfo.name()) == 0) {
709 const char *elementName = classInfo.value();
711 if (qstrcmp(elementName,
"auto") == 0) {
712 const char *strippedClassName = metaObject->className();
713 for (
const char *c = strippedClassName; *c !=
'\0'; c++) {
715 strippedClassName = c + 1;
717 elementName = strippedClassName;
718 }
else if (qstrcmp(elementName,
"anonymous") == 0) {
719 if (elementNames.isEmpty())
720 elementNames.push_back(
nullptr);
721 else if (elementNames[0] !=
nullptr)
722 qWarning() << metaObject->className() <<
"is both anonymous and named";
726 if (!elementNames.isEmpty() && elementNames[0] ==
nullptr) {
727 qWarning() << metaObject->className() <<
"is both anonymous and named";
728 elementNames[0] = elementName;
730 elementNames.push_back(elementName);
745 for (
int i = 1, end = elementNames->length(); i < end; ++i)
746 otherNames.append(QString::fromUtf8(elementNames->at(i)));
747 elementNames =
nullptr;
750 for (
const QString &otherName : std::as_const(otherNames))
751 QQmlMetaType::registerTypeAlias(typeId, otherName);
755 const ElementNames *elementNames;
756 QVarLengthArray<QString, 8> otherNames;
761 const QQmlPrivate::RegisterTypeAndRevisions &type,
762 const ElementNames &elementNames)
764 using namespace QQmlPrivate;
766 const bool isValueType = !(type.typeId.flags() & QMetaType::PointerToQObject);
767 const bool creatable = (elementNames[0] !=
nullptr || isValueType)
768 && boolClassInfo(type.classInfoMetaObject,
"QML.Creatable",
true);
770 QString noCreateReason;
771 ValueTypeCreationMethod creationMethod = ValueTypeCreationMethod::None;
774 noCreateReason = QString::fromUtf8(
775 classInfo(type.classInfoMetaObject,
"QML.UncreatableReason"));
776 if (noCreateReason.isEmpty())
777 noCreateReason = QLatin1String(
"Type cannot be created in QML.");
778 }
else if (isValueType) {
779 const char *method = classInfo(type.classInfoMetaObject,
"QML.CreationMethod");
780 if (qstrcmp(method,
"structured") == 0)
781 creationMethod = ValueTypeCreationMethod::Structured;
782 else if (qstrcmp(method,
"construct") == 0)
783 creationMethod = ValueTypeCreationMethod::Construct;
786 RegisterType typeRevision = {
787 QQmlPrivate::RegisterType::CurrentVersion,
790 creatable ? type.objectSize : 0,
794 type.createValueType,
799 type.attachedPropertiesFunction,
800 type.attachedPropertiesMetaObject,
801 type.parserStatusCast,
802 type.valueSourceCast,
803 type.valueInterceptorCast,
804 type.extensionObjectCreate,
805 type.extensionMetaObject,
808 type.structVersion > 0 ? type.finalizerCast : -1,
812 QQmlPrivate::RegisterSequentialContainer sequenceRevision = {
818 type.structVersion > 1 ? type.listMetaSequence : QMetaSequence(),
822 const QTypeRevision added = revisionClassInfo(
823 type.classInfoMetaObject,
"QML.AddedInVersion",
824 QTypeRevision::fromVersion(type.version.majorVersion(), 0));
825 const QTypeRevision removed = revisionClassInfo(
826 type.classInfoMetaObject,
"QML.RemovedInVersion");
827 const QList<QTypeRevision> furtherRevisions = revisionClassInfos(type.classInfoMetaObject,
830 auto revisions = prepareRevisions(type.metaObject, added) + furtherRevisions;
831 if (type.attachedPropertiesMetaObject)
832 revisions += availableRevisions(type.attachedPropertiesMetaObject);
833 uniqueRevisions(&revisions, type.version, added);
836 for (QTypeRevision revision : std::as_const(revisions)) {
837 if (revision.hasMajorVersion() && revision.majorVersion() > type.version.majorVersion())
840 assignVersions(&typeRevision, revision, type.version);
843 if (typeRevision.version < added
844 || (removed.isValid() && !(typeRevision.version < removed))) {
845 typeRevision.elementName =
nullptr;
846 typeRevision.create =
nullptr;
847 typeRevision.userdata =
nullptr;
849 typeRevision.elementName = elementNames[0];
850 typeRevision.create = creatable ? type.create :
nullptr;
851 typeRevision.userdata = type.userdata;
854 typeRevision.customParser = type.customParserFactory();
855 const int id = qmlregister(TypeRegistration, &typeRevision);
857 type.qmlTypeIds->append(id);
859 if (typeRevision.elementName)
860 aliasRegistrar.registerAliases(id);
862 if (sequenceRevision.metaSequence != QMetaSequence()) {
863 sequenceRevision.version = typeRevision.version;
864 sequenceRevision.revision = typeRevision.revision;
865 const int id = QQmlPrivate::qmlregister(
866 QQmlPrivate::SequentialContainerRegistration, &sequenceRevision);
868 type.qmlTypeIds->append(id);
874 const QQmlPrivate::RegisterSingletonTypeAndRevisions &type,
875 const ElementNames &elementNames)
877 using namespace QQmlPrivate;
879 RegisterSingletonType revisionRegistration = {
886 type.instanceMetaObject,
888 type.extensionObjectCreate,
889 type.extensionMetaObject,
892 const QQmlType::SingletonInstanceInfo::ConstPtr siinfo
893 = singletonInstanceInfo(revisionRegistration);
895 const QTypeRevision added = revisionClassInfo(
896 type.classInfoMetaObject,
"QML.AddedInVersion",
897 QTypeRevision::fromVersion(type.version.majorVersion(), 0));
898 const QTypeRevision removed = revisionClassInfo(
899 type.classInfoMetaObject,
"QML.RemovedInVersion");
900 const QList<QTypeRevision> furtherRevisions = revisionClassInfos(type.classInfoMetaObject,
903 auto revisions = prepareRevisions(type.instanceMetaObject, added) + furtherRevisions;
904 uniqueRevisions(&revisions, type.version, added);
907 for (QTypeRevision revision : std::as_const(revisions)) {
908 if (revision.hasMajorVersion() && revision.majorVersion() > type.version.majorVersion())
911 assignVersions(&revisionRegistration, revision, type.version);
914 if (revisionRegistration.version < added
915 || (removed.isValid() && !(revisionRegistration.version < removed))) {
916 revisionRegistration.typeName =
nullptr;
917 revisionRegistration.qObjectApi =
nullptr;
919 revisionRegistration.typeName = elementNames[0];
920 revisionRegistration.qObjectApi = type.qObjectApi;
923 const int id = finalizeType(
924 QQmlMetaType::registerSingletonType(revisionRegistration, siinfo));
926 type.qmlTypeIds->append(id);
928 if (revisionRegistration.typeName)
929 aliasRegistrar.registerAliases(id);
934
935
936
937int QQmlPrivate::qmlregister(RegistrationType type,
void *data)
940 case AutoParentRegistration:
941 return QQmlMetaType::registerAutoParentFunction(
942 *
reinterpret_cast<RegisterAutoParent *>(data));
943 case QmlUnitCacheHookRegistration:
944 return QQmlMetaType::registerUnitCacheHook(
945 *
reinterpret_cast<RegisterQmlUnitCacheHook *>(data));
946 case TypeAndRevisionsRegistration: {
947 const RegisterTypeAndRevisions &type = *
reinterpret_cast<RegisterTypeAndRevisions *>(data);
948 if (type.structVersion > 1 && type.forceAnonymous) {
949 doRegisterTypeAndRevisions(type, {
nullptr});
951 const ElementNames names = classElementNames(type.classInfoMetaObject);
952 if (names.isEmpty()) {
953 qWarning().nospace() <<
"Missing QML.Element class info for "
954 << type.classInfoMetaObject->className();
956 doRegisterTypeAndRevisions(type, names);
962 case SingletonAndRevisionsRegistration: {
963 const RegisterSingletonTypeAndRevisions &type
964 = *
reinterpret_cast<RegisterSingletonTypeAndRevisions *>(data);
965 const ElementNames names = classElementNames(type.classInfoMetaObject);
966 if (names.isEmpty()) {
967 qWarning().nospace() <<
"Missing QML.Element class info for "
968 << type.classInfoMetaObject->className();
970 doRegisterSingletonAndRevisions(type, names);
974 case SequentialContainerAndRevisionsRegistration: {
975 const RegisterSequentialContainerAndRevisions &type
976 = *
reinterpret_cast<RegisterSequentialContainerAndRevisions *>(data);
977 RegisterSequentialContainer revisionRegistration = {
987 const QTypeRevision added = revisionClassInfo(
988 type.classInfoMetaObject,
"QML.AddedInVersion",
989 QTypeRevision::fromMinorVersion(0));
990 QList<QTypeRevision> revisions = revisionClassInfos(
991 type.classInfoMetaObject,
"QML.ExtraVersion");
992 revisions.append(added);
993 uniqueRevisions(&revisions, type.version, added);
995 for (QTypeRevision revision : std::as_const(revisions)) {
996 if (revision < added)
998 if (revision.hasMajorVersion() && revision.majorVersion() > type.version.majorVersion())
1001 assignVersions(&revisionRegistration, revision, type.version);
1002 const int id = qmlregister(SequentialContainerRegistration, &revisionRegistration);
1003 if (type.qmlTypeIds)
1004 type.qmlTypeIds->append(id);
1008 case TypeRegistration:
1009 return finalizeType(
1010 QQmlMetaType::registerType(*
reinterpret_cast<RegisterType *>(data)));
1011 case InterfaceRegistration:
1012 return finalizeType(
1013 QQmlMetaType::registerInterface(*
reinterpret_cast<RegisterInterface *>(data)));
1014 case SingletonRegistration:
1015 return finalizeType(QQmlMetaType::registerSingletonType(
1016 *
reinterpret_cast<RegisterSingletonType *>(data),
1017 singletonInstanceInfo(*
reinterpret_cast<RegisterSingletonType *>(data))));
1018 case CompositeRegistration:
1019 return finalizeType(QQmlMetaType::registerCompositeType(
1020 *
reinterpret_cast<RegisterCompositeType *>(data)));
1021 case CompositeSingletonRegistration:
1022 return finalizeType(QQmlMetaType::registerCompositeSingletonType(
1023 *
reinterpret_cast<RegisterCompositeSingletonType *>(data),
1024 singletonInstanceInfo(*
reinterpret_cast<RegisterCompositeSingletonType *>(data))));
1025 case SequentialContainerRegistration:
1026 return finalizeType(QQmlMetaType::registerSequentialContainer(
1027 *
reinterpret_cast<RegisterSequentialContainer *>(data)));
1035void QQmlPrivate::qmlunregister(RegistrationType type, quintptr data)
1038 case AutoParentRegistration:
1039 QQmlMetaType::unregisterAutoParentFunction(
reinterpret_cast<AutoParentFunction>(data));
1041 case QmlUnitCacheHookRegistration:
1042 QQmlMetaType::removeCachedUnitLookupFunction(
1043 reinterpret_cast<QmlUnitCacheLookupFunction>(data));
1045 case SequentialContainerRegistration:
1046 QQmlMetaType::unregisterSequentialContainer(data);
1048 case TypeRegistration:
1049 case InterfaceRegistration:
1050 case SingletonRegistration:
1051 case CompositeRegistration:
1052 case CompositeSingletonRegistration:
1053 QQmlMetaType::unregisterType(data);
1055 case TypeAndRevisionsRegistration:
1056 case SingletonAndRevisionsRegistration:
1057 case SequentialContainerAndRevisionsRegistration:
1067QList<QTypeRevision> QQmlPrivate::revisionClassInfos(
const QMetaObject *metaObject,
1070 QList<QTypeRevision> revisions;
1071 for (
int index = indexOfOwnClassInfo(metaObject, key); index != -1;
1072 index = indexOfOwnClassInfo(metaObject, key, index - 1)) {
1073 revisions.push_back(QTypeRevision::fromEncodedVersion(
1074 QLatin1StringView(metaObject->classInfo(index).value()).toInt()));
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113int qmlRegisterTypeNotAvailable(
1114 const char *uri,
int versionMajor,
int versionMinor,
1115 const char *qmlName,
const QString &message)
1118 uri, versionMajor, versionMinor, qmlName, message);
1124 const char *uri,
int versionMajor,
const QMetaObject *classInfoMetaObject,
1125 QList<
int> *qmlTypeIds,
const QMetaObject *extension,
bool)
1129 RegisterTypeAndRevisions type = {
1131 QmlMetaType<T>::self(),
1132 QmlMetaType<T>::list(),
1139 QTypeRevision::fromMajorVersion(versionMajor),
1141 &QQmlTypeNotAvailable::staticMetaObject,
1142 classInfoMetaObject,
1144 attachedPropertiesFunc<T>(),
1145 attachedPropertiesMetaObject<T>(),
1147 StaticCastSelector<T, QQmlParserStatus>::cast(),
1148 StaticCastSelector<T, QQmlPropertyValueSource>::cast(),
1149 StaticCastSelector<T, QQmlPropertyValueInterceptor>::cast(),
1153 qmlCreateCustomParser<T>,
1155 QQmlPrivate::StaticCastSelector<T, QQmlFinalizerHook>::cast(),
1157 QmlMetaType<T>::sequence(),
1160 qmlregister(TypeAndRevisionsRegistration, &type);
1178 QQmlEngine *engine = aotContext->qmlEngine();
1179 return engine ? QQmlEnginePrivate::get(aotContext->qmlEngine())->propertyCapture :
nullptr;
1212static bool markPointer(
const QVariant &element, QV4::MarkStack *markStack)
1214 if (!element.metaType().flags().testFlag(QMetaType::PointerToQObject))
1217 QV4::QObjectWrapper::markWrapper(
1218 *
static_cast<QObject *
const *>(element.constData()), markStack);
1224#define ADD_CASE(Type, id, T)
1225 case QMetaType::Type:
1227 const QMetaType elementMetaType = element.metaType();
1228 switch (elementMetaType.id()) {
1229 case QMetaType::QVariantMap:
1230 for (
const QVariant &variant : *
static_cast<
const QVariantMap *>(element.constData()))
1231 elements->push_back(variant);
1233 case QMetaType::QVariantHash:
1234 for (
const QVariant &variant : *
static_cast<
const QVariantHash *>(element.constData()))
1235 elements->push_back(variant);
1237 case QMetaType::QVariantList:
1238 for (
const QVariant &variant : *
static_cast<
const QVariantList *>(element.constData()))
1239 elements->push_back(variant);
1241 QT_FOR_EACH_STATIC_PRIMITIVE_TYPE(ADD_CASE)
1242 QT_FOR_EACH_STATIC_CORE_CLASS(ADD_CASE)
1243 QT_FOR_EACH_STATIC_GUI_CLASS(ADD_CASE)
1244 case QMetaType::QStringList:
1245 case QMetaType::QByteArrayList:
1251 if (elementMetaType == QMetaType::fromType<QJSValue>()
1252 || elementMetaType == QMetaType::fromType<QJSManagedValue>()
1253 || elementMetaType == QMetaType::fromType<QJSPrimitiveValue>()) {
1259 QMetaSequence::Iterable iterable;
1260 if (!QMetaType::convert(
1261 element.metaType(), element.constData(),
1262 QMetaType::fromType<QMetaSequence::Iterable>(), &iterable)) {
1266 switch (iterable.metaContainer().valueMetaType().id()) {
1267 QT_FOR_EACH_STATIC_PRIMITIVE_TYPE(ADD_CASE)
1268 QT_FOR_EACH_STATIC_CORE_CLASS(ADD_CASE)
1269 QT_FOR_EACH_STATIC_GUI_CLASS(ADD_CASE)
1270 case QMetaType::QStringList:
1271 case QMetaType::QByteArrayList:
1277 for (
auto it = iterable.constBegin(), end = iterable.constEnd(); it != end; ++it)
1278 elements->push_back(*it);
1321static bool inherits(
const QQmlPropertyCache *descendent,
const QQmlPropertyCache *ancestor)
1323 for (
const QQmlPropertyCache *cache = descendent; cache; cache = cache->parent().data()) {
1324 if (cache == ancestor)
1423 void *
a[] = {
target,
nullptr };
1435 void *
a[] = {
source,
nullptr };
1527template<
typename Op>
1557 void *
args[] = {
nullptr };
1576 const bool isUnsigned = enumType.flags() & QMetaType::IsUnsignedEnumeration;
1577 switch (enumType.sizeOf()) {
1580 ? numberType == QMetaType::fromType<quint8>()
1581 : numberType == QMetaType::fromType<qint8>();
1584 ? numberType == QMetaType::fromType<ushort>()
1585 : numberType == QMetaType::fromType<
short>();
1592 ? (numberType == QMetaType::fromType<
int>()
1593 || numberType == QMetaType::fromType<uint>())
1594 : numberType == QMetaType::fromType<
int>();
1597 ? numberType == QMetaType::fromType<qulonglong>()
1598 : numberType == QMetaType::fromType<qlonglong>();
1607 return !type.isValid()
1608 || type == QMetaType::fromType<QVariant>()
1609 || type == QMetaType::fromType<QJSPrimitiveValue>();
1614 if (source == target)
1617 if ((source.flags() & QMetaType::IsQmlList)
1618 && (target.flags() & QMetaType::IsQmlList)) {
1624 if (target.flags() & QMetaType::PointerToQObject) {
1627 const QMetaObject *targetMetaObject = target.metaObject();
1628 const QMetaObject *sourceMetaObject = source.metaObject();
1629 if (!sourceMetaObject)
1630 sourceMetaObject = QQmlMetaType::metaObjectForType(source).metaObject();
1632 while (sourceMetaObject && sourceMetaObject != targetMetaObject)
1633 sourceMetaObject = sourceMetaObject->superClass();
1635 return sourceMetaObject !=
nullptr;
1638 if (target.flags() & QMetaType::IsEnumeration)
1639 return isEnumUnderlyingType(target, source);
1641 if (source.flags() & QMetaType::IsEnumeration)
1642 return isEnumUnderlyingType(source, target);
1644 if (!source.isValid())
1645 return canHoldVoid(target);
1716template<QV4::Lookup::Call FallbackCall>
1718 const AOTCompiledContext *aotContext, QV4::Lookup *lookup, QObject *object)
1720 QV4::Scope scope(aotContext->engine->handle());
1721 QV4::PropertyKey id = scope.engine->identifierTable->asPropertyKey(
1722 aotContext->compilationUnit->runtimeStrings[lookup->nameIndex]);
1724 Q_ASSERT(id.isString());
1726 QV4::ScopedString name(scope, id.asStringOrSymbol());
1728 Q_ASSERT(!name->equals(scope.engine->id_toString()));
1729 Q_ASSERT(!name->equals(scope.engine->id_destroy()));
1731 QQmlData *ddata = QQmlData::get(object,
true);
1733 if (ddata->isQueuedForDeletion)
1736 const QQmlPropertyData *property;
1737 if (!ddata->propertyCache) {
1738 property = QQmlPropertyCache::property(object, name, aotContext->qmlContext,
nullptr);
1740 property = ddata->propertyCache->property(
1741 name.getPointer(), object, aotContext->qmlContext);
1745 const QMetaObject *metaObject = object->metaObject();
1749 const int coreIndex = metaObject->indexOfProperty(
1750 name->toQStringNoThrow().toUtf8().constData());
1754 const QMetaProperty property = metaObject->property(coreIndex);
1756 lookup->releasePropertyCache();
1758 lookup->qobjectFallbackLookup.metaObject = quintptr(metaObject) + 1;
1759 lookup->qobjectFallbackLookup.metaType = quintptr(property.metaType().iface()) + 1;
1760 lookup->qobjectFallbackLookup.coreIndex = coreIndex;
1761 lookup->qobjectFallbackLookup.notifyIndex =
1762 QMetaObjectPrivate::signalIndex(property.notifySignal());
1764 if constexpr (FallbackCall == QV4::Lookup::Call::ContextGetterScopeObjectPropertyFallback
1765 || FallbackCall == QV4::Lookup::Call::GetterQObjectPropertyFallback) {
1766 lookup->qobjectFallbackLookup.isConstantOrResettable = property.isConstant() ? 1 : 0;
1767 }
else if constexpr (FallbackCall == QV4::Lookup::Call::SetterQObjectPropertyFallback) {
1768 lookup->qobjectFallbackLookup.isConstantOrResettable = property.isResettable() ? 1 : 0;
1773 Q_ASSERT(ddata->propertyCache);
1775 QV4::setupQObjectLookup(lookup, ddata, property);
1781template<QV4::Lookup::Call ObjectCall, QV4::Lookup::Call FallbackCall,
LookupType Type>
1784 QV4::ExecutionEngine *v4 = aotContext->engine->handle();
1785 if (v4->hasException) {
1786 v4->amendException();
1790 QV4::Lookup *lookup = aotContext->compilationUnit->runtimeLookups + index;
1791 switch (initObjectLookup<FallbackCall>(aotContext, lookup, object)) {
1793 lookup->call = ObjectCall;
1797 lookup->call = FallbackCall;
1801 v4->throwTypeError();
1810 QV4::Lookup *lookup, QV4::ExecutableCompilationUnit *compilationUnit,
1811 const QMetaObject *metaObject)
1813 Q_ASSERT(metaObject);
1814 const QByteArray name = compilationUnit->runtimeStrings[lookup->nameIndex]->toQString().toUtf8();
1815 const int coreIndex = metaObject->indexOfProperty(name.constData());
1816 QMetaType lookupType = metaObject->property(coreIndex).metaType();
1817 lookup->qgadgetLookup.metaObject = quintptr(metaObject) + 1;
1818 lookup->qgadgetLookup.coreIndex = coreIndex;
1819 lookup->qgadgetLookup.metaType = lookupType.iface();
1883#if QT_CONFIG(translation)
1933 if (type == QMetaType::fromType<QVariant>())
1934 return !
static_cast<
const QVariant *>(value)->isValid();
1935 if (type == QMetaType::fromType<QJSValue>())
1936 return static_cast<
const QJSValue *>(value)->isUndefined();
1937 if (type == QMetaType::fromType<QJSPrimitiveValue>()) {
1938 return static_cast<
const QJSPrimitiveValue *>(value)->type()
1939 == QJSPrimitiveValue::Undefined;
2038 QStringLiteral(
"Value is null and could not be converted to an object"));
2064 QStringLiteral(
"A QmlLoggingCatgory was provided without a valid name"));
2132 const QQmlType &type,
const QV4::CompiledData::ParameterType ¶meter)
2134 return parameter.isList() ? type.qListTypeId() : type.typeId();
2185 for (
int i = 0;
i <
argc; ++
i)
2259 const AOTCompiledContext *aotContext, QV4::Lookup *lookup,
const QString &object)
2261 aotContext->engine->handle()->throwTypeError(
2262 QStringLiteral(
"Property '%1' of object %2 is not a function").arg(
2263 aotContext->compilationUnit->runtimeStrings[lookup->nameIndex]->toQString(),
2291 QV4::QObjectMethod *method, QV4::Lookup *lookup,
int relativeMethodIndex)
2293 Q_ASSERT(lookup->qobjectMethodLookup.method.get() == method->d());
2295 const auto *d = method->d();
2296 const int methodCount = d->methodCount;
2298 if (methodCount == 1) {
2307 lookup->qobjectMethodLookup.propertyData = d->methods;
2311 for (
int i = 0, end = d->methodCount; i != end; ++i) {
2312 const QMetaMethod metaMethod = d->methods[i].metaMethod();
2313 if (metaMethod.relativeMethodIndex() != relativeMethodIndex)
2316 lookup->qobjectMethodLookup.propertyData = d->methods + i;
2666template<QV4::Lookup::Call call>
2667static void initTypeWrapperLookup(
2668 const AOTCompiledContext *context, QV4::Lookup *lookup, uint importNamespace)
2670 Q_ASSERT(!context->engine->hasError());
2671 if (importNamespace != AOTCompiledContext::InvalidStringId) {
2672 QV4::Scope scope(context->engine->handle());
2673 QV4::ScopedString import(scope, context->compilationUnit->runtimeStrings[importNamespace]);
2675 QQmlTypeLoader *typeLoader = scope.engine->typeLoader();
2676 Q_ASSERT(typeLoader);
2677 if (
const QQmlImportRef *importRef
2678 = context->qmlContext->imports()->query(import, typeLoader).importNamespace) {
2680 QV4::Scoped<QV4::QQmlTypeWrapper> wrapper(
2681 scope, QV4::QQmlTypeWrapper::create(
2682 scope.engine,
nullptr, context->qmlContext->imports(), importRef));
2685 wrapper = lookup->getter(context->engine->handle(), wrapper);
2688 lookup->releasePropertyCache();
2690 lookup->call = call;
2692 case QV4::Lookup::Call::ContextGetterSingleton:
2693 lookup->qmlContextSingletonLookup.singletonObject.set(scope.engine, wrapper->heapObject());
2695 case QV4::Lookup::Call::ContextGetterType:
2696 lookup->qmlTypeLookup.qmlTypeWrapper.set(scope.engine, wrapper->heapObject());
2703 scope.engine->throwTypeError();
2705 QV4::ExecutionEngine *v4 = context->engine->handle();
2706 lookup->contextGetter(v4,
nullptr);
2707 if (lookup->call != call) {
2709 = QLatin1String(call == QV4::Lookup::Call::ContextGetterSingleton
2710 ?
"%1 was a singleton at compile time, "
2711 "but is not a singleton anymore."
2712 :
"%1 was not a singleton at compile time, "
2713 "but is a singleton now.")
2714 .arg(context->compilationUnit->runtimeStrings[lookup->nameIndex]->toQString());
2715 v4->throwTypeError(error);
2995 QStringLiteral(
"Value is null and could not be converted to an object"));
3049 QV4::Lookup *lookup,
const QMetaObject *metaObject,
void *target,
void *value)
3051 void *args[] = { value,
nullptr };
3052 metaObject->d.static_metacall(
3053 reinterpret_cast<QObject *>(target), QMetaObject::WriteProperty,
3054 lookup->qgadgetLookup.coreIndex, args);
3059 QV4::Lookup *lookup,
const QMetaObject *metaObject,
void *target, QV4::ExecutionEngine *v4)
3061 const QMetaProperty property = metaObject->property(lookup->qgadgetLookup.coreIndex);
3062 if (property.isResettable()) {
3063 void *args[] = {
nullptr };
3064 metaObject->d.static_metacall(
3065 reinterpret_cast<QObject *>(target), QMetaObject::ResetProperty,
3066 lookup->qgadgetLookup.coreIndex, args);
3069 QLatin1String(
"Cannot assign [undefined] to ") +
3070 QLatin1String(property.metaType().name()));
3077 QV4::ExecutionEngine *v4, QV4::Lookup *lookup,
const QMetaObject *metaObject,
3078 void *target,
void *value)
3080 QVariant *variant =
static_cast<QVariant *>(value);
3081 const QMetaType propType = metaObject->property(lookup->qgadgetLookup.coreIndex).metaType();
3082 if (propType == QMetaType::fromType<QVariant>())
3083 return storeValueProperty(lookup, metaObject, target, variant);
3085 if (!variant->isValid())
3086 return resetValueProperty(lookup, metaObject, target, v4);
3088 if (isTypeCompatible(variant->metaType(), propType))
3089 return storeValueProperty(lookup, metaObject, target, variant->data());
3091 QVariant converted(propType);
3092 QV4::Scope scope(v4);
3093 QV4::ScopedValue val(scope, v4->fromVariant(*variant));
3094 if (v4->metaTypeFromJS(val, propType, converted.data())
3095 || QMetaType::convert(
3096 variant->metaType(), variant->constData(), propType, converted.data())) {
3097 return storeValueProperty(lookup, metaObject, target, converted.data());
3101 QLatin1String(
"Cannot assign ") + QLatin1String(variant->metaType().name())
3102 + QLatin1String(
" to ") + QLatin1String(propType.name()));
3134void initValueLookup(
3135 const AOTCompiledContext *aotContext, uint index,
const QMetaObject *metaObject)
3137 QV4::ExecutionEngine *v4 = aotContext->engine->handle();
3138 if (v4->hasException) {
3139 v4->amendException();
3143 QV4::Lookup *lookup = aotContext->compilationUnit->runtimeLookups + index;
3144 initValueLookup(lookup, aotContext->compilationUnit, metaObject);
3145 lookup->call = QV4::Lookup::Call::SetterValueTypeProperty;
3209 Validator(QQmlEngine *engine, QV4::CompiledData::CompilationUnit *cu);
3211 bool validateLookup(
const Lookup &lookup,
const Signature &signature);
3214 bool validatePropertyLookup(
const QMetaObject *mo,
const QString &member,
3215 const PropertySignature &expected)
const;
3216 bool validateEnumKeyLookup(
const QMetaObject *mo,
const QString &member,
3217 const QString &enumName,
const EnumKeySignature &expected)
const;
3218 bool validateMethodLookup(
const QMetaObject *mo,
const QString &member,
3219 const MethodSignature &expected)
const;
3220 bool methodMatchesSignature(
const QMetaMethod &method,
const QString &member,
3221 const MethodSignature &expected)
const;
3223 bool typesMatch(
const QMetaType &actual,
const Type &expected)
const;
3224 const QMetaObject *metaObjectForType(
const Type &type)
const;
3225 QQmlRefPointer<QQmlTypeData> getTypeFromModule(
const QString &moduleName,
3226 const QString &typeName)
const;
3227 QString qrcUrlForModule(
const QString &moduleName)
const;
3228 const QMetaObject *baseMOAtDepth(
const QMetaObject *mo,
int depth)
const;
3230 QQmlEngine *m_engine =
nullptr;
3231 QV4::CompiledData::CompilationUnit *m_compilationUnit =
nullptr;
3232 QQmlTypeLoader *m_loader =
nullptr;
3235Validator::Validator(QQmlEngine *engine, QV4::CompiledData::CompilationUnit *cu)
3236 : m_engine(engine), m_compilationUnit(cu), m_loader(QQmlTypeLoader::get(engine))
3239 Q_ASSERT(m_compilationUnit);
3243bool Validator::validateLookup(
const Lookup &lookup,
const Signature &signature)
3245 if (!m_engine || !m_compilationUnit || !m_loader)
3248 const auto *mo = metaObjectForType(lookup.base);
3252 if (
const auto *sig = std::get_if<PropertySignature>(&signature)) {
3253 return validatePropertyLookup(mo, lookup.member, *sig);
3254 }
else if (
const auto *sig = std::get_if<EnumKeySignature>(&signature)) {
3255 return validateEnumKeyLookup(mo, lookup.enumName, lookup.member, *sig);
3256 }
else if (
const auto *sig = std::get_if<MethodSignature>(&signature)) {
3257 return validateMethodLookup(mo, lookup.member, *sig);
3260 Q_UNREACHABLE_RETURN(
false);
3263bool Validator::validatePropertyLookup(
const QMetaObject *mo,
const QString &member,
3264 const PropertySignature &expected)
const
3266 const int index = mo->indexOfProperty(member.toUtf8());
3270 const auto prop = mo->property(index);
3271 if (!prop.isValid())
3274 if (prop.relativePropertyIndex() != expected.relativeIndex)
3277 return typesMatch(prop.metaType(), expected.type);
3280bool Validator::validateEnumKeyLookup(
const QMetaObject *mo,
const QString &enumName,
3281 const QString &member,
const EnumKeySignature &expected)
const
3283 const int index = mo->indexOfEnumerator(enumName.toUtf8());
3287 const auto enumerator = mo->enumerator(index);
3288 if (!enumerator.isValid())
3291 if (enumerator.isFlag() != (expected.isFlag == IsFlag::Yes))
3294 const auto actualValue = enumerator.keyToValue64(member.toUtf8());
3295 return actualValue.has_value() && expected.value == *actualValue;
3298bool Validator::methodMatchesSignature(
const QMetaMethod &method,
const QString &member,
3299 const MethodSignature &expected)
const
3301 if (method.nameView() != member.toUtf8())
3304 if (method.relativeMethodIndex() != expected.relativeIndex)
3307 if ((method.methodType() == QMetaMethod::Signal) != (expected.isSignal == IsSignal::Yes))
3310 if (!typesMatch(method.returnMetaType(), expected.types[0]))
3313 const int paramCount = method.parameterCount();
3314 const auto &expectedParamNames = expected.paramNames;
3315 if (paramCount !=
int(expectedParamNames.size()))
3318 const auto actualParameterNames = method.parameterNames();
3319 for (
int i = 0; i < paramCount; ++i) {
3320 if (actualParameterNames[i] != expectedParamNames[i].toUtf8())
3324 const auto &expectedParamTypes = expected.types;
3325 for (
int i = 0; i < paramCount; ++i) {
3326 if (!typesMatch(method.parameterMetaType(i), expectedParamTypes[i + 1]))
3332bool Validator::validateMethodLookup(
const QMetaObject *mo,
const QString &member,
3333 const MethodSignature &expected)
const
3336 for (
int i = mo->methodCount() - 1; i >= 0; --i) {
3337 if (methodMatchesSignature(mo->method(i), member, expected))
3344static QByteArrayView trimConstPointer(QByteArrayView typeName)
3346 QByteArrayView noConst = typeName.trimmed();
3347 const QByteArrayView c =
"const";
3348 if (noConst.startsWith(c))
3349 noConst.slice(c.length());
3350 QByteArrayView res = noConst.trimmed();
3351 for (
auto it = typeName.crbegin(); it != typeName.crend(); ++it) {
3352 if (*it ==
' ' || *it ==
'*')
3353 res = res.chopped(1);
3360bool Validator::typesMatch(
const QMetaType &actual,
const Type &expected)
const
3362 if (expected.isComposite == IsComposite::No) {
3364 const QByteArray actualStar = trimConstPointer(actual.name()) +
'*';
3365 const QByteArray expectedStar = trimConstPointer(expected.name.toLatin1()) +
'*';
3366 return QMetaType::fromName(actualStar) == QMetaType::fromName(expectedStar);
3369 const auto *actualMo = actual.metaObject();
3373 const auto *expectedMO = metaObjectForType(expected);
3377 return actualMo == expectedMO;
3380const QMetaObject *Validator::metaObjectForType(
const Type &type)
const
3382 if (type.isComposite == IsComposite::No) {
3383 const QString &extensionTypeName = type.icNameOrExtensionTypeName;
3384 const QString &typeName = extensionTypeName.isEmpty() ? type.name : extensionTypeName;
3385 const QString typeNameStar = typeName + u'*';
3386 const QMetaType mt = QMetaType::fromName(typeNameStar.toUtf8());
3387 return mt.metaObject();
3390 if (type.module.isEmpty() || type.name.isEmpty())
3393 const auto typeData = getTypeFromModule(type.module, type.name);
3394 if (typeData.isNull())
3397 if (type.isInlineComponent == IsIC::Yes)
3398 return typeData->qmlType(type.icNameOrExtensionTypeName).typeId().metaObject();
3400 const auto *cu = typeData->compilationUnit();
3404 return cu->metaType().metaObject();
3407QQmlRefPointer<QQmlTypeData> Validator::getTypeFromModule(
const QString &moduleName,
3408 const QString &typeName)
const
3411 if (moduleName == s_thisCuModule && typeName == s_thisCuType) {
3412 typeUrl = m_compilationUnit->finalUrlString();
3414 Q_ASSERT(moduleName != s_thisCuModule);
3415 Q_ASSERT(typeName != s_thisCuType);
3417 QString moduleUrl = qrcUrlForModule(moduleName);
3418 if (moduleUrl.isEmpty())
3421 QQmlDirParser parser;
3422 const QUrl qmldirUrl(moduleUrl + QStringLiteral(
"qmldir"));
3423 const auto *data = m_loader->getQmldir(qmldirUrl).data();
3424 if (!parser.parse(data->content()))
3427 const auto &components = parser.components();
3428 const auto it = components.constFind(typeName);
3429 if (it == components.constEnd())
3432 typeUrl = moduleUrl + it->fileName;
3435 return m_loader->getType(QUrl(typeUrl), QQmlTypeLoader::Synchronous);
3438QString Validator::qrcUrlForModule(
const QString &moduleName)
const
3440 for (
const auto &url : m_loader->urlsForModule(moduleName)) {
3441 if (url.startsWith(QStringLiteral(
"qrc")))
3447bool validateLookupSignature(QQmlEngine *engine, QV4::CompiledData::CompilationUnit *cu,
3448 const Lookup &lookup,
const Signature &signature)
3450 Validator validator(engine, cu);
3451 return validator.validateLookup(lookup, signature);
3459
3460
3461
3462
3463
3466
3467
3468
3469
3470
3471
3472
3473
3474
3475
3476
3479
3480
3481
3482
3483
3484
3485
3486
3487
3488
3489
3490
3491
3492
3493
3494
3495
3496
3497
3498
3499
3500
3501
3502
3503
3504
3505
3506
3507
3508
3509
3510
3511
3512
3513
3514
3515
3516
3517
3518
3519
3520
3521
3522
3523
3524
3525
3526
3527
3528
3529
3532
3533
3534
3535
3536
3537
3538
3539
3540
3541
3542
3543
3544
3545
3546
3547
3548
3551
3552
3553
3554
3555
3556
3557
3558
3559
3560
3561
3562
3563
3564
3565
3566
3567
3570
3571
3572
3573
3574
3575
3576
3577
3578
3579
3580
3581
3584
3585
3586
3587
3588
3589
3590
3591
3592
3593
3594
3595
3596
3597
3598
3599
3600
3601
3602
3605
3606
3607
3608
3609
3610
3611
3612
3613
3614
3615
3616
3617
3618
3619
3622
3623
3624
3625
3626
3627
3628
3629
3630
3631
3632
3633
3634
3635
3636
3637
3638
3639
3640
3641
3642
3643
3644
3645
3646
3647
3648
3649
3650
3651
3652
3653
3654
3655
3656
3657
3658
3659
3660
3661
3662
3663
3664
3665
3666
3667
3668
3669
3670
3671
3672
3673
3674
3675
3676
3677
3678
3679
3680
3681
3682
3683
3684
3685
3686
3687
3688
3689
3690
3691
3692
3693
3694
3695
3696
3697
3698
3699
3700
3701
3702
3703
3706
3707
3708
3709
3710
3711
3712
3713
3714
3715
3716
3717
3718
3719
3720
3721
3722
3723
3724
3725
3726
3727
3728
3729
3730
3731
3732
3733
3734
3735
3736
3737
3738
3741
3742
3743
3744
3745
3746
3747
3748
3749
3750
3751
3752
3753
3754
3755
3756
3757
3758
3759
3760
3761
3762
3763
3764
3765
3766
3767
3768
3769
3770
3771
3772
3773
3774
3775
3776
3777
3778
3779
3780
3781
3782
3783
3784
3785
3786
3787
3788
3789
3790
3791
3792
3793
3794
3795
3796
3797
3800
3801
3802
3803
3804
3805
3806
3807
3808
3809
3810
3811
3812
3813
3814
3815
3816
3817
3818
3819
3820
3823
3824
3825
3826
3827
3828
3829
3830
3831
3832
3833
3834
3835
3836
3837
3838
3839
3840
3841
3842
3843
3844
3845
3846
3847
3848
3849
3850
3851
3852
3853
3854
3855
3856
3857
3858
3859
3860
3861
3862
3863
3864
3865
3866
3867
3868
3869
3870
3871
3872
3873
3874
3875
3876
3877
3878
3879
3880
3881
3882
3883
3884
3885
3886
3887
3888
3889
3890
3891
3892
3893
3894
3895
3896
3897
3898
3899
3900
3901
3902
3903
3904
3905
3906
3907
3908
3909
3910
3911
3912
3913
3914
3917
3918
3919
3920
3921
3922
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
3937
3938
3939
3940
3941
3942
3943
3944
3945
3946
3947
3948
3949
3950
3951
3952
3953
3954
3955
3956
3957
3958
3959
3960
3961
3962
3965
3966
3967
3968
3969
3970
3971
3972
3973
3974
3975
3976
3977
3978
3979
3980
3981
3982
3983
3984
3985
3986
3987
3988
3989
3990
3991
3992
3993
3994
3995
3996
3997
3998
3999
4000
4001
4002
4003
4004
4005
4006
4007
4008
4009
4010
4011
4012
4013
4014
4015
4016
4017
4018
4019
4020
4021
4022
4023
4024
4025
4026
4027
4028
4029
4030
4031
4032
4033
4034
4035
4036
4037
4038
4039
4040
4041
4042
4043
4044
4045
4046
4047
4048
4049
4050
4051
4052
4053
4054
4055
4056
4057
4058
4061
4062
4063
4064
4065
4066
4067
4068
4069
4070
4071
4072
PropertyResult loadFallbackAsVariant(QV4::Lookup *lookup, QObject *object, void *target, const AOTCompiledContext *aotContext)
static ObjectLookupResult initObjectLookup(const AOTCompiledContext *aotContext, QV4::Lookup *lookup, QObject *object)
void qmlRegisterTypeAndRevisions< QQmlTypeNotAvailable, void >(const char *uri, int versionMajor, const QMetaObject *classInfoMetaObject, QList< int > *qmlTypeIds, const QMetaObject *extension, bool)
PropertyResult writeBackObjectAsVariant(QV4::Lookup *lookup, QObject *object, void *source)
static PropertyResult writeBackFallbackProperty(QV4::Lookup *lookup, QObject *object, void *source)
static PropertyResult changeFallbackProperty(QV4::Lookup *lookup, QObject *object, Op op)
static FallbackPropertyQmlData findFallbackPropertyQmlData(QV4::Lookup *lookup, QObject *object)
static void throwIsNotAFunctionError(const AOTCompiledContext *aotContext, QV4::Lookup *lookup, const QString &object)
static bool markPointer(const QVariant &element, QV4::MarkStack *markStack)
PropertyResult loadObjectProperty(QV4::Lookup *lookup, QObject *object, void *target, const AOTCompiledContext *aotContext)
static bool isEnumUnderlyingType(QMetaType enumType, QMetaType numberType)
static PropertyResult storeFallbackAsVariant(QV4::ExecutionEngine *v4, QV4::Lookup *lookup, QObject *object, void *value)
static void iterateVariant(const QVariant &element, std::vector< QVariant > *elements)
static PropertyResult changeObjectProperty(QV4::Lookup *lookup, QObject *object, Op op)
static PropertyResult storeObjectProperty(QV4::Lookup *lookup, QObject *object, void *value)
PropertyResult loadObjectAsVariant(QV4::Lookup *lookup, QObject *object, void *target, const AOTCompiledContext *aotContext)
static bool callQObjectMethod(QV4::ExecutionEngine *engine, QV4::Lookup *lookup, QObject *thisObject, void **args, int argc)
ObjectPropertyQmlData findObjectPropertyQmlData(QV4::Lookup *lookup, QObject *object)
static void captureFallbackProperty(QObject *object, int coreIndex, int notifyIndex, bool isConstant, const AOTCompiledContext *aotContext)
static void initValueLookup(QV4::Lookup *lookup, QV4::ExecutableCompilationUnit *compilationUnit, const QMetaObject *metaObject)
static bool inherits(const QQmlPropertyCache *descendent, const QQmlPropertyCache *ancestor)
static bool canHoldVoid(QMetaType type)
static bool tryEnsureMethodsCache(QV4::QObjectMethod *method, QObject *object)
static void captureObjectProperty(QObject *object, const QQmlPropertyCache *propertyCache, const QQmlPropertyData *property, const AOTCompiledContext *aotContext)
PropertyResult writeBackFallbackAsVariant(QV4::Lookup *lookup, QObject *object, void *source)
static PropertyResult storeFallbackProperty(QV4::Lookup *lookup, QObject *object, void *value)
static bool isUndefined(const void *value, QMetaType type)
static bool callQObjectMethodAsVariant(QV4::ExecutionEngine *engine, QV4::Lookup *lookup, QObject *thisObject, void **args, int argc)
static QMetaType jsTypedFunctionArgument(const QQmlType &type, const QV4::CompiledData::ParameterType ¶meter)
static PropertyResult resetFallbackProperty(QV4::Lookup *lookup, QObject *object, QV4::ExecutionEngine *v4)
static void resolveQObjectMethodOverload(QV4::QObjectMethod *method, QV4::Lookup *lookup, int relativeMethodIndex)
static PropertyResult loadFallbackProperty(QV4::Lookup *lookup, QObject *object, void *target, const AOTCompiledContext *aotContext)
static bool callArrowFunction(QV4::ExecutionEngine *engine, QV4::ArrowFunction *function, QObject *thisObject, void **args, int argc)
static PropertyResult resetObjectProperty(QV4::Lookup *lookup, QObject *object, QV4::ExecutionEngine *v4)
static PropertyResult storeObjectAsVariant(QV4::ExecutionEngine *v4, QV4::Lookup *lookup, QObject *object, void *value)
static bool callQObjectMethodWithTypes(QV4::ExecutionEngine *engine, QV4::Lookup *lookup, QObject *thisObject, void **args, QMetaType *types, int argc)
static bool isTypeCompatible(QMetaType source, QMetaType target)
PropertyResult writeBackObjectProperty(QV4::Lookup *lookup, QObject *object, void *source)
void initObjectLookup(const AOTCompiledContext *aotContext, uint index, QObject *object)
static QQmlPropertyCapture * propertyCapture(const AOTCompiledContext *aotContext)
Combined button and popup list for selecting options.
QQmlAttachedPropertiesFunc qmlAttachedPropertiesFunction(QObject *object, const QMetaObject *attachedMetaObject)
static QList< QTypeRevision > availableRevisions(const QMetaObject *metaObject)
static void doRegisterSingletonAndRevisions(const QQmlPrivate::RegisterSingletonTypeAndRevisions &type, const ElementNames &elementNames)
static ElementNames classElementNames(const QMetaObject *metaObject)
QObject * qmlAttachedPropertiesObject(QObject *object, QQmlAttachedPropertiesFunc func, bool createIfMissing)
static void uniqueRevisions(QList< QTypeRevision > *revisions, QTypeRevision defaultVersion, QTypeRevision added)
void assignVersions(Registration *registration, QTypeRevision revision, QTypeRevision defaultVersion)
static int finalizeType(const QQmlType &dtype)
QQmlEngine * qmlEngine(const QObject *obj)
QQmlContext * qmlContext(const QObject *obj)
static QObject * resolveAttachedProperties(QQmlAttachedPropertiesFunc pf, QQmlData *data, QObject *object, bool create)
QT_BEGIN_NAMESPACE void qmlExecuteDeferred(QObject *object)
\inmodule QtQml \title Functions to register C++ types to QML
static QList< QTypeRevision > prepareRevisions(const QMetaObject *metaObject, QTypeRevision added)
static QQmlDirParser::Import resolveImport(const QString &uri, int importMajor, int importMinor)
static bool checkSingletonInstance(QQmlEngine *engine, QObject *instance)
static void doRegisterTypeAndRevisions(const QQmlPrivate::RegisterTypeAndRevisions &type, const ElementNames &elementNames)
static QTypeRevision resolveModuleVersion(int moduleMajor)
static QQmlType::SingletonInstanceInfo::ConstPtr singletonInstanceInfo(const QQmlPrivate::RegisterSingletonType &type)
Q_QML_EXPORT void qmlRegisterModuleImport(const char *uri, int moduleMajor, const char *import, int importMajor=QQmlModuleImportLatest, int importMinor=QQmlModuleImportLatest)
Q_QML_EXPORT bool qmlProtectModule(const char *uri, int majVersion)
Q_QML_EXPORT void qmlUnregisterModuleImport(const char *uri, int moduleMajor, const char *import, int importMajor=QQmlModuleImportLatest, int importMinor=QQmlModuleImportLatest)
Q_QML_EXPORT void qmlRegisterModule(const char *uri, int versionMajor, int versionMinor)
AliasRegistrar(const ElementNames *elementNames)
void registerAliases(int typeId)
const QMetaObject * metaObject