feat: remove stopOnDeskSwitch, its broken
This commit is contained in:
@ -30,30 +30,6 @@ int main(int argc, char **argv)
|
||||
Log log;
|
||||
EventQueue events;
|
||||
|
||||
// HACK: the `--active-desktop` arg actually belongs in the `deskflow-core` binary,
|
||||
// but we are placing it here in the server binary temporarily until we are ready to
|
||||
// ship the `deskflow-core` binary. we are deliberately not integrating `--active-desktop`
|
||||
// into the existing `ServerApp` arg parsing code as that would be a waste of time.
|
||||
#if SYSAPI_WIN32
|
||||
for (int i = 1; i < argc; ++i) {
|
||||
std::string arg(argv[i]);
|
||||
// This is called by the daemon (running in session 0) when it needs to know the name of the
|
||||
// interactive desktop.
|
||||
// It is necessary to run a utility process because the daemon runs in session 0, which does not
|
||||
// have access to the active desktop, and so cannot query it's name.
|
||||
if (arg == "--active-desktop") {
|
||||
const auto name = ArchMiscWindows::getActiveDesktopName();
|
||||
if (name.empty()) {
|
||||
LOG((CLOG_CRIT "failed to get active desktop name"));
|
||||
return kExitFailed;
|
||||
}
|
||||
|
||||
LOG((CLOG_PRINT "%s", name.c_str()));
|
||||
return kExitSuccess;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
ServerApp app(&events);
|
||||
return app.run(argc, argv);
|
||||
}
|
||||
|
||||
@ -75,8 +75,7 @@ void Settings::cleanSettings()
|
||||
QVariant Settings::defaultValue(const QString &key)
|
||||
{
|
||||
if ((key == Gui::Autohide) || (key == Core::StartedBefore) || (key == Core::PreventSleep) ||
|
||||
(key == Server::ExternalConfig) || (key == Client::InvertScrollDirection) || (key == Log::ToFile) ||
|
||||
(key == Core::StopOnDeskSwitch)) {
|
||||
(key == Server::ExternalConfig) || (key == Client::InvertScrollDirection) || (key == Log::ToFile)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@ -47,7 +47,6 @@ public:
|
||||
inline static const auto PreventSleep = QStringLiteral("core/preventSleep");
|
||||
inline static const auto ProcessMode = QStringLiteral("core/processMode");
|
||||
inline static const auto ScreenName = QStringLiteral("core/screenName");
|
||||
inline static const auto StopOnDeskSwitch = QStringLiteral("core/stopOnDeskSwitch");
|
||||
inline static const auto StartedBefore = QStringLiteral("core/startedBefore");
|
||||
inline static const auto UpdateUrl = QStringLiteral("core/updateUrl");
|
||||
};
|
||||
@ -166,7 +165,6 @@ private:
|
||||
, Settings::Core::ProcessMode
|
||||
, Settings::Core::ScreenName
|
||||
, Settings::Core::StartedBefore
|
||||
, Settings::Core::StopOnDeskSwitch
|
||||
, Settings::Core::UpdateUrl
|
||||
, Settings::Daemon::Command
|
||||
, Settings::Daemon::Elevate
|
||||
|
||||
@ -120,16 +120,10 @@ bool ArgParser::parsePlatformArgs(
|
||||
deskflow::ArgsBase &argsBase, const int &argc, const char *const *argv, int &i, bool isServer
|
||||
)
|
||||
{
|
||||
#if WINAPI_MSWINDOWS
|
||||
if (isArg(i, argc, argv, nullptr, "--stop-on-desk-switch")) {
|
||||
argsBase.m_stopOnDeskSwitch = true;
|
||||
} else {
|
||||
// option not supported here
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
#elif WINAPI_XWINDOWS
|
||||
#if !WINAPI_XWINDOWS
|
||||
// no options for carbon or windows
|
||||
return false;
|
||||
#else
|
||||
|
||||
if (isArg(i, argc, argv, "-display", "--display", 1)) {
|
||||
// use alternative display
|
||||
@ -146,9 +140,6 @@ bool ArgParser::parsePlatformArgs(
|
||||
}
|
||||
|
||||
return true;
|
||||
#elif WINAPI_CARBON
|
||||
// no options for carbon
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@ -80,10 +80,6 @@ public:
|
||||
/// @brief Stop this computer from sleeping
|
||||
bool m_preventSleep = false;
|
||||
|
||||
#if SYSAPI_WIN32
|
||||
bool m_stopOnDeskSwitch = false;
|
||||
#endif
|
||||
|
||||
#if WINAPI_XWINDOWS
|
||||
bool m_disableXInitThreads = false;
|
||||
#endif
|
||||
|
||||
@ -171,10 +171,7 @@ deskflow::Screen *ClientApp::createScreen()
|
||||
{
|
||||
#if WINAPI_MSWINDOWS
|
||||
return new deskflow::Screen(
|
||||
new MSWindowsScreen(
|
||||
false, args().m_noHooks, args().m_stopOnDeskSwitch, m_events, args().m_enableLangSync,
|
||||
args().m_clientScrollDirection
|
||||
),
|
||||
new MSWindowsScreen(false, args().m_noHooks, m_events, args().m_enableLangSync, args().m_clientScrollDirection),
|
||||
m_events
|
||||
);
|
||||
#endif
|
||||
|
||||
@ -561,9 +561,7 @@ bool ServerApp::startServer()
|
||||
deskflow::Screen *ServerApp::createScreen()
|
||||
{
|
||||
#if WINAPI_MSWINDOWS
|
||||
return new deskflow::Screen(
|
||||
new MSWindowsScreen(true, args().m_noHooks, args().m_stopOnDeskSwitch, m_events), m_events
|
||||
);
|
||||
return new deskflow::Screen(new MSWindowsScreen(true, args().m_noHooks, m_events), m_events);
|
||||
#endif
|
||||
|
||||
#if defined(WINAPI_XWINDOWS) or defined(WINAPI_LIBEI)
|
||||
|
||||
@ -457,23 +457,6 @@ bool CoreProcess::addGenericArgs(QStringList &args, const ProcessMode processMod
|
||||
|
||||
args << "--name" << Settings::value(Settings::Core::ScreenName).toString();
|
||||
|
||||
if (processMode != ProcessMode::Desktop) {
|
||||
#if defined(Q_OS_WIN)
|
||||
// tell the client/server to shut down when a ms windows desk
|
||||
// is switched; this is because we may need to elevate or not
|
||||
// based on which desk the user is in (login always needs
|
||||
// elevation, where as default desk does not).
|
||||
// Note that this is only enabled when deskflow is set to elevate
|
||||
// 'as needed' (e.g. on a UAC dialog popup) in order to prevent
|
||||
// unnecessary restarts when deskflow was started elevated or
|
||||
// when it is not allowed to elevate. In these cases restarting
|
||||
// the server is fruitless.
|
||||
if (Settings::value(Settings::Core::StopOnDeskSwitch).toBool()) {
|
||||
args << "--stop-on-desk-switch";
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifndef Q_OS_LINUX
|
||||
|
||||
if (m_serverConfig.enableDragAndDrop()) {
|
||||
|
||||
@ -68,25 +68,6 @@ void SettingsDialog::initConnections()
|
||||
connect(ui->btnTlsCertPath, &QPushButton::clicked, this, &SettingsDialog::browseCertificatePath);
|
||||
connect(ui->btnBrowseLog, &QPushButton::clicked, this, &SettingsDialog::browseLogPath);
|
||||
connect(ui->cbLogToFile, &QCheckBox::toggled, this, &SettingsDialog::setLogToFile);
|
||||
connect(ui->cbElevateDaemon, &QCheckBox::toggled, this, [&](bool checked) {
|
||||
if (!checked)
|
||||
return;
|
||||
if (ui->cbStopOnDeskSwitch->isChecked()) {
|
||||
blockSignals(true);
|
||||
ui->cbStopOnDeskSwitch->setChecked(false);
|
||||
blockSignals(false);
|
||||
}
|
||||
});
|
||||
|
||||
connect(ui->cbStopOnDeskSwitch, &QCheckBox::toggled, this, [&](bool checked) {
|
||||
if (!checked)
|
||||
return;
|
||||
if (ui->cbElevateDaemon->isChecked()) {
|
||||
blockSignals(true);
|
||||
ui->cbElevateDaemon->setChecked(false);
|
||||
blockSignals(false);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void SettingsDialog::regenCertificates()
|
||||
@ -151,7 +132,6 @@ void SettingsDialog::accept()
|
||||
Settings::setValue(Settings::Log::Level, ui->comboLogLevel->currentIndex());
|
||||
Settings::setValue(Settings::Log::ToFile, ui->cbLogToFile->isChecked());
|
||||
Settings::setValue(Settings::Log::File, ui->lineLogFilename->text());
|
||||
Settings::setValue(Settings::Core::StopOnDeskSwitch, ui->cbStopOnDeskSwitch->isChecked());
|
||||
Settings::setValue(Settings::Daemon::Elevate, ui->cbElevateDaemon->isChecked());
|
||||
Settings::setValue(Settings::Gui::Autohide, ui->cbAutoHide->isChecked());
|
||||
Settings::setValue(Settings::Gui::AutoUpdateCheck, ui->cbAutoUpdate->isChecked());
|
||||
@ -187,7 +167,6 @@ void SettingsDialog::loadFromConfig()
|
||||
ui->cbLanguageSync->setChecked(Settings::value(Settings::Client::LanguageSync).toBool());
|
||||
ui->cbScrollDirection->setChecked(Settings::value(Settings::Client::InvertScrollDirection).toBool());
|
||||
ui->cbCloseToTray->setChecked(Settings::value(Settings::Gui::CloseToTray).toBool());
|
||||
ui->cbStopOnDeskSwitch->setChecked(Settings::value(Settings::Core::StopOnDeskSwitch).toBool());
|
||||
ui->cbElevateDaemon->setChecked(Settings::value(Settings::Daemon::Elevate).toBool());
|
||||
ui->cbAutoUpdate->setChecked(Settings::value(Settings::Gui::AutoUpdateCheck).toBool());
|
||||
|
||||
@ -288,7 +267,6 @@ void SettingsDialog::updateControls()
|
||||
if (Settings::isNativeMode()) {
|
||||
ui->groupService->setEnabled(writable);
|
||||
ui->cbElevateDaemon->setEnabled(writable && serviceChecked);
|
||||
ui->cbStopOnDeskSwitch->setEnabled(writable && serviceChecked);
|
||||
} else if (ui->groupService->isVisibleTo(ui->tabAdvanced)) {
|
||||
ui->groupService->setVisible(false);
|
||||
const int bottomMargin = ui->tabAdvanced->layout()->contentsMargins().bottom() +
|
||||
|
||||
@ -560,19 +560,6 @@
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="_6">
|
||||
<item row="2" column="0">
|
||||
<widget class="QCheckBox" name="cbStopOnDeskSwitch">
|
||||
<property name="toolTip">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Run as system only when at the login screen and UAC prompt</string>
|
||||
</property>
|
||||
<property name="autoExclusive">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QCheckBox" name="cbElevateDaemon">
|
||||
<property name="text">
|
||||
|
||||
@ -107,8 +107,7 @@ static void send_mouse_input(DWORD dwFlags, DWORD dx, DWORD dy, DWORD dwData)
|
||||
//
|
||||
|
||||
MSWindowsDesks::MSWindowsDesks(
|
||||
bool isPrimary, bool noHooks, const IScreenSaver *screensaver, IEventQueue *events, IJob *updateKeys,
|
||||
bool stopOnDeskSwitch
|
||||
bool isPrimary, bool noHooks, const IScreenSaver *screensaver, IEventQueue *events, IJob *updateKeys
|
||||
)
|
||||
: m_isPrimary(isPrimary),
|
||||
m_noHooks(noHooks),
|
||||
@ -128,8 +127,7 @@ MSWindowsDesks::MSWindowsDesks(
|
||||
m_mutex(),
|
||||
m_deskReady(&m_mutex, false),
|
||||
m_updateKeys(updateKeys),
|
||||
m_events(events),
|
||||
m_stopOnDeskSwitch(stopOnDeskSwitch)
|
||||
m_events(events)
|
||||
{
|
||||
|
||||
m_cursor = createBlankCursor();
|
||||
@ -757,18 +755,6 @@ void MSWindowsDesks::checkDesk()
|
||||
desk = index->second;
|
||||
}
|
||||
|
||||
// if we are told to shut down on desk switch, and this is not the
|
||||
// first switch, then shut down.
|
||||
if (m_stopOnDeskSwitch && m_activeDesk != NULL && name != m_activeDeskName) {
|
||||
if (name.empty()) {
|
||||
LOG_DEBUG("shutting down because of desk switch, desktop name unknown");
|
||||
} else {
|
||||
LOG_DEBUG("shutting down because of desk switch to: %s", name.c_str());
|
||||
}
|
||||
m_events->addEvent(Event(Event::kQuit));
|
||||
return;
|
||||
}
|
||||
|
||||
// if active desktop changed then tell the old and new desk threads
|
||||
// about the change. don't switch desktops when the screensaver is
|
||||
// active becaue we'd most likely switch to the screensaver desktop
|
||||
|
||||
@ -54,10 +54,7 @@ public:
|
||||
updated in a thread attached to the current desk.
|
||||
\p hookLibrary must be a handle to the hook library.
|
||||
*/
|
||||
MSWindowsDesks(
|
||||
bool isPrimary, bool noHooks, const IScreenSaver *screensaver, IEventQueue *events, IJob *updateKeys,
|
||||
bool stopOnDeskSwitch
|
||||
);
|
||||
MSWindowsDesks(bool isPrimary, bool noHooks, const IScreenSaver *screensaver, IEventQueue *events, IJob *updateKeys);
|
||||
~MSWindowsDesks();
|
||||
|
||||
//! @name manipulators
|
||||
@ -278,7 +275,4 @@ private:
|
||||
bool m_leaveForegroundOption;
|
||||
|
||||
IEventQueue *m_events;
|
||||
|
||||
// true if program should stop on desk switch.
|
||||
bool m_stopOnDeskSwitch;
|
||||
};
|
||||
|
||||
@ -82,7 +82,7 @@ HINSTANCE MSWindowsScreen::s_windowInstance = NULL;
|
||||
MSWindowsScreen *MSWindowsScreen::s_screen = NULL;
|
||||
|
||||
MSWindowsScreen::MSWindowsScreen(
|
||||
bool isPrimary, bool noHooks, bool stopOnDeskSwitch, IEventQueue *events, bool enableLangSync,
|
||||
bool isPrimary, bool noHooks, IEventQueue *events, bool enableLangSync,
|
||||
deskflow::ClientScrollDirection scrollDirection
|
||||
)
|
||||
: PlatformScreen(events, scrollDirection),
|
||||
@ -130,7 +130,7 @@ MSWindowsScreen::MSWindowsScreen(
|
||||
m_screensaver = new MSWindowsScreenSaver();
|
||||
m_desks = new MSWindowsDesks(
|
||||
m_isPrimary, m_noHooks, m_screensaver, m_events,
|
||||
new TMethodJob<MSWindowsScreen>(this, &MSWindowsScreen::updateKeysCB), stopOnDeskSwitch
|
||||
new TMethodJob<MSWindowsScreen>(this, &MSWindowsScreen::updateKeysCB)
|
||||
);
|
||||
m_keyState = new MSWindowsKeyState(
|
||||
m_desks, getEventTarget(), m_events, AppUtil::instance().getKeyboardLayoutList(), enableLangSync
|
||||
|
||||
@ -33,7 +33,7 @@ class MSWindowsScreen : public PlatformScreen
|
||||
{
|
||||
public:
|
||||
MSWindowsScreen(
|
||||
bool isPrimary, bool noHooks, bool stopOnDeskSwitch, IEventQueue *events, bool enableLangSync = false,
|
||||
bool isPrimary, bool noHooks, IEventQueue *events, bool enableLangSync = false,
|
||||
deskflow::ClientScrollDirection scrollDirection = deskflow::ClientScrollDirection::SERVER
|
||||
);
|
||||
virtual ~MSWindowsScreen();
|
||||
|
||||
@ -149,13 +149,9 @@ MSWindowsWatchdog::getUserToken(LPSECURITY_ATTRIBUTES security, bool elevatedTok
|
||||
{
|
||||
m_session.updateActiveSession();
|
||||
|
||||
// always elevate if we are at the vista/7 login screen. we could also
|
||||
// elevate for the uac dialog (consent.exe) but this would be pointless,
|
||||
// since deskflow would re-launch as non-elevated after the desk switch,
|
||||
// and so would be unusable with the new elevated process taking focus.
|
||||
if (elevatedToken || m_session.isProcessInSession("logonui.exe", nullptr)) {
|
||||
if (elevatedToken) {
|
||||
|
||||
LOG_DEBUG("getting elevated token, %s", (elevatedToken ? "elevation required" : "at login screen"));
|
||||
LOG_DEBUG("getting elevated token");
|
||||
|
||||
HANDLE process;
|
||||
if (!m_session.isProcessInSession("winlogon.exe", &process)) {
|
||||
@ -290,16 +286,9 @@ void MSWindowsWatchdog::startProcess()
|
||||
} else {
|
||||
LOG_DEBUG("starting new process in user session");
|
||||
|
||||
LOG_DEBUG("getting active desktop name");
|
||||
const auto activeDesktopName = runActiveDesktopUtility();
|
||||
|
||||
LOG_DEBUG("active desktop name: %s", activeDesktopName.c_str());
|
||||
// When we're at a UAC prompt, lock screen, or the login screen, Windows switches to the Winlogon desktop.
|
||||
const auto isOnSecureDesktop = activeDesktopName == "Winlogon";
|
||||
|
||||
SECURITY_ATTRIBUTES sa;
|
||||
ZeroMemory(&sa, sizeof(SECURITY_ATTRIBUTES));
|
||||
HANDLE userToken = getUserToken(&sa, isOnSecureDesktop || m_elevateProcess);
|
||||
HANDLE userToken = getUserToken(&sa, m_elevateProcess);
|
||||
|
||||
// set UIAccess to fix Windows 8 GUI interaction
|
||||
DWORD uiAccess = 1;
|
||||
@ -438,53 +427,6 @@ void MSWindowsWatchdog::shutdownExistingProcesses()
|
||||
CloseHandle(snapshot);
|
||||
}
|
||||
|
||||
std::string MSWindowsWatchdog::runActiveDesktopUtility()
|
||||
{
|
||||
char fileNameBuffer[MAX_PATH];
|
||||
GetModuleFileName(NULL, fileNameBuffer, MAX_PATH);
|
||||
std::string fileName(fileNameBuffer);
|
||||
size_t lastSlash = fileName.find_last_of("\\");
|
||||
const auto installDir = fileName.substr(0, lastSlash);
|
||||
|
||||
const auto coreBinPath = installDir + "\\deskflow-server.exe";
|
||||
std::string utilityCommand = "\"" + coreBinPath + "\" --active-desktop";
|
||||
|
||||
LOG_DEBUG("starting active desktop utility: %s", utilityCommand.c_str());
|
||||
|
||||
SECURITY_ATTRIBUTES sa;
|
||||
ZeroMemory(&sa, sizeof(SECURITY_ATTRIBUTES));
|
||||
HANDLE userToken = getUserToken(&sa, true);
|
||||
|
||||
deskflow::platform::MSWindowsProcess process(utilityCommand);
|
||||
process.createPipes();
|
||||
|
||||
if (!process.startAsUser(userToken, &sa)) {
|
||||
LOG_ERR("could not start active desktop process");
|
||||
throw XArch(new XArchEvalWindows());
|
||||
}
|
||||
|
||||
LOG_DEBUG("started active desktop process, pid=%d", process.info().dwProcessId);
|
||||
if (const auto exitCode = process.waitForExit(); exitCode != kExitSuccess) {
|
||||
LOG_ERR("active desktop process, exit code: %d", exitCode);
|
||||
throw XArch("could not get active desktop");
|
||||
}
|
||||
|
||||
LOG_DEBUG("reading active desktop std error");
|
||||
if (const auto error = process.readStdError(); !error.empty()) {
|
||||
LOG_WARN("active desktop process, error: %s", error.c_str());
|
||||
}
|
||||
|
||||
LOG_DEBUG("reading active desktop std output");
|
||||
auto output = process.readStdOutput();
|
||||
if (output.empty()) {
|
||||
LOG_ERR("could not get active desktop, no output");
|
||||
throw XArch("could not get active desktop");
|
||||
}
|
||||
|
||||
output.erase(output.find_last_not_of("\r\n") + 1);
|
||||
return output;
|
||||
}
|
||||
|
||||
MSWindowsWatchdog::ProcessState MSWindowsWatchdog::handleStartError(const std::string_view &message)
|
||||
{
|
||||
const auto kStartDelaySeconds = 1;
|
||||
|
||||
@ -111,16 +111,6 @@ private:
|
||||
*/
|
||||
void initSasFunc();
|
||||
|
||||
/**
|
||||
* @brief Re-run the process to get the active desktop name.
|
||||
*
|
||||
* It is necessary to run a utility process because the daemon runs in session 0, which does not
|
||||
* have access to the active desktop, and so cannot query it's name.
|
||||
*
|
||||
* @return std::string The name of the active desktop.
|
||||
*/
|
||||
std::string runActiveDesktopUtility();
|
||||
|
||||
/**
|
||||
* @brief Allows the SendSAS function to be called from other processes.
|
||||
*
|
||||
|
||||
Reference in New Issue
Block a user