diff options
-rw-r--r-- | src/qml/compiler/compiler.pri | 2 | ||||
-rw-r--r-- | src/qml/compiler/qv4compileddata.cpp | 45 | ||||
-rw-r--r-- | src/qml/compiler/qv4compileddata_p.h | 6 | ||||
-rw-r--r-- | src/qml/compiler/qv4compiler.cpp | 4 | ||||
-rw-r--r-- | src/qml/qml.pro | 3 |
5 files changed, 21 insertions, 39 deletions
diff --git a/src/qml/compiler/compiler.pri b/src/qml/compiler/compiler.pri index 2ca0c39acc..95096db51d 100644 --- a/src/qml/compiler/compiler.pri +++ b/src/qml/compiler/compiler.pri @@ -40,8 +40,6 @@ SOURCES += \ unix: SOURCES += $$PWD/qv4compilationunitmapper_unix.cpp else: SOURCES += $$PWD/qv4compilationunitmapper_win.cpp - -qtConfig(private_tests):qtConfig(dlopen): QMAKE_USE_PRIVATE += libdl } gcc { diff --git a/src/qml/compiler/qv4compileddata.cpp b/src/qml/compiler/qv4compileddata.cpp index 6220c1bc11..8dcc068a06 100644 --- a/src/qml/compiler/qv4compileddata.cpp +++ b/src/qml/compiler/qv4compileddata.cpp @@ -70,18 +70,14 @@ #include <algorithm> -#if defined(QT_BUILD_INTERNAL) -#if defined(Q_OS_UNIX) && !defined(QT_NO_DYNAMIC_CAST) -#include <dlfcn.h> -#endif -#endif - QT_BEGIN_NAMESPACE namespace QV4 { namespace CompiledData { +static_assert(sizeof(Unit::libraryVersionHash) >= QML_COMPILE_HASH_LENGTH + 1, "Compile hash length exceeds reserved size in data structure. Please adjust and bump the format version"); + #if !defined(V4_BOOTSTRAP) static QString cacheFilePath(const QUrl &url) { @@ -686,32 +682,6 @@ void ResolvedTypeReference::doDynamicTypeCheck() isFullyDynamicType = qtTypeInherits<QQmlPropertyMap>(mo); } -static QByteArray ownLibraryChecksum() -{ - static QByteArray libraryChecksum; - static bool checksumInitialized = false; - if (checksumInitialized) - return libraryChecksum; - checksumInitialized = true; -#if defined(QT_BUILD_INTERNAL) && !defined(QT_NO_DYNAMIC_CAST) && QT_CONFIG(dlopen) - // This is a bit of a hack to make development easier. When hacking on the code generator - // the cache files may end up being re-used. To avoid that we also add the checksum of - // the QtQml library. - Dl_info libInfo; - if (dladdr(reinterpret_cast<void *>(&ownLibraryChecksum), &libInfo) != 0) { - QFile library(QFile::decodeName(libInfo.dli_fname)); - if (library.open(QIODevice::ReadOnly)) { - QCryptographicHash hash(QCryptographicHash::Md5); - hash.addData(&library); - libraryChecksum = hash.result(); - } - } -#else - libraryChecksum = QByteArray(QML_COMPILE_HASH); -#endif - return libraryChecksum; -} - bool ResolvedTypeReferenceMap::addToHash(QCryptographicHash *hash, QQmlEngine *engine) const { for (auto it = constBegin(), end = constEnd(); it != end; ++it) { @@ -719,8 +689,6 @@ bool ResolvedTypeReferenceMap::addToHash(QCryptographicHash *hash, QQmlEngine *e return false; } - hash->addData(ownLibraryChecksum()); - return true; } @@ -785,6 +753,15 @@ bool Unit::verifyHeader(QDateTime expectedSourceTimeStamp, QString *errorString) } } +#if defined(QML_COMPILE_HASH) + if (qstrcmp(QML_COMPILE_HASH, libraryVersionHash) != 0) { + *errorString = QStringLiteral("QML library version mismatch. Expected compile hash does not match"); + return false; + } +#else +#error "QML_COMPILE_HASH must be defined for the build of QtDeclarative to ensure version checking for cache files" +#endif + return true; #else Q_UNUSED(expectedSourceTimeStamp) diff --git a/src/qml/compiler/qv4compileddata_p.h b/src/qml/compiler/qv4compileddata_p.h index 49360bc3f1..1df9d6794f 100644 --- a/src/qml/compiler/qv4compileddata_p.h +++ b/src/qml/compiler/qv4compileddata_p.h @@ -72,7 +72,7 @@ QT_BEGIN_NAMESPACE // Bump this whenever the compiler data structures change in an incompatible way. -#define QV4_DATA_STRUCTURE_VERSION 0x18 +#define QV4_DATA_STRUCTURE_VERSION 0x19 class QIODevice; class QQmlPropertyCache; @@ -688,6 +688,8 @@ struct Unit quint32_le unitSize; // Size of the Unit and any depending data. // END DO NOT CHANGE THESE FIELDS EVER + char libraryVersionHash[48]; + char md5Checksum[16]; // checksum of all bytes following this field. void generateChecksum(); @@ -793,7 +795,7 @@ struct Unit } }; -static_assert(sizeof(Unit) == 144, "Unit structure needs to have the expected size to be binary compatible on disk when generated by host compiler and loaded by target"); +static_assert(sizeof(Unit) == 192, "Unit structure needs to have the expected size to be binary compatible on disk when generated by host compiler and loaded by target"); struct TypeReference { diff --git a/src/qml/compiler/qv4compiler.cpp b/src/qml/compiler/qv4compiler.cpp index ccc909c199..c9e535c93f 100644 --- a/src/qml/compiler/qv4compiler.cpp +++ b/src/qml/compiler/qv4compiler.cpp @@ -48,6 +48,9 @@ #include <wtf/MathExtras.h> #include <QCryptographicHash> +// generated by qmake: +#include "qml_compile_hash_p.h" + QV4::Compiler::StringTableGenerator::StringTableGenerator() { clear(); @@ -396,6 +399,7 @@ QV4::CompiledData::Unit QV4::Compiler::JSUnitGenerator::generateHeader(QV4::Comp unit.flags |= module->unitFlags; unit.version = QV4_DATA_STRUCTURE_VERSION; unit.qtVersion = QT_VERSION; + qstrcpy(unit.libraryVersionHash, QML_COMPILE_HASH); memset(unit.md5Checksum, 0, sizeof(unit.md5Checksum)); memset(unit.dependencyMD5Checksum, 0, sizeof(unit.dependencyMD5Checksum)); diff --git a/src/qml/qml.pro b/src/qml/qml.pro index f75bfa0313..2137877427 100644 --- a/src/qml/qml.pro +++ b/src/qml/qml.pro @@ -36,7 +36,8 @@ DEFINES += QT_NO_FOREACH } compile_hash_contents = \ "// Generated file, DO NOT EDIT" \ - "$${LITERAL_HASH}define QML_COMPILE_HASH \"$$QML_COMPILE_HASH\"" + "$${LITERAL_HASH}define QML_COMPILE_HASH \"$$QML_COMPILE_HASH\"" \ + "$${LITERAL_HASH}define QML_COMPILE_HASH_LENGTH $$str_size($$QML_COMPILE_HASH)" write_file("$$OUT_PWD/qml_compile_hash_p.h", compile_hash_contents)|error() } |