diff --git a/src/gui/gui.pro b/src/gui/gui.pro index 69c2f530..4900d0df 100644 --- a/src/gui/gui.pro +++ b/src/gui/gui.pro @@ -53,7 +53,8 @@ SOURCES += src/main.cpp \ src/AddClientDialog.cpp \ src/CommandProcess.cpp \ src/WebClient.cpp \ - src/PluginWizardPage.cpp + src/PluginWizardPage.cpp \ + src/PluginManager.cpp HEADERS += src/MainWindow.h \ src/AboutDialog.h \ src/ServerConfig.h \ @@ -92,7 +93,9 @@ HEADERS += src/MainWindow.h \ src/CommandProcess.h \ src/WebClient.h \ src/EditionType.h \ - src/PluginWizardPage.h + src/PluginWizardPage.h \ + src/ProcessorArch.h \ + src/PluginManager.h RESOURCES += res/Synergy.qrc RC_FILE = res/win/Synergy.rc macx { diff --git a/src/gui/src/DataDownloader.cpp b/src/gui/src/DataDownloader.cpp index ced73f88..f67682ec 100644 --- a/src/gui/src/DataDownloader.cpp +++ b/src/gui/src/DataDownloader.cpp @@ -17,37 +17,39 @@ #include "DataDownloader.h" -DataDownloader::DataDownloader(QUrl url, QObject* parent) : +DataDownloader::DataDownloader(QObject* parent) : QObject(parent) { - connect(&m_WebCtrl, SIGNAL(finished(QNetworkReply*)), - SLOT(fileDownloaded(QNetworkReply*))); - - QNetworkRequest request(url); - m_pReply = m_WebCtrl.get(request); + connect(&m_NetworkManager, SIGNAL(finished(QNetworkReply*)), + SLOT(complete(QNetworkReply*))); } DataDownloader::~DataDownloader() { - } -void DataDownloader::fileDownloaded(QNetworkReply* reply) +void DataDownloader::complete(QNetworkReply* reply) { - m_DownloadedData = reply->readAll(); + m_Data = reply->readAll(); reply->deleteLater(); - if (!m_DownloadedData.isEmpty()) { - emit downloaded(); + if (!m_Data.isEmpty()) { + emit isComplete(); } } -QByteArray DataDownloader::downloadedData() const +QByteArray DataDownloader::data() const { - return m_DownloadedData; + return m_Data; } -void DataDownloader::cancelDownload() +void DataDownloader::cancel() { m_pReply->abort(); } + +void DataDownloader::download(QUrl url) +{ + QNetworkRequest request(url); + m_pReply = m_NetworkManager.get(request); +} diff --git a/src/gui/src/DataDownloader.h b/src/gui/src/DataDownloader.h index 4839c57d..e596ca36 100644 --- a/src/gui/src/DataDownloader.h +++ b/src/gui/src/DataDownloader.h @@ -27,23 +27,24 @@ class DataDownloader : public QObject { Q_OBJECT + public: - explicit DataDownloader(QUrl url, QObject* parent = 0); + explicit DataDownloader(QObject* parent = 0); virtual ~DataDownloader(); - QByteArray downloadedData() const; - void cancelDownload(); + QByteArray data() const; + void cancel(); + void download(QUrl url); signals: - void downloaded(); + void isComplete(); private slots: - void fileDownloaded(QNetworkReply* reply); + void complete(QNetworkReply* reply); private: - - QNetworkAccessManager m_WebCtrl; - QByteArray m_DownloadedData; + QNetworkAccessManager m_NetworkManager; + QByteArray m_Data; QNetworkReply* m_pReply; }; diff --git a/src/gui/src/MainWindow.cpp b/src/gui/src/MainWindow.cpp index e826222b..eebd753f 100644 --- a/src/gui/src/MainWindow.cpp +++ b/src/gui/src/MainWindow.cpp @@ -30,6 +30,7 @@ #include "CommandProcess.h" #include "EditionType.h" #include "QUtility.h" +#include "ProcessorArch.h" #include #include @@ -54,10 +55,10 @@ #if defined(Q_OS_WIN) static const char synergyConfigName[] = "synergy.sgc"; static const QString synergyConfigFilter(QObject::tr("Synergy Configurations (*.sgc);;All files (*.*)")); -static const char bonjourUrl[] = "http://synergy-project.org/bonjour/"; -static const char bonjour32Url[] = "http://synergy-project.org/bonjour/Bonjour.msi"; -static const char bonjour64Url[] = "http://synergy-project.org/bonjour/Bonjour64.msi"; -static const char bonjourInstaller[] = "BonjourSetup.msi"; +static QString bonjourBaseUrl = "http://synergy-project.org/bonjour/"; +static const char bonjourFilename32[] = "Bonjour.msi"; +static const char bonjourFilename64[] = "Bonjour64.msi"; +static const char bonjourTargetFilename[] = "Bonjour.msi"; #else static const char synergyConfigName[] = "synergy.conf"; static const QString synergyConfigFilter(QObject::tr("Synergy Configurations (*.conf);;All files (*.*)")); @@ -865,26 +866,6 @@ void MainWindow::serverDetected(const QString name) } } -int MainWindow::checkWinArch() -{ -#if defined(Q_OS_WIN) - SYSTEM_INFO systemInfo; - GetNativeSystemInfo(&systemInfo); - - switch (systemInfo.wProcessorArchitecture) { - case PROCESSOR_ARCHITECTURE_INTEL: - return x86; - case PROCESSOR_ARCHITECTURE_IA64: - return x64; - case PROCESSOR_ARCHITECTURE_AMD64: - return x64; - default: - appendLogNote("failed to detect system architecture"); - } -#endif - return unknown; -} - void MainWindow::setEdition(int type) { QString title; @@ -1063,33 +1044,30 @@ bool MainWindow::isBonjourRunning() void MainWindow::downloadBonjour() { #if defined(Q_OS_WIN) - QUrl url; - int arch = checkWinArch(); - if (arch == x86) { - url.setUrl(bonjour32Url); + int arch = checkProcessorArch(); + if (arch == Win_x86) { + url.setUrl(bonjourBaseUrl + bonjourFilename32); appendLogNote("downloading 32-bit Bonjour"); } - else if (arch == x64) { - url.setUrl(bonjour64Url); + else if (arch == Win_x64) { + url.setUrl(bonjourBaseUrl + bonjourFilename64); appendLogNote("downloading 64-bit Bonjour"); } else { - QString msg("Failed to detect system architecture.\n" - "Please download the installer manually from this link:\n"); - QMessageBox::warning( + QMessageBox::critical( this, tr("Synergy"), - msg + bonjourUrl); + tr("Failed to detect system architecture.")); return; } - if (m_pDataDownloader != NULL) { - delete m_pDataDownloader; - m_pDataDownloader = NULL; + + if (m_pDataDownloader == NULL) { + m_pDataDownloader = new DataDownloader(this); + connect(m_pDataDownloader, SIGNAL(isComplete()), SLOT(installBonjour())); } - m_pDataDownloader = new DataDownloader(url, this); - connect(m_pDataDownloader, SIGNAL(downloaded()), SLOT(installBonjour())); + m_pDataDownloader->download(url); if (m_DownloadMessageBox == NULL) { m_DownloadMessageBox = new QMessageBox(this); @@ -1104,7 +1082,7 @@ void MainWindow::downloadBonjour() m_DownloadMessageBox->exec(); if (m_DownloadMessageBox->clickedButton() == m_pCancelButton) { - m_pDataDownloader->cancelDownload(); + m_pDataDownloader->cancel(); } #endif } @@ -1115,21 +1093,19 @@ void MainWindow::installBonjour() QString tempLocation = QDesktopServices::storageLocation( QDesktopServices::TempLocation); QString filename = tempLocation; - filename.append("\\").append(bonjourInstaller); + filename.append("\\").append(bonjourTargetFilename); QFile file(filename); if (!file.open(QIODevice::WriteOnly)) { m_DownloadMessageBox->hide(); QMessageBox::warning( this, "Synergy", - "Failed to download Bonjour installer to location: " + - tempLocation + "\n" - "Please download the installer manually from this link: \n" + - bonjourUrl); + tr("Failed to download Bonjour installer to location: %1") + .arg(tempLocation)); return; } - file.write(m_pDataDownloader->downloadedData()); + file.write(m_pDataDownloader->data()); file.close(); QStringList arguments; diff --git a/src/gui/src/MainWindow.h b/src/gui/src/MainWindow.h index 0af1bf4f..3aab49d0 100644 --- a/src/gui/src/MainWindow.h +++ b/src/gui/src/MainWindow.h @@ -83,12 +83,6 @@ class MainWindow : public QMainWindow, public Ui::MainWindowBase Info }; - enum qProcessorArch { - x86, - x64, - unknown - }; - public: MainWindow(QSettings& settings, AppConfig& appConfig); ~MainWindow(); @@ -111,7 +105,6 @@ class MainWindow : public QMainWindow, public Ui::MainWindowBase void autoAddScreen(const QString name); void updateZeroconfService(); void serverDetected(const QString name); - int checkWinArch(); void setEdition(int type); public slots: diff --git a/src/gui/src/PluginManager.cpp b/src/gui/src/PluginManager.cpp new file mode 100644 index 00000000..637b108c --- /dev/null +++ b/src/gui/src/PluginManager.cpp @@ -0,0 +1,207 @@ +/* + * synergy -- mouse and keyboard sharing utility + * Copyright (C) 2015 Synergy Si Ltd. + * + * This package is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * found in the file COPYING that should have accompanied this file. + * + * This package is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#include "PluginManager.h" + +#include "DataDownloader.h" +#include "QUtility.h" +#include "ProcessorArch.h" + +#include +#include +#include +#include +#include + +static const char kGetPluginDirArg[] = "--get-plugin-dir"; + +static QString kPluginsBaseUrl = "http://synergy-project.org/files/plugins/"; +static const char kWinProcessorArch32[] = "Windows-x86"; +static const char kWinProcessorArch64[] = "Windows-x64"; +static const char kMacProcessorArch[] = "MacOSX-i386"; +static const char kLinuxProcessorArch32[] = "Linux-i686"; +static const char kLinuxProcessorArch64[] = "Linux-x86_64"; +#if defined(Q_OS_WIN) +static const char kWinPluginExt[] = ".dll"; +#elif defined(Q_OS_MAC) +static const char kMacPluginPrefix[] = "lib"; +static const char kMacPluginExt[] = ".dylib"; +#else +static const char kLinuxPluginPrefix[] = "lib"; +static const char kLinuxPluginExt[] = ".so"; +#endif + +PluginManager::PluginManager(QStringList pluginList) : + m_PluginList(pluginList), + m_DownloadIndex(-1), + m_pPluginDownloader(NULL) +{ +} + +PluginManager::~PluginManager() +{ + if (m_pPluginDownloader != NULL) { + delete m_pPluginDownloader; + } +} + +void PluginManager::downloadPlugins() +{ + if (m_pPluginDownloader != NULL) { + savePlugin(); + if (m_DownloadIndex != m_PluginList.size() - 1) { + emit downloadNext(); + } + else { + emit downloadFinished(); + return; + } + } + + m_DownloadIndex++; + + if (m_DownloadIndex < m_PluginList.size()) { + QUrl url; + QString pluginUrl = getPluginUrl(m_PluginList.at(m_DownloadIndex)); + url.setUrl(pluginUrl); + + if (m_pPluginDownloader == NULL) { + m_pPluginDownloader = new DataDownloader(); + connect(m_pPluginDownloader, SIGNAL(isComplete()), this, SLOT(downloadPlugins())); + } + m_pPluginDownloader->download(url); + } +} + +void PluginManager::savePlugin() +{ + QString pluginDir = getPluginDir(); + if (pluginDir.isEmpty()) { + return; + } + + QString filename = pluginDir; + QString pluginName = m_PluginList.at(m_DownloadIndex); + pluginName = getPluginOSSpecificName(pluginName); + filename.append(QDir::separator()).append(pluginName); + + QFile file(filename); + if (!file.open(QIODevice::WriteOnly)) { + QMessageBox::warning( + (QWidget*)parent(), "Synergy", + tr("Failed to download plugin %1 to location: %2") + .arg(m_PluginList.at(m_DownloadIndex)) + .arg(pluginDir)); + return; + } + + file.write(m_pPluginDownloader->data()); + file.close(); +} + + +QString PluginManager::getPluginDir() +{ + QString program(QCoreApplication::applicationDirPath() + "/syntool"); + + QProcess process; + process.setReadChannel(QProcess::StandardOutput); + QStringList args(kGetPluginDirArg); + process.start(program, args); + bool success = process.waitForStarted(); + + QString out, error; + if (success) + { + if (process.waitForFinished()) { + out = process.readAllStandardOutput(); + error = process.readAllStandardError(); + } + } + + out = out.trimmed(); + error = error.trimmed(); + + if (out.isEmpty() || + !error.isEmpty() || + !success || + process.exitCode() != 0) + { + QMessageBox::critical( + (QWidget*)parent(), tr("Synergy"), + tr("An error occured while trying to get " + "plugin directory from syntool. Code: %1\nError: %2") + .arg(process.exitCode()) + .arg(error.isEmpty() ? "Unknown" : error)); + return ""; + } + + // create the path if not exist + // TODO: synergy folder should be hidden + QDir dir(out); + if (!dir.exists()) { + dir.mkpath("."); + } + + return out; +} + +QString PluginManager::getPluginUrl(const QString& pluginName) +{ + QString result; + result = kPluginsBaseUrl.append(pluginName).append("/1.0/"); + + int arch = checkProcessorArch(); + if (arch == Win_x86) { + result.append(kWinProcessorArch32); + } + else if (arch == Win_x64) { + result.append(kWinProcessorArch64); + } + else if (arch == Mac_i386) { + result.append(kMacProcessorArch); + } + else if (arch == Linux_i686) { + result.append(kLinuxProcessorArch32); + } + else if (arch == Linux_x86_64) { + result.append(kLinuxProcessorArch64); + } + else { + QMessageBox::critical( + (QWidget*)parent(), tr("Synergy"), + tr("Failed to detect system architecture.")); + return ""; + } + result.append("/"); + result.append(getPluginOSSpecificName(pluginName)); + + return result; +} + +QString PluginManager::getPluginOSSpecificName(const QString& pluginName) +{ + QString result = pluginName; +#if defined(Q_OS_WIN) + result.append(kWinPluginExt); +#elif defined(Q_OS_MAC) + result = kMacPluginPrefix + pluginName + kMacPluginExt; +#else + result = kLinuxPluginPrefix + pluginName + kLinuxPluginExt; +#endif + return result; +} diff --git a/src/gui/src/PluginManager.h b/src/gui/src/PluginManager.h new file mode 100644 index 00000000..07038db2 --- /dev/null +++ b/src/gui/src/PluginManager.h @@ -0,0 +1,56 @@ +/* + * synergy -- mouse and keyboard sharing utility + * Copyright (C) 2015 Synergy Si Ltd. + * + * This package is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * found in the file COPYING that should have accompanied this file. + * + * This package is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef PLUGINMANAGER_H +#define PLUGINMANAGER_H + +#include +#include +#include + +class DataDownloader; + +class PluginManager: public QObject +{ + Q_OBJECT + +public: + PluginManager(QStringList pluginList); + ~PluginManager(); + + int downloadIndex() { return m_DownloadIndex; } + +public slots: + void downloadPlugins(); + +private: + void savePlugin(); + QString getPluginDir(); + QString getPluginUrl(const QString& pluginName); + QString getPluginOSSpecificName(const QString& pluginName); + +signals: + void downloadNext(); + void downloadFinished(); + +private: + QStringList m_PluginList; + int m_DownloadIndex; + DataDownloader* m_pPluginDownloader; +}; + +#endif // PLUGINMANAGER_H diff --git a/src/gui/src/PluginWizardPage.cpp b/src/gui/src/PluginWizardPage.cpp index e9037887..4007cd56 100644 --- a/src/gui/src/PluginWizardPage.cpp +++ b/src/gui/src/PluginWizardPage.cpp @@ -2,6 +2,7 @@ #include "ui_PluginWizardPageBase.h" #include "WebClient.h" +#include "PluginManager.h" #include #include @@ -9,7 +10,8 @@ PluginWizardPage::PluginWizardPage(QWidget *parent) : QWizardPage(parent), m_Finished(false), - m_pWebClient(NULL) + m_pWebClient(NULL), + m_pPluginManager(NULL) { setupUi(this); @@ -23,24 +25,28 @@ PluginWizardPage::~PluginWizardPage() if (m_pWebClient != NULL) { delete m_pWebClient; } + + if (m_pPluginManager != NULL) { + delete m_pPluginManager; + } } void PluginWizardPage::changeEvent(QEvent *e) { - QWizardPage::changeEvent(e); - switch (e->type()) { - case QEvent::LanguageChange: + QWizardPage::changeEvent(e); + switch (e->type()) { + case QEvent::LanguageChange: retranslateUi(this); - break; - default: - break; - } + break; + default: + break; + } } void PluginWizardPage::queryPluginDone() { - QStringList plguinList = m_pWebClient->getPluginList(); - if (plguinList.isEmpty()) { + QStringList pluginList = m_pWebClient->getPluginList(); + if (pluginList.isEmpty()) { if (!m_pWebClient->getLastError().isEmpty()) { updateStatus(m_pWebClient->getLastError()); m_Finished = true; @@ -48,15 +54,73 @@ void PluginWizardPage::queryPluginDone() } } else { - updateStatus(plguinList.at(0)); + downloadPlugins(); } } +void PluginWizardPage::updateDownloadStatus() +{ + QStringList pluginList = m_pWebClient->getPluginList(); + int index = m_pPluginManager->downloadIndex(); + updateStatus( + tr("Downloading plugin: %1 (%2/%3)") + .arg(pluginList.at(index + 1)) + .arg(index + 2) + .arg(pluginList.size())); +} + +void PluginWizardPage::finished() +{ + updateStatus(tr("Plugins are ready.")); + stopSpinning(); + m_Finished = true; + emit completeChanged(); +} + void PluginWizardPage::updateStatus(QString info) { m_pLabelStatus->setText(info); } +void PluginWizardPage::downloadPlugins() +{ + QStringList pluginList = m_pWebClient->getPluginList(); + m_pPluginManager = new PluginManager(pluginList); + QThread* thread = new QThread; + + connect(m_pPluginManager, + SIGNAL(downloadNext()), + this, + SLOT(updateDownloadStatus())); + + connect(m_pPluginManager, + SIGNAL(downloadFinished()), + this, + SLOT(finished())); + + connect(m_pPluginManager, + SIGNAL(downloadFinished()), + thread, + SLOT(quit())); + + connect(thread, + SIGNAL(finished()), + thread, + SLOT(deleteLater())); + + updateStatus( + tr("Downloading plugin: %1 (1/%2)") + .arg(pluginList.at(0)) + .arg(pluginList.size())); + + QMetaObject::invokeMethod(m_pPluginManager, "downloadPlugins", Qt::QueuedConnection); +} + +void PluginWizardPage::stopSpinning() +{ + m_pLabelSpinning->hide(); +} + bool PluginWizardPage::isComplete() const { return m_Finished; @@ -69,13 +133,15 @@ void PluginWizardPage::initializePage() if (m_Email.isEmpty() || m_Password.isEmpty()) { updateStatus("No plugin available."); - //TODO: stop spinning icon + stopSpinning(); m_Finished = true; emit completeChanged(); return; } + m_pLabelSpinning->show(); + m_pWebClient = new WebClient(); m_pWebClient->setEmail(m_Email); m_pWebClient->setPassword(m_Password); @@ -86,7 +152,11 @@ void PluginWizardPage::initializePage() this, SLOT(queryPluginDone())); - connect(m_pWebClient, SIGNAL(queryPluginDone()), thread, SLOT(quit())); + connect(m_pWebClient, + SIGNAL(queryPluginDone()), + thread, + SLOT(quit())); + connect(thread, SIGNAL(finished()), thread, SLOT(deleteLater())); m_pWebClient->moveToThread(thread); diff --git a/src/gui/src/PluginWizardPage.h b/src/gui/src/PluginWizardPage.h index ed7163bf..49ff4944 100644 --- a/src/gui/src/PluginWizardPage.h +++ b/src/gui/src/PluginWizardPage.h @@ -5,6 +5,7 @@ #include class WebClient; +class PluginManager; class PluginWizardPage : public QWizardPage, public Ui::PluginWizardPage { @@ -26,14 +27,19 @@ protected: protected slots: void queryPluginDone(); + void updateDownloadStatus(); + void finished(); private: void updateStatus(QString info); + void downloadPlugins(); + void stopSpinning(); private: bool m_Finished; - WebClient* m_pWebClient; QString m_Email; QString m_Password; + WebClient* m_pWebClient; + PluginManager* m_pPluginManager; }; #endif // PLUGINWIZARDPAGE_H diff --git a/src/gui/src/ProcessorArch.h b/src/gui/src/ProcessorArch.h new file mode 100644 index 00000000..61c60d65 --- /dev/null +++ b/src/gui/src/ProcessorArch.h @@ -0,0 +1,30 @@ +/* + * synergy -- mouse and keyboard sharing utility + * Copyright (C) 2015 Synergy Si Ltd. + * + * This package is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * found in the file COPYING that should have accompanied this file. + * + * This package is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef PROCESSORARCH_H +#define PROCESSORARCH_H + +enum qProcessorArch { + Win_x86, + Win_x64, + Mac_i386, + Linux_i686, + Linux_x86_64, + unknown +}; + +#endif // PROCESSORARCH_H diff --git a/src/gui/src/QUtility.cpp b/src/gui/src/QUtility.cpp index aad274c3..c9902cf0 100644 --- a/src/gui/src/QUtility.cpp +++ b/src/gui/src/QUtility.cpp @@ -17,6 +17,23 @@ #include "QUtility.h" +#include "ProcessorArch.h" + +#if defined(Q_OS_LINUX) +#include +#endif + +#if defined(Q_OS_WIN) +#define _WIN32_WINNT 0x0501 +#define WIN32_LEAN_AND_MEAN +#include +#endif + +#if defined(Q_OS_LINUX) +static const char kLinuxI686[] = "i686"; +static const char kLinuxX8664[] = "x86_64"; +#endif + void setIndexFromItemData(QComboBox* comboBox, const QVariant& itemData) { for (int i = 0; i < comboBox->count(); ++i) @@ -49,3 +66,59 @@ QString getFirstMacAddress() } return mac; } + +int checkProcessorArch() +{ +#if defined(Q_OS_WIN) + SYSTEM_INFO systemInfo; + GetNativeSystemInfo(&systemInfo); + + switch (systemInfo.wProcessorArchitecture) { + case PROCESSOR_ARCHITECTURE_INTEL: + return Win_x86; + case PROCESSOR_ARCHITECTURE_IA64: + return Win_x64; + case PROCESSOR_ARCHITECTURE_AMD64: + return Win_x64; + default: + return unknown; + } +#elif defined(Q_OS_MAC) + return Mac_i386; +#else + QString program("uname"); + QStringList args("-m"); + QProcess process; + process.setReadChannel(QProcess::StandardOutput); + process.start(program, args); + bool success = process.waitForStarted(); + + QString out, error; + if (success) + { + if (process.waitForFinished()) { + out = process.readAllStandardOutput(); + error = process.readAllStandardError(); + } + } + + out = out.trimmed(); + error = error.trimmed(); + + if (out.isEmpty() || + !error.isEmpty() || + !success || + process.exitCode() != 0) + { + return unknown; + } + + if (out == kLinuxI686) { + return Linux_i686; + } + else if (out == kLinuxX8664) { + return Linux_x86_64; + } +#endif + return unknown; +} diff --git a/src/gui/src/QUtility.h b/src/gui/src/QUtility.h index 2cbd7a57..d000c15e 100644 --- a/src/gui/src/QUtility.h +++ b/src/gui/src/QUtility.h @@ -25,3 +25,4 @@ void setIndexFromItemData(QComboBox* comboBox, const QVariant& itemData); QString hash(const QString& string); QString getFirstMacAddress(); +int checkProcessorArch(); diff --git a/src/lib/arch/IArchFile.h b/src/lib/arch/IArchFile.h index 7b2ef16b..517fbf99 100644 --- a/src/lib/arch/IArchFile.h +++ b/src/lib/arch/IArchFile.h @@ -62,6 +62,12 @@ public: */ virtual std::string getLogDirectory() = 0; + //! Get plugins directory + /*! + Returns the plugin files directory. + */ + virtual std::string getPluginDirectory() = 0; + //! Concatenate path components /*! Concatenate pathname components with a directory separator diff --git a/src/lib/arch/unix/ArchFileUnix.cpp b/src/lib/arch/unix/ArchFileUnix.cpp index 0dd84636..ff6ed0c4 100644 --- a/src/lib/arch/unix/ArchFileUnix.cpp +++ b/src/lib/arch/unix/ArchFileUnix.cpp @@ -104,6 +104,16 @@ ArchFileUnix::getLogDirectory() return "/var/log"; } +std::string +ArchFileUnix::getPluginDirectory() +{ +#if WINAPI_XWINDOWS + return getUserDirectory().append("/.synergy/plugins"); +#else + return getUserDirectory().append("/Libraries/Synergy/Plugins"); +#endif +} + std::string ArchFileUnix::concatPath(const std::string& prefix, const std::string& suffix) diff --git a/src/lib/arch/unix/ArchFileUnix.h b/src/lib/arch/unix/ArchFileUnix.h index 200ae60b..2818d26b 100644 --- a/src/lib/arch/unix/ArchFileUnix.h +++ b/src/lib/arch/unix/ArchFileUnix.h @@ -34,6 +34,7 @@ public: virtual std::string getSystemDirectory(); virtual std::string getInstalledDirectory(); virtual std::string getLogDirectory(); + virtual std::string getPluginDirectory(); virtual std::string concatPath(const std::string& prefix, const std::string& suffix); }; diff --git a/src/lib/arch/win32/ArchFileWindows.cpp b/src/lib/arch/win32/ArchFileWindows.cpp index 81455d60..ec1fabe8 100644 --- a/src/lib/arch/win32/ArchFileWindows.cpp +++ b/src/lib/arch/win32/ArchFileWindows.cpp @@ -139,6 +139,14 @@ ArchFileWindows::getLogDirectory() return getInstalledDirectory(); } +std::string +ArchFileWindows::getPluginDirectory() +{ + std::string dir = getUserDirectory(); + dir.append("\\Synergy\\Plugins"); + return dir; +} + std::string ArchFileWindows::concatPath(const std::string& prefix, const std::string& suffix) diff --git a/src/lib/arch/win32/ArchFileWindows.h b/src/lib/arch/win32/ArchFileWindows.h index 8c1e63cc..c4745073 100644 --- a/src/lib/arch/win32/ArchFileWindows.h +++ b/src/lib/arch/win32/ArchFileWindows.h @@ -34,6 +34,7 @@ public: virtual std::string getSystemDirectory(); virtual std::string getInstalledDirectory(); virtual std::string getLogDirectory(); + virtual std::string getPluginDirectory(); virtual std::string concatPath(const std::string& prefix, const std::string& suffix); }; diff --git a/src/lib/synergy/ArgParser.cpp b/src/lib/synergy/ArgParser.cpp index d20772dd..6f0307a9 100644 --- a/src/lib/synergy/ArgParser.cpp +++ b/src/lib/synergy/ArgParser.cpp @@ -173,6 +173,10 @@ ArgParser::parseToolArgs(ToolArgs& args, int argc, const char* const* argv) args.m_getPluginList = true; return true; } + if (isArg(i, argc, argv, NULL, "--get-plugin-dir", 0)) { + args.m_getPluginDir = true; + return true; + } else { return false; } diff --git a/src/lib/synergy/ToolApp.cpp b/src/lib/synergy/ToolApp.cpp index 02d35b71..a7d4a88b 100644 --- a/src/lib/synergy/ToolApp.cpp +++ b/src/lib/synergy/ToolApp.cpp @@ -73,6 +73,9 @@ ToolApp::run(int argc, char** argv) else if (m_args.m_getPluginList) { getPluginList(); } + else if (m_args.m_getPluginDir) { + std::cout << ARCH->getPluginDirectory() << std::endl; + } else { throw XSynergy("Nothing to do"); } diff --git a/src/lib/synergy/ToolArgs.cpp b/src/lib/synergy/ToolArgs.cpp index 5b46e3b9..6155a9e8 100644 --- a/src/lib/synergy/ToolArgs.cpp +++ b/src/lib/synergy/ToolArgs.cpp @@ -20,6 +20,7 @@ ToolArgs::ToolArgs() : m_printActiveDesktopName(false), m_loginAuthenticate(false), - m_getPluginList(false) + m_getPluginList(false), + m_getPluginDir(false) { } diff --git a/src/lib/synergy/ToolArgs.h b/src/lib/synergy/ToolArgs.h index bef5d64e..c820f3f5 100644 --- a/src/lib/synergy/ToolArgs.h +++ b/src/lib/synergy/ToolArgs.h @@ -27,4 +27,5 @@ public: bool m_printActiveDesktopName; bool m_loginAuthenticate; bool m_getPluginList; + bool m_getPluginDir; };