Show message box explaining why settings are read-only (#7437)

* Swap assert for warning log lines

* Flush on IPC write

* Flush on cleanup instead of write

* Record core started setting

* Show server first start message

* Show message when active scope is read-only

* Show read only message on change

* Show read only on window show

* Try to improve main window size policy

* Revert addition of resizer

* Remove redundant file path fiddling

* Remove dead code and fixed missing const

* Print path and use queued connection

* Improve read-only message on Windows

* Only show toggle warning when dialog visible

* Update ChangeLog

* Fixed include
This commit is contained in:
Nick Bolton 2024-08-12 16:39:18 +01:00 committed by GitHub
parent 30ea95fb3d
commit 9464aa46b8
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
25 changed files with 277 additions and 106 deletions

View file

@ -79,6 +79,7 @@ Enhancements:
- #7434 Show dark logo in dark mode and improve .env loader
- #7435 Add reset settings menu action and env var
- #7436 Introduced new env vars for testing
- #7437 Show message box explaining why settings are read-only
# 1.14.6

View file

@ -799,7 +799,7 @@ void MainWindow::closeEvent(QCloseEvent *event) {
qDebug("window should hide to tray");
}
void MainWindow::showFirstRunMessage() {
void MainWindow::showFirstConnectedMessage() {
if (m_AppConfig.startedBefore()) {
return;
}
@ -808,7 +808,7 @@ void MainWindow::showFirstRunMessage() {
m_ConfigScopes.save();
const auto isServer = m_CoreProcess.mode() == CoreMode::Server;
messages::showFirstRunMessage(
messages::showFirstConnectedMessage(
this, m_AppConfig.closeToTray(), m_AppConfig.enableService(), isServer);
}
@ -887,10 +887,14 @@ void MainWindow::updateStatus() {
}
void MainWindow::onCoreProcessStateChanged(CoreProcessState state) {
qDebug("core process state changed: %d", static_cast<int>(state));
updateStatus();
if (state == CoreProcessState::Started) {
qDebug("recording that core has started");
m_AppConfig.setStartedBefore(true);
m_ConfigScopes.save();
}
if (state == CoreProcessState::Started ||
state == CoreProcessState::Starting) {
disconnect(
@ -933,7 +937,7 @@ void MainWindow::onCoreConnectionStateChanged(CoreConnectionState state) {
if (state != CoreConnectionState::Connected) {
secureSocket(false);
} else if (isVisible()) {
showFirstRunMessage();
showFirstConnectedMessage();
showDevThanksMessage();
}
}
@ -1127,12 +1131,21 @@ void MainWindow::enableServer(bool enable) {
m_AppConfig.setServerGroupChecked(enable);
m_pRadioGroupServer->setChecked(enable);
m_pWidgetServer->setEnabled(enable);
m_pWidgetServerInverse->setVisible(m_AppConfig.invertConnection());
m_pWidgetServerInput->setVisible(m_AppConfig.invertConnection());
if (enable) {
m_pButtonToggleStart->setEnabled(true);
m_pActionStartCore->setEnabled(true);
m_CoreProcess.setMode(CoreProcess::Mode::Server);
// The server can run without any clients configured, and this is actually
// what you'll want to do the first time since you'll be prompted when an
// unrecognized client tries to connect.
if (!m_AppConfig.startedBefore()) {
qDebug("auto-starting core server for first time");
m_CoreProcess.start();
messages::showFirstServerStartMessage(this);
}
}
}
@ -1140,8 +1153,8 @@ void MainWindow::enableClient(bool enable) {
qDebug(enable ? "client enabled" : "client disabled");
m_AppConfig.setClientGroupChecked(enable);
m_pRadioGroupClient->setChecked(enable);
m_pWidgetClient->setEnabled(enable);
m_pWidgetClient->setVisible(!m_AppConfig.invertConnection());
m_pWidgetClientInput->setEnabled(enable);
m_pWidgetClientInput->setVisible(!m_AppConfig.invertConnection());
if (enable) {
m_pButtonToggleStart->setEnabled(true);

View file

@ -176,7 +176,7 @@ private:
void setupControls();
void resizeEvent(QResizeEvent *event) override;
void moveEvent(QMoveEvent *event) override;
void showFirstRunMessage();
void showFirstConnectedMessage();
void showDevThanksMessage();
QString productName() const;
void updateStatus();

View file

@ -110,29 +110,49 @@
<property name="spacing">
<number>15</number>
</property>
<item>
<layout class="QVBoxLayout" name="verticalLayout_3">
<property name="spacing">
<number>0</number>
<item alignment="Qt::AlignTop">
<widget class="QWidget" name="m_pWidgetServerRadio" native="true">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<item>
<widget class="QRadioButton" name="m_pRadioGroupServer">
<property name="text">
<string>Use this computer's keyboard and mouse</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>(make this computer the server)</string>
</property>
<property name="indent">
<number>20</number>
</property>
</widget>
</item>
</layout>
<layout class="QVBoxLayout" name="verticalLayout_3">
<property name="spacing">
<number>0</number>
</property>
<property name="leftMargin">
<number>0</number>
</property>
<property name="topMargin">
<number>0</number>
</property>
<property name="rightMargin">
<number>0</number>
</property>
<property name="bottomMargin">
<number>0</number>
</property>
<item>
<widget class="QRadioButton" name="m_pRadioGroupServer">
<property name="text">
<string>Use this computer's keyboard and mouse</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>(make this computer the server)</string>
</property>
<property name="indent">
<number>20</number>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item alignment="Qt::AlignTop">
<widget class="QWidget" name="m_pWidgetServer" native="true">
@ -153,7 +173,7 @@
<number>0</number>
</property>
<item>
<widget class="QWidget" name="m_pWidgetServerInverse" native="true">
<widget class="QWidget" name="m_pWidgetServerInput" native="true">
<layout class="QVBoxLayout" name="m_pLayoutServerInverse">
<property name="spacing">
<number>15</number>
@ -231,7 +251,7 @@
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
<height>1</height>
</size>
</property>
</spacer>
@ -278,32 +298,52 @@
<property name="spacing">
<number>15</number>
</property>
<item>
<layout class="QVBoxLayout" name="verticalLayout_6">
<property name="spacing">
<number>0</number>
<item alignment="Qt::AlignTop">
<widget class="QWidget" name="m_pWidgetClientRadio" native="true">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<item>
<widget class="QRadioButton" name="m_pRadioGroupClient">
<property name="text">
<string>Use another computer’s mouse and keyboard</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label_2">
<property name="text">
<string>(make this computer the client)</string>
</property>
<property name="indent">
<number>20</number>
</property>
</widget>
</item>
</layout>
<layout class="QVBoxLayout" name="verticalLayout_6">
<property name="spacing">
<number>0</number>
</property>
<property name="leftMargin">
<number>0</number>
</property>
<property name="topMargin">
<number>0</number>
</property>
<property name="rightMargin">
<number>0</number>
</property>
<property name="bottomMargin">
<number>0</number>
</property>
<item>
<widget class="QRadioButton" name="m_pRadioGroupClient">
<property name="text">
<string>Use another computer’s mouse and keyboard</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label_2">
<property name="text">
<string>(make this computer the client)</string>
</property>
<property name="indent">
<number>20</number>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item alignment="Qt::AlignTop">
<widget class="QWidget" name="m_pWidgetClient" native="true">
<widget class="QWidget" name="m_pWidgetClientInput" native="true">
<layout class="QVBoxLayout" name="m_pLayoutClient">
<property name="spacing">
<number>15</number>
@ -378,7 +418,7 @@
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
<height>1</height>
</size>
</property>
</spacer>

View file

@ -50,8 +50,6 @@ public:
static void msleep(unsigned long msecs) { QThread::msleep(msecs); }
};
QString getSystemSettingPath();
#if defined(Q_OS_MAC)
bool checkMacAssistiveDevices();
#endif

View file

@ -20,7 +20,7 @@
#include <QByteArray>
#include <QDataStream>
#include <QIODevice>
#include <qlogging.h>
#include <QtGlobal>
namespace synergy::gui {

View file

@ -394,6 +394,8 @@ void AppConfig::loadScope(ConfigScopes::Scope scope) {
m_Scopes.setActiveScope(scope);
qDebug("active scope file path: %s", qPrintable(m_Scopes.activeFilePath()));
// only signal ready if there is at least one setting in the required scope.
// this prevents the current settings from being set back to default.
if (m_Scopes.scopeContains(
@ -443,7 +445,7 @@ void AppConfig::persistLogDir() const {
// Begin getters
///////////////////////////////////////////////////////////////////////////////
IConfigScopes &AppConfig::scopes() { return m_Scopes; }
IConfigScopes &AppConfig::scopes() const { return m_Scopes; }
bool AppConfig::activationHasRun() const { return m_ActivationHasRun; }

View file

@ -126,7 +126,6 @@ public:
IConfigScopes &scopes,
std::shared_ptr<Deps> deps = std::make_shared<Deps>());
IConfigScopes &scopes();
void determineScope();
/**
@ -139,6 +138,7 @@ public:
// Getters (overrides)
//
IConfigScopes &scopes() const override;
ProcessMode processMode() const override;
ElevateMode elevateMode() const override;
bool tlsEnabled() const override;
@ -189,6 +189,7 @@ public:
//
// Setters (overrides)
//
void setScreenName(const QString &s) override;
void setPort(int i) override;
void setNetworkInterface(const QString &s) override;
@ -211,9 +212,9 @@ public:
// Setters (new methods)
//
void setStartedBefore(bool b);
void setActivationHasRun(bool value);
void setWizardHasRun();
void setStartedBefore(bool b);
void setSerialKey(const QString &serialKey);
void clearSerialKey();
void setLicenseNextCheck(unsigned long long);

View file

@ -59,7 +59,7 @@ public:
Scope activeScope() const override;
QSettingsProxy &activeSettings() override;
const QSettingsProxy &activeSettings() const override;
QString activeFilePath() const;
QString activeFilePath() const override;
signals:
void ready();

View file

@ -19,6 +19,8 @@
#include "ElevateMode.h"
#include "gui/config/IConfigScopes.h"
#include <QString>
namespace synergy::gui {
@ -26,13 +28,16 @@ namespace synergy::gui {
enum class ProcessMode { kService, kDesktop };
class IAppConfig {
using IConfigScopes = synergy::gui::IConfigScopes;
public:
virtual ~IAppConfig() = default;
//
// Setters
// Getters
//
virtual IConfigScopes &scopes() const = 0;
virtual QString tlsCertPath() const = 0;
virtual int tlsKeyLength() const = 0;
virtual bool tlsEnabled() const = 0;
@ -64,7 +69,7 @@ public:
virtual bool clientGroupChecked() const = 0;
//
// Getters
// Setters
//
virtual void setLoadFromSystemScope(bool loadFromSystemScope) = 0;

View file

@ -38,6 +38,7 @@ public:
virtual bool isActiveScopeWritable() const = 0;
virtual QSettingsProxy &activeSettings() = 0;
virtual const QSettingsProxy &activeSettings() const = 0;
virtual QString activeFilePath() const = 0;
/**
* @brief Signals to listeners that the settings that they should read.

View file

@ -35,6 +35,7 @@
#include <QRegularExpression>
#include <QStandardPaths>
#include <QTimer>
#include <QtGlobal>
using namespace synergy::license;
using namespace synergy::gui::license;
@ -59,7 +60,25 @@ QString processModeToString(ProcessMode mode) {
return "service";
default:
qFatal("invalid process mode");
return "";
abort();
}
}
QString processStateToString(CoreProcess::ProcessState state) {
using enum CoreProcess::ProcessState;
switch (state) {
case Starting:
return "starting";
case Started:
return "started";
case Stopping:
return "stopping";
case Stopped:
return "stopped";
default:
qFatal("invalid process state");
abort();
}
}
@ -139,8 +158,8 @@ QString CoreProcess::Deps::getProfileRoot() const {
//
CoreProcess::CoreProcess(
IAppConfig &appConfig, IServerConfig &serverConfig, const ILicense &license,
std::shared_ptr<Deps> deps)
const IAppConfig &appConfig, const IServerConfig &serverConfig,
const ILicense &license, std::shared_ptr<Deps> deps)
: m_appConfig(appConfig),
m_serverConfig(serverConfig),
m_license(license),
@ -175,7 +194,9 @@ void CoreProcess::onIpcClientServiceReady() {
qDebug("service ready, continuing core process stop");
stop();
} else {
qCritical("service ready, but process state is not starting or stopping");
// This may happen when the IPC connection fails and then reconnects.
qWarning(
"ignoring service ready, process state is not starting or stopping");
}
}
@ -644,6 +665,10 @@ void CoreProcess::setProcessState(ProcessState state) {
return;
}
qDebug(
"core process state changed: %s -> %s", //
qPrintable(processStateToString(m_processState)),
qPrintable(processStateToString(state)));
m_processState = state;
emit processStateChanged(state);
}

View file

@ -59,7 +59,7 @@ public:
enum class ConnectionState { Disconnected, Connecting, Connected, Listening };
explicit CoreProcess(
IAppConfig &appConfig, IServerConfig &serverConfig,
const IAppConfig &appConfig, const IServerConfig &serverConfig,
const ILicense &license,
std::shared_ptr<Deps> deps = std::make_shared<Deps>());
@ -119,8 +119,8 @@ private:
void checkOSXNotification(const QString &line);
#endif
IAppConfig &m_appConfig;
IServerConfig &m_serverConfig;
const IAppConfig &m_appConfig;
const IServerConfig &m_serverConfig;
const ILicense &m_license;
std::shared_ptr<Deps> m_pDeps;
QString m_address;

View file

@ -21,6 +21,7 @@
#include "UpgradeDialog.h"
#include "gui/core/CoreProcess.h"
#include "gui/license/license_config.h"
#include "gui/messages.h"
#include "gui/tls/TlsCertificate.h"
#include "gui/tls/TlsUtility.h"
#include "gui/validators/ScreenNameValidator.h"
@ -61,6 +62,15 @@ SettingsDialog::SettingsDialog(
m_pScreenNameError = new validators::ValidationError(this);
m_pLineEditScreenName->setValidator(new validators::ScreenNameValidator(
m_pLineEditScreenName, m_pScreenNameError, &serverConfig.screens()));
connect(
this, &SettingsDialog::shown, this,
[this] {
if (!m_appConfig.isActiveScopeWritable()) {
showReadOnlyMessage();
}
},
Qt::QueuedConnection);
}
//
@ -107,6 +117,10 @@ void SettingsDialog::on_m_pRadioSystemScope_toggled(bool checked) {
m_appConfig.setLoadFromSystemScope(checked);
loadFromConfig();
updateControls();
if (isVisible() && !m_appConfig.isActiveScopeWritable()) {
showReadOnlyMessage();
}
}
void SettingsDialog::on_m_pPushButtonTlsCertPath_clicked() {
@ -147,6 +161,16 @@ void SettingsDialog::on_m_pCheckBoxServiceEnabled_toggled(bool) {
// End of auto-connect slots
//
void SettingsDialog::showEvent(QShowEvent *event) {
QDialog::showEvent(event);
emit shown();
}
void SettingsDialog::showReadOnlyMessage() {
const auto activeScopeFilename = m_appConfig.scopes().activeFilePath();
messages::showReadOnlySettings(this, activeScopeFilename);
}
void SettingsDialog::accept() {
if (!m_pLineEditScreenName->hasAcceptableInput()) {
QMessageBox::warning(
@ -228,6 +252,7 @@ void SettingsDialog::updateTlsControls() {
const auto tlsEnabled = m_tlsUtility.isAvailableAndEnabled();
const auto writable = m_appConfig.isActiveScopeWritable();
m_pCheckBoxEnableTls->setEnabled(writable);
m_pCheckBoxEnableTls->setChecked(writable && tlsEnabled);
m_pLineEditTlsCertPath->setText(m_appConfig.tlsCertPath());

View file

@ -39,10 +39,14 @@ class SettingsDialog : public QDialog, public Ui::SettingsDialogBase {
Q_OBJECT
public:
void extracted();
SettingsDialog(
QWidget *parent, IAppConfig &appConfig, const IServerConfig &serverConfig,
const License &license, const CoreProcess &coreProcess);
signals:
void shown();
private slots:
void on_m_pCheckBoxEnableTls_clicked(bool checked);
void on_m_pCheckBoxLogToFile_stateChanged(int);
@ -56,6 +60,11 @@ private slots:
private:
void accept() override;
void reject() override;
void showEvent(QShowEvent *event) override;
bool isClientMode() const;
void updateTlsControls();
void updateTlsControlsEnabled();
void showReadOnlyMessage();
/// @brief Load all settings.
void loadFromConfig();
@ -69,10 +78,6 @@ private:
/// @brief Enables controls when they should be.
void updateControls();
bool isClientMode() const;
void updateTlsControls();
void updateTlsControlsEnabled();
[[no_unique_address]] CoreTool m_coreTool;
validators::ValidationError *m_pScreenNameError;

View file

@ -23,9 +23,8 @@
class QDataStreamProxy {
public:
explicit QDataStreamProxy() = default;
explicit QDataStreamProxy(QTcpSocket *socket) {
m_Stream = std::make_unique<QDataStream>(socket);
}
explicit QDataStreamProxy(QTcpSocket *socket)
: m_Stream(std::make_unique<QDataStream>(socket)) {}
virtual ~QDataStreamProxy() = default;
virtual qint64 writeRawData(const char *data, int len) {

View file

@ -79,14 +79,17 @@ void QIpcClient::connectToHost() {
}
void QIpcClient::disconnectFromHost() {
m_isConnecting = false;
qInfo("disconnected from background service");
m_pReader->stop();
m_pSocket->flush();
m_pSocket->close();
m_isConnecting = false;
m_isConnected = false;
qInfo("disconnected from background service");
}
void QIpcClient::onSocketError(QAbstractSocket::SocketError socketError) const {
void QIpcClient::onSocketError(QAbstractSocket::SocketError socketError) {
QString text;
switch (socketError) {
case 0:
@ -101,6 +104,7 @@ void QIpcClient::onSocketError(QAbstractSocket::SocketError socketError) const {
}
qWarning("ipc connection error, %s", qUtf8Printable(text));
m_isConnected = false;
QTimer::singleShot(kRetryInterval, this, &QIpcClient::onRetryConnect);
}
@ -154,6 +158,12 @@ void QIpcClient::sendCommand(
void QIpcClient::onIpcReaderHelloBack() {
qDebug("ipc hello back received");
if (m_isConnected) {
qWarning("ipc already connected, ignoring hello back");
return;
}
m_isConnected = true;
serviceReady();
}

View file

@ -48,7 +48,7 @@ private slots:
void onRetryConnect();
void onSocketConnected() const;
void onIpcReaderHelloBack();
void onSocketError(QAbstractSocket::SocketError error) const;
void onSocketError(QAbstractSocket::SocketError error);
void onIpcReaderRead(const QString &text);
private:

View file

@ -149,7 +149,16 @@ void showCloseReminder(QWidget *parent) {
QMessageBox::information(parent, "Notification area icon", message);
}
void showFirstRunMessage(
void showFirstServerStartMessage(QWidget *parent) {
QMessageBox::information(
parent, "Server is running",
"<p>Great, the server is now running.</p>"
"<p>Now you can connect your other computers to this server. "
"You should see a prompt here on the server when a new client tries to "
"connect.</p>");
}
void showFirstConnectedMessage(
QWidget *parent, bool closeToTray, bool enableService, bool isServer) {
auto message = QString("<p>Synergy is now connected!</p>");
@ -265,4 +274,13 @@ bool showClearSettings(QWidget *parent) {
return message.clickedButton() == clear;
}
void showReadOnlySettings(QWidget *parent, const QString &systemSettingsPath) {
QString nativePath = QDir::toNativeSeparators(systemSettingsPath);
QMessageBox::information(
parent, "Read-only settings",
QString("<p>Settings are read-only because you only have read access "
"to the file:</p><p>%1</p>")
.arg(nativePath));
}
} // namespace synergy::gui::messages

View file

@ -33,7 +33,9 @@ void messageHandler(
void raiseCriticalDialog();
void showFirstRunMessage(
void showFirstServerStartMessage(QWidget *parent);
void showFirstConnectedMessage(
QWidget *parent, bool closeToTray, bool enableService, bool isServer);
void showCloseReminder(QWidget *parent);
@ -48,4 +50,6 @@ showNewClientPrompt(QWidget *parent, const QString &clientName);
bool showClearSettings(QWidget *parent);
void showReadOnlySettings(QWidget *parent, const QString &systemSettingsPath);
} // namespace synergy::gui::messages

View file

@ -29,26 +29,29 @@
namespace synergy::gui::proxy {
const auto kLegacyOrgDomain = "http-symless-com";
const auto kSystemConfigFilename = "SystemConfig.ini";
const auto kLegacySystemConfigFilename = "SystemConfig.ini";
#if defined(Q_OS_UNIX)
const auto kUnixSystemConfigPath = "/usr/local/etc/symless/";
const auto kUnixSystemConfigPath = "/usr/local/etc/";
#endif
//
// Free functions
//
QString getSystemSettingPath() {
const QString settingFilename(kSystemConfigFilename);
/**
* @brief The base dir for the system settings file.
*
* Important: Qt will append the org name as a dir, and the app name as the
* settings filename, i.e.: `{base-dir}/Synergy/Synergy.ini`
*/
QString getSystemSettingsBaseDir() {
#if defined(Q_OS_WIN)
return QCoreApplication::applicationDirPath() + QDir::separator();
#elif defined(Q_OS_MAC)
// it would be nice to use /Library dir, but qt has no elevate system.
return kUnixSystemConfigPath + settingFilename;
#elif defined(Q_OS_LINUX)
// qt already adds application and filename to the end of the path on linux.
return QCoreApplication::applicationDirPath();
#elif defined(Q_OS_UNIX)
// Qt already adds application and filename to the end of the path.
// On macOS, it would be nice to use /Library dir, but qt has no elevate
// system.
return kUnixSystemConfigPath;
#else
#error "unsupported platform"
@ -62,7 +65,8 @@ void migrateLegacySystemSettings(QSettings &settings) {
}
QSettings::setPath(
QSettings::IniFormat, QSettings::SystemScope, kSystemConfigFilename);
QSettings::IniFormat, QSettings::SystemScope,
kLegacySystemConfigFilename);
QSettings oldSystemSettings(
QSettings::IniFormat, QSettings::SystemScope,
QCoreApplication::organizationName(),
@ -75,7 +79,7 @@ void migrateLegacySystemSettings(QSettings &settings) {
}
QSettings::setPath(
QSettings::IniFormat, QSettings::SystemScope, getSystemSettingPath());
QSettings::IniFormat, QSettings::SystemScope, getSystemSettingsBaseDir());
}
void migrateLegacyUserSettings(QSettings &newSettings) {
@ -151,7 +155,7 @@ void QSettingsProxy::loadSystem() {
QSettings::setPath(
QSettings::Format::IniFormat, QSettings::Scope::SystemScope,
getSystemSettingPath());
getSystemSettingsBaseDir());
m_pSettings = std::make_unique<QSettings>(
QSettings::Format::IniFormat, QSettings::Scope::SystemScope, orgName,

View file

@ -21,7 +21,7 @@
namespace synergy::gui::proxy {
QString getSystemSettingPath();
QString getSystemSettingBaseDir();
class QSettingsProxy {
public:

View file

@ -57,9 +57,27 @@ Screen::~Screen() {
}
assert(!m_enabled);
// TODO: why assert this? it appears to be false when an elevated dialog
// appears on windows and the process is killed.
assert(m_entered == m_isPrimary);
// Originally there was an assert here added before 2009 (history not in
// tact). This condition seems to occur on a Windows client when the process
// is shut down to make way for a new elevated process (e.g. at login screen).
// The reason why this assert was originally added is unclear, and was causing
// pain when using debug builds; you lose control of the client when it's at
// the login screen. Therefore it has been converted to a warning so that we
// can still see when it happens but it won't cause the process to pause. This
// also gives us the added benefit of seeing when it happens in production.
// Perhaps it indicates that the cursor is still being controlled on the
// client while it's shutting down? i.e. the screen is entered and is not the
// server, or the screen is not entered and is the server.
if (m_entered == m_isPrimary) {
LOG(
(CLOG_DEBUG "current screen: entered=%s, primary=%s", //
m_entered ? "yes" : "no", m_isPrimary ? "yes" : "no"));
if (m_isPrimary) {
LOG((CLOG_WARN "current primary screen is not entered on shutdown"));
} else {
LOG((CLOG_WARN "current secondary screen is entered on shutdown"));
}
}
delete m_screen;
LOG((CLOG_DEBUG "closed display"));

View file

@ -39,9 +39,10 @@ public:
}
//
// Setters
// Getters
//
MOCK_METHOD(synergy::gui::IConfigScopes &, scopes, (), (const, override));
MOCK_METHOD(QString, tlsCertPath, (), (const, override));
MOCK_METHOD(int, tlsKeyLength, (), (const, override));
MOCK_METHOD(bool, tlsEnabled, (), (const, override));
@ -73,7 +74,7 @@ public:
MOCK_METHOD(bool, clientGroupChecked, (), (const, override));
//
// Getters
// Setters
//
MOCK_METHOD(

View file

@ -49,6 +49,7 @@ public:
MOCK_METHOD(const QSettingsProxy &, activeSettings, (), (const, override));
MOCK_METHOD(QSettingsProxy &, activeSettings, (), (override));
MOCK_METHOD(void, save, (bool), (override));
MOCK_METHOD(QString, activeFilePath, (), (const, override));
};
struct DepsMock : public AppConfig::Deps {