6#include <private/inlinecomponentutils_p.h>
7#include <private/qml_compile_hash_p.h>
8#include <private/qqmlscriptdata_p.h>
9#include <private/qqmltypenamecache_p.h>
10#include <private/qv4resolvedtypereference_p.h>
12#include <QtQml/qqmlfile.h>
14#include <QtCore/qdir.h>
15#include <QtCore/qscopeguard.h>
16#include <QtCore/qstandardpaths.h>
20#if defined(QML_COMPILE_HASH) && defined(QML_COMPILE_HASH_LENGTH) && QML_COMPILE_HASH_LENGTH > 0
28 "Compile hash length exceeds reserved size in data structure. Please adjust and bump the format version");
30# error "QML_COMPILE_HASH must be defined for the build of QtDeclarative to ensure version checking for cache files"
36namespace CompiledData {
42 *errorString =
QStringLiteral(
"Magic bytes in the header do not match");
47 *errorString =
QString::fromUtf8(
"V4 data structure version mismatch. Found %1 expected %2")
61 if (!expectedSourceTimeStamp.isValid())
64 if (expectedSourceTimeStamp.isValid()
66 *errorString =
QStringLiteral(
"QML source file has a different time stamp than cached file.");
71#if defined(QML_COMPILE_HASH) && defined(QML_COMPILE_HASH_LENGTH) && QML_COMPILE_HASH_LENGTH > 0
73 *errorString =
QStringLiteral(
"QML compile hashes don't match. Found %1 expected %2")
76 .toPercentEncoding()),
78 QByteArray(qml_compile_hash, QML_COMPILE_HASH_LENGTH)
79 .toPercentEncoding()));
83#error "QML_COMPILE_HASH must be defined for the build of QtDeclarative to ensure version checking for cache files"
104 if (!this->
operator[](
key)->addToHash(
hash, checksums))
130#if Q_BYTE_ORDER == Q_BIG_ENDIAN
144 fileNameHash.addData(localSourcePath.toUtf8());
163 auto cacheFile = std::make_unique<CompilationUnitMapper>();
166 for (
const QString &cachePath : cachePaths) {
167 Unit *mappedUnit = cacheFile->get(cachePath, sourceTimeStamp, errorString);
172 const Unit *
const oldDataPtr
177 auto dataPtrRevert =
qScopeGuard([
this, oldData](){
182 if (mappedUnit->sourceFileIndex != 0) {
183 if (mappedUnit->sourceFileIndex >=
185 *errorString =
QStringLiteral(
"QML source file index is invalid.");
190 *errorString =
QStringLiteral(
"QML source file has moved to a different location.");
195 dataPtrRevert.dismiss();
196 free(
const_cast<Unit*
>(oldDataPtr));
206 if (
unitData()->sourceTimeStamp == 0) {
207 *errorString =
QStringLiteral(
"Missing time stamp for source file");
220 cachePath,
data,
size, errorString)) {
233 for (
uint i = 0;
i <
data->moduleRequestTableSize; ++
i)
241 if (
ref->type().typeId() ==
type)
265 const QQmlRefPointer<QV4::CompiledData::CompilationUnit> &compilationUnit,
268 if (
type.isInlineComponentType()) {
270 if (compilationUnit->icRootName) {
271 icRootName =
type.elementName();
272 std::swap(*compilationUnit->icRootName, icRootName);
274 compilationUnit->icRootName = std::make_unique<QString>(
type.elementName());
280 compilationUnit->icRootName.reset();
282 std::swap(*compilationUnit->icRootName, icRootName);
291 if (propertyCaches.needsVMEMetaObject(0)) {
293 if (
type.isValid()) {
305 auto *typeRef = resolvedTypes.value(
obj->inheritedTypeNameIndex);
307 if (
const auto compilationUnit = typeRef->compilationUnit())
308 qmlType = compilationUnit->qmlType;
310 qmlType = typeRef->type();
315 std::vector<QV4::CompiledData::InlineComponent> allICs {};
316 for (
int i=0;
i != objectCount(); ++
i) {
318 for (
auto it =
obj->inlineComponentsBegin();
it !=
obj->inlineComponentsEnd(); ++
it) {
319 allICs.push_back(*
it);
323 nodes.resize(allICs.size());
324 std::iota(nodes.begin(), nodes.end(), 0);
326 adjacencyList.resize(nodes.size());
327 fillAdjacencyListForInlineComponents(
this, adjacencyList, nodes, allICs);
328 bool hasCycle =
false;
329 auto nodesSorted = topoSort(nodes, adjacencyList, hasCycle);
335 for (
auto nodeIt = nodesSorted.rbegin(); nodeIt != nodesSorted.rend(); ++nodeIt) {
336 const auto &ic = allICs.at(nodeIt->index());
337 const int lastICRoot = ic.objectIndex;
338 for (
int i = ic.objectIndex;
i<objectCount(); ++
i) {
340 bool leftCurrentInlineComponent
344 if (leftCurrentInlineComponent)
346 const QString lastICRootName = stringAt(ic.nameIndex);
347 inlineComponentData[lastICRootName].totalBindingCount
350 if (
auto *typeRef = resolvedTypes.value(
obj->inheritedTypeNameIndex)) {
351 const auto type = typeRef->type();
352 if (
type.isValid() &&
type.parserStatusCast() != -1)
353 ++inlineComponentData[lastICRootName].totalParserStatusCount;
355 ++inlineComponentData[lastICRootName].totalObjectCount;
356 if (
const auto compilationUnit = typeRef->compilationUnit()) {
361 auto &icData = inlineComponentData[lastICRootName];
362 icData.totalBindingCount += compilationUnit->totalBindingsCount();
363 icData.totalParserStatusCount += compilationUnit->totalParserStatusCount();
364 icData.totalObjectCount += compilationUnit->totalObjectCount();
370 int bindingCount = 0;
371 int parserStatusCount = 0;
378 bindingCount +=
obj->nBindings;
379 if (
auto *typeRef = resolvedTypes.value(
obj->inheritedTypeNameIndex)) {
380 const auto type = typeRef->type();
381 if (
type.isValid() &&
type.parserStatusCast() != -1)
384 if (
const auto compilationUnit = typeRef->compilationUnit()) {
386 bindingCount += compilationUnit->totalBindingsCount();
387 parserStatusCount += compilationUnit->totalParserStatusCount();
388 objectCount += compilationUnit->totalObjectCount();
394 m_totalBindingsCount = bindingCount;
395 m_totalParserStatusCount = parserStatusCount;
396 m_totalObjectCount = objectCount;
408 if (!dependencyHasher) {
409 for (
size_t i = 0;
i <
sizeof(
data->dependencyMD5Checksum); ++
i) {
410 if (
data->dependencyMD5Checksum[
i] != 0)
416 return checksum.size() ==
sizeof(
data->dependencyMD5Checksum)
417 && memcmp(
data->dependencyMD5Checksum,
checksum.constData(),
418 sizeof(
data->dependencyMD5Checksum)) == 0;
423 if (inlineComponentName.
isEmpty())
struct capHdr __attribute__
DarwinBluetooth::RequestQueue requests
static QString applicationFilePath()
Returns the file path of the application executable.
\inmodule QtCore\reentrant
static QDir root()
Returns the root directory.
QDateTime lastModified() const
Returns the date and time when the file was last modified.
QString completeSuffix() const
Returns the complete suffix (extension) of the file.
qsizetype size() const noexcept
Returns the number of items in the hash.
const_iterator constEnd() const noexcept
Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the imaginary item after the ...
const_iterator constBegin() const noexcept
Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the first item in the hash.
QList< int > keys() const
Returns a list containing all the keys in the hash, in an arbitrary order.
iterator end() noexcept
Returns an \l{STL-style iterators}{STL-style iterator} pointing to the imaginary item after the last ...
static bool isLocalFile(const QString &url)
Returns true if url is a local file that can be opened with \l{QFile}.
static QString urlToLocalFileOrQrc(const QString &)
If url is a local file returns a path suitable for passing to \l{QFile}.
static QString writableLocation(StandardLocation type)
\macro QT_RESTRICTED_CAST_FROM_ASCII
static QString fromLatin1(QByteArrayView ba)
This is an overloaded member function, provided for convenience. It differs from the above function o...
static QString fromLocal8Bit(QByteArrayView ba)
This is an overloaded member function, provided for convenience. It differs from the above function o...
bool isEmpty() const noexcept
Returns true if the string has no characters; otherwise returns false.
static QString fromUtf8(QByteArrayView utf8)
This is an overloaded member function, provided for convenience. It differs from the above function o...
static void invalidate(const QString &cacheFilePath)
static bool writeDataToFile(const QString &outputFileName, const char *data, quint32 size, QString *errorString)
bool saveToDisk(const std::function< bool(const Char *, quint32)> &writer) const
QHash< int, QWidget * > hash
[35multi]
qDeleteAll(list.begin(), list.end())
QSet< QString >::iterator it
Combined button and popup list for selecting options.
void processInlinComponentType(const QQmlType &type, const QQmlRefPointer< QV4::CompiledData::CompilationUnit > &compilationUnit, F &&populateIcData)
std::function< QByteArray()> DependentTypesHasher
static const char magic_str[]
std::vector< std::vector< Node * > > AdjacencyList
int qstrncmp(const char *str1, const char *str2, size_t len)
typedef QByteArray(EGLAPIENTRYP PFNQGSGETDISPLAYSPROC)()
static quint32 checksum(const QByteArray &table)
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLenum GLenum GLsizei count
GLint GLsizei GLsizei GLenum GLenum GLsizei void * data
QScopeGuard< typename std::decay< F >::type > qScopeGuard(F &&f)
[qScopeGuard]
QLatin1StringView QLatin1String
#define QStringLiteral(str)
Q_CORE_EXPORT QByteArray qgetenv(const char *varName)
#define QV4_DATA_STRUCTURE_VERSION
QUrl url("example.com")
[constructor-url-reference]
\inmodule QtCore \reentrant
QString stringAt(uint index) const
std::unique_ptr< CompilationUnitMapper > backingFile
QHash< QString, InlineComponentData > inlineComponentData
Q_QML_EXPORT ~CompilationUnit()
void setUnitData(const Unit *unitData, const QmlUnit *qmlUnit=nullptr, const QString &fileName=QString(), const QString &finalUrlString=QString())
std::unique_ptr< QString > icRootName
Q_QML_EXPORT bool saveToDisk(const QUrl &unitUrl, QString *errorString)
ResolvedTypeReference * resolvedType(int id) const
CompilationUnit(const Unit *unitData, const QQmlPrivate::AOTCompiledFunction *aotCompiledFunctions, const QString &fileName=QString(), const QString &finalUrlString=QString())
ResolvedTypeReferenceMap resolvedTypes
bool verifyChecksum(const CompiledData::DependentTypesHasher &dependencyHasher) const
Q_QML_EXPORT QStringList moduleRequests() const
QQmlType qmlTypeForComponent(const QString &inlineComponentName=QString()) const
QString finalUrlString() const
void finalizeCompositeType(const QQmlType &type)
const Unit * unitData() const
int totalParserStatusCount() const
int totalObjectCount() const
int totalBindingsCount() const
static Q_QML_EXPORT QString localCacheFilePath(const QUrl &url)
QStringList dynamicStrings
Q_QML_EXPORT bool loadFromDisk(const QUrl &url, const QDateTime &sourceTimeStamp, QString *errorString)
int m_totalParserStatusCount
const StaticValue * constants
@ IsPartOfInlineComponent
bool addToHash(QCryptographicHash *hash, QHash< quintptr, QByteArray > *checksums) const
bool verifyHeader(QDateTime expectedSourceTimeStamp, QString *errorString) const
char libraryVersionHash[QmlCompileHashSpace]
qint64_le sourceTimeStamp