diff --git a/src/gui/src/MainWindow.cpp b/src/gui/src/MainWindow.cpp index 1ecfde01..fa09d8ad 100644 --- a/src/gui/src/MainWindow.cpp +++ b/src/gui/src/MainWindow.cpp @@ -1351,3 +1351,12 @@ QString MainWindow::getProfileRootForArg() return QString("\"%1\"").arg(dir); } + +void MainWindow::delay(unsigned int s) +{ + QTime dieTime= QTime::currentTime().addSecs(s); + + while( QTime::currentTime() < dieTime ) { + QCoreApplication::processEvents(QEventLoop::AllEvents, 100); + } +} diff --git a/src/gui/src/MainWindow.h b/src/gui/src/MainWindow.h index 80b1dbb4..7f81d177 100644 --- a/src/gui/src/MainWindow.h +++ b/src/gui/src/MainWindow.h @@ -63,6 +63,7 @@ class MainWindow : public QMainWindow, public Ui::MainWindowBase friend class QSynergyApplication; friend class SetupWizard; + friend class PluginWizardPage; public: enum qSynergyState @@ -108,6 +109,7 @@ class MainWindow : public QMainWindow, public Ui::MainWindowBase void serverDetected(const QString name); void setEdition(int type); void updateLocalFingerprint(); + void delay(unsigned int); public slots: void appendLogRaw(const QString& text); diff --git a/src/gui/src/PluginWizardPage.cpp b/src/gui/src/PluginWizardPage.cpp index 9c2994a6..331d6a0c 100644 --- a/src/gui/src/PluginWizardPage.cpp +++ b/src/gui/src/PluginWizardPage.cpp @@ -22,16 +22,18 @@ #include "FileSysClient.h" #include "WebClient.h" #include "PluginManager.h" +#include "MainWindow.h" #include #include +#include -PluginWizardPage::PluginWizardPage(AppConfig& appConfig, QWidget *parent) : +PluginWizardPage::PluginWizardPage(MainWindow& mainWindow, QWidget *parent) : QWizardPage(parent), m_Finished(false), m_pFileSysClient(NULL), m_pSslCertificate(NULL), - m_AppConfig(appConfig) + m_mainWindow(mainWindow) { setupUi(this); @@ -77,14 +79,18 @@ void PluginWizardPage::queryPluginDone() showFinished(); } else { + m_mainWindow.stopSynergy(); + m_mainWindow.delay(5); copyPlugins(); + m_mainWindow.startSynergy(); + m_mainWindow.delay(5); } } void PluginWizardPage::finished() { // TODO: we should check if ns plugin exists - m_AppConfig.setCryptoEnabled(true); + m_mainWindow.appConfig().setCryptoEnabled(true); updateStatus(tr("Plugins installed successfully.")); showFinished(); diff --git a/src/gui/src/PluginWizardPage.h b/src/gui/src/PluginWizardPage.h index dbd834b7..8b2006b7 100644 --- a/src/gui/src/PluginWizardPage.h +++ b/src/gui/src/PluginWizardPage.h @@ -27,13 +27,14 @@ class FileSysClient; class WebClient; class SslCertificate; +class MainWindow; class PluginWizardPage : public QWizardPage, public Ui::PluginWizardPage { Q_OBJECT public: - PluginWizardPage(AppConfig& appConfig, QWidget *parent = 0); + PluginWizardPage(MainWindow& mainWindow, QWidget *parent = 0); ~PluginWizardPage(); void setFinished(bool b) { m_Finished = b; } @@ -66,6 +67,6 @@ private: PluginManager m_PluginManager; SslCertificate* m_pSslCertificate; QThread* m_pThread; - AppConfig& m_AppConfig; + MainWindow& m_mainWindow; }; #endif // PLUGINWIZARDPAGE_H diff --git a/src/gui/src/SetupWizard.cpp b/src/gui/src/SetupWizard.cpp index b4414142..5bb400fb 100644 --- a/src/gui/src/SetupWizard.cpp +++ b/src/gui/src/SetupWizard.cpp @@ -30,7 +30,7 @@ SetupWizard::SetupWizard(MainWindow& mainWindow, bool startMain) : m_Edition(Unknown) { setupUi(this); - m_pPluginPage = new PluginWizardPage(mainWindow.appConfig()); + m_pPluginPage = new PluginWizardPage(mainWindow); addPage(m_pPluginPage); #if defined(Q_OS_MAC) diff --git a/src/lib/arch/unix/ArchPluginUnix.cpp b/src/lib/arch/unix/ArchPluginUnix.cpp index 3e390f06..bba2b017 100644 --- a/src/lib/arch/unix/ArchPluginUnix.cpp +++ b/src/lib/arch/unix/ArchPluginUnix.cpp @@ -35,6 +35,7 @@ typedef void (*cleanupFunc)(); void* g_eventTarget = NULL; IEventQueue* g_events = NULL; +static const char kPre174Plugin[] = "Pre-1.7.4"; ArchPluginUnix::ArchPluginUnix() { @@ -82,7 +83,13 @@ ArchPluginUnix::load() String filename = synergy::string::removeFileExt(*it); m_pluginTable.insert(std::make_pair(filename, library)); - LOG((CLOG_DEBUG "loaded plugin: %s", (*it).c_str())); + + const char * version = (char*)invoke( filename.c_str(),"version",NULL); + if (version == NULL) { + version = kPre174Plugin; + } + + LOG((CLOG_DEBUG "loaded plugin: %s (%s)", (*it).c_str(),version)); } } diff --git a/src/lib/arch/win32/ArchPluginWindows.cpp b/src/lib/arch/win32/ArchPluginWindows.cpp index 1f560e06..37440d7c 100644 --- a/src/lib/arch/win32/ArchPluginWindows.cpp +++ b/src/lib/arch/win32/ArchPluginWindows.cpp @@ -34,6 +34,7 @@ typedef void (*cleanupFunc)(); void* g_eventTarget = NULL; IEventQueue* g_events = NULL; +static const char * kPre174Plugin = "Pre-1.7.v"; ArchPluginWindows::ArchPluginWindows() { @@ -69,9 +70,9 @@ ArchPluginWindows::load() String filename = synergy::string::removeFileExt(*it); m_pluginTable.insert(std::make_pair(filename, lib)); - char * version = (char*)invoke( filename.c_str(),"version",NULL); + const char * version = (char*)invoke( filename.c_str(),"version",NULL); if (version == NULL) { - version = "Pre-1.7.4"; + version = kPre174Plugin; } LOG((CLOG_DEBUG "loaded plugin: %s (%s)", (*it).c_str(),version)); diff --git a/src/lib/plugin/ns/SecureSocket.cpp b/src/lib/plugin/ns/SecureSocket.cpp index b753188a..40c3f219 100644 --- a/src/lib/plugin/ns/SecureSocket.cpp +++ b/src/lib/plugin/ns/SecureSocket.cpp @@ -299,6 +299,7 @@ SecureSocket::secureAccept(int socket) LOG((CLOG_INFO "client connection may not be secure")); m_secureReady = false; ARCH->sleep(1); + retry = 0; return -1; // Failed, error out } @@ -342,6 +343,7 @@ SecureSocket::secureConnect(int socket) if (isFatal()) { LOG((CLOG_ERR "failed to connect secure socket")); + retry = 0; return -1; } @@ -352,6 +354,7 @@ SecureSocket::secureConnect(int socket) return 0; } + retry = 0; // No error, set ready, process and return ok m_secureReady = true; if (verifyCertFingerprint()) { @@ -417,23 +420,29 @@ SecureSocket::checkResult(int status, int& retry) break; case SSL_ERROR_WANT_READ: - m_readable = true; retry++; LOG((CLOG_DEBUG2 "want to read, error=%d, attempt=%d", errorCode, retry)); break; case SSL_ERROR_WANT_WRITE: + // Need to make sure the socket is known to be writable so the impending + // select action actually triggers on a write. This isn't necessary for + // m_readable because the socket logic is always readable m_writable = true; retry++; LOG((CLOG_DEBUG2 "want to write, error=%d, attempt=%d", errorCode, retry)); break; case SSL_ERROR_WANT_CONNECT: - case SSL_ERROR_WANT_ACCEPT: retry++; LOG((CLOG_DEBUG2 "want to connect, error=%d, attempt=%d", errorCode, retry)); break; + case SSL_ERROR_WANT_ACCEPT: + retry++; + LOG((CLOG_DEBUG2 "want to accept, error=%d, attempt=%d", errorCode, retry)); + break; + case SSL_ERROR_SYSCALL: LOG((CLOG_ERR "ssl error occurred (system call failure)")); if (ERR_peek_error() == 0) { @@ -595,14 +604,20 @@ SecureSocket::serviceConnect(ISocketMultiplexerJob* job, status = secureConnect(getSocket()->m_fd); #endif + // If status < 0, error happened + if (status < 0) { + return NULL; + } + + // If status > 0, success if (status > 0) { return newJob(); } - else if (status == 0) { - return job; - } - // If status < 0, error happened - return NULL; + + // Retry case + return new TSocketMultiplexerMethodJob( + this, &SecureSocket::serviceConnect, + getSocket(), isReadable(), isWritable()); } ISocketMultiplexerJob* @@ -617,15 +632,20 @@ SecureSocket::serviceAccept(ISocketMultiplexerJob* job, #elif SYSAPI_UNIX status = secureAccept(getSocket()->m_fd); #endif + // If status < 0, error happened + if (status < 0) { + return NULL; + } + // If status > 0, success if (status > 0) { return newJob(); } - else if (status == 0) { - return job; - } - // If status < 0, error happened - return NULL; + + // Retry case + return new TSocketMultiplexerMethodJob( + this, &SecureSocket::serviceAccept, + getSocket(), isReadable(), isWritable()); } void