1 /**************************************************************************** 2 ** 3 ** Copyright (C) 2016 The Qt Company Ltd. 4 ** Contact: https://www.qt.io/licensing/ 5 ** 6 ** This file is part of Qt Creator. 7 ** 8 ** Commercial License Usage 9 ** Licensees holding valid commercial Qt licenses may use this file in 10 ** accordance with the commercial license agreement provided with the 11 ** Software or, alternatively, in accordance with the terms contained in 12 ** a written agreement between you and The Qt Company. For licensing terms 13 ** and conditions see https://www.qt.io/terms-conditions. For further 14 ** information use the contact form at https://www.qt.io/contact-us. 15 ** 16 ** GNU General Public License Usage 17 ** Alternatively, this file may be used under the terms of the GNU 18 ** General Public License version 3 as published by the Free Software 19 ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT 20 ** included in the packaging of this file. Please review the following 21 ** information to ensure the GNU General Public License requirements will 22 ** be met: https://www.gnu.org/licenses/gpl-3.0.html. 23 ** 24 ****************************************************************************/ 25 26 #pragma once 27 28 #include "../projectexplorer_export.h" 29 30 #include <utils/id.h> 31 #include <utils/hostosinfo.h> 32 33 #include <QAbstractSocket> 34 #include <QCoreApplication> 35 #include <QDir> 36 #include <QList> 37 #include <QObject> 38 #include <QSharedPointer> 39 #include <QUrl> 40 #include <QVariantMap> 41 42 #include <functional> 43 #include <memory> 44 45 QT_BEGIN_NAMESPACE 46 class QWidget; 47 QT_END_NAMESPACE 48 49 namespace QSsh { class SshConnectionParameters; } 50 51 namespace Utils { 52 class CommandLine; 53 class Environment; 54 class FilePath; 55 class Icon; 56 class PortList; 57 class Port; 58 class QtcProcess; 59 } // Utils 60 61 namespace ProjectExplorer { 62 63 class Connection; 64 class DeviceProcess; 65 class DeviceProcessList; 66 class Kit; 67 class Runnable; 68 69 namespace Internal { class IDevicePrivate; } 70 71 class IDeviceWidget; 72 class DeviceTester; 73 74 class PROJECTEXPLORER_EXPORT DeviceProcessSignalOperation : public QObject 75 { 76 Q_OBJECT 77 public: 78 using Ptr = QSharedPointer<DeviceProcessSignalOperation>; 79 80 virtual void killProcess(qint64 pid) = 0; 81 virtual void killProcess(const QString &filePath) = 0; 82 virtual void interruptProcess(qint64 pid) = 0; 83 virtual void interruptProcess(const QString &filePath) = 0; 84 85 void setDebuggerCommand(const QString &cmd); 86 87 signals: 88 // If the error message is empty the operation was successful 89 void finished(const QString &errorMessage); 90 91 protected: 92 explicit DeviceProcessSignalOperation(); 93 94 QString m_debuggerCommand; 95 QString m_errorMessage; 96 }; 97 98 class PROJECTEXPLORER_EXPORT DeviceEnvironmentFetcher : public QObject 99 { 100 Q_OBJECT 101 public: 102 using Ptr = QSharedPointer<DeviceEnvironmentFetcher>; 103 104 virtual void start() = 0; 105 106 signals: 107 void finished(const Utils::Environment &env, bool success); 108 109 protected: 110 explicit DeviceEnvironmentFetcher(); 111 }; 112 113 class PROJECTEXPLORER_EXPORT PortsGatheringMethod 114 { 115 public: 116 using Ptr = QSharedPointer<const PortsGatheringMethod>; 117 118 virtual ~PortsGatheringMethod() = default; 119 virtual Runnable runnable(QAbstractSocket::NetworkLayerProtocol protocol) const = 0; 120 virtual QList<Utils::Port> usedPorts(const QByteArray &commandOutput) const = 0; 121 }; 122 123 // See cpp file for documentation. 124 class PROJECTEXPLORER_EXPORT IDevice : public QEnableSharedFromThis<IDevice> 125 { 126 friend class Internal::IDevicePrivate; 127 public: 128 using Ptr = QSharedPointer<IDevice>; 129 using ConstPtr = QSharedPointer<const IDevice>; 130 131 enum Origin { ManuallyAdded, AutoDetected }; 132 enum MachineType { Hardware, Emulator }; 133 134 virtual ~IDevice(); 135 136 Ptr clone() const; 137 138 QString displayName() const; 139 void setDisplayName(const QString &name); 140 void setDefaultDisplayName(const QString &name); 141 142 // Provide some information on the device suitable for formated 143 // output, e.g. in tool tips. Get a list of name value pairs. 144 class DeviceInfoItem { 145 public: DeviceInfoItem(const QString & k,const QString & v)146 DeviceInfoItem(const QString &k, const QString &v) : key(k), value(v) { } 147 148 QString key; 149 QString value; 150 }; 151 using DeviceInfo = QList<DeviceInfoItem>; 152 virtual DeviceInfo deviceInformation() const; 153 154 Utils::Id type() const; 155 void setType(Utils::Id type); 156 157 bool isAutoDetected() const; 158 Utils::Id id() const; 159 160 virtual bool isCompatibleWith(const Kit *k) const; 161 162 QString displayType() const; 163 Utils::OsType osType() const; 164 165 virtual IDeviceWidget *createWidget() = 0; 166 167 struct DeviceAction { 168 QString display; 169 std::function<void(const IDevice::Ptr &device, QWidget *parent)> execute; 170 }; 171 void addDeviceAction(const DeviceAction &deviceAction); 172 const QList<DeviceAction> deviceActions() const; 173 174 // Devices that can auto detect ports need not return a ports gathering method. Such devices can 175 // obtain a free port on demand. eg: Desktop device. canAutoDetectPorts()176 virtual bool canAutoDetectPorts() const { return false; } 177 virtual PortsGatheringMethod::Ptr portsGatheringMethod() const; canCreateProcessModel()178 virtual bool canCreateProcessModel() const { return false; } 179 virtual DeviceProcessList *createProcessListModel(QObject *parent = nullptr) const; hasDeviceTester()180 virtual bool hasDeviceTester() const { return false; } 181 virtual DeviceTester *createDeviceTester() const; 182 canCreateProcess()183 virtual bool canCreateProcess() const { return false; } 184 virtual DeviceProcess *createProcess(QObject *parent) const; 185 virtual DeviceProcessSignalOperation::Ptr signalOperation() const = 0; 186 virtual DeviceEnvironmentFetcher::Ptr environmentFetcher() const; 187 188 enum DeviceState { DeviceReadyToUse, DeviceConnected, DeviceDisconnected, DeviceStateUnknown }; 189 DeviceState deviceState() const; 190 void setDeviceState(const DeviceState state); 191 QString deviceStateToString() const; 192 193 virtual void fromMap(const QVariantMap &map); 194 virtual QVariantMap toMap() const; 195 196 static Utils::Id typeFromMap(const QVariantMap &map); 197 static Utils::Id idFromMap(const QVariantMap &map); 198 199 static QString defaultPrivateKeyFilePath(); 200 static QString defaultPublicKeyFilePath(); 201 202 QSsh::SshConnectionParameters sshParameters() const; 203 void setSshParameters(const QSsh::SshConnectionParameters &sshParameters); 204 205 enum ControlChannelHint { QmlControlChannel }; 206 virtual QUrl toolControlChannel(const ControlChannelHint &) const; 207 208 Utils::PortList freePorts() const; 209 void setFreePorts(const Utils::PortList &freePorts); 210 211 MachineType machineType() const; 212 void setMachineType(MachineType machineType); 213 214 QString debugServerPath() const; 215 void setDebugServerPath(const QString &path); 216 217 QString qmlRunCommand() const; 218 void setQmlRunCommand(const QString &path); 219 220 void setExtraData(Utils::Id kind, const QVariant &data); 221 QVariant extraData(Utils::Id kind) const; 222 223 void setupId(Origin origin, Utils::Id id = Utils::Id()); 224 225 bool canOpenTerminal() const; 226 void openTerminal(const Utils::Environment &env, const QString &workingDir) const; 227 228 bool isEmptyCommandAllowed() const; 229 void setAllowEmptyCommand(bool allow); 230 isWindowsDevice()231 bool isWindowsDevice() const { return osType() == Utils::OsTypeWindows; } isLinuxDevice()232 bool isLinuxDevice() const { return osType() == Utils::OsTypeLinux; } isMacDevice()233 bool isMacDevice() const { return osType() == Utils::OsTypeMac; } 234 bool isAnyUnixDevice() const; 235 236 virtual Utils::FilePath mapToGlobalPath(const Utils::FilePath &pathOnDevice) const; 237 238 virtual bool handlesFile(const Utils::FilePath &filePath) const; 239 virtual bool isExecutableFile(const Utils::FilePath &filePath) const; 240 virtual bool isReadableFile(const Utils::FilePath &filePath) const; 241 virtual bool isWritableFile(const Utils::FilePath &filePath) const; 242 virtual bool isReadableDirectory(const Utils::FilePath &filePath) const; 243 virtual bool isWritableDirectory(const Utils::FilePath &filePath) const; 244 virtual bool isFile(const Utils::FilePath &filePath) const; 245 virtual bool isDirectory(const Utils::FilePath &filePath) const; 246 virtual bool ensureWritableDirectory(const Utils::FilePath &filePath) const; 247 virtual bool ensureExistingFile(const Utils::FilePath &filePath) const; 248 virtual bool createDirectory(const Utils::FilePath &filePath) const; 249 virtual bool exists(const Utils::FilePath &filePath) const; 250 virtual bool removeFile(const Utils::FilePath &filePath) const; 251 virtual bool removeRecursively(const Utils::FilePath &filePath) const; 252 virtual bool copyFile(const Utils::FilePath &filePath, const Utils::FilePath &target) const; 253 virtual bool renameFile(const Utils::FilePath &filePath, const Utils::FilePath &target) const; 254 virtual Utils::FilePath searchExecutableInPath(const QString &fileName) const; 255 virtual Utils::FilePath searchExecutable(const QString &fileName, 256 const QList<Utils::FilePath> &dirs) const; 257 virtual Utils::FilePath symLinkTarget(const Utils::FilePath &filePath) const; 258 virtual QList<Utils::FilePath> directoryEntries(const Utils::FilePath &filePath, 259 const QStringList &nameFilters, 260 QDir::Filters filters, 261 QDir::SortFlags sort = QDir::NoSort) const; 262 virtual QByteArray fileContents(const Utils::FilePath &filePath, 263 qint64 limit, 264 qint64 offset) const; 265 virtual bool writeFileContents(const Utils::FilePath &filePath, const QByteArray &data) const; 266 virtual QDateTime lastModified(const Utils::FilePath &filePath) const; 267 virtual QFile::Permissions permissions(const Utils::FilePath &filePath) const; 268 virtual void runProcess(Utils::QtcProcess &process) const; 269 virtual Utils::Environment systemEnvironment() const; 270 aboutToBeRemoved()271 virtual void aboutToBeRemoved() const {} 272 273 protected: 274 IDevice(); 275 276 using OpenTerminal = std::function<void(const Utils::Environment &, const QString &)>; 277 void setOpenTerminal(const OpenTerminal &openTerminal); 278 void setDisplayType(const QString &type); 279 void setOsType(Utils::OsType osType); 280 281 private: 282 IDevice(const IDevice &) = delete; 283 IDevice &operator=(const IDevice &) = delete; 284 285 int version() const; 286 287 const std::unique_ptr<Internal::IDevicePrivate> d; 288 friend class DeviceManager; 289 }; 290 291 292 class PROJECTEXPLORER_EXPORT DeviceTester : public QObject 293 { 294 Q_OBJECT 295 296 public: 297 enum TestResult { TestSuccess, TestFailure }; 298 299 virtual void testDevice(const ProjectExplorer::IDevice::Ptr &deviceConfiguration) = 0; 300 virtual void stopTest() = 0; 301 302 signals: 303 void progressMessage(const QString &message); 304 void errorMessage(const QString &message); 305 void finished(ProjectExplorer::DeviceTester::TestResult result); 306 307 protected: 308 explicit DeviceTester(QObject *parent = nullptr); 309 }; 310 311 } // namespace ProjectExplorer 312