Docker: Fix debugger auto-detection

Mark detected debuggers as such and give them some bonus to match,
overriding other hacks.

Change-Id: Iaf4d88fa22dd50e68124b61087d4c742f7a56d0f
Reviewed-by: Christian Stenger <christian.stenger@qt.io>
This commit is contained in:
hjk
2021-07-09 17:39:50 +02:00
parent e8521e6fe1
commit 076d1bf10a
8 changed files with 35 additions and 17 deletions

View File

@@ -57,7 +57,8 @@ const char DEBUGGER_INFORMATION_COMMAND[] = "Binary";
const char DEBUGGER_INFORMATION_DISPLAYNAME[] = "DisplayName"; const char DEBUGGER_INFORMATION_DISPLAYNAME[] = "DisplayName";
const char DEBUGGER_INFORMATION_ID[] = "Id"; const char DEBUGGER_INFORMATION_ID[] = "Id";
const char DEBUGGER_INFORMATION_ENGINETYPE[] = "EngineType"; const char DEBUGGER_INFORMATION_ENGINETYPE[] = "EngineType";
const char DEBUGGER_INFORMATION_AUTODETECTED[] = "AutoDetected"; const char DEBUGGER_INFORMATION_AUTODETECTED[] = "AutoDetected"; // FIXME: Merge into DetectionSource
const char DEBUGGER_INFORMATION_DETECTION_SOURCE[] = "DetectionSource";
const char DEBUGGER_INFORMATION_VERSION[] = "Version"; const char DEBUGGER_INFORMATION_VERSION[] = "Version";
const char DEBUGGER_INFORMATION_ABIS[] = "Abis"; const char DEBUGGER_INFORMATION_ABIS[] = "Abis";
const char DEBUGGER_INFORMATION_LASTMODIFIED[] = "LastModified"; const char DEBUGGER_INFORMATION_LASTMODIFIED[] = "LastModified";
@@ -113,6 +114,7 @@ DebuggerItem::DebuggerItem(const QVariantMap &data)
m_workingDirectory = FilePath::fromVariant(data.value(DEBUGGER_INFORMATION_WORKINGDIRECTORY)); m_workingDirectory = FilePath::fromVariant(data.value(DEBUGGER_INFORMATION_WORKINGDIRECTORY));
m_unexpandedDisplayName = data.value(DEBUGGER_INFORMATION_DISPLAYNAME).toString(); m_unexpandedDisplayName = data.value(DEBUGGER_INFORMATION_DISPLAYNAME).toString();
m_isAutoDetected = data.value(DEBUGGER_INFORMATION_AUTODETECTED, false).toBool(); m_isAutoDetected = data.value(DEBUGGER_INFORMATION_AUTODETECTED, false).toBool();
m_detectionSource = data.value(DEBUGGER_INFORMATION_DETECTION_SOURCE).toString();
m_version = data.value(DEBUGGER_INFORMATION_VERSION).toString(); m_version = data.value(DEBUGGER_INFORMATION_VERSION).toString();
m_engineType = DebuggerEngineType(data.value(DEBUGGER_INFORMATION_ENGINETYPE, m_engineType = DebuggerEngineType(data.value(DEBUGGER_INFORMATION_ENGINETYPE,
static_cast<int>(NoEngineType)).toInt()); static_cast<int>(NoEngineType)).toInt());
@@ -210,8 +212,8 @@ void DebuggerItem::reinitializeFromFile(const Utils::Environment &sysEnv)
const bool unableToFindAVersion = (0 == version); const bool unableToFindAVersion = (0 == version);
const bool gdbSupportsConfigurationFlag = (version >= 70700); const bool gdbSupportsConfigurationFlag = (version >= 70700);
if (gdbSupportsConfigurationFlag || unableToFindAVersion) { if (gdbSupportsConfigurationFlag || unableToFindAVersion) {
const auto gdbConfiguration = getConfigurationOfGdbCommand(m_command, sysEnv); const QString gdbConfiguration = getConfigurationOfGdbCommand(m_command, sysEnv);
const auto gdbTargetAbiString = const QString gdbTargetAbiString =
extractGdbTargetAbiStringFromGdbOutput(gdbConfiguration); extractGdbTargetAbiStringFromGdbOutput(gdbConfiguration);
if (!gdbTargetAbiString.isEmpty()) { if (!gdbTargetAbiString.isEmpty()) {
m_abis.append(Abi::abiFromTargetTriplet(gdbTargetAbiString)); m_abis.append(Abi::abiFromTargetTriplet(gdbTargetAbiString));
@@ -318,6 +320,7 @@ bool DebuggerItem::operator==(const DebuggerItem &other) const
return m_id == other.m_id return m_id == other.m_id
&& m_unexpandedDisplayName == other.m_unexpandedDisplayName && m_unexpandedDisplayName == other.m_unexpandedDisplayName
&& m_isAutoDetected == other.m_isAutoDetected && m_isAutoDetected == other.m_isAutoDetected
&& m_detectionSource == other.m_detectionSource
&& m_command == other.m_command && m_command == other.m_command
&& m_workingDirectory == other.m_workingDirectory; && m_workingDirectory == other.m_workingDirectory;
} }
@@ -331,6 +334,7 @@ QVariantMap DebuggerItem::toMap() const
data.insert(DEBUGGER_INFORMATION_WORKINGDIRECTORY, m_workingDirectory.toVariant()); data.insert(DEBUGGER_INFORMATION_WORKINGDIRECTORY, m_workingDirectory.toVariant());
data.insert(DEBUGGER_INFORMATION_ENGINETYPE, int(m_engineType)); data.insert(DEBUGGER_INFORMATION_ENGINETYPE, int(m_engineType));
data.insert(DEBUGGER_INFORMATION_AUTODETECTED, m_isAutoDetected); data.insert(DEBUGGER_INFORMATION_AUTODETECTED, m_isAutoDetected);
data.insert(DEBUGGER_INFORMATION_DETECTION_SOURCE, m_detectionSource);
data.insert(DEBUGGER_INFORMATION_VERSION, m_version); data.insert(DEBUGGER_INFORMATION_VERSION, m_version);
data.insert(DEBUGGER_INFORMATION_ABIS, abiNames()); data.insert(DEBUGGER_INFORMATION_ABIS, abiNames());
data.insert(DEBUGGER_INFORMATION_LASTMODIFIED, m_lastModified); data.insert(DEBUGGER_INFORMATION_LASTMODIFIED, m_lastModified);

View File

@@ -103,6 +103,9 @@ public:
Utils::FilePath workingDirectory() const { return m_workingDirectory; } Utils::FilePath workingDirectory() const { return m_workingDirectory; }
void setWorkingDirectory(const Utils::FilePath &workingPath) { m_workingDirectory = workingPath; } void setWorkingDirectory(const Utils::FilePath &workingPath) { m_workingDirectory = workingPath; }
QString detectionSource() const { return m_detectionSource; }
void setDetectionSource(const QString &source) { m_detectionSource = source; }
private: private:
DebuggerItem(const QVariant &id); DebuggerItem(const QVariant &id);
void initMacroExpander(); void initMacroExpander();
@@ -116,6 +119,7 @@ private:
QString m_version; QString m_version;
ProjectExplorer::Abis m_abis; ProjectExplorer::Abis m_abis;
QDateTime m_lastModified; QDateTime m_lastModified;
QString m_detectionSource;
friend class Internal::DebuggerConfigWidget; friend class Internal::DebuggerConfigWidget;
friend class Internal::DebuggerItemConfigWidget; friend class Internal::DebuggerItemConfigWidget;

View File

@@ -92,7 +92,7 @@ public:
QVariant registerDebugger(const DebuggerItem &item); QVariant registerDebugger(const DebuggerItem &item);
void readDebuggers(const FilePath &fileName, bool isSystem); void readDebuggers(const FilePath &fileName, bool isSystem);
void autoDetectCdbDebuggers(); void autoDetectCdbDebuggers();
void autoDetectGdbOrLldbDebuggers(const FilePath &deviceRoot); void autoDetectGdbOrLldbDebuggers(const FilePath &deviceRoot, const QString &detectionSource);
void autoDetectUvscDebuggers(); void autoDetectUvscDebuggers();
QString uniqueDisplayName(const QString &base); QString uniqueDisplayName(const QString &base);
@@ -556,7 +556,6 @@ void DebuggerConfigWidget::addDebugger()
{ {
DebuggerItem item; DebuggerItem item;
item.createId(); item.createId();
item.setAutoDetected(false);
item.setEngineType(NoEngineType); item.setEngineType(NoEngineType);
item.setUnexpandedDisplayName(d->uniqueDisplayName(tr("New Debugger"))); item.setUnexpandedDisplayName(d->uniqueDisplayName(tr("New Debugger")));
item.setAutoDetected(false); item.setAutoDetected(false);
@@ -715,7 +714,8 @@ static Utils::FilePaths searchGdbPathsFromRegistry()
return searchPaths; return searchPaths;
} }
void DebuggerItemManagerPrivate::autoDetectGdbOrLldbDebuggers(const FilePath &deviceRoot) void DebuggerItemManagerPrivate::autoDetectGdbOrLldbDebuggers(const FilePath &deviceRoot,
const QString &detectionSource)
{ {
const QStringList filters = {"gdb-i686-pc-mingw32", "gdb-i686-pc-mingw32.exe", "gdb", const QStringList filters = {"gdb-i686-pc-mingw32", "gdb-i686-pc-mingw32.exe", "gdb",
"gdb.exe", "lldb", "lldb.exe", "lldb-[1-9]*", "gdb.exe", "lldb", "lldb.exe", "lldb-[1-9]*",
@@ -784,14 +784,17 @@ void DebuggerItemManagerPrivate::autoDetectGdbOrLldbDebuggers(const FilePath &de
} }
DebuggerItem item; DebuggerItem item;
item.createId(); item.createId();
item.setDetectionSource(detectionSource);
// Intentionally set items with non-empty source as manual for now to
// give the user a chance to remove them. FIXME: Think of a better way.
item.setAutoDetected(detectionSource.isEmpty());
item.setCommand(command); item.setCommand(command);
item.reinitializeFromFile(); item.reinitializeFromFile();
if (item.engineType() == NoEngineType) if (item.engineType() == NoEngineType)
continue; continue;
//: %1: Debugger engine type (GDB, LLDB, CDB...), %2: Path //: %1: Debugger engine type (GDB, LLDB, CDB...), %2: Path
item.setUnexpandedDisplayName(tr("System %1 at %2") const QString name = detectionSource.isEmpty() ? tr("System %1 at %2") : tr("Detected %1 at %2");
.arg(item.engineTypeName()).arg(command.toUserOutput())); item.setUnexpandedDisplayName(name.arg(item.engineTypeName()).arg(command.toUserOutput()));
item.setAutoDetected(true);
m_model->addDebugger(item); m_model->addDebugger(item);
} }
} }
@@ -942,7 +945,7 @@ void DebuggerItemManagerPrivate::restoreDebuggers()
// Auto detect current. // Auto detect current.
autoDetectCdbDebuggers(); autoDetectCdbDebuggers();
autoDetectGdbOrLldbDebuggers({}); autoDetectGdbOrLldbDebuggers({}, {});
autoDetectUvscDebuggers(); autoDetectUvscDebuggers();
} }
@@ -1026,9 +1029,10 @@ void DebuggerItemManager::deregisterDebugger(const QVariant &id)
}); });
} }
void DebuggerItemManager::autoDetectDebuggersForDevice(const Utils::FilePath &deviceRoot) void DebuggerItemManager::autoDetectDebuggersForDevice(const FilePath &deviceRoot,
const QString &detectionSource)
{ {
d->autoDetectGdbOrLldbDebuggers(deviceRoot); d->autoDetectGdbOrLldbDebuggers(deviceRoot, detectionSource);
} }
} // namespace Debugger } // namespace Debugger

View File

@@ -52,7 +52,8 @@ public:
static QVariant registerDebugger(const DebuggerItem &item); static QVariant registerDebugger(const DebuggerItem &item);
static void deregisterDebugger(const QVariant &id); static void deregisterDebugger(const QVariant &id);
static void autoDetectDebuggersForDevice(const Utils::FilePath &deviceRoot); static void autoDetectDebuggersForDevice(const Utils::FilePath &deviceRoot,
const QString &detectionSource);
static const DebuggerItem *findByCommand(const Utils::FilePath &command); static const DebuggerItem *findByCommand(const Utils::FilePath &command);
static const DebuggerItem *findById(const QVariant &id); static const DebuggerItem *findById(const QVariant &id);

View File

@@ -185,9 +185,12 @@ void DebuggerKitAspect::setup(Kit *k)
// This improves the situation a bit if a cross-compilation tool chain has the // This improves the situation a bit if a cross-compilation tool chain has the
// same ABI as the host. // same ABI as the host.
if (level == DebuggerItem::MatchesPerfectly if (level == DebuggerItem::MatchesPerfectly
&& !item.command().needsDevice()
&& systemEnvironment.path().contains(item.command().parentDir())) { && systemEnvironment.path().contains(item.command().parentDir())) {
level = DebuggerItem::MatchesPerfectlyInPath; level = DebuggerItem::MatchesPerfectlyInPath;
} }
if (!item.detectionSource().isEmpty() && item.detectionSource() == k->autoDetectionSource())
level = DebuggerItem::MatchLevel(level + 2);
} else if (rawId.type() == QVariant::String) { } else if (rawId.type() == QVariant::String) {
// New structure. // New structure.
if (item.id() == rawId) { if (item.id() == rawId) {

View File

@@ -1746,9 +1746,10 @@ void DebuggerPlugin::getEnginesState(QByteArray *json) const
*json = QJsonDocument(QJsonObject::fromVariantMap(result)).toJson(); *json = QJsonDocument(QJsonObject::fromVariantMap(result)).toJson();
} }
void DebuggerPlugin::autoDetectDebuggersForDevice(const FilePath &deviceRoot) void DebuggerPlugin::autoDetectDebuggersForDevice(const FilePath &deviceRoot,
const QString &detectionId)
{ {
dd->m_debuggerItemManager.autoDetectDebuggersForDevice(deviceRoot); dd->m_debuggerItemManager.autoDetectDebuggersForDevice(deviceRoot, detectionId);
} }
void DebuggerPluginPrivate::attachToQmlPort() void DebuggerPluginPrivate::attachToQmlPort()

View File

@@ -59,7 +59,7 @@ private:
Q_SLOT void getEnginesState(QByteArray *json) const; Q_SLOT void getEnginesState(QByteArray *json) const;
// Called from DockerDevice // Called from DockerDevice
Q_SLOT void autoDetectDebuggersForDevice(const Utils::FilePath &deviceRoot); Q_SLOT void autoDetectDebuggersForDevice(const Utils::FilePath &deviceRoot, const QString &detectionId);
QVector<QObject *> createTestObjects() const override; QVector<QObject *> createTestObjects() const override;
}; };

View File

@@ -570,7 +570,8 @@ void KitDetectorPrivate::autoDetectDebugger()
const FilePath deviceRoot = m_device->mapToGlobalPath({}); const FilePath deviceRoot = m_device->mapToGlobalPath({});
const bool res = QMetaObject::invokeMethod(debuggerPlugin, const bool res = QMetaObject::invokeMethod(debuggerPlugin,
"autoDetectDebuggersForDevice", "autoDetectDebuggersForDevice",
Q_ARG(Utils::FilePath, deviceRoot)); Q_ARG(Utils::FilePath, deviceRoot),
Q_ARG(QString, m_sharedId));
QTC_CHECK(res); QTC_CHECK(res);
} }