diff options
-rw-r--r-- | src/libs/utils/filepath.cpp | 10 | ||||
-rw-r--r-- | src/libs/utils/filepath.h | 3 | ||||
-rw-r--r-- | src/plugins/debugger/gdb/gdbengine.cpp | 4 | ||||
-rw-r--r-- | src/plugins/debugger/stackframe.cpp | 3 | ||||
-rw-r--r-- | src/plugins/docker/dockerdevice.cpp | 27 | ||||
-rw-r--r-- | src/plugins/docker/dockerdevice.h | 1 | ||||
-rw-r--r-- | src/plugins/projectexplorer/devicesupport/devicemanager.cpp | 8 | ||||
-rw-r--r-- | src/plugins/projectexplorer/devicesupport/idevice.cpp | 10 | ||||
-rw-r--r-- | src/plugins/projectexplorer/devicesupport/idevice.h | 2 |
9 files changed, 64 insertions, 4 deletions
diff --git a/src/libs/utils/filepath.cpp b/src/libs/utils/filepath.cpp index 7f4e38d73a..944fe2a5ce 100644 --- a/src/libs/utils/filepath.cpp +++ b/src/libs/utils/filepath.cpp @@ -1588,6 +1588,16 @@ FilePath FilePath::resolvePath(const QString &tail) const return resolvePath(FilePath::fromString(tail)); } +expected_str<FilePath> FilePath::localSource() const +{ + if (!needsDevice()) + return *this; + + QTC_ASSERT(s_deviceHooks.localSource, + return make_unexpected(Tr::tr("No 'localSource' device hook set."))); + return s_deviceHooks.localSource(*this); +} + // Cleans path part similar to QDir::cleanPath() // - directory separators normalized (that is, platform-native // separators converted to "/") and redundant ones removed, and "."s and ".."s diff --git a/src/libs/utils/filepath.h b/src/libs/utils/filepath.h index 5f5a5bad7f..2897b278ec 100644 --- a/src/libs/utils/filepath.h +++ b/src/libs/utils/filepath.h @@ -238,6 +238,8 @@ public: [[nodiscard]] static int schemeAndHostLength(const QStringView path); static QString calcRelativePath(const QString &absolutePath, const QString &absoluteAnchorPath); + //! Returns a filepath the represents the same file on a local drive + expected_str<FilePath> localSource() const; private: friend class ::tst_fileutils; @@ -268,6 +270,7 @@ public: std::function<bool(const FilePath &, const FilePath &)> ensureReachable; std::function<Environment(const FilePath &)> environment; std::function<bool(const FilePath &left, const FilePath &right)> isSameDevice; + std::function<expected_str<FilePath>(const FilePath &)> localSource; }; } // namespace Utils diff --git a/src/plugins/debugger/gdb/gdbengine.cpp b/src/plugins/debugger/gdb/gdbengine.cpp index 67e0dd72e5..b3327cac37 100644 --- a/src/plugins/debugger/gdb/gdbengine.cpp +++ b/src/plugins/debugger/gdb/gdbengine.cpp @@ -1165,7 +1165,9 @@ void GdbEngine::handleStopResponse(const GdbMi &data) showMessage("INVALID STOPPED REASON", LogWarning); } - const FilePath fileName = FilePath::fromString(fullName); + const FilePath onDevicePath = FilePath::fromString(fullName).onDevice( + runParameters().debugger.command.executable()); + const FilePath fileName = onDevicePath.localSource().value_or(onDevicePath); if (!nr.isEmpty() && frame.isValid()) { // Use opportunity to update the breakpoint marker position. diff --git a/src/plugins/debugger/stackframe.cpp b/src/plugins/debugger/stackframe.cpp index 1a68e4ae3a..740868889e 100644 --- a/src/plugins/debugger/stackframe.cpp +++ b/src/plugins/debugger/stackframe.cpp @@ -74,7 +74,8 @@ StackFrame StackFrame::parseFrame(const GdbMi &frameMi, const DebuggerRunParamet frame.function = frameMi["function"].data(); frame.module = frameMi["module"].data(); const FilePath debugger = rp.debugger.command.executable(); - frame.file = FilePath::fromString(frameMi["file"].data()).onDevice(debugger); + const FilePath onDevicePath = FilePath::fromString(frameMi["file"].data()).onDevice(debugger); + frame.file = onDevicePath.localSource().value_or(onDevicePath); frame.line = frameMi["line"].toInt(); frame.address = frameMi["address"].toAddress(); frame.context = frameMi["context"].data(); diff --git a/src/plugins/docker/dockerdevice.cpp b/src/plugins/docker/dockerdevice.cpp index c37e2d106e..a71ccfef50 100644 --- a/src/plugins/docker/dockerdevice.cpp +++ b/src/plugins/docker/dockerdevice.cpp @@ -144,6 +144,7 @@ public: void changeMounts(QStringList newMounts); bool ensureReachable(const FilePath &other); void shutdown(); + expected_str<FilePath> localSource(const FilePath &other) const; QString containerId() { return m_container; } DockerDeviceData data() { return m_data; } @@ -828,6 +829,11 @@ bool DockerDevice::ensureReachable(const FilePath &other) const return d->ensureReachable(other.parentDir()); } +expected_str<FilePath> DockerDevice::localSource(const Utils::FilePath &other) const +{ + return d->localSource(other); +} + Environment DockerDevice::systemEnvironment() const { return d->environment(); @@ -1125,6 +1131,27 @@ void DockerDevicePrivate::changeMounts(QStringList newMounts) } } +expected_str<FilePath> DockerDevicePrivate::localSource(const FilePath &other) const +{ + const auto devicePath = FilePath::fromString(other.path()); + for (const TemporaryMountInfo &info : m_temporaryMounts) { + if (devicePath.isChildOf(info.containerPath)) { + const FilePath relativePath = devicePath.relativeChildPath(info.containerPath); + return info.path.pathAppended(relativePath.path()); + } + } + + for (const QString &mount : m_data.mounts) { + const FilePath mountPoint = FilePath::fromString(mount); + if (devicePath.isChildOf(mountPoint)) { + const FilePath relativePath = devicePath.relativeChildPath(mountPoint); + return mountPoint.pathAppended(relativePath.path()); + } + } + + return make_unexpected(Tr::tr("localSource: No mount point found for %1").arg(other.toString())); +} + bool DockerDevicePrivate::ensureReachable(const FilePath &other) { for (const QString &mount : m_data.mounts) { diff --git a/src/plugins/docker/dockerdevice.h b/src/plugins/docker/dockerdevice.h index 4c5cd20e92..03bfc3f2a6 100644 --- a/src/plugins/docker/dockerdevice.h +++ b/src/plugins/docker/dockerdevice.h @@ -86,6 +86,7 @@ public: bool handlesFile(const Utils::FilePath &filePath) const override; bool ensureReachable(const Utils::FilePath &other) const override; + Utils::expected_str<Utils::FilePath> localSource(const Utils::FilePath &other) const override; Utils::Environment systemEnvironment() const override; diff --git a/src/plugins/projectexplorer/devicesupport/devicemanager.cpp b/src/plugins/projectexplorer/devicesupport/devicemanager.cpp index f65839bacc..f23bf70113 100644 --- a/src/plugins/projectexplorer/devicesupport/devicemanager.cpp +++ b/src/plugins/projectexplorer/devicesupport/devicemanager.cpp @@ -4,6 +4,7 @@ #include "devicemanager.h" #include "idevicefactory.h" +#include "projectexplorertr.h" #include <coreplugin/icore.h> #include <coreplugin/messagemanager.h> @@ -414,6 +415,13 @@ DeviceManager::DeviceManager(bool isInstance) : d(std::make_unique<DeviceManager return leftDevice == rightDevice; }; + deviceHooks.localSource = [](const FilePath &file) -> expected_str<FilePath> { + auto device = DeviceManager::deviceForPath(file); + if (!device) + return make_unexpected(Tr::tr("No device for path \"%1\"").arg(file.toUserOutput())); + return device->localSource(file); + }; + deviceHooks.fileAccess = [](const FilePath &filePath) -> DeviceFileAccess * { if (!filePath.needsDevice()) return DesktopDeviceFileAccess::instance(); diff --git a/src/plugins/projectexplorer/devicesupport/idevice.cpp b/src/plugins/projectexplorer/devicesupport/idevice.cpp index 83cfa72fd3..e1cc72bc71 100644 --- a/src/plugins/projectexplorer/devicesupport/idevice.cpp +++ b/src/plugins/projectexplorer/devicesupport/idevice.cpp @@ -10,11 +10,11 @@ #include "../kit.h" #include "../kitinformation.h" +#include "../projectexplorertr.h" +#include "../target.h" #include <coreplugin/icore.h> -#include <projectexplorer/target.h> - #include <utils/devicefileaccess.h> #include <utils/displayname.h> #include <utils/icon.h> @@ -630,6 +630,12 @@ bool IDevice::ensureReachable(const FilePath &other) const return handlesFile(other); // Some first approximation. } +expected_str<FilePath> IDevice::localSource(const Utils::FilePath &other) const +{ + Q_UNUSED(other); + return make_unexpected(Tr::tr("localSource() not implemented for this device type.")); +} + bool IDevice::prepareForBuild(const Target *target) { Q_UNUSED(target) diff --git a/src/plugins/projectexplorer/devicesupport/idevice.h b/src/plugins/projectexplorer/devicesupport/idevice.h index b61e9c9471..e2dfe57ffd 100644 --- a/src/plugins/projectexplorer/devicesupport/idevice.h +++ b/src/plugins/projectexplorer/devicesupport/idevice.h @@ -7,6 +7,7 @@ #include "idevicefwd.h" #include <utils/id.h> +#include <utils/expected.h> #include <utils/filepath.h> #include <utils/hostosinfo.h> #include <utils/tasktree.h> @@ -215,6 +216,7 @@ public: virtual void aboutToBeRemoved() const {} virtual bool ensureReachable(const Utils::FilePath &other) const; + virtual Utils::expected_str<Utils::FilePath> localSource(const Utils::FilePath &other) const; virtual bool prepareForBuild(const Target *target); virtual std::optional<Utils::FilePath> clangdExecutable() const; |