Unify QLibraryInfo settings

Exporting QLibraryInfo internals allows to reuse settings in
qmake/qtpath without having to keep its own instance.
Also there is no need to check setting groups in QLibraryInfo
except the 'Paths' group, since this logic belongs to qmake/qtpaths
only.

Change-Id: If762defba025ad7f7489f8a86ef5768a8628bd2f
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
This commit is contained in:
Alexey Edelev 2021-03-15 14:25:34 +01:00
parent a423c0d211
commit 6fb569af95
7 changed files with 158 additions and 110 deletions

View File

@ -32,6 +32,7 @@
#include "option.h" #include "option.h"
#include "cachekeys.h" #include "cachekeys.h"
#include "metamakefile.h" #include "metamakefile.h"
#include <qcoreapplication.h>
#include <qnamespace.h> #include <qnamespace.h>
#include <qdebug.h> #include <qdebug.h>
#include <qregularexpression.h> #include <qregularexpression.h>
@ -598,5 +599,7 @@ QT_END_NAMESPACE
int main(int argc, char **argv) int main(int argc, char **argv)
{ {
// Set name of the qmake application in QCoreApplication instance
QT_PREPEND_NAMESPACE(QCoreApplication) app(argc, argv);
return QT_PREPEND_NAMESPACE(runQMake)(argc, argv); return QT_PREPEND_NAMESPACE(runQMake)(argc, argv);
} }

View File

@ -33,10 +33,12 @@
#include <qregularexpression.h> #include <qregularexpression.h>
#include <qhash.h> #include <qhash.h>
#include <qdebug.h> #include <qdebug.h>
#include <qmakelibraryinfo.h>
#include <stdlib.h> #include <stdlib.h>
#include <stdarg.h> #include <stdarg.h>
#include <qmakelibraryinfo.h>
#include <private/qlibraryinfo_p.h>
QT_BEGIN_NAMESPACE QT_BEGIN_NAMESPACE
using namespace QMakeInternal; using namespace QMakeInternal;
@ -203,7 +205,7 @@ Option::parseCommandLine(QStringList &args, QMakeCmdLineParserState &state)
default: default:
QMakeGlobals::ArgumentReturn cmdRet = globals->addCommandLineArguments(state, args, &x); QMakeGlobals::ArgumentReturn cmdRet = globals->addCommandLineArguments(state, args, &x);
if (cmdRet == QMakeGlobals::ArgumentsOk) { if (cmdRet == QMakeGlobals::ArgumentsOk) {
QMakeLibraryInfo::qtconfManualPath = globals->qtconf; QLibraryInfoPrivate::qtconfManualPath = globals->qtconf;
break; break;
} }
if (cmdRet == QMakeGlobals::ArgumentMalformed) { if (cmdRet == QMakeGlobals::ArgumentMalformed) {
@ -340,7 +342,6 @@ Option::init(int argc, char **argv)
#endif #endif
; ;
} }
QMakeLibraryInfo::binaryAbsLocation = globals->qmake_abslocation;
} else { } else {
Option::qmake_mode = Option::QMAKE_GENERATE_MAKEFILE; Option::qmake_mode = Option::QMAKE_GENERATE_MAKEFILE;
} }

View File

@ -46,62 +46,27 @@
#include <qsettings.h> #include <qsettings.h>
#include <qscopedpointer.h> #include <qscopedpointer.h>
#include <qstringlist.h> #include <qstringlist.h>
#include <private/qlibraryinfo_p.h>
#include <utility> #include <utility>
QT_BEGIN_NAMESPACE QT_BEGIN_NAMESPACE
QString QMakeLibraryInfo::binaryAbsLocation;
QString QMakeLibraryInfo::qtconfManualPath;
struct QMakeLibrarySettings struct QMakeLibrarySettings
{ {
QMakeLibrarySettings() { load(); } QMakeLibrarySettings() { load(); }
void load(); void load();
QScopedPointer<QSettings> settings;
bool haveDevicePaths; bool haveDevicePaths;
bool haveEffectiveSourcePaths; bool haveEffectiveSourcePaths;
bool haveEffectivePaths; bool haveEffectivePaths;
bool havePaths; bool havePaths;
bool reloadOnQAppAvailable;
}; };
Q_GLOBAL_STATIC(QMakeLibrarySettings, qmake_library_settings) Q_GLOBAL_STATIC(QMakeLibrarySettings, qmake_library_settings)
QSettings *QMakeLibraryInfo::findConfiguration()
{
QString qtconfig = libraryInfoFile();
if (!qtconfig.isEmpty())
return new QSettings(qtconfig, QSettings::IniFormat);
return nullptr; // no luck
}
QSettings *QMakeLibraryInfo::configuration()
{
QMakeLibrarySettings *ls = qmake_library_settings();
return ls ? ls->settings.data() : nullptr;
}
void QMakeLibraryInfo::reload()
{
if (qmake_library_settings.exists())
qmake_library_settings->load();
}
bool QMakeLibraryInfo::haveGroup(PathGroup group)
{
QMakeLibrarySettings *ls = qmake_library_settings();
return ls
&& (group == EffectiveSourcePaths ? ls->haveEffectiveSourcePaths
: group == EffectivePaths ? ls->haveEffectivePaths
: group == DevicePaths ? ls->haveDevicePaths
: ls->havePaths);
}
void QMakeLibrarySettings::load() void QMakeLibrarySettings::load()
{ {
settings.reset(QMakeLibraryInfo::findConfiguration()); QSettings *settings = QLibraryInfoPrivate::configuration();
if (settings) { if (settings) {
QStringList children = settings->childGroups(); QStringList children = settings->childGroups();
haveDevicePaths = children.contains(QLatin1String("DevicePaths")); haveDevicePaths = children.contains(QLatin1String("DevicePaths"));
@ -120,6 +85,23 @@ void QMakeLibrarySettings::load()
} }
} }
void QMakeLibraryInfo::reload()
{
QLibraryInfoPrivate::reload();
if (qmake_library_settings.exists())
qmake_library_settings->load();
}
bool QMakeLibraryInfo::haveGroup(PathGroup group)
{
QMakeLibrarySettings *ls = qmake_library_settings();
return ls
&& (group == EffectiveSourcePaths ? ls->haveEffectiveSourcePaths
: group == EffectivePaths ? ls->haveEffectivePaths
: group == DevicePaths ? ls->haveDevicePaths
: ls->havePaths);
}
void QMakeLibraryInfo::sysrootify(QString &path) void QMakeLibraryInfo::sysrootify(QString &path)
{ {
// Acceptable values for SysrootifyPrefixPath are "true" and "false" // Acceptable values for SysrootifyPrefixPath are "true" and "false"
@ -165,9 +147,6 @@ static QLibraryInfo::LibraryPath hostToTargetPathEnum(int loc)
qFatal("Unhandled host path %d in hostToTargetPathEnum.", loc); qFatal("Unhandled host path %d in hostToTargetPathEnum.", loc);
} }
// from qlibraryinfo.cpp:
void qlibraryinfo_keyAndDefault(QLibraryInfo::LibraryPath loc, QString *key, QString *value);
struct LocationInfo struct LocationInfo
{ {
QString key; QString key;
@ -179,10 +158,10 @@ static LocationInfo defaultLocationInfo(int loc)
LocationInfo result; LocationInfo result;
if (loc < QMakeLibraryInfo::FirstHostPath) { if (loc < QMakeLibraryInfo::FirstHostPath) {
qlibraryinfo_keyAndDefault(static_cast<QLibraryInfo::LibraryPath>(loc), QLibraryInfoPrivate::keyAndDefault(static_cast<QLibraryInfo::LibraryPath>(loc),
&result.key, &result.defaultValue); &result.key, &result.defaultValue);
} else if (loc <= QMakeLibraryInfo::LastHostPath) { } else if (loc <= QMakeLibraryInfo::LastHostPath) {
qlibraryinfo_keyAndDefault(hostToTargetPathEnum(loc), &result.key, &result.defaultValue); QLibraryInfoPrivate::keyAndDefault(hostToTargetPathEnum(loc), &result.key, &result.defaultValue);
result.key.prepend(QStringLiteral("Host")); result.key.prepend(QStringLiteral("Host"));
} else if (loc == QMakeLibraryInfo::SysrootPath) { } else if (loc == QMakeLibraryInfo::SysrootPath) {
result.key = QStringLiteral("Sysroot"); result.key = QStringLiteral("Sysroot");
@ -236,7 +215,8 @@ QString QMakeLibraryInfo::rawLocation(int loc, QMakeLibraryInfo::PathGroup group
LocationInfo locinfo = defaultLocationInfo(loc); LocationInfo locinfo = defaultLocationInfo(loc);
if (!locinfo.key.isNull()) { if (!locinfo.key.isNull()) {
QSettings *config = QMakeLibraryInfo::configuration(); QSettings *config = QLibraryInfoPrivate::configuration();
Q_ASSERT(config != nullptr);
config->beginGroup(QLatin1String(group == DevicePaths ? "DevicePaths" config->beginGroup(QLatin1String(group == DevicePaths ? "DevicePaths"
: group == EffectiveSourcePaths : group == EffectiveSourcePaths
? "EffectiveSourcePaths" ? "EffectiveSourcePaths"
@ -298,7 +278,10 @@ QString QMakeLibraryInfo::rawLocation(int loc, QMakeLibraryInfo::PathGroup group
// We make the prefix/sysroot path absolute to the executable's directory. // We make the prefix/sysroot path absolute to the executable's directory.
// loc == PrefixPath while a sysroot is set would make no sense here. // loc == PrefixPath while a sysroot is set would make no sense here.
// loc == SysrootPath only makes sense if qmake lives inside the sysroot itself. // loc == SysrootPath only makes sense if qmake lives inside the sysroot itself.
baseDir = QFileInfo(libraryInfoFile()).absolutePath(); QSettings *config = QLibraryInfoPrivate::configuration();
if (config != nullptr) {
baseDir = QFileInfo(config->fileName()).absolutePath();
}
} else if (loc >= FirstHostPath && loc <= LastHostPath) { } else if (loc >= FirstHostPath && loc <= LastHostPath) {
// We make any other host path absolute to the host prefix directory. // We make any other host path absolute to the host prefix directory.
baseDir = rawLocation(HostPrefixPath, group); baseDir = rawLocation(HostPrefixPath, group);
@ -313,20 +296,4 @@ QString QMakeLibraryInfo::rawLocation(int loc, QMakeLibraryInfo::PathGroup group
return ret; return ret;
} }
QString QMakeLibraryInfo::libraryInfoFile()
{
if (!qtconfManualPath.isEmpty())
return qtconfManualPath;
if (!binaryAbsLocation.isEmpty()) {
QDir dir(QFileInfo(binaryAbsLocation).absolutePath());
QString qtconfig = dir.filePath("qt" QT_STRINGIFY(QT_VERSION_MAJOR) ".conf");
if (QFile::exists(qtconfig))
return qtconfig;
qtconfig = dir.filePath("qt.conf");
if (QFile::exists(qtconfig))
return qtconfig;
}
return QString();
}
QT_END_NAMESPACE QT_END_NAMESPACE

View File

@ -50,10 +50,7 @@ class QSettings;
struct QMakeLibraryInfo struct QMakeLibraryInfo
{ {
static QSettings *findConfiguration();
static QSettings *configuration();
static QString path(int loc); static QString path(int loc);
static QStringList platformPluginArguments(const QString &platformName);
/* This enum has to start after the last value in QLibraryInfo::LibraryPath(NOT SettingsPath!). /* This enum has to start after the last value in QLibraryInfo::LibraryPath(NOT SettingsPath!).
* See qconfig.cpp.in and QLibraryInfo for details. * See qconfig.cpp.in and QLibraryInfo for details.
@ -78,12 +75,6 @@ struct QMakeLibraryInfo
static void reload(); static void reload();
static bool haveGroup(PathGroup group); static bool haveGroup(PathGroup group);
static void sysrootify(QString &path); static void sysrootify(QString &path);
static QString binaryAbsLocation;
static QString qtconfManualPath;
private:
static QString libraryInfoFile();
}; };
QT_END_NAMESPACE QT_END_NAMESPACE

View File

@ -41,7 +41,7 @@ qt_internal_add_module(Core
global/qglobal.cpp global/qglobal.h global/qglobal.cpp global/qglobal.h
global/qglobalstatic.h global/qglobalstatic.h
global/qhooks.cpp global/qhooks_p.h global/qhooks.cpp global/qhooks_p.h
global/qlibraryinfo.cpp global/qlibraryinfo.h global/qlibraryinfo.cpp global/qlibraryinfo.h global/qlibraryinfo_p.h
global/qlogging.cpp global/qlogging.h global/qlogging.cpp global/qlogging.h
global/qmalloc.cpp global/qmalloc.cpp
# global/qnamespace.h # special case # global/qnamespace.h # special case

View File

@ -45,6 +45,7 @@
#include "qsettings.h" #include "qsettings.h"
#endif #endif
#include "qlibraryinfo.h" #include "qlibraryinfo.h"
#include "qlibraryinfo_p.h"
#include "qscopedpointer.h" #include "qscopedpointer.h"
#include "qcoreapplication.h" #include "qcoreapplication.h"
@ -72,65 +73,53 @@ extern void qDumpCPUFeatures(); // in qsimd.cpp
#if QT_CONFIG(settings) #if QT_CONFIG(settings)
static QSettings *findConfiguration();
struct QLibrarySettings struct QLibrarySettings
{ {
QLibrarySettings(); QLibrarySettings();
void load(); void load();
QSettings *configuration();
QScopedPointer<QSettings> settings; QScopedPointer<QSettings> settings;
bool havePaths;
bool reloadOnQAppAvailable; bool reloadOnQAppAvailable;
}; };
Q_GLOBAL_STATIC(QLibrarySettings, qt_library_settings) Q_GLOBAL_STATIC(QLibrarySettings, qt_library_settings)
class QLibraryInfoPrivate QLibrarySettings::QLibrarySettings() : havePaths(false)
{ , reloadOnQAppAvailable(false)
public:
static QSettings *findConfiguration();
static QSettings *configuration()
{
QLibrarySettings *ls = qt_library_settings();
if (ls) {
if (ls->reloadOnQAppAvailable && QCoreApplication::instance() != nullptr)
ls->load();
return ls->settings.data();
} else {
return nullptr;
}
}
};
QLibrarySettings::QLibrarySettings()
{ {
load(); load();
} }
QSettings *QLibrarySettings::configuration()
{
if (reloadOnQAppAvailable && QCoreApplication::instance() != nullptr)
load();
return settings.data();
}
void QLibrarySettings::load() void QLibrarySettings::load()
{ {
// If we get any settings here, those won't change when the application shows up. // If we get any settings here, those won't change when the application shows up.
settings.reset(QLibraryInfoPrivate::findConfiguration()); settings.reset(findConfiguration());
reloadOnQAppAvailable = (settings.data() == nullptr && QCoreApplication::instance() == nullptr); reloadOnQAppAvailable = (settings.data() == nullptr && QCoreApplication::instance() == nullptr);
bool haveDevicePaths;
bool haveEffectivePaths;
bool havePaths;
if (settings) { if (settings) {
// This code needs to be in the regular library, as otherwise a qt.conf that // This code needs to be in the regular library, as otherwise a qt.conf that
// works for qmake would break things for dynamically built Qt tools. // works for qmake would break things for dynamically built Qt tools.
QStringList children = settings->childGroups(); QStringList children = settings->childGroups();
haveDevicePaths = children.contains(QLatin1String("DevicePaths")); havePaths = !children.contains(QLatin1String("Platforms"))
// EffectiveSourcePaths is for the Qt build only, so needs no backwards compat trickery.
bool haveEffectiveSourcePaths = false;
haveEffectivePaths = haveEffectiveSourcePaths || children.contains(QLatin1String("EffectivePaths"));
// Backwards compat: an existing but empty file is claimed to contain the Paths section.
havePaths = (!haveDevicePaths && !haveEffectivePaths
&& !children.contains(QLatin1String("Platforms")))
|| children.contains(QLatin1String("Paths")); || children.contains(QLatin1String("Paths"));
if (!havePaths)
settings.reset(nullptr);
} }
} }
QSettings *QLibraryInfoPrivate::findConfiguration() static QSettings *findConfiguration()
{ {
if (!QLibraryInfoPrivate::qtconfManualPath.isEmpty())
return new QSettings(QLibraryInfoPrivate::qtconfManualPath, QSettings::IniFormat);
QString qtconfig = QStringLiteral(":/qt/etc/qt.conf"); QString qtconfig = QStringLiteral(":/qt/etc/qt.conf");
if (QFile::exists(qtconfig)) if (QFile::exists(qtconfig))
return new QSettings(qtconfig, QSettings::IniFormat); return new QSettings(qtconfig, QSettings::IniFormat);
@ -161,6 +150,25 @@ QSettings *QLibraryInfoPrivate::findConfiguration()
return nullptr; //no luck return nullptr; //no luck
} }
QString QLibraryInfoPrivate::qtconfManualPath;
QSettings *QLibraryInfoPrivate::configuration()
{
QLibrarySettings *ls = qt_library_settings();
return ls ? ls->configuration() : nullptr;
}
void QLibraryInfoPrivate::reload()
{
if (qt_library_settings.exists())
qt_library_settings->load();
}
static bool havePaths() {
QLibrarySettings *ls = qt_library_settings();
return ls && ls->havePaths;
}
#endif // settings #endif // settings
/*! /*!
@ -503,7 +511,7 @@ static QString getPrefix()
#endif #endif
} }
Q_CORE_EXPORT void qlibraryinfo_keyAndDefault(QLibraryInfo::LibraryPath loc, QString *key, void QLibraryInfoPrivate::keyAndDefault(QLibraryInfo::LibraryPath loc, QString *key,
QString *value) QString *value)
{ {
if (unsigned(loc) < sizeof(qtConfEntries)/sizeof(qtConfEntries[0])) { if (unsigned(loc) < sizeof(qtConfEntries)/sizeof(qtConfEntries[0])) {
@ -539,15 +547,15 @@ QString QLibraryInfo::path(LibraryPath p)
QString ret; QString ret;
bool fromConf = false; bool fromConf = false;
#if QT_CONFIG(settings) #if QT_CONFIG(settings)
if (QLibraryInfoPrivate::configuration()) if (havePaths()) {
{
fromConf = true; fromConf = true;
QString key; QString key;
QString defaultValue; QString defaultValue;
qlibraryinfo_keyAndDefault(loc, &key, &defaultValue); QLibraryInfoPrivate::keyAndDefault(loc, &key, &defaultValue);
if (!key.isNull()) { if (!key.isNull()) {
QSettings *config = QLibraryInfoPrivate::configuration(); QSettings *config = QLibraryInfoPrivate::configuration();
Q_ASSERT(config != nullptr);
config->beginGroup(QLatin1String("Paths")); config->beginGroup(QLatin1String("Paths"));
ret = config->value(key, defaultValue).toString(); ret = config->value(key, defaultValue).toString();
@ -628,7 +636,7 @@ QString QLibraryInfo::path(LibraryPath p)
QStringList QLibraryInfo::platformPluginArguments(const QString &platformName) QStringList QLibraryInfo::platformPluginArguments(const QString &platformName)
{ {
#if QT_CONFIG(settings) #if QT_CONFIG(settings)
QScopedPointer<const QSettings> settings(QLibraryInfoPrivate::findConfiguration()); QScopedPointer<const QSettings> settings(findConfiguration());
if (!settings.isNull()) { if (!settings.isNull()) {
const QString key = QLatin1String("Platforms") const QString key = QLatin1String("Platforms")
+ QLatin1Char('/') + QLatin1Char('/')

View File

@ -0,0 +1,78 @@
/****************************************************************************
**
** Copyright (C) 2021 The Qt Company Ltd.
** Copyright (C) 2016 Intel Corporation.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the QtCore module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 3 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL3 included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 3 requirements
** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 2.0 or (at your option) the GNU General
** Public license version 3 or any later version approved by the KDE Free
** Qt Foundation. The licenses are as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-2.0.html and
** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QLIBRARYINFO_P_H
#define QLIBRARYINFO_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of a number of Qt sources files. This header file may change from
// version to version without notice, or even be removed.
//
// We mean it.
//
#include "QtCore/qlibraryinfo.h"
#if QT_CONFIG(settings)
# include "QtCore/qsettings.h"
#endif
#include "QtCore/qstring.h"
QT_BEGIN_NAMESPACE
class Q_CORE_EXPORT QLibraryInfoPrivate final
{
public:
#if QT_CONFIG(settings)
static QSettings *configuration();
static void reload();
static QString qtconfManualPath;
#endif
static void keyAndDefault(QLibraryInfo::LibraryPath loc, QString *key,
QString *value);
};
QT_END_NAMESPACE
#endif // QLIBRARYINFO_P_H