diff --git a/.github/workflows/sonarcloud-analysis.yml b/.github/workflows/sonarcloud-analysis.yml
index 61af45eff..52b1fc0f5 100644
--- a/.github/workflows/sonarcloud-analysis.yml
+++ b/.github/workflows/sonarcloud-analysis.yml
@@ -19,7 +19,7 @@ jobs:
sonarcloud-analysis:
if: ${{ vars.SONAR_SCANNER_ENABLED }}
- runs-on: ubuntu-24.04-16-core-x64
+ runs-on: ubuntu-24.04-32-core-x64
container: symless/synergy-core:ubuntu-22.04-amd64
timeout-minutes: 20
@@ -27,6 +27,7 @@ jobs:
SONAR_SCANNER_VERSION: 6.1.0.4477
SONAR_SCANNER_OPTS: -server
SONAR_SCANNER_URL_BASE: https://binaries.sonarsource.com/Distribution/sonar-scanner-cli
+ SONAR_SCANNER_THREADS: 32
steps:
- name: Checkout
@@ -83,7 +84,7 @@ jobs:
-Dsonar.cfamily.build-wrapper-output=bw-output \
-Dsonar.host.url=https://sonarcloud.io \
-Dsonar.coverageReportPaths=build/coverage.xml \
- -Dsonar.cfamily.threads=2
+ -Dsonar.cfamily.threads=${{ env.SONAR_SCANNER_THREADS }}
env:
SONAR_TOKEN: ${{secrets.SONAR_TOKEN}}
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
diff --git a/.gitignore b/.gitignore
index 88b9a7285..56067f54d 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,5 @@
# temp dirs created during build
/build
-/bin
/dist
/deps
/tmp
diff --git a/.vscode/tasks.json b/.vscode/tasks.json
index 9f24b1ed0..e9d78ce96 100644
--- a/.vscode/tasks.json
+++ b/.vscode/tasks.json
@@ -14,9 +14,9 @@
},
{
"type": "cmake",
- "label": "coverage",
+ "label": "clean",
"command": "build",
- "targets": ["coverage"],
+ "targets": ["clean"],
"preset": "${command:cmake.activeBuildPresetName}",
"group": "build"
},
@@ -32,6 +32,17 @@
"command": "${workspaceFolder}/build/bin/synergy",
"dependsOn": ["build"]
},
+ {
+ "label": "clean-gcda",
+ "type": "shell",
+ "command": "find . -name '*.gcda' -delete",
+ "windows": {
+ "command": "$null" // no-op
+ },
+ "presentation": {
+ "reveal": "silent"
+ }
+ },
{
"label": "unittests (current)",
"type": "shell",
@@ -42,7 +53,7 @@
"--ignore-return-code",
"--filter-file=${file}"
],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
},
{
"label": "integtests (current)",
@@ -54,21 +65,21 @@
"--ignore-return-code",
"--filter-file=${file}"
],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
},
{
"label": "unittests (all)",
"type": "shell",
"command": "python",
"args": ["./scripts/tests.py", "--unit-tests", "--ignore-return-code"],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
},
{
"label": "integtests (all)",
"type": "shell",
"command": "python",
"args": ["./scripts/tests.py", "--integ-tests", "--ignore-return-code"],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
},
{
"label": "unittests (current, valgrind)",
@@ -81,7 +92,7 @@
"--filter-file=${file}",
"--valgrind"
],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
},
{
"label": "integtests (current, valgrind)",
@@ -94,7 +105,7 @@
"--filter-file=${file}",
"--valgrind"
],
- "dependsOn": ["build"]
+ "dependsOn": ["build", "clean-gcda"]
}
]
}
diff --git a/CMakeLists.txt b/CMakeLists.txt
index c3ba38851..ecaaf24f8 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -19,6 +19,7 @@ project(synergy-core C CXX)
include(cmake/Version.cmake)
include(cmake/Definitions.cmake)
+include(cmake/Build.cmake)
include(cmake/Libraries.cmake)
include(cmake/Packaging.cmake)
@@ -28,3 +29,5 @@ configure_libs()
configure_packaging()
add_subdirectory(src)
+
+post_config_all()
diff --git a/ChangeLog b/ChangeLog
index 0de307bd3..642a28249 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -24,7 +24,7 @@ Enhancements:
- #7326 Restore lpDesktop assignment in Windows daemon
- #7327 Only use Ninja to build on Windows
- #7328 Reset error state before calling Process32Next
-- #1177 Split CMake presets into debug and release
+- #7330 Split CMake presets into debug and release
- #7331 Script to install deps (Windows only for now)
- #7332 Static link OpenSSL libs in CMake preset for Windows
- #7333 Update VS Code config for Windows daemon debugging
@@ -50,10 +50,11 @@ Enhancements:
- #7380 Add `qt6-qpa-plugins` Qt dependency for Debian
- #7381 Set macOS min version to macOS 12.0
- #7382 Re-run `macdeployqt6` to copy missing Qt 6 dependencies
+- #7383 Solve SonarCloud security hotspots and bugs
- #7384 Run `install_deps.py` script when building containers weekly
- #7389 Correct Qt macOS target and drop `Core5Compat` lib
-- #7383 Solve SonarCloud security hotspots and bugs
- #7401 Run Valgrind on unit tests in CI to detect memory leaks
+- #7403 Solve low hanging reliability and maintainability issues
# 1.14.6
diff --git a/cmake/Build.cmake b/cmake/Build.cmake
new file mode 100644
index 000000000..f0c232c7f
--- /dev/null
+++ b/cmake/Build.cmake
@@ -0,0 +1,61 @@
+# Synergy -- mouse and keyboard sharing utility
+# Copyright (C) 2024 Symless 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 LICENSE 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 .
+
+macro(post_config)
+
+ # Build to a temp bin dir on Windows and then copy to the final bin dir
+ # (ignore copy fail). It is neccesary to do this. Since the binary may already
+ # be running and you can't write to a running binary (on Windows). It's common
+ # to use Synergy to develop Synergy (i.e. eating your own dog food immediately
+ # making it).
+ if(WIN32)
+
+ if(NOT target)
+ message(FATAL_ERROR "target not set")
+ endif()
+
+ set_target_properties(${target} PROPERTIES RUNTIME_OUTPUT_DIRECTORY
+ ${BIN_TEMP_DIR})
+ endif()
+
+endmacro()
+
+macro(post_config_all)
+
+ # Always try to copy the files to the bin directory after every build, even if
+ # there was nothing to do. This is because the copy may have failed last time
+ # due to the file being in use, and we'll usually want to try again.
+ if(WIN32)
+
+ if(NOT EXISTS ${PYTHON_BIN})
+ message(FATAL_ERROR "Python not found at: ${PYTHON_BIN}")
+ endif()
+
+ add_custom_target(
+ run_post_build ALL
+ COMMAND ${PYTHON_BIN} ${CMAKE_SOURCE_DIR}/scripts/fancy_copy.py
+ ${BIN_TEMP_DIR} ${CMAKE_BINARY_DIR}/bin --ignore-errors
+ VERBATIM
+ COMMENT "Copying files to bin dir")
+
+ add_dependencies(
+ run_post_build
+ synergy
+ synergyc
+ synergys
+ synergyd)
+ endif()
+
+endmacro()
diff --git a/cmake/Definitions.cmake b/cmake/Definitions.cmake
index e43b59268..1245ea024 100644
--- a/cmake/Definitions.cmake
+++ b/cmake/Definitions.cmake
@@ -28,6 +28,7 @@ macro(configure_definitions)
configure_ninja()
configure_options()
+ configure_python()
if("${VERSION_URL}" STREQUAL "")
set(VERSION_URL "https://api.symless.com/version?version=v1")
@@ -58,17 +59,20 @@ macro(configure_definitions)
add_definitions(-DNDEBUG)
endif()
- # TODO: find out why we need these, and remove them if we don't
+ # TODO: find out why we need these, and remove them if we don't.
if(COMMAND cmake_policy)
cmake_policy(SET CMP0003 NEW)
cmake_policy(SET CMP0005 NEW)
endif()
+ # TODO: explain why we're adding headers to sources.
if(${CMAKE_GENERATOR} STREQUAL "Unix Makefiles")
- set(SYNERGY_ADD_HEADERS FALSE)
+ set(ADD_HEADERS_TO_SOURCES FALSE)
else()
- set(SYNERGY_ADD_HEADERS TRUE)
+ set(ADD_HEADERS_TO_SOURCES TRUE)
endif()
+
+ set(BIN_TEMP_DIR ${CMAKE_BINARY_DIR}/temp/bin)
endmacro()
macro(configure_ninja)
diff --git a/cmake/Libraries.cmake b/cmake/Libraries.cmake
index 8ca7a7e8a..a0c6a4f85 100644
--- a/cmake/Libraries.cmake
+++ b/cmake/Libraries.cmake
@@ -361,3 +361,11 @@ macro(update_submodules)
endif()
endmacro()
+
+macro(configure_python)
+ if(WIN32)
+ set(PYTHON_BIN "${CMAKE_BINARY_DIR}/python/Scripts/python.exe")
+ else()
+ set(PYTHON_BIN "${CMAKE_BINARY_DIR}/python/bin/python")
+ endif()
+endmacro()
diff --git a/scripts/fancy_copy.py b/scripts/fancy_copy.py
new file mode 100644
index 000000000..3d6e69a43
--- /dev/null
+++ b/scripts/fancy_copy.py
@@ -0,0 +1,41 @@
+#!/usr/bin/env python3
+
+import argparse
+import lib.env as env
+import lib.file_utils as file_utils
+
+
+def main():
+ """
+ Cross platform script to copy files and directories.
+ This script was mostly created beause the default `copy` command on Windows is too noisy.
+ If this becomes complex it must be replaced with a library.
+ """
+
+ # important: load venv before loading modules that install deps.
+ env.ensure_in_venv(__file__)
+
+ parser = argparse.ArgumentParser()
+ parser.add_argument("source", help="Source pattern to copy from")
+ parser.add_argument("target", help="Destination pattern to copy to")
+ parser.add_argument(
+ "--ignore-errors", action="store_true", help="Ignore errors when copying"
+ )
+ parser.add_argument(
+ "--verbose", action="store_true", help="Print more information to the console"
+ )
+ args = parser.parse_args()
+
+ options = file_utils.CopyOptions(args.ignore_errors, args.verbose)
+
+ try:
+ file_utils.copy(args.source, args.target, options)
+ except Exception as e:
+ if not args.ignore_errors:
+ raise e
+ else:
+ print(f"Error: {e}")
+
+
+if __name__ == "__main__":
+ main()
diff --git a/scripts/lib/file_utils.py b/scripts/lib/file_utils.py
new file mode 100644
index 000000000..278c0cfae
--- /dev/null
+++ b/scripts/lib/file_utils.py
@@ -0,0 +1,80 @@
+import glob, os, shutil, sys
+
+import colorama # type: ignore
+from colorama import Fore # type: ignore
+
+colorama.init()
+
+
+class CopyOptions:
+ def __init__(self, ignore_errors, verbose):
+ self.ignore_errors = ignore_errors
+ self.verbose = verbose
+
+
+class CopyContext:
+ def __init__(self):
+ self.errors = 0
+ self.permission_error = False
+
+
+def copy(source, target, options):
+ """Copy files and directories from source to target."""
+
+ context = CopyContext()
+ if options.verbose:
+ print(f"Copying files from {source} to {target}")
+ for match in glob.glob(source):
+
+ if os.path.isfile(match):
+ copy_file(match, target, options, context)
+ elif os.path.isdir(match):
+ copy_dir(match, target, options, context)
+ else:
+ raise RuntimeError(f"Path {match} is not a file or directory")
+
+ if context.errors and options.ignore_errors:
+ print(
+ f"{Fore.YELLOW}WARNING:{Fore.RESET} Ignored {context.errors} copy error(s)"
+ )
+
+ if context.permission_error:
+ print(
+ f"{Fore.BLUE}HINT:{Fore.RESET} A permission error may mean that the file is in use"
+ )
+
+
+def copy_dir(match, target, options, context):
+ if options.verbose:
+ print(f"Copying directory {match} to {target}")
+
+ try:
+ shutil.copytree(match, target, dirs_exist_ok=True)
+
+ except PermissionError as e:
+ context.permission_error = True
+ handle_copy_error(e, options, context)
+ except Exception as e:
+ handle_copy_error(e, options, context)
+
+
+def copy_file(match, target, options, context):
+ if options.verbose:
+ print(f"Copying file {match} to {target}")
+
+ try:
+ shutil.copy(match, target)
+ except PermissionError as e:
+ context.permission_error = True
+ handle_copy_error(e, options, context)
+ except Exception as e:
+ handle_copy_error(e, options, context)
+
+
+def handle_copy_error(e, options, context):
+ context.errors += 1
+
+ if not options.ignore_errors:
+ raise e
+ else:
+ print(f"{Fore.YELLOW}WARNING:{Fore.RESET} Copy failed: {e}", file=sys.stderr)
diff --git a/scripts/windows_daemon.py b/scripts/windows_daemon.py
index 2bea265fe..daf36a1d0 100644
--- a/scripts/windows_daemon.py
+++ b/scripts/windows_daemon.py
@@ -1,14 +1,13 @@
-import os
-import subprocess
-import sys
-import argparse
-import glob
+import os, sys, time, subprocess, argparse, glob
import lib.windows as windows
+import lib.file_utils as file_utils
+import psutil
-BIN_NAME = "synergyd"
-SOURCE_BIN_DIR = os.path.join("build", "bin")
-TARGET_BIN_DIR = "bin"
+DEFAULT_BIN_NAME = "synergyd"
+DEFAULT_SOURCE_DIR = os.path.join("build", "temp", "bin")
+DEFAULT_TARGET_DIR = os.path.join("build", "bin")
SERVICE_NOT_RUNNING_ERROR = 2
+ERROR_ACCESS_VIOLATION = 0xC0000005
def main():
@@ -16,10 +15,9 @@ def main():
parser = argparse.ArgumentParser()
parser.add_argument("--pause-on-exit", action="store_true")
- parser.add_argument("--source-bin-dir", default=SOURCE_BIN_DIR)
- parser.add_argument("--target-bin-dir", default=TARGET_BIN_DIR)
- parser.add_argument("--source-bin-name", default=BIN_NAME)
- parser.add_argument("--target-bin-name", default=BIN_NAME)
+ parser.add_argument("--source-dir", default=DEFAULT_SOURCE_DIR)
+ parser.add_argument("--target-dir", default=DEFAULT_TARGET_DIR)
+ parser.add_argument("--bin-name", default=DEFAULT_BIN_NAME)
args = parser.parse_args()
if not windows.is_admin():
@@ -28,19 +26,18 @@ def main():
try:
reinstall(
- args.source_bin_dir,
- args.target_bin_dir,
- args.source_bin_name,
- args.target_bin_name,
+ args.source_dir,
+ args.target_dir,
+ args.bin_name,
)
except Exception as e:
- print(f"Error: {e}")
+ print(f"Error: {e}", file=sys.stderr)
if args.pause_on_exit:
input("Press enter to continue...")
-def reinstall(source_bin_dir, target_bin_dir, source_bin_name, target_bin_name):
+def reinstall(source_dir, target_dir, bin_name):
"""Stops the running daemon service, copies files, and reinstalls."""
print("Stopping daemon service")
@@ -52,43 +49,64 @@ def reinstall(source_bin_dir, target_bin_dir, source_bin_name, target_bin_name):
else:
raise e
- copy_bin_files(source_bin_dir, target_bin_dir, source_bin_name, target_bin_name)
+ source_bin_path = f"{os.path.join(source_dir, bin_name)}.exe"
- target_bin_file = f"{os.path.join(target_bin_dir, target_bin_name)}.exe"
+ # Wait for Windows to release the file handles after process termination.
+ while is_any_process_running(target_dir):
+ print("Waiting for file handles to release")
+ time.sleep(1)
+
+ options = file_utils.CopyOptions(ignore_errors=True, verbose=False)
+ print(f"Copying files from {source_dir} to {target_dir}")
+ file_utils.copy(f"{source_dir}/*", target_dir, options)
print("Removing old daemon service")
- subprocess.run([target_bin_file, "/uninstall"], shell=True, check=True)
+ try:
+ subprocess.run([source_bin_path, "/uninstall"], shell=True, check=True)
+ except subprocess.CalledProcessError as e:
+ check_access_violation(e.returncode, source_bin_path)
+ if e.returncode != 0:
+ print(
+ f"Warning: Uninstall failed, return code: {e.returncode}",
+ file=sys.stderr,
+ )
- print("Installing daemon service")
- subprocess.run([target_bin_file, "/install"], shell=True, check=True)
+ target_bin_path = os.path.join(target_dir, bin_name + ".exe")
+
+ try:
+ print("Installing daemon service")
+ subprocess.run([target_bin_path, "/install"], shell=True, check=True)
+ except subprocess.CalledProcessError as e:
+ check_access_violation(e.returncode, target_bin_path)
+ if e.returncode != 0:
+ print(f"Warning: Install failed, return code: {e.returncode}")
-def copy_bin_files(source_bin_dir, target_bin_dir, source_bin_name, target_bin_name):
-
- if not os.path.isdir(source_bin_dir):
- raise RuntimeError(f"Invalid source bin dir: {source_bin_dir}")
-
- print(f"Persisting dir: {target_bin_dir}")
- os.makedirs(target_bin_dir, exist_ok=True)
-
- source_bin_glob = f"{source_bin_name}*"
- source_files = glob.glob(os.path.join(source_bin_dir, source_bin_glob))
-
- if not source_files:
- raise RuntimeError(
- f"No files found in {source_bin_dir} matching {source_bin_glob}"
+def check_access_violation(return_code, bin_path):
+ if return_code == ERROR_ACCESS_VIOLATION:
+ print(
+ f"Warning: Process crashed with memory access violation: {bin_path}",
+ file=sys.stderr,
)
- for source_file in source_files:
- base_name = os.path.basename(source_file)
- base_name = base_name.replace(source_bin_name, target_bin_name)
- target_file = os.path.join(target_bin_dir, base_name)
- print(f"Copying {source_file} to {target_file}")
- # use the copy command; shutil.copy gives us a permission denied error.
+
+def is_any_process_running(dir):
+ """Check if there is any running process that contains the given directory."""
+
+ print(f"Checking if any process is running in: {dir}")
+ for proc in psutil.process_iter(attrs=["name", "exe"]):
+ exe = proc.info["exe"]
+
+ if not exe:
+ continue
+
try:
- subprocess.run(["copy", source_file, target_file], shell=True, check=True)
- except subprocess.CalledProcessError as e:
- print(f"Copy failed: {e}")
+ if dir.lower() in exe.lower():
+ print(f"Process found: {exe}")
+ return True
+ except (psutil.NoSuchProcess, psutil.AccessDenied):
+ pass
+ return False
main()
diff --git a/src/cmd/synergyc/CMakeLists.txt b/src/cmd/synergyc/CMakeLists.txt
index 8f3a5f01b..45c60fb0e 100644
--- a/src/cmd/synergyc/CMakeLists.txt
+++ b/src/cmd/synergyc/CMakeLists.txt
@@ -44,7 +44,7 @@ endif()
list(APPEND sources ${arch_sources})
list(APPEND headers ${arch_headers})
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
@@ -69,3 +69,5 @@ if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
install(TARGETS ${target} DESTINATION bin)
endif()
+
+post_config()
diff --git a/src/cmd/synergyd/CMakeLists.txt b/src/cmd/synergyd/CMakeLists.txt
index d6087a163..545724242 100644
--- a/src/cmd/synergyd/CMakeLists.txt
+++ b/src/cmd/synergyd/CMakeLists.txt
@@ -38,3 +38,5 @@ target_link_libraries(
synlib
shared
${libs})
+
+post_config()
diff --git a/src/cmd/synergys/CMakeLists.txt b/src/cmd/synergys/CMakeLists.txt
index 60942febe..021c6c486 100644
--- a/src/cmd/synergys/CMakeLists.txt
+++ b/src/cmd/synergys/CMakeLists.txt
@@ -44,7 +44,7 @@ endif()
list(APPEND sources ${arch_sources})
list(APPEND headers ${arch_headers})
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
@@ -69,3 +69,5 @@ if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
install(TARGETS ${target} DESTINATION bin)
endif()
+
+post_config()
diff --git a/src/gui/CMakeLists.txt b/src/gui/CMakeLists.txt
index 56d17ee6f..2262e49dd 100644
--- a/src/gui/CMakeLists.txt
+++ b/src/gui/CMakeLists.txt
@@ -1,3 +1,20 @@
+# Synergy -- mouse and keyboard sharing utility
+# Copyright (C) 2024 Symless 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 LICENSE 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 .
+
+set(target synergy)
+
find_package(
Qt6
COMPONENTS Core Widgets Network
@@ -33,7 +50,7 @@ if(WIN32)
endif()
add_executable(
- synergy WIN32
+ ${target} WIN32
${GUI_SOURCE_FILES}
${GUI_UI_FILES}
${GUI_RC_FILES}
@@ -41,16 +58,16 @@ add_executable(
${QM_FILES})
include_directories(./src)
-target_link_libraries(synergy shared)
+target_link_libraries(${target} shared)
-target_link_libraries(synergy Qt6::Core Qt6::Widgets Qt6::Network)
+target_link_libraries(${target} Qt6::Core Qt6::Widgets Qt6::Network)
target_compile_definitions(
- synergy PRIVATE -DSYNERGY_VERSION_STAGE="${SYNERGY_VERSION_STAGE}")
-target_compile_definitions(synergy
+ ${target} PRIVATE -DSYNERGY_VERSION_STAGE="${SYNERGY_VERSION_STAGE}")
+target_compile_definitions(${target}
PRIVATE -DSYNERGY_REVISION="${SYNERGY_REVISION}")
if(WIN32)
- set_target_properties(synergy PROPERTIES LINK_FLAGS "/NODEFAULTLIB:LIBCMT")
+ set_target_properties(${target} PROPERTIES LINK_FLAGS "/NODEFAULTLIB:LIBCMT")
endif()
if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
@@ -61,13 +78,13 @@ if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
set(MACDEPLOYQT_CMD
"${MACDEPLOYQT_BIN} ${SYNERGY_BUNDLE_APP_DIR} -always-overwrite")
- install(TARGETS synergy DESTINATION ${SYNERGY_BUNDLE_BINARY_DIR})
+ install(TARGETS ${target} DESTINATION ${SYNERGY_BUNDLE_BINARY_DIR})
install(CODE "MESSAGE (\"Running: ${MACDEPLOYQT_CMD}\")")
install(CODE "execute_process(COMMAND ${MACDEPLOYQT_CMD})")
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
- install(TARGETS synergy DESTINATION bin)
+ install(TARGETS ${target} DESTINATION bin)
elseif(WIN32)
@@ -96,7 +113,7 @@ elseif(WIN32)
if(TARGET Qt6::windeployqt)
# execute windeployqt in a tmp directory after build
add_custom_command(
- TARGET synergy
+ TARGET ${target}
POST_BUILD
COMMAND set PATH=%PATH%$${qt6_install_prefix}/bin
COMMAND Qt6::windeployqt
@@ -104,3 +121,5 @@ elseif(WIN32)
endif()
endif()
+
+post_config()
diff --git a/src/gui/src/ElevateMode.h b/src/gui/src/ElevateMode.h
index 8b00fea0e..0d87f4e98 100644
--- a/src/gui/src/ElevateMode.h
+++ b/src/gui/src/ElevateMode.h
@@ -22,8 +22,8 @@
// command line argument to synergy core, determines if the server restarts
// when switching Windows desktops (e.g. when Windows UAC dialog pops up).
// The second, passed as a boolean flag to Synergyd over the IPC inside
-// kIpcCommandMessage, determines whether Synergy should be started with
-// elevated privileges.
+// IpcMessageType::CommandMessage, determines whether Synergy should be started
+// with elevated privileges.
//
// The matrix for these two behaviours is as follows:
// SodS Elevate
diff --git a/src/gui/src/IpcReader.cpp b/src/gui/src/IpcReader.cpp
index 73fe67cfc..8631e010f 100644
--- a/src/gui/src/IpcReader.cpp
+++ b/src/gui/src/IpcReader.cpp
@@ -17,7 +17,7 @@
*/
#include "IpcReader.h"
-#include "Ipc.h"
+#include "shared/Ipc.h"
#include
#include
#include
diff --git a/src/gui/src/MainWindow.h b/src/gui/src/MainWindow.h
index 232cb4c05..fe808d2fd 100644
--- a/src/gui/src/MainWindow.h
+++ b/src/gui/src/MainWindow.h
@@ -31,13 +31,12 @@
#include "AppConfig.h"
#include "ClientConnection.h"
#include "ConfigWriter.h"
-#include "Ipc.h"
#include "QIpcClient.h"
#include "ServerConfig.h"
#include "ServerConnection.h"
-#include "VersionChecker.h"
-
#include "TrayIcon.h"
+#include "VersionChecker.h"
+#include "shared/Ipc.h"
class QAction;
class QMenu;
@@ -169,8 +168,7 @@ protected:
bool clientArgs(QStringList &args, QString &app);
bool serverArgs(QStringList &args, QString &app);
void setStatus(const QString &status);
- void
- sendIpcMessage(qIpcMessageType type, const char *buffer, bool showErrors);
+ void sendIpcMessage(IpcMessageType type, const char *buffer, bool showErrors);
void updateFromLogLine(const QString &line);
QString getIPAddresses();
void stopService();
diff --git a/src/gui/src/QIpcClient.cpp b/src/gui/src/QIpcClient.cpp
index 6a327e73a..515ac8ed3 100644
--- a/src/gui/src/QIpcClient.cpp
+++ b/src/gui/src/QIpcClient.cpp
@@ -16,12 +16,13 @@
*/
#include "QIpcClient.h"
-#include "Ipc.h"
#include "IpcReader.h"
+#include "shared/Ipc.h"
#include
#include
#include
+#include
QIpcClient::QIpcClient(const StreamProvider &streamProvider)
: m_ReaderStarted(false),
@@ -61,7 +62,8 @@ void QIpcClient::connectToHost() {
m_Enabled = true;
infoMessage("connecting to service...");
- m_Socket->connectToHost(QHostAddress(QHostAddress::LocalHost), IPC_PORT);
+ const auto port = static_cast(kIpcPort);
+ m_Socket->connectToHost(QHostAddress(QHostAddress::LocalHost), port);
if (!m_ReaderStarted) {
m_Reader->start();
@@ -105,7 +107,7 @@ void QIpcClient::sendHello() {
stream->writeRawData(kIpcMsgHello, 4);
char typeBuf[1];
- typeBuf[0] = kIpcClientGui;
+ typeBuf[0] = static_cast(IpcClientType::GUI);
stream->writeRawData(typeBuf, 1);
}
diff --git a/src/lib/arch/CMakeLists.txt b/src/lib/arch/CMakeLists.txt
index d49bc34e7..d1fa02a34 100644
--- a/src/lib/arch/CMakeLists.txt
+++ b/src/lib/arch/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
@@ -33,7 +33,7 @@ endif()
list(APPEND sources ${arch_sources})
list(APPEND headers ${arch_headers})
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/base/CMakeLists.txt b/src/lib/base/CMakeLists.txt
index 3a6416bab..a84258745 100644
--- a/src/lib/base/CMakeLists.txt
+++ b/src/lib/base/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/base/log_outputters.cpp b/src/lib/base/log_outputters.cpp
index 11cb2e203..5be96dad8 100644
--- a/src/lib/base/log_outputters.cpp
+++ b/src/lib/base/log_outputters.cpp
@@ -212,40 +212,3 @@ void FileLogOutputter::open(const char *title) {}
void FileLogOutputter::close() {}
void FileLogOutputter::show(bool showIfEmpty) {}
-
-//
-// MesssageBoxLogOutputter
-//
-
-MesssageBoxLogOutputter::MesssageBoxLogOutputter() {
- // do nothing
-}
-
-MesssageBoxLogOutputter::~MesssageBoxLogOutputter() {
- // do nothing
-}
-
-void MesssageBoxLogOutputter::open(const char *title) {
- // do nothing
-}
-
-void MesssageBoxLogOutputter::close() {
- // do nothing
-}
-
-void MesssageBoxLogOutputter::show(bool showIfEmpty) {
- // do nothing
-}
-
-bool MesssageBoxLogOutputter::write(ELevel level, const char *msg) {
- // don't spam user with messages.
- if (level > kERROR) {
- return true;
- }
-
-#if SYSAPI_WIN32
- MessageBox(NULL, msg, CLOG->getFilterName(level), MB_OK);
-#endif
-
- return true;
-}
diff --git a/src/lib/base/log_outputters.h b/src/lib/base/log_outputters.h
index 2bf65060e..61d1efa02 100644
--- a/src/lib/base/log_outputters.h
+++ b/src/lib/base/log_outputters.h
@@ -160,19 +160,3 @@ private:
UInt32 m_maxBufferSize;
Buffer m_buffer;
};
-
-//! Write log to message box
-/*!
-The level for each message is ignored.
-*/
-class MesssageBoxLogOutputter : public ILogOutputter {
-public:
- MesssageBoxLogOutputter();
- virtual ~MesssageBoxLogOutputter();
-
- // ILogOutputter overrides
- virtual void open(const char *title);
- virtual void close();
- virtual void show(bool showIfEmpty);
- virtual bool write(ELevel level, const char *message);
-};
diff --git a/src/lib/client/CMakeLists.txt b/src/lib/client/CMakeLists.txt
index 298a02274..a74afe69b 100644
--- a/src/lib/client/CMakeLists.txt
+++ b/src/lib/client/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/common/CMakeLists.txt b/src/lib/common/CMakeLists.txt
index 4f66ba841..6c08ef760 100644
--- a/src/lib/common/CMakeLists.txt
+++ b/src/lib/common/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/io/CMakeLists.txt b/src/lib/io/CMakeLists.txt
index ee52610d3..4093a970b 100644
--- a/src/lib/io/CMakeLists.txt
+++ b/src/lib/io/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/ipc/CMakeLists.txt b/src/lib/ipc/CMakeLists.txt
index 0d535f405..9ca26df86 100644
--- a/src/lib/ipc/CMakeLists.txt
+++ b/src/lib/ipc/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/ipc/IpcClient.cpp b/src/lib/ipc/IpcClient.cpp
index fe8736908..c9bd18797 100644
--- a/src/lib/ipc/IpcClient.cpp
+++ b/src/lib/ipc/IpcClient.cpp
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -18,16 +17,16 @@
#include "ipc/IpcClient.h"
#include "base/TMethodEventJob.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcServerProxy.h"
+#include "shared/Ipc.h"
//
// IpcClient
//
IpcClient::IpcClient(IEventQueue *events, SocketMultiplexer *socketMultiplexer)
- : m_serverAddress(NetworkAddress(IPC_HOST, IPC_PORT)),
+ : m_serverAddress(NetworkAddress(kIpcHost, kIpcPort)),
m_socket(events, socketMultiplexer),
m_server(nullptr),
m_events(events) {
@@ -36,7 +35,7 @@ IpcClient::IpcClient(IEventQueue *events, SocketMultiplexer *socketMultiplexer)
IpcClient::IpcClient(
IEventQueue *events, SocketMultiplexer *socketMultiplexer, int port)
- : m_serverAddress(NetworkAddress(IPC_HOST, port)),
+ : m_serverAddress(NetworkAddress(kIpcHost, port)),
m_socket(events, socketMultiplexer),
m_server(nullptr),
m_events(events) {
@@ -81,7 +80,7 @@ void IpcClient::handleConnected(const Event &, void *) {
m_events->forIpcClient().connected(), this, m_server,
Event::kDontFreeData));
- IpcHelloMessage message(kIpcClientNode);
+ IpcHelloMessage message(IpcClientType::Node);
send(message);
}
diff --git a/src/lib/ipc/IpcClientProxy.cpp b/src/lib/ipc/IpcClientProxy.cpp
index 7c5dcc7fb..2c9949e90 100644
--- a/src/lib/ipc/IpcClientProxy.cpp
+++ b/src/lib/ipc/IpcClientProxy.cpp
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -18,13 +17,12 @@
#include "ipc/IpcClientProxy.h"
-#include "arch/Arch.h"
#include "base/Log.h"
#include "base/TMethodEventJob.h"
#include "io/IStream.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcSettingMessage.h"
+#include "shared/Ipc.h"
#include "synergy/ProtocolUtil.h"
//
@@ -33,10 +31,6 @@
IpcClientProxy::IpcClientProxy(synergy::IStream &stream, IEventQueue *events)
: m_stream(stream),
- m_clientType(kIpcClientUnknown),
- m_disconnecting(false),
- m_readMutex(ARCH->newMutex()),
- m_writeMutex(ARCH->newMutex()),
m_events(events) {
m_events->adoptHandler(
m_events->forIStream().inputReady(), stream.getEventTarget(),
@@ -135,7 +129,7 @@ void IpcClientProxy::send(const IpcMessage &message) {
LOG((CLOG_DEBUG4 "ipc write: %d", message.type()));
switch (message.type()) {
- case kIpcLogLine: {
+ case IpcMessageType::LogLine: {
const IpcLogLineMessage &llm =
static_cast(message);
const String logLine = llm.logLine();
@@ -143,11 +137,11 @@ void IpcClientProxy::send(const IpcMessage &message) {
break;
}
- case kIpcShutdown:
+ case IpcMessageType::Shutdown:
ProtocolUtil::writef(&m_stream, kIpcMsgShutdown);
break;
- case kIpcHelloBack:
+ case IpcMessageType::HelloBack:
ProtocolUtil::writef(&m_stream, kIpcMsgHelloBack);
break;
@@ -161,7 +155,7 @@ IpcHelloMessage *IpcClientProxy::parseHello() {
UInt8 type;
ProtocolUtil::readf(&m_stream, kIpcMsgHello + 4, &type);
- m_clientType = static_cast(type);
+ m_clientType = static_cast(type);
// must be deleted by event handler.
return new IpcHelloMessage(m_clientType);
diff --git a/src/lib/ipc/IpcClientProxy.h b/src/lib/ipc/IpcClientProxy.h
index 4b61900da..7362d16a2 100644
--- a/src/lib/ipc/IpcClientProxy.h
+++ b/src/lib/ipc/IpcClientProxy.h
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -18,10 +17,11 @@
#pragma once
+#include "arch/Arch.h"
#include "arch/IArchMultithread.h"
#include "base/Event.h"
#include "base/EventTypes.h"
-#include "ipc/Ipc.h"
+#include "shared/Ipc.h"
namespace synergy {
class IStream;
@@ -56,9 +56,9 @@ private:
private:
synergy::IStream &m_stream;
- EIpcClientType m_clientType;
- bool m_disconnecting;
- ArchMutex m_readMutex;
- ArchMutex m_writeMutex;
IEventQueue *m_events;
+ IpcClientType m_clientType = IpcClientType::Unknown;
+ bool m_disconnecting = false;
+ ArchMutex m_readMutex = ARCH->newMutex();
+ ArchMutex m_writeMutex = ARCH->newMutex();
};
diff --git a/src/lib/ipc/IpcLogOutputter.cpp b/src/lib/ipc/IpcLogOutputter.cpp
index 91891714a..2b4213100 100644
--- a/src/lib/ipc/IpcLogOutputter.cpp
+++ b/src/lib/ipc/IpcLogOutputter.cpp
@@ -24,11 +24,11 @@
#include "base/EventQueue.h"
#include "base/TMethodEventJob.h"
#include "base/TMethodJob.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcClientProxy.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcServer.h"
#include "mt/Thread.h"
+#include "shared/Ipc.h"
enum EIpcLogOutputter {
kBufferMaxSize = 1000,
@@ -38,7 +38,7 @@ enum EIpcLogOutputter {
};
IpcLogOutputter::IpcLogOutputter(
- IpcServer &ipcServer, EIpcClientType clientType, bool useThread)
+ IpcServer &ipcServer, IpcClientType clientType, bool useThread)
: m_ipcServer(ipcServer),
m_bufferMutex(ARCH->newMutex()),
m_sending(false),
@@ -179,7 +179,7 @@ void IpcLogOutputter::sendBuffer() {
IpcLogLineMessage message(getChunk(kMaxSendLines));
m_sending = true;
- m_ipcServer.send(message, kIpcClientGui);
+ m_ipcServer.send(message, IpcClientType::GUI);
m_sending = false;
}
diff --git a/src/lib/ipc/IpcLogOutputter.h b/src/lib/ipc/IpcLogOutputter.h
index a0f866cc6..a38a3380e 100644
--- a/src/lib/ipc/IpcLogOutputter.h
+++ b/src/lib/ipc/IpcLogOutputter.h
@@ -21,7 +21,7 @@
#include "arch/Arch.h"
#include "arch/IArchMultithread.h"
#include "base/ILogOutputter.h"
-#include "ipc/Ipc.h"
+#include "shared/Ipc.h"
#include
@@ -41,7 +41,7 @@ public:
using the \c sendBuffer() function.
*/
IpcLogOutputter(
- IpcServer &ipcServer, EIpcClientType clientType, bool useThread);
+ IpcServer &ipcServer, IpcClientType clientType, bool useThread);
IpcLogOutputter(IpcLogOutputter const &) = delete;
virtual ~IpcLogOutputter();
@@ -115,6 +115,6 @@ private:
double m_bufferRateTimeLimit;
UInt16 m_bufferWriteCount;
double m_bufferRateStart;
- EIpcClientType m_clientType;
+ IpcClientType m_clientType;
ArchMutex m_runningMutex;
};
diff --git a/src/lib/ipc/IpcMessage.cpp b/src/lib/ipc/IpcMessage.cpp
index e2fd70a64..955564b39 100644
--- a/src/lib/ipc/IpcMessage.cpp
+++ b/src/lib/ipc/IpcMessage.cpp
@@ -17,35 +17,25 @@
*/
#include "ipc/IpcMessage.h"
-#include "ipc/Ipc.h"
+#include "shared/Ipc.h"
-IpcMessage::IpcMessage(UInt8 type) : m_type(type) {}
+IpcMessage::IpcMessage(IpcMessageType type) : m_type(type) {}
-IpcMessage::~IpcMessage() {}
-
-IpcHelloMessage::IpcHelloMessage(EIpcClientType clientType)
- : IpcMessage(kIpcHello),
+IpcHelloMessage::IpcHelloMessage(IpcClientType clientType)
+ : IpcMessage(IpcMessageType::Hello),
m_clientType(clientType) {}
-IpcHelloMessage::~IpcHelloMessage() {}
+IpcHelloBackMessage::IpcHelloBackMessage()
+ : IpcMessage(IpcMessageType::HelloBack) {}
-IpcHelloBackMessage::IpcHelloBackMessage() : IpcMessage(kIpcHelloBack) {}
-
-IpcHelloBackMessage::~IpcHelloBackMessage() {}
-
-IpcShutdownMessage::IpcShutdownMessage() : IpcMessage(kIpcShutdown) {}
-
-IpcShutdownMessage::~IpcShutdownMessage() {}
+IpcShutdownMessage::IpcShutdownMessage()
+ : IpcMessage(IpcMessageType::Shutdown) {}
IpcLogLineMessage::IpcLogLineMessage(const String &logLine)
- : IpcMessage(kIpcLogLine),
+ : IpcMessage(IpcMessageType::LogLine),
m_logLine(logLine) {}
-IpcLogLineMessage::~IpcLogLineMessage() {}
-
IpcCommandMessage::IpcCommandMessage(const String &command, bool elevate)
- : IpcMessage(kIpcCommand),
+ : IpcMessage(IpcMessageType::Command),
m_command(command),
m_elevate(elevate) {}
-
-IpcCommandMessage::~IpcCommandMessage() {}
diff --git a/src/lib/ipc/IpcMessage.h b/src/lib/ipc/IpcMessage.h
index a10a4647c..594d6c666 100644
--- a/src/lib/ipc/IpcMessage.h
+++ b/src/lib/ipc/IpcMessage.h
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -19,52 +18,51 @@
#pragma once
#include "base/Event.h"
-#include "base/EventTypes.h"
#include "base/String.h"
-#include "ipc/Ipc.h"
+#include "shared/Ipc.h"
class IpcMessage : public EventData {
public:
- virtual ~IpcMessage();
+ ~IpcMessage() override = default;
//! Gets the message type ID.
- UInt8 type() const { return m_type; }
+ IpcMessageType type() const { return m_type; }
protected:
- IpcMessage(UInt8 type);
+ explicit IpcMessage(IpcMessageType type);
private:
- UInt8 m_type;
+ IpcMessageType m_type;
};
class IpcHelloMessage : public IpcMessage {
public:
- IpcHelloMessage(EIpcClientType clientType);
- virtual ~IpcHelloMessage();
+ explicit IpcHelloMessage(IpcClientType clientType);
+ ~IpcHelloMessage() override = default;
//! Gets the message type ID.
- EIpcClientType clientType() const { return m_clientType; }
+ IpcClientType clientType() const { return m_clientType; }
private:
- EIpcClientType m_clientType;
+ IpcClientType m_clientType;
};
class IpcHelloBackMessage : public IpcMessage {
public:
- IpcHelloBackMessage();
- virtual ~IpcHelloBackMessage();
+ explicit IpcHelloBackMessage();
+ ~IpcHelloBackMessage() override = default;
};
class IpcShutdownMessage : public IpcMessage {
public:
- IpcShutdownMessage();
- virtual ~IpcShutdownMessage();
+ explicit IpcShutdownMessage();
+ ~IpcShutdownMessage() override = default;
};
class IpcLogLineMessage : public IpcMessage {
public:
- IpcLogLineMessage(const String &logLine);
- virtual ~IpcLogLineMessage();
+ explicit IpcLogLineMessage(const String &logLine);
+ ~IpcLogLineMessage() override = default;
//! Gets the log line.
String logLine() const { return m_logLine; }
@@ -75,8 +73,8 @@ private:
class IpcCommandMessage : public IpcMessage {
public:
- IpcCommandMessage(const String &command, bool elevate);
- virtual ~IpcCommandMessage();
+ explicit IpcCommandMessage(const String &command, bool elevate);
+ ~IpcCommandMessage() override = default;
//! Gets the command.
String command() const { return m_command; }
diff --git a/src/lib/ipc/IpcServer.cpp b/src/lib/ipc/IpcServer.cpp
index 1cafec99d..0c3f6f730 100644
--- a/src/lib/ipc/IpcServer.cpp
+++ b/src/lib/ipc/IpcServer.cpp
@@ -23,10 +23,10 @@
#include "base/Log.h"
#include "base/TMethodEventJob.h"
#include "io/IStream.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcClientProxy.h"
#include "ipc/IpcMessage.h"
#include "net/IDataSocket.h"
+#include "shared/Ipc.h"
//
// IpcServer
@@ -37,7 +37,7 @@ IpcServer::IpcServer(IEventQueue *events, SocketMultiplexer *socketMultiplexer)
m_events(events),
m_socketMultiplexer(socketMultiplexer),
m_socket(nullptr),
- m_address(NetworkAddress(IPC_HOST, IPC_PORT)) {
+ m_address(NetworkAddress(kIpcHost, kIpcPort)) {
init();
}
@@ -46,7 +46,7 @@ IpcServer::IpcServer(
: m_mock(false),
m_events(events),
m_socketMultiplexer(socketMultiplexer),
- m_address(NetworkAddress(IPC_HOST, port)) {
+ m_address(NetworkAddress(kIpcHost, port)) {
init();
}
@@ -135,7 +135,7 @@ void IpcServer::deleteClient(IpcClientProxy *proxy) {
delete proxy;
}
-bool IpcServer::hasClients(EIpcClientType clientType) const {
+bool IpcServer::hasClients(IpcClientType clientType) const {
ArchMutexLock lock(m_clientsMutex);
if (m_clients.empty()) {
@@ -155,7 +155,7 @@ bool IpcServer::hasClients(EIpcClientType clientType) const {
return false;
}
-void IpcServer::send(const IpcMessage &message, EIpcClientType filterType) {
+void IpcServer::send(const IpcMessage &message, IpcClientType filterType) {
ArchMutexLock lock(m_clientsMutex);
ClientList::iterator it;
diff --git a/src/lib/ipc/IpcServer.h b/src/lib/ipc/IpcServer.h
index 36357d856..453a9abe9 100644
--- a/src/lib/ipc/IpcServer.h
+++ b/src/lib/ipc/IpcServer.h
@@ -20,9 +20,9 @@
#include "arch/Arch.h"
#include "base/EventTypes.h"
-#include "ipc/Ipc.h"
#include "net/NetworkAddress.h"
#include "net/TCPListenSocket.h"
+#include "shared/Ipc.h"
#include
@@ -58,14 +58,14 @@ public:
virtual void listen();
//! Send a message to all clients matching the filter type.
- virtual void send(const IpcMessage &message, EIpcClientType filterType);
+ virtual void send(const IpcMessage &message, IpcClientType filterType);
//@}
//! @name accessors
//@{
//! Returns true when there are clients of the specified type connected.
- virtual bool hasClients(EIpcClientType clientType) const;
+ virtual bool hasClients(IpcClientType clientType) const;
//@}
diff --git a/src/lib/ipc/IpcServerProxy.cpp b/src/lib/ipc/IpcServerProxy.cpp
index 545d9b2cb..25578e93f 100644
--- a/src/lib/ipc/IpcServerProxy.cpp
+++ b/src/lib/ipc/IpcServerProxy.cpp
@@ -21,8 +21,8 @@
#include "base/Log.h"
#include "base/TMethodEventJob.h"
#include "io/IStream.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcMessage.h"
+#include "shared/Ipc.h"
#include "synergy/ProtocolUtil.h"
//
@@ -78,13 +78,13 @@ void IpcServerProxy::send(const IpcMessage &message) {
LOG((CLOG_DEBUG4 "ipc write: %d", message.type()));
switch (message.type()) {
- case kIpcHello: {
+ case IpcMessageType::Hello: {
const IpcHelloMessage &hm = static_cast(message);
ProtocolUtil::writef(&m_stream, kIpcMsgHello, hm.clientType());
break;
}
- case kIpcCommand: {
+ case IpcMessageType::Command: {
const IpcCommandMessage &cm =
static_cast(message);
const String command = cm.command();
diff --git a/src/lib/ipc/IpcSettingMessage.cpp b/src/lib/ipc/IpcSettingMessage.cpp
index b539520bb..3ba9a5310 100644
--- a/src/lib/ipc/IpcSettingMessage.cpp
+++ b/src/lib/ipc/IpcSettingMessage.cpp
@@ -20,7 +20,7 @@
IpcSettingMessage::IpcSettingMessage(
const std::string &name, const std::string &value)
- : IpcMessage(kIpcSetting),
+ : IpcMessage(IpcMessageType::Setting),
m_name(name),
m_value(value) {}
diff --git a/src/lib/mt/CMakeLists.txt b/src/lib/mt/CMakeLists.txt
index 10e440a2f..671a2768b 100644
--- a/src/lib/mt/CMakeLists.txt
+++ b/src/lib/mt/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/net/CMakeLists.txt b/src/lib/net/CMakeLists.txt
index da3afb27d..29ffd3768 100644
--- a/src/lib/net/CMakeLists.txt
+++ b/src/lib/net/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h" "InverseSockets/*.h")
file(GLOB sources "*.cpp" "InverseSockets/*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/platform/CMakeLists.txt b/src/lib/platform/CMakeLists.txt
index 30679a8fb..a8b23812b 100644
--- a/src/lib/platform/CMakeLists.txt
+++ b/src/lib/platform/CMakeLists.txt
@@ -31,7 +31,7 @@ elseif(UNIX)
file(GLOB sources "XWindows*.cpp")
endif()
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/platform/MSWindowsWatchdog.cpp b/src/lib/platform/MSWindowsWatchdog.cpp
index c8652c1c8..2b4e783db 100644
--- a/src/lib/platform/MSWindowsWatchdog.cpp
+++ b/src/lib/platform/MSWindowsWatchdog.cpp
@@ -23,11 +23,11 @@
#include "base/Log.h"
#include "base/TMethodJob.h"
#include "base/log_outputters.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcLogOutputter.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcServer.h"
#include "mt/Thread.h"
+#include "shared/Ipc.h"
#include "synergy/App.h"
#include "synergy/ArgsBase.h"
@@ -510,7 +510,7 @@ void MSWindowsWatchdog::shutdownProcess(HANDLE handle, DWORD pid, int timeout) {
}
IpcShutdownMessage shutdown;
- m_ipcServer.send(shutdown, kIpcClientNode);
+ m_ipcServer.send(shutdown, IpcClientType::Node);
// wait for process to exit gracefully.
double start = ARCH->time();
diff --git a/src/lib/platform/XWindowsClipboard.cpp b/src/lib/platform/XWindowsClipboard.cpp
index 7c72d2c30..8c1ad4ac6 100644
--- a/src/lib/platform/XWindowsClipboard.cpp
+++ b/src/lib/platform/XWindowsClipboard.cpp
@@ -21,8 +21,8 @@
#include "arch/Arch.h"
#include "base/Log.h"
#include "base/Stopwatch.h"
+#include "common/basic_types.h"
#include "common/stdvector.h"
-#include "mt/Thread.h"
#include "platform/XWindowsClipboardBMPConverter.h"
#include "platform/XWindowsClipboardHTMLConverter.h"
#include "platform/XWindowsClipboardTextConverter.h"
@@ -534,13 +534,13 @@ bool XWindowsClipboard::icccmGetSelection(
assert(data != nullptr);
// request data conversion
- CICCCMGetClipboard getter(m_window, m_time, m_atomData);
- if (!getter.readClipboard(
+ if (CICCCMGetClipboard getter(m_window, m_time, m_atomData);
+ !getter.readClipboard(
m_display, m_selection, target, actualTarget, data)) {
LOG(
(CLOG_DEBUG1 "can't get data for selection target %s",
XWindowsUtil::atomToString(m_display, target).c_str()));
- LOGC(getter.m_error, (CLOG_WARN "icccm violation by clipboard owner"));
+ LOGC(getter.error(), (CLOG_WARN "icccm violation by clipboard owner"));
return false;
} else if (*actualTarget == None) {
LOG(
@@ -630,7 +630,7 @@ bool XWindowsClipboard::motifOwnsClipboard() const {
if (data.size() >= sizeof(MotifClipHeader)) {
MotifClipHeader header;
std::memcpy(&header, data.data(), sizeof(header));
- if ((header.m_id == kMotifClipHeader) &&
+ if ((header.m_id == MotifClip::Header) &&
(static_cast(header.m_selectionOwner) == owner)) {
return true;
}
@@ -658,7 +658,7 @@ void XWindowsClipboard::motifFillCache() {
return;
}
std::memcpy(&header, data.data(), sizeof(header));
- if (header.m_id != kMotifClipHeader || header.m_numItems < 1) {
+ if (header.m_id != MotifClip::Header || header.m_numItems < 1) {
return;
}
@@ -678,7 +678,7 @@ void XWindowsClipboard::motifFillCache() {
return;
}
std::memcpy(&item, data.data(), sizeof(item));
- if (item.m_id != kMotifClipItem ||
+ if (item.m_id != MotifClip::Item ||
item.m_numFormats - item.m_numDeletedFormats < 1) {
return;
}
@@ -707,7 +707,7 @@ void XWindowsClipboard::motifFillCache() {
continue;
}
std::memcpy(&motifFormat, data.data(), sizeof(motifFormat));
- if (motifFormat.m_id != kMotifClipFormat || motifFormat.m_length < 0 ||
+ if (motifFormat.m_id != MotifClip::Format || motifFormat.m_length < 0 ||
motifFormat.m_type == None || motifFormat.m_deleted != 0) {
continue;
}
@@ -1197,18 +1197,7 @@ XWindowsClipboard::CICCCMGetClipboard::CICCCMGetClipboard(
Window requestor, Time time, Atom property)
: m_requestor(requestor),
m_time(time),
- m_property(property),
- m_incr(false),
- m_failed(false),
- m_done(false),
- m_reading(false),
- m_error(false) {
- // do nothing
-}
-
-XWindowsClipboard::CICCCMGetClipboard::~CICCCMGetClipboard() {
- // do nothing
-}
+ m_property(property) {}
bool XWindowsClipboard::CICCCMGetClipboard::readClipboard(
Display *display, Atom selection, Atom target, Atom *actualTarget,
diff --git a/src/lib/platform/XWindowsClipboard.h b/src/lib/platform/XWindowsClipboard.h
index bb4ba96ea..ea88c905a 100644
--- a/src/lib/platform/XWindowsClipboard.h
+++ b/src/lib/platform/XWindowsClipboard.h
@@ -132,6 +132,7 @@ private:
void fillCache() const;
void doFillCache();
+protected:
//
// helper classes
//
@@ -140,7 +141,7 @@ private:
class CICCCMGetClipboard {
public:
CICCCMGetClipboard(Window requestor, Time time, Atom property);
- ~CICCCMGetClipboard();
+ ~CICCCMGetClipboard() = default;
// convert the given selection to the given type. returns
// true iff the conversion was successful or the conversion
@@ -156,16 +157,16 @@ private:
Window m_requestor;
Time m_time;
Atom m_property;
- bool m_incr;
- bool m_failed;
- bool m_done;
+ bool m_incr = false;
+ bool m_failed = false;
+ bool m_done = false;
// atoms needed for the protocol
- Atom m_atomNone; // NONE, not None
- Atom m_atomIncr;
+ Atom m_atomNone = None;
+ Atom m_atomIncr = None;
// true iff we've received the selection notify
- bool m_reading;
+ bool m_reading = false;
// the converted selection data
String *m_data = nullptr;
@@ -174,18 +175,20 @@ private:
// selection owner cannot convert to the requested type.
Atom *m_actualTarget = nullptr;
- public:
// true iff the selection owner didn't follow ICCCM conventions
- bool m_error;
+ bool m_error = false;
+
+ public:
+ bool error() const { return m_error; }
};
// Motif structure IDs
- enum { kMotifClipFormat = 1, kMotifClipItem, kMotifClipHeader };
+ enum class MotifClip : SInt32 { Format = 1, Item = 2, Header = 3 };
// _MOTIF_CLIP_HEADER structure
class MotifClipHeader {
public:
- SInt32 m_id; // kMotifClipHeader
+ MotifClip m_id;
SInt32 m_pad1[3];
SInt32 m_item;
SInt32 m_pad2[4];
@@ -198,7 +201,7 @@ private:
// Motif clip item structure
class MotifClipItem {
public:
- SInt32 m_id; // kMotifClipItem
+ MotifClip m_id;
SInt32 m_pad1[5];
SInt32 m_size;
SInt32 m_numFormats;
@@ -209,7 +212,7 @@ private:
// Motif clip format structure
class MotifClipFormat {
public:
- SInt32 m_id; // kMotifClipFormat
+ MotifClip m_id;
SInt32 m_pad1[6];
SInt32 m_length;
SInt32 m_data;
diff --git a/src/lib/server/CMakeLists.txt b/src/lib/server/CMakeLists.txt
index a2ff5f6f2..f0adc6324 100644
--- a/src/lib/server/CMakeLists.txt
+++ b/src/lib/server/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/shared/CMakeLists.txt b/src/lib/shared/CMakeLists.txt
index 9d91779eb..a58291bfe 100644
--- a/src/lib/shared/CMakeLists.txt
+++ b/src/lib/shared/CMakeLists.txt
@@ -17,7 +17,7 @@
file(GLOB headers "*.h")
file(GLOB sources "*.cpp")
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/ipc/Ipc.cpp b/src/lib/shared/Ipc.cpp
similarity index 62%
rename from src/lib/ipc/Ipc.cpp
rename to src/lib/shared/Ipc.cpp
index d7f9fba72..74179ffc2 100644
--- a/src/lib/ipc/Ipc.cpp
+++ b/src/lib/shared/Ipc.cpp
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -16,11 +15,14 @@
* along with this program. If not, see .
*/
-#include "ipc/Ipc.h"
+#include "Ipc.h"
-const char *kIpcMsgHello = "IHEL%1i";
-const char *kIpcMsgHelloBack = "IHEL";
-const char *kIpcMsgLogLine = "ILOG%s";
-const char *kIpcMsgCommand = "ICMD%s%1i";
-const char *kIpcMsgShutdown = "ISDN";
-const char *kIpcMsgSetting = "SSET%s%s";
+const char *const kIpcHost = "127.0.0.1";
+const int kIpcPort = 24801;
+
+const char *const kIpcMsgHello = "IHEL%1i";
+const char *const kIpcMsgHelloBack = "IHEL";
+const char *const kIpcMsgLogLine = "ILOG%s";
+const char *const kIpcMsgCommand = "ICMD%s%1i";
+const char *const kIpcMsgShutdown = "ISDN";
+const char *const kIpcMsgSetting = "SSET%s%s";
diff --git a/src/lib/ipc/Ipc.h b/src/lib/shared/Ipc.h
similarity index 71%
rename from src/lib/ipc/Ipc.h
rename to src/lib/shared/Ipc.h
index 22253276d..46b8a2eec 100644
--- a/src/lib/ipc/Ipc.h
+++ b/src/lib/shared/Ipc.h
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -18,42 +17,44 @@
#pragma once
-#define IPC_HOST "127.0.0.1"
-#define IPC_PORT 24801
+#include "common/basic_types.h"
-enum EIpcMessage {
- kIpcHello,
- kIpcHelloBack,
- kIpcLogLine,
- kIpcCommand,
- kIpcShutdown,
- kIpcSetting
+enum class IpcMessageType : UInt8 {
+ Hello,
+ HelloBack,
+ LogLine,
+ Command,
+ Shutdown,
+ Setting
};
-enum EIpcClientType { kIpcClientUnknown, kIpcClientGui, kIpcClientNode };
+enum class IpcClientType { Unknown, GUI, Node };
+
+extern const char *const kIpcHost;
+extern const int kIpcPort;
// handshake: node/gui -> daemon
// $1 = type, the client identifies it's self as gui or node (synergyc/s).
-extern const char *kIpcMsgHello;
+extern const char *const kIpcMsgHello;
// handshake: daemon -> node/gui
// the daemon responds to the handshake.
-extern const char *kIpcMsgHelloBack;
+extern const char *const kIpcMsgHelloBack;
// log line: daemon -> gui
// $1 = aggregate log lines collected from synergys/c or the daemon itself.
-extern const char *kIpcMsgLogLine;
+extern const char *const kIpcMsgLogLine;
// command: gui -> daemon
// $1 = command; the command for the daemon to launch, typically the full
// path to synergys/c. $2 = true when process must be elevated on ms windows.
-extern const char *kIpcMsgCommand;
+extern const char *const kIpcMsgCommand;
// shutdown: daemon -> node
// the daemon tells synergys/c to shut down gracefully.
-extern const char *kIpcMsgShutdown;
+extern const char *const kIpcMsgShutdown;
// set setting: gui -> daemon
// $1 = setting name
// $2 = setting value
-extern const char *kIpcMsgSetting;
+extern const char *const kIpcMsgSetting;
diff --git a/src/lib/synergy/App.cpp b/src/lib/synergy/App.cpp
index 4e1ae33d7..efc904e6b 100644
--- a/src/lib/synergy/App.cpp
+++ b/src/lib/synergy/App.cpp
@@ -1,6 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
+ * Copyright (C) 2012 Symless Ltd.
* Copyright (C) 2002 Chris Schoeneman
*
* This package is free software; you can redistribute it and/or
@@ -27,9 +27,9 @@
#include "base/XBase.h"
#include "base/log_outputters.h"
#include "common/Version.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcServerProxy.h"
+#include "shared/Ipc.h"
#include "synergy/ArgsBase.h"
#include "synergy/XSynergy.h"
#include "synergy/protocol_types.h"
@@ -230,7 +230,7 @@ void App::cleanupIpcClient() {
void App::handleIpcMessage(const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
- if (m->type() == kIpcShutdown) {
+ if (m->type() == IpcMessageType::Shutdown) {
LOG((CLOG_INFO "got ipc shutdown message"));
m_events->addEvent(Event(Event::kQuit));
}
diff --git a/src/lib/synergy/CMakeLists.txt b/src/lib/synergy/CMakeLists.txt
index 4e07c7780..29acc491c 100644
--- a/src/lib/synergy/CMakeLists.txt
+++ b/src/lib/synergy/CMakeLists.txt
@@ -39,7 +39,7 @@ endif()
list(APPEND sources ${arch_sources})
list(APPEND headers ${arch_headers})
-if(SYNERGY_ADD_HEADERS)
+if(ADD_HEADERS_TO_SOURCES)
list(APPEND sources ${headers})
endif()
diff --git a/src/lib/synergy/DaemonApp.cpp b/src/lib/synergy/DaemonApp.cpp
index 8fe7f8d85..0c73186e1 100644
--- a/src/lib/synergy/DaemonApp.cpp
+++ b/src/lib/synergy/DaemonApp.cpp
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -25,41 +24,43 @@
#include "base/EventQueue.h"
#include "base/Log.h"
#include "base/TMethodEventJob.h"
-#include "base/TMethodJob.h"
#include "base/log_outputters.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcClientProxy.h"
#include "ipc/IpcLogOutputter.h"
#include "ipc/IpcMessage.h"
#include "ipc/IpcSettingMessage.h"
#include "net/SocketMultiplexer.h"
+#include "shared/Ipc.h"
#include "synergy/App.h"
#include "synergy/ArgParser.h"
#include "synergy/ClientArgs.h"
#include "synergy/ServerArgs.h"
-#include "synergy/protocol_types.h"
#if SYSAPI_WIN32
#include "arch/win32/ArchMiscWindows.h"
-#include "arch/win32/XArchWindows.h"
#include "platform/MSWindowsDebugOutputter.h"
#include "platform/MSWindowsEventQueueBuffer.h"
-#include "platform/MSWindowsScreen.h"
#include "platform/MSWindowsWatchdog.h"
#include "synergy/Screen.h"
#define WIN32_LEAN_AND_MEAN
#include
-#endif
+#elif SYSAPI_UNIX
#include
+
+#endif
+
+#include
#include
#include
using namespace std;
+const char *const kLogFilename = "synergyd.log";
+
namespace {
void updateSetting(const IpcMessage &message) {
try {
@@ -84,7 +85,7 @@ bool isServerCommandLine(const std::vector &cmd) {
} // namespace
-DaemonApp *DaemonApp::s_instance = NULL;
+DaemonApp *DaemonApp::s_instance = nullptr;
int mainLoopStatic() {
DaemonApp::s_instance->mainLoop(true);
@@ -99,18 +100,9 @@ int winMainLoopStatic(int, const char **) {
}
#endif
-DaemonApp::DaemonApp()
- : m_ipcServer(nullptr),
- m_ipcLogOutputter(nullptr),
-#if SYSAPI_WIN32
- m_watchdog(nullptr),
-#endif
- m_events(nullptr),
- m_fileLogOutputter(nullptr) {
- s_instance = this;
-}
+DaemonApp::DaemonApp() { s_instance = this; }
-DaemonApp::~DaemonApp() {}
+DaemonApp::~DaemonApp() { s_instance = nullptr; }
int DaemonApp::run(int argc, char **argv) {
#if SYSAPI_WIN32
@@ -122,8 +114,7 @@ int DaemonApp::run(int argc, char **argv) {
arch.init();
Log log;
- EventQueue events;
- m_events = &events;
+ m_events = std::make_unique();
bool uninstall = false;
try {
@@ -134,8 +125,7 @@ int DaemonApp::run(int argc, char **argv) {
#endif
// default log level to system setting.
- string logLevel = arch.setting("LogLevel");
- if (logLevel != "")
+ if (string logLevel = arch.setting("LogLevel"); logLevel != "")
log.setFilter(logLevel.c_str());
bool foreground = false;
@@ -210,8 +200,9 @@ void DaemonApp::mainLoop(bool logToFile, bool foreground) {
DAEMON_RUNNING(true);
if (logToFile) {
- m_fileLogOutputter = new FileLogOutputter(logFilename().c_str());
- CLOG->insert(m_fileLogOutputter);
+ m_fileLogOutputter =
+ std::make_unique(logFilename().c_str());
+ CLOG->insert(m_fileLogOutputter.get());
}
// create socket multiplexer. this must happen after daemonization
@@ -219,20 +210,21 @@ void DaemonApp::mainLoop(bool logToFile, bool foreground) {
SocketMultiplexer multiplexer;
// uses event queue, must be created here.
- m_ipcServer = new IpcServer(m_events, &multiplexer);
+ m_ipcServer = std::make_unique(m_events.get(), &multiplexer);
// send logging to gui via ipc, log system adopts outputter.
- m_ipcLogOutputter = new IpcLogOutputter(*m_ipcServer, kIpcClientGui, true);
- CLOG->insert(m_ipcLogOutputter);
+ m_ipcLogOutputter = std::make_unique(
+ *m_ipcServer, IpcClientType::GUI, true);
+ CLOG->insert(m_ipcLogOutputter.get());
#if SYSAPI_WIN32
- m_watchdog = new MSWindowsWatchdog(
+ m_watchdog = std::make_unique(
false, *m_ipcServer, *m_ipcLogOutputter, foreground);
- m_watchdog->setFileLogOutputter(m_fileLogOutputter);
+ m_watchdog->setFileLogOutputter(m_fileLogOutputter.get());
#endif
m_events->adoptHandler(
- m_events->forIpcServer().messageReceived(), m_ipcServer,
+ m_events->forIpcServer().messageReceived(), m_ipcServer.get(),
new TMethodEventJob(this, &DaemonApp::handleIpcMessage));
m_ipcServer->listen();
@@ -240,7 +232,7 @@ void DaemonApp::mainLoop(bool logToFile, bool foreground) {
#if SYSAPI_WIN32
// install the platform event queue to handle service stop events.
- m_events->adoptBuffer(new MSWindowsEventQueueBuffer(m_events));
+ m_events->adoptBuffer(new MSWindowsEventQueueBuffer(m_events.get()));
String command = ARCH->setting("Command");
bool elevate = ARCH->setting("Elevate") == "1";
@@ -255,15 +247,12 @@ void DaemonApp::mainLoop(bool logToFile, bool foreground) {
#if SYSAPI_WIN32
m_watchdog->stop();
- delete m_watchdog;
#endif
m_events->removeHandler(
- m_events->forIpcServer().messageReceived(), m_ipcServer);
+ m_events->forIpcServer().messageReceived(), m_ipcServer.get());
- CLOG->remove(m_ipcLogOutputter);
- delete m_ipcLogOutputter;
- delete m_ipcServer;
+ CLOG->remove(m_ipcLogOutputter.get());
DAEMON_RUNNING(false);
} catch (std::exception &e) {
@@ -287,7 +276,7 @@ std::string DaemonApp::logFilename() {
if (logFilename.empty()) {
logFilename = ARCH->getLogDirectory();
logFilename.append("/");
- logFilename.append(LOG_FILENAME);
+ logFilename.append(kLogFilename);
}
return logFilename;
@@ -296,7 +285,7 @@ std::string DaemonApp::logFilename() {
void DaemonApp::handleIpcMessage(const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
switch (m->type()) {
- case kIpcCommand: {
+ case IpcMessageType::Command: {
IpcCommandMessage *cm = static_cast(m);
String command = cm->command();
@@ -361,14 +350,14 @@ void DaemonApp::handleIpcMessage(const Event &e, void *) {
break;
}
- case kIpcHello: {
+ case IpcMessageType::Hello: {
IpcHelloMessage *hm = static_cast(m);
String type;
switch (hm->clientType()) {
- case kIpcClientGui:
+ case IpcClientType::GUI:
type = "gui";
break;
- case kIpcClientNode:
+ case IpcClientType::Node:
type = "node";
break;
default:
@@ -379,7 +368,7 @@ void DaemonApp::handleIpcMessage(const Event &e, void *) {
LOG((CLOG_DEBUG "ipc hello, type=%s", type.c_str()));
// TODO: implement hello back handling in s1 gui and node (server/client).
- if (hm->clientType() == kIpcClientGui) {
+ if (hm->clientType() == IpcClientType::GUI) {
LOG((CLOG_DEBUG "sending ipc hello back"));
IpcHelloBackMessage hbm;
m_ipcServer->send(hbm, hm->clientType());
@@ -394,7 +383,7 @@ void DaemonApp::handleIpcMessage(const Event &e, void *) {
break;
}
- case kIpcSetting:
+ case IpcMessageType::Setting:
updateSetting(*m);
break;
}
diff --git a/src/lib/synergy/DaemonApp.h b/src/lib/synergy/DaemonApp.h
index 197c3e4ab..0dd94a86a 100644
--- a/src/lib/synergy/DaemonApp.h
+++ b/src/lib/synergy/DaemonApp.h
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2012 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -18,9 +17,9 @@
#pragma once
-#include "arch/Arch.h"
#include "ipc/IpcServer.h"
+#include
#include
class Event;
@@ -31,11 +30,13 @@ class FileLogOutputter;
class MSWindowsWatchdog;
#endif
+extern const char *const kLogFilename;
+
class DaemonApp {
public:
DaemonApp();
- virtual ~DaemonApp();
+ ~DaemonApp();
int run(int argc, char **argv);
void mainLoop(bool logToFile, bool foreground = false);
@@ -49,14 +50,12 @@ public:
static DaemonApp *s_instance;
#if SYSAPI_WIN32
- MSWindowsWatchdog *m_watchdog;
+ std::unique_ptr m_watchdog;
#endif
private:
- IpcServer *m_ipcServer;
- IpcLogOutputter *m_ipcLogOutputter;
- IEventQueue *m_events;
- FileLogOutputter *m_fileLogOutputter;
+ std::unique_ptr m_ipcServer;
+ std::unique_ptr m_ipcLogOutputter;
+ std::unique_ptr m_events;
+ std::unique_ptr m_fileLogOutputter;
};
-
-#define LOG_FILENAME "synergyd.log"
diff --git a/src/test/CMakeLists.txt b/src/test/CMakeLists.txt
index ad7f338d7..cc682af00 100644
--- a/src/test/CMakeLists.txt
+++ b/src/test/CMakeLists.txt
@@ -14,18 +14,158 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see .
-include_directories(
- ../../ext/googletest/googletest ../../ext/googletest/googletest/include
- ../../ext/googletest/googlemock ../../ext/googletest/googlemock/include)
+macro(config_all_tests)
-add_library(gtest STATIC ../../ext/googletest/googletest/src/gtest-all.cc)
-add_library(gmock STATIC ../../ext/googletest/googlemock/src/gmock-all.cc)
+ set(base_dir ${CMAKE_SOURCE_DIR})
+ set(src_dir ${base_dir}/src)
+ set(test_base_dir ${src_dir}/test)
+ set(ext_dir ${base_dir}/ext)
+ set(gtest_base_dir ${ext_dir}/googletest)
+ set(gui_dir ${src_dir}/gui/src)
-if(UNIX)
- # ignore warnings in gtest and gmock
- set_target_properties(gtest PROPERTIES COMPILE_FLAGS "-w")
- set_target_properties(gmock PROPERTIES COMPILE_FLAGS "-w")
-endif()
+ config_test_deps()
-add_subdirectory(integtests)
-add_subdirectory(unittests)
+ add_subdirectory(integtests)
+ add_subdirectory(unittests)
+
+endmacro()
+
+macro(config_test)
+
+ include_directories(
+ ${test_base_dir}
+ ${src_dir}
+ ${src_dir}/lib
+ ${gui_dir}
+ ${ext_dir})
+
+ set_sources()
+
+endmacro()
+
+macro(set_sources)
+
+ file(GLOB_RECURSE headers ${CMAKE_CURRENT_SOURCE_DIR}/*.h)
+ file(GLOB_RECURSE sources ${CMAKE_CURRENT_SOURCE_DIR}/*.cpp)
+
+ file(GLOB_RECURSE shared_headers ${test_base_dir}/shared/*.h)
+ file(GLOB_RECURSE shared_sources ${test_base_dir}/shared/*.cpp)
+
+ list(APPEND headers ${shared_headers})
+ list(APPEND sources ${shared_sources})
+
+ file(GLOB_RECURSE mock_headers ${test_base_dir}/mock/*.h)
+ file(GLOB_RECURSE mock_sources ${test_base_dir}/mock/*.cpp)
+
+ list(APPEND headers ${mock_headers})
+ list(APPEND sources ${mock_sources})
+
+ file(GLOB_RECURSE gui_sources ${gui_dir}/*.cpp)
+
+ file(GLOB activation_sources ${gui_dir}/*Activation* ${gui_dir}/*License*)
+ if(NOT ENABLE_LICENSING)
+ list(REMOVE_ITEM gui_sources ${activation_sources})
+ endif()
+
+ # remove main gui as the test already has its own main.
+ file(GLOB gui_main ${gui_dir}/main.cpp)
+ list(REMOVE_ITEM gui_sources ${gui_main})
+
+ if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
+ file(GLOB mac_gui_sources ${gui_dir}/*.mm)
+ list(APPEND gui_sources ${mac_gui_sources})
+ endif()
+
+ list(APPEND sources ${gui_sources})
+
+ if(ADD_HEADERS_TO_SOURCES)
+ list(APPEND sources ${headers})
+ endif()
+
+ if(WIN32)
+ list(APPEND sources ${CMAKE_BINARY_DIR}/src/version.rc)
+ endif()
+
+ add_platform_sources()
+
+endmacro()
+
+macro(add_platform_sources)
+
+ set(platform_dir ${CMAKE_CURRENT_SOURCE_DIR}/platform)
+
+ # Remove platform files so that specific platform files can be added later.
+ # This is a bit weird, but it's simpler to include everything, remove all
+ # platform files, then only include the platforms we need.
+ file(GLOB_RECURSE all_platform_files ${platform_dir}/*)
+ list(REMOVE_ITEM headers ${all_platform_files})
+ list(REMOVE_ITEM sources ${all_platform_files})
+
+ if(WIN32)
+ file(GLOB platform_sources ${platform_dir}/MSWindows*.cpp)
+ file(GLOB platform_headers ${platform_dir}/MSWindows*.h)
+ elseif(APPLE)
+ file(GLOB platform_sources ${platform_dir}/OSX*.cpp)
+ file(GLOB platform_headers ${platform_dir}/OSX*.h)
+ elseif(UNIX)
+ file(GLOB platform_sources ${platform_dir}/XWindows*.cpp)
+ file(GLOB platform_headers ${platform_dir}/XWindows*.h)
+ endif()
+
+ list(APPEND sources ${platform_sources})
+ list(APPEND headers ${platform_headers})
+
+endmacro()
+
+macro(config_test_deps)
+
+ set(CMAKE_AUTOMOC ON)
+ set(CMAKE_AUTORCC ON)
+ set(CMAKE_AUTOUIC ON)
+ set(CMAKE_INCLUDE_CURRENT_DIR ON)
+
+ find_package(
+ Qt6
+ COMPONENTS Core Widgets Network Test
+ REQUIRED)
+
+ set(gtest_dir ${gtest_base_dir}/googletest)
+ set(gmock_dir ${gtest_base_dir}/googlemock)
+
+ include_directories(${gtest_dir} ${gmock_dir} ${gtest_dir}/include
+ ${gmock_dir}/include)
+
+ add_library(gtest STATIC ${gtest_dir}/src/gtest-all.cc)
+ add_library(gmock STATIC ${gmock_dir}/src/gmock-all.cc)
+
+ if(UNIX)
+ # ignore warnings in gtest and gmock
+ set_target_properties(gtest PROPERTIES COMPILE_FLAGS "-w")
+ set_target_properties(gmock PROPERTIES COMPILE_FLAGS "-w")
+ endif()
+
+ set(test_libs
+ arch
+ base
+ client
+ server
+ common
+ io
+ net
+ platform
+ server
+ synlib
+ mt
+ ipc
+ gtest
+ gmock
+ shared
+ Qt6::Core
+ Qt6::Widgets
+ Qt6::Network
+ Qt6::Test
+ ${libs})
+
+endmacro()
+
+config_all_tests()
diff --git a/src/test/integtests/CMakeLists.txt b/src/test/integtests/CMakeLists.txt
index 58c256a04..82b350ac6 100644
--- a/src/test/integtests/CMakeLists.txt
+++ b/src/test/integtests/CMakeLists.txt
@@ -14,67 +14,7 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see .
-file(GLOB_RECURSE headers "*.h")
-file(GLOB_RECURSE sources "*.cpp")
-
-# remove platform files (specific platform added later).
-file(GLOB_RECURSE remove_platform "platform/*")
-list(REMOVE_ITEM headers ${remove_platform})
-list(REMOVE_ITEM sources ${remove_platform})
-
-# platform
-if(WIN32)
- file(GLOB platform_sources "platform/MSWindows*.cpp")
- file(GLOB platform_headers "platform/MSWindows*.h")
-elseif(APPLE)
- file(GLOB platform_sources "platform/OSX*.cpp")
- file(GLOB platform_headers "platform/OSX*.h")
-elseif(UNIX)
- file(GLOB platform_sources "platform/XWindows*.cpp")
- file(GLOB platform_headers "platform/XWindows*.h")
-endif()
-
-list(APPEND sources ${platform_sources})
-list(APPEND headers ${platform_headers})
-
-file(GLOB_RECURSE shared_headers "../../test/shared/*.h")
-file(GLOB_RECURSE shared_sources "../../test/shared/*.cpp")
-
-list(APPEND headers ${shared_headers})
-list(APPEND sources ${shared_sources})
-
-file(GLOB_RECURSE mock_headers "../../test/mock/*.h")
-file(GLOB_RECURSE mock_sources "../../test/mock/*.cpp")
-
-list(APPEND headers ${mock_headers})
-list(APPEND sources ${mock_sources})
-
-if(SYNERGY_ADD_HEADERS)
- list(APPEND sources ${headers})
-endif()
-
-if(WIN32)
- list(APPEND sources ${CMAKE_BINARY_DIR}/src/version.rc)
-endif()
-
-include_directories(
- ../../ ../../lib/ ../../../ext/googletest/googletest/include
- ../../../ext/googletest/googlemock/include)
-
-add_executable(integtests ${sources})
-target_link_libraries(
- integtests
- arch
- base
- client
- common
- io
- ipc
- mt
- net
- platform
- server
- synlib
- gtest
- gmock
- ${libs})
+config_test()
+set(target integtests)
+add_executable(${target} ${sources})
+target_link_libraries(${target} ${test_libs})
diff --git a/src/test/unittests/gui/MainWindowTests.cpp b/src/test/integtests/gui/MainWindowTests.cpp
similarity index 100%
rename from src/test/unittests/gui/MainWindowTests.cpp
rename to src/test/integtests/gui/MainWindowTests.cpp
diff --git a/src/test/integtests/ipc/IpcTests.cpp b/src/test/integtests/ipc/IpcTests.cpp
index ad42732a6..679e2366e 100644
--- a/src/test/integtests/ipc/IpcTests.cpp
+++ b/src/test/integtests/ipc/IpcTests.cpp
@@ -27,7 +27,6 @@
#include "base/String.h"
#include "base/TMethodEventJob.h"
#include "base/TMethodJob.h"
-#include "ipc/Ipc.h"
#include "ipc/IpcClient.h"
#include "ipc/IpcClientProxy.h"
#include "ipc/IpcMessage.h"
@@ -35,11 +34,12 @@
#include "ipc/IpcServerProxy.h"
#include "mt/Thread.h"
#include "net/SocketMultiplexer.h"
+#include "shared/Ipc.h"
#include "test/shared/TestEventQueue.h"
#include
-#define TEST_IPC_PORT 24802
+const int kTestPort = 24802;
class IpcTests : public ::testing::Test {
public:
@@ -65,7 +65,7 @@ public:
TEST_F(IpcTests, connectToServer) {
SocketMultiplexer socketMultiplexer;
- IpcServer server(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcServer server(&m_events, &socketMultiplexer, kTestPort);
server.listen();
m_connectToServer_server = &server;
@@ -74,7 +74,7 @@ TEST_F(IpcTests, connectToServer) {
new TMethodEventJob(
this, &IpcTests::connectToServer_handleMessageReceived));
- IpcClient client(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcClient client(&m_events, &socketMultiplexer, kTestPort);
client.connect();
m_events.initQuitTimeout(5);
@@ -88,7 +88,7 @@ TEST_F(IpcTests, connectToServer) {
TEST_F(IpcTests, sendMessageToServer) {
SocketMultiplexer socketMultiplexer;
- IpcServer server(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcServer server(&m_events, &socketMultiplexer, kTestPort);
server.listen();
// event handler sends "test" command to server.
@@ -97,7 +97,7 @@ TEST_F(IpcTests, sendMessageToServer) {
new TMethodEventJob(
this, &IpcTests::sendMessageToServer_serverHandleMessageReceived));
- IpcClient client(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcClient client(&m_events, &socketMultiplexer, kTestPort);
client.connect();
m_sendMessageToServer_client = &client;
@@ -111,7 +111,7 @@ TEST_F(IpcTests, sendMessageToServer) {
TEST_F(IpcTests, sendMessageToClient) {
SocketMultiplexer socketMultiplexer;
- IpcServer server(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcServer server(&m_events, &socketMultiplexer, kTestPort);
server.listen();
m_sendMessageToClient_server = &server;
@@ -121,7 +121,7 @@ TEST_F(IpcTests, sendMessageToClient) {
new TMethodEventJob(
this, &IpcTests::sendMessageToClient_serverHandleClientConnected));
- IpcClient client(&m_events, &socketMultiplexer, TEST_IPC_PORT);
+ IpcClient client(&m_events, &socketMultiplexer, kTestPort);
client.connect();
m_events.adoptHandler(
@@ -149,9 +149,9 @@ IpcTests::~IpcTests() {}
void IpcTests::connectToServer_handleMessageReceived(const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
- if (m->type() == kIpcHello) {
+ if (m->type() == IpcMessageType::Hello) {
m_connectToServer_hasClientNode =
- m_connectToServer_server->hasClients(kIpcClientNode);
+ m_connectToServer_server->hasClients(IpcClientType::Node);
m_connectToServer_helloMessageReceived = true;
m_events.raiseQuitEvent();
}
@@ -160,11 +160,11 @@ void IpcTests::connectToServer_handleMessageReceived(const Event &e, void *) {
void IpcTests::sendMessageToServer_serverHandleMessageReceived(
const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
- if (m->type() == kIpcHello) {
+ if (m->type() == IpcMessageType::Hello) {
LOG((CLOG_DEBUG "client said hello, sending test to server"));
IpcCommandMessage m("test", true);
m_sendMessageToServer_client->send(m);
- } else if (m->type() == kIpcCommand) {
+ } else if (m->type() == IpcMessageType::Command) {
IpcCommandMessage *cm = static_cast(m);
LOG((CLOG_DEBUG "got ipc command message, %d", cm->command().c_str()));
m_sendMessageToServer_receivedString = cm->command();
@@ -175,17 +175,17 @@ void IpcTests::sendMessageToServer_serverHandleMessageReceived(
void IpcTests::sendMessageToClient_serverHandleClientConnected(
const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
- if (m->type() == kIpcHello) {
+ if (m->type() == IpcMessageType::Hello) {
LOG((CLOG_DEBUG "client said hello, sending test to client"));
IpcLogLineMessage m("test");
- m_sendMessageToClient_server->send(m, kIpcClientNode);
+ m_sendMessageToClient_server->send(m, IpcClientType::Node);
}
}
void IpcTests::sendMessageToClient_clientHandleMessageReceived(
const Event &e, void *) {
IpcMessage *m = static_cast(e.getDataObject());
- if (m->type() == kIpcLogLine) {
+ if (m->type() == IpcMessageType::LogLine) {
IpcLogLineMessage *llm = static_cast(m);
LOG((CLOG_DEBUG "got ipc log message, %d", llm->logLine().c_str()));
m_sendMessageToClient_receivedString = llm->logLine();
diff --git a/src/test/integtests/platform/XWindowsClipboardTests.cpp b/src/test/integtests/platform/XWindowsClipboardTests.cpp
index 362750dc6..78963843a 100644
--- a/src/test/integtests/platform/XWindowsClipboardTests.cpp
+++ b/src/test/integtests/platform/XWindowsClipboardTests.cpp
@@ -16,142 +16,122 @@
* along with this program. If not, see .
*/
-// TODO: fix tests - compile error on linux
-#if 0
-
#include "platform/XWindowsClipboard.h"
+#include "test/shared/undef_x11_macros.h"
+
#include
-#include
+#include
-class CXWindowsClipboardTests : public ::testing::Test
-{
+class XWindowsClipboardTests : public ::testing::Test {
protected:
- virtual void
- SetUp()
- {
- m_display = XOpenDisplay(NULL);
- int screen = DefaultScreen(m_display);
- Window root = XRootWindow(m_display, screen);
-
- XSetWindowAttributes attr;
- attr.do_not_propagate_mask = 0;
- attr.override_redirect = True;
- attr.cursor = Cursor();
-
- m_window = XCreateWindow(
- m_display, root, 0, 0, 1, 1, 0, 0,
- InputOnly, CopyFromParent, 0, &attr);
- }
+ void SetUp() override {
+ m_display = XOpenDisplay(nullptr);
+ int screen = DefaultScreen(m_display);
+ Window root = XRootWindow(m_display, screen);
- virtual void
- TearDown()
- {
- XDestroyWindow(m_display, m_window);
- XCloseDisplay(m_display);
- }
+ XSetWindowAttributes attr;
+ attr.do_not_propagate_mask = 0;
+ attr.override_redirect = True;
+ attr.cursor = Cursor();
- CXWindowsClipboard&
- createClipboard()
- {
- CXWindowsClipboard* clipboard;
- clipboard = new CXWindowsClipboard(m_display, m_window, 0);
- clipboard->open(0); // needed to empty the clipboard
- clipboard->empty(); // needed to own the clipboard
- return *clipboard;
- }
+ m_window = XCreateWindow(
+ m_display, root, 0, 0, 1, 1, 0, 0, InputOnly, nullptr, 0, &attr);
- Display* m_display;
- Window m_window;
+ m_clipboard = std::make_unique(m_display, m_window, 0);
+ m_clipboard->open(0);
+ m_clipboard->empty();
+ }
+
+ void TearDown() override {
+ XDestroyWindow(m_display, m_window);
+ XCloseDisplay(m_display);
+ }
+
+ XWindowsClipboard &getClipboard() { return *m_clipboard; }
+
+private:
+ Display *m_display;
+ Window m_window;
+ std::unique_ptr m_clipboard;
};
-TEST_F(CXWindowsClipboardTests, empty_openCalled_returnsTrue)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- bool actual = clipboard.empty();
-
- EXPECT_EQ(true, actual);
+TEST_F(XWindowsClipboardTests, empty_openCalled_returnsTrue) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ bool actual = clipboard.empty();
+
+ EXPECT_EQ(true, actual);
}
-TEST_F(CXWindowsClipboardTests, empty_singleFormat_hasReturnsFalse)
-{
- CXWindowsClipboard clipboard = createClipboard();
- clipboard.add(CXWindowsClipboard::kText, "synergy rocks!");
-
- clipboard.empty();
-
- bool actual = clipboard.has(CXWindowsClipboard::kText);
- EXPECT_FALSE(actual);
+TEST_F(XWindowsClipboardTests, empty_singleFormat_hasReturnsFalse) {
+ XWindowsClipboard &clipboard = getClipboard();
+ clipboard.add(XWindowsClipboard::kText, "synergy rocks!");
+
+ clipboard.empty();
+
+ bool actual = clipboard.has(XWindowsClipboard::kText);
+ EXPECT_FALSE(actual);
}
-TEST_F(CXWindowsClipboardTests, add_newValue_valueWasStored)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- clipboard.add(IClipboard::kText, "synergy rocks!");
-
- String actual = clipboard.get(IClipboard::kText);
- EXPECT_EQ("synergy rocks!", actual);
+TEST_F(XWindowsClipboardTests, add_newValue_valueWasStored) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ clipboard.add(IClipboard::kText, "synergy rocks!");
+
+ String actual = clipboard.get(IClipboard::kText);
+ EXPECT_EQ("synergy rocks!", actual);
}
-TEST_F(CXWindowsClipboardTests, add_replaceValue_valueWasReplaced)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- clipboard.add(IClipboard::kText, "synergy rocks!");
- clipboard.add(IClipboard::kText, "maxivista sucks"); // haha, just kidding.
-
- String actual = clipboard.get(IClipboard::kText);
- EXPECT_EQ("maxivista sucks", actual);
+TEST_F(XWindowsClipboardTests, add_replaceValue_valueWasReplaced) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ clipboard.add(IClipboard::kText, "synergy rocks!");
+ clipboard.add(IClipboard::kText, "maxivista sucks"); // haha, just kidding.
+
+ String actual = clipboard.get(IClipboard::kText);
+ EXPECT_EQ("maxivista sucks", actual);
}
-TEST_F(CXWindowsClipboardTests, close_isOpen_noErrors)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- // clipboard opened in createClipboard()
- clipboard.close();
-
- // can't assert anything
+TEST_F(XWindowsClipboardTests, close_isOpen_noErrors) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ // clipboard opened in createClipboard()
+ clipboard.close();
+
+ // can't assert anything
}
-TEST_F(CXWindowsClipboardTests, has_withFormatAdded_returnsTrue)
-{
- CXWindowsClipboard clipboard = createClipboard();
- clipboard.add(IClipboard::kText, "synergy rocks!");
-
- bool actual = clipboard.has(IClipboard::kText);
-
- EXPECT_EQ(true, actual);
+TEST_F(XWindowsClipboardTests, has_withFormatAdded_returnsTrue) {
+ XWindowsClipboard &clipboard = getClipboard();
+ clipboard.add(IClipboard::kText, "synergy rocks!");
+
+ bool actual = clipboard.has(IClipboard::kText);
+
+ EXPECT_EQ(true, actual);
}
-TEST_F(CXWindowsClipboardTests, has_withNoFormats_returnsFalse)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- bool actual = clipboard.has(IClipboard::kText);
-
- EXPECT_FALSE(actual);
+TEST_F(XWindowsClipboardTests, has_withNoFormats_returnsFalse) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ bool actual = clipboard.has(IClipboard::kText);
+
+ EXPECT_FALSE(actual);
}
-TEST_F(CXWindowsClipboardTests, get_withNoFormats_returnsEmpty)
-{
- CXWindowsClipboard clipboard = createClipboard();
-
- String actual = clipboard.get(IClipboard::kText);
-
- EXPECT_EQ("", actual);
+TEST_F(XWindowsClipboardTests, get_withNoFormats_returnsEmpty) {
+ XWindowsClipboard &clipboard = getClipboard();
+
+ String actual = clipboard.get(IClipboard::kText);
+
+ EXPECT_EQ("", actual);
}
-TEST_F(CXWindowsClipboardTests, get_withFormatAdded_returnsExpected)
-{
- CXWindowsClipboard clipboard = createClipboard();
- clipboard.add(IClipboard::kText, "synergy rocks!");
-
- String actual = clipboard.get(IClipboard::kText);
-
- EXPECT_EQ("synergy rocks!", actual);
-}
+TEST_F(XWindowsClipboardTests, get_withFormatAdded_returnsExpected) {
+ XWindowsClipboard &clipboard = getClipboard();
+ clipboard.add(IClipboard::kText, "synergy rocks!");
-#endif
+ String actual = clipboard.get(IClipboard::kText);
+
+ EXPECT_EQ("synergy rocks!", actual);
+}
diff --git a/src/test/mock/ipc/MockIpcServer.h b/src/test/mock/ipc/MockIpcServer.h
index abe7bf1e9..7e0e7163c 100644
--- a/src/test/mock/ipc/MockIpcServer.h
+++ b/src/test/mock/ipc/MockIpcServer.h
@@ -45,8 +45,8 @@ public:
}
MOCK_METHOD(void, listen, (), (override));
- MOCK_METHOD(void, send, (const IpcMessage &, EIpcClientType), (override));
- MOCK_METHOD(bool, hasClients, (EIpcClientType), (const, override));
+ MOCK_METHOD(void, send, (const IpcMessage &, IpcClientType), (override));
+ MOCK_METHOD(bool, hasClients, (IpcClientType), (const, override));
void delegateToFake() {
ON_CALL(*this, send(_, _))
@@ -56,7 +56,7 @@ public:
void waitForSend() { ARCH->waitCondVar(m_sendCond, m_sendMutex, 5); }
private:
- void mockSend(const IpcMessage &, EIpcClientType) {
+ void mockSend(const IpcMessage &, IpcClientType) {
ArchMutexLock lock(m_sendMutex);
ARCH->broadcastCondVar(m_sendCond);
}
diff --git a/src/gui/src/Ipc.cpp b/src/test/shared/undef_x11_macros.h
similarity index 68%
rename from src/gui/src/Ipc.cpp
rename to src/test/shared/undef_x11_macros.h
index 39be8686c..aabf58bf3 100644
--- a/src/gui/src/Ipc.cpp
+++ b/src/test/shared/undef_x11_macros.h
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2024 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -16,11 +15,12 @@
* along with this program. If not, see .
*/
-// this class is a duplicate of /src/lib/ipc/Ipc.cpp
+/**
+ * This header fixes conflicts between X11 and Google Test.
+ *
+ * It should be included after headers of code under test (that use X11)
+ * and before including Google Test headers.
+ */
-#include "Ipc.h"
-
-const char *kIpcMsgHello = "IHEL%1i";
-const char *kIpcMsgLogLine = "ILOG%s";
-const char *kIpcMsgCommand = "ICMD%s%1i";
-const char *kIpcMsgShutdown = "ISDN";
+#undef None // NOSONAR
+#undef Bool // NOSONAR
diff --git a/src/test/unittests/CMakeLists.txt b/src/test/unittests/CMakeLists.txt
index ef9117b42..45df145f1 100644
--- a/src/test/unittests/CMakeLists.txt
+++ b/src/test/unittests/CMakeLists.txt
@@ -14,110 +14,7 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see .
+config_test()
set(target unittests)
-
-file(GLOB_RECURSE headers "*.h" "languages/*.h")
-file(GLOB_RECURSE sources "*.cpp" "languages/*.cpp")
-
-file(GLOB_RECURSE remove_platform "platform/*")
-list(REMOVE_ITEM headers ${remove_platform})
-list(REMOVE_ITEM sources ${remove_platform})
-
-file(GLOB_RECURSE shared_headers "../../test/shared/*.h")
-file(GLOB_RECURSE shared_sources "../../test/shared/*.cpp")
-
-list(APPEND headers ${shared_headers})
-list(APPEND sources ${shared_sources})
-
-file(GLOB_RECURSE mock_headers "../../test/mock/*.h")
-file(GLOB_RECURSE mock_sources "../../test/mock/*.cpp")
-
-list(APPEND headers ${mock_headers})
-list(APPEND sources ${mock_sources})
-
-set(gui_dir "../../gui/src")
-file(GLOB_RECURSE gui_sources "${gui_dir}/*.cpp")
-
-file(GLOB activation_sources "${gui_dir}/*Activation*" "${gui_dir}/*License*")
-if(NOT ENABLE_LICENSING)
- list(REMOVE_ITEM gui_sources ${activation_sources})
-endif()
-
-# remove main gui as the test already has its own main.
-file(GLOB gui_main "${gui_dir}/main.cpp")
-list(REMOVE_ITEM gui_sources ${gui_main})
-
-if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
- file(GLOB mac_gui_sources "${gui_dir}/*.mm")
- list(APPEND gui_sources ${mac_gui_sources})
-endif()
-
-list(APPEND sources ${gui_sources})
-
-# platform
-if(WIN32)
- file(GLOB platform_sources "platform/MSWindows*.cpp")
- file(GLOB platform_headers "platform/MSWindows*.h")
-elseif(APPLE)
- file(GLOB platform_sources "platform/OSX*.cpp")
- file(GLOB platform_headers "platform/OSX*.h")
-elseif(UNIX)
- file(GLOB platform_sources "platform/XWindows*.cpp")
- file(GLOB platform_headers "platform/XWindows*.h")
-endif()
-
-list(APPEND sources ${platform_sources})
-list(APPEND headers ${platform_headers})
-
-set(ext_dir "../../../ext")
-
-include_directories(
- "../.."
- "../../lib"
- ${ext_dir}
- ${gui_dir}
- "${ext_dir}/gtest/include"
- "${ext_dir}/gmock/include")
-
-if(SYNERGY_ADD_HEADERS)
- list(APPEND sources ${headers})
-endif()
-
-if(WIN32)
- list(APPEND sources ${CMAKE_BINARY_DIR}/src/version.rc)
-endif()
-
-set(CMAKE_AUTOMOC ON)
-set(CMAKE_AUTORCC ON)
-set(CMAKE_AUTOUIC ON)
-set(CMAKE_INCLUDE_CURRENT_DIR ON)
-
-find_package(
- Qt6
- COMPONENTS Core Widgets Network Test
- REQUIRED)
-
add_executable(${target} ${sources})
-
-target_link_libraries(
- ${target}
- arch
- base
- client
- server
- common
- io
- net
- platform
- server
- synlib
- mt
- ipc
- gtest
- gmock
- shared
- Qt6::Core
- Qt6::Widgets
- Qt6::Network
- Qt6::Test
- ${libs})
+target_link_libraries(${target} ${test_libs})
diff --git a/src/test/unittests/ipc/IpcLogOutputterTests.cpp b/src/test/unittests/ipc/IpcLogOutputterTests.cpp
index ceebd6c7b..f52e60850 100644
--- a/src/test/unittests/ipc/IpcLogOutputterTests.cpp
+++ b/src/test/unittests/ipc/IpcLogOutputterTests.cpp
@@ -62,7 +62,7 @@ using namespace synergy;
// _)).Times(1); EXPECT_CALL(mockServer, send(IpcLogLineMessageEq("mock
// 2\n"), _)).Times(1);
//
-// IpcLogOutputter outputter(mockServer, kIpcClientUnknown, true);
+// IpcLogOutputter outputter(mockServer, IpcClientType::Unknown, true);
// outputter.write(kNOTE, "mock 1");
// mockServer.waitForSend();
// outputter.write(kNOTE, "mock 2");
@@ -78,7 +78,7 @@ using namespace synergy;
// EXPECT_CALL(mockServer, send(IpcLogLineMessageEq("mock 2\nmock 3\n"),
// _)).Times(1);
//
-// IpcLogOutputter outputter(mockServer, kIpcClientUnknown, false);
+// IpcLogOutputter outputter(mockServer, IpcClientType::Unknown, false);
// outputter.bufferMaxSize(2);
//
// // log more lines than the buffer can contain
@@ -98,7 +98,7 @@ using namespace synergy;
// EXPECT_CALL(mockServer, send(IpcLogLineMessageEq("mock 1\nmock 2\n"),
// _)).Times(1);
//
-// IpcLogOutputter outputter(mockServer, kIpcClientUnknown, false);
+// IpcLogOutputter outputter(mockServer, IpcClientType::Unknown, false);
// outputter.bufferMaxSize(2);
//
// // log more lines than the buffer can contain
@@ -156,7 +156,7 @@ using namespace synergy;
// _)).Times(1); EXPECT_CALL(mockServer, send(IpcLogLineMessageEq("mock
// 3\nmock 4\n"), _)).Times(1);
//
-// IpcLogOutputter outputter(mockServer, kIpcClientUnknown, false);
+// IpcLogOutputter outputter(mockServer, IpcClientType::Unknown, false);
// outputter.bufferRateLimit(4, 1); // 1s (should be plenty of time)
//
// // log 1 more line than the buffer can accept in time limit.
diff --git a/src/gui/src/Ipc.h b/src/test/unittests/platform/XWindowsClipboardTests.cpp
similarity index 54%
rename from src/gui/src/Ipc.h
rename to src/test/unittests/platform/XWindowsClipboardTests.cpp
index 76d7bc6b0..3bb4f9f60 100644
--- a/src/gui/src/Ipc.h
+++ b/src/test/unittests/platform/XWindowsClipboardTests.cpp
@@ -1,7 +1,6 @@
/*
* synergy -- mouse and keyboard sharing utility
- * Copyright (C) 2012-2016 Symless Ltd.
- * Copyright (C) 2012 Nick Bolton
+ * Copyright (C) 2024 Symless Ltd.
*
* This package is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -16,27 +15,24 @@
* along with this program. If not, see .
*/
-// this class is a duplicate of /src/lib/ipc/Ipc.h
+#include "platform/XWindowsClipboard.h"
-#pragma once
+#include "test/shared/undef_x11_macros.h"
-#define IPC_HOST "127.0.0.1"
-#define IPC_PORT 24801
+#include
-enum qIpcMessageType {
- kIpcHello,
- kIpcLogLine,
- kIpcCommand,
- kIpcShutdown,
+const auto None = 0L;
+
+class TestXWindowsClipboard : public XWindowsClipboard {
+public:
+ class TestCICCCMGetClipboard : public CICCCMGetClipboard {
+ public:
+ TestCICCCMGetClipboard() : CICCCMGetClipboard(None, None, None) {}
+ };
};
-enum qIpcClientType {
- kIpcClientUnknown,
- kIpcClientGui,
- kIpcClientNode,
-};
+TEST(XWindowsClipboardTests_CICCCMGetClipboard, ctor_default_errorNone) {
+ TestXWindowsClipboard::TestCICCCMGetClipboard clipboard;
-extern const char *kIpcMsgHello;
-extern const char *kIpcMsgLogLine;
-extern const char *kIpcMsgCommand;
-extern const char *kIpcMsgShutdown;
+ EXPECT_EQ(None, clipboard.error());
+}