diff --git a/CMakeLists.txt b/CMakeLists.txt index a0095ebb..caef7384 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -52,6 +52,10 @@ set(BUILD_TIMESTAMP ${DBUS_BUILD_TIMESTAMP}) ########### basic vars ############### +if(UNIX AND CMAKE_SYSTEM_NAME STREQUAL "Linux") + set(DBUS_LINUX 1) +endif() + include(GNUInstallDirs) if(DBUSDIR) @@ -135,6 +139,44 @@ option(DBUS_DISABLE_ASSERT "Disable assertion checking" OFF) option(DBUS_ENABLE_STATS "enable bus daemon usage statistics" OFF) option(DBUS_ENABLE_CONTAINERS "enable restricted servers for app-containers" OFF) +if(DBUS_LINUX) + add_auto_option(ENABLE_SYSTEMD "build with systemd at_console support" AUTO) + include(FindPkgConfig) + pkg_check_modules(SYSTEMD libsystemd>=209) + if(NOT SYSTEMD_FOUND) + pkg_check_modules(SYSTEMD libsystemd-login>=32 libsystemd-daemon>=32 libsystemd-journal>=32) + endif() + check_auto_option(ENABLE_SYSTEMD "systemd support" SYSTEMD_FOUND "systemd") + if(ENABLE_SYSTEMD AND SYSTEMD_FOUND) + set(DBUS_BUS_ENABLE_SYSTEMD ON) + set(HAVE_SYSTEMD ${SYSTEMD_FOUND}) + endif() + option(ENABLE_USER_SESSION "enable user-session semantics for session bus under systemd" OFF) + set(DBUS_ENABLE_USER_SESSION ${ENABLE_USER_SESSION}) + + add_path_option(WITH_SYSTEMD_SYSTEMUNITDIR "Directory for systemd service files" "") + add_path_option(WITH_SYSTEMD_USERUNITDIR "Directory for systemd user service files" "") + # get defaults + pkg_check_modules(_SYSTEMD systemd) + if(_SYSTEMD_FOUND) + pkg_get_variable(_SYSTEMD_PREFIX systemd prefix) + pkg_get_variable(_SYSTEMD_SYSTEMUNITDIR systemd systemdsystemunitdir) + pkg_get_variable(_SYSTEMD_USERUNITDIR systemd systemduserunitdir) + # remove install prefix, which may not match the current prefix + string(REPLACE "${_SYSTEMD_PREFIX}/" "" DBUS_SYSTEMD_SYSTEMUNITDIR ${_SYSTEMD_SYSTEMUNITDIR}) + string(REPLACE "${_SYSTEMD_PREFIX}/" "" DBUS_SYSTEMD_USERUNITDIR ${_SYSTEMD_USERUNITDIR}) + else() + set(DBUS_SYSTEMD_SYSTEMUNITDIR lib/systemd/system) + set(DBUS_SYSTEMD_USERUNITDIR lib/systemd/user) + endif() + if(WITH_SYSTEMD_SYSTEMUNITDIR) + set(DBUS_SYSTEMD_SYSTEMUNITDIR ${WITH_SYSTEMD_SYSTEMUNITDIR}) + endif() + if(WITH_SYSTEMD_USERUNITDIR) + set(DBUS_SYSTEMD_USERUNITDIR ${WITH_SYSTEMD_USERUNITDIR}) + endif() +endif() + if(WIN32) set(FD_SETSIZE "8192" CACHE STRING "The maximum number of connections that can be handled at once") endif() @@ -609,6 +651,9 @@ message(" Building bus stats API: ${DBUS_ENABLE_STATS} " message(" installing system libs: ${DBUS_INSTALL_SYSTEM_LIBS} ") message(" Building inotify support: ${DBUS_BUS_ENABLE_INOTIFY} ") message(" Building kqueue support: ${DBUS_BUS_ENABLE_KQUEUE} ") +message(" Building systemd support: ${DBUS_BUS_ENABLE_SYSTEMD} ") +message(" systemd system install dir:${DBUS_SYSTEMD_SYSTEMUNITDIR} ") +message(" systemd user install dir: ${DBUS_SYSTEMD_USERUNITDIR} ") message(" Building Doxygen docs: ${DBUS_ENABLE_DOXYGEN_DOCS} ") message(" Building Qt help docs: ${DBUS_ENABLE_QTHELP_DOCS} ") message(" Building XML docs: ${DBUS_ENABLE_XML_DOCS} ") @@ -679,7 +724,6 @@ add_custom_target(help-options # if(DBUS_ENABLE_PKGCONFIG) set(PLATFORM_LIBS pthread ${LIBRT}) - include(FindPkgConfig QUIET) if(PKG_CONFIG_FOUND) # convert lists of link libraries into -lstdc++ -lm etc.. foreach(LIB ${CMAKE_C_IMPLICIT_LINK_LIBRARIES} ${PLATFORM_LIBS}) diff --git a/README.cmake b/README.cmake index e6bc9725..7c984430 100644 --- a/README.cmake +++ b/README.cmake @@ -149,6 +149,18 @@ DBUS_ENABLE_STATS:BOOL=OFF // enable restricted servers for app containers DBUS_ENABLE_CONTAINERS:BOOL=OFF +// build with systemd at_console support +ENABLE_SYSTEMD:STRING=AUTO + +// Directory for systemd service files +WITH_SYSTEMD_SYSTEMUNITDIR:STRING= + +// enable user-session semantics for session bus under systemd +ENABLE_USER_SESSION:BOOL=ON + +// Directory for systemd user service files +WITH_SYSTEMD_USERUNITDIR:STRING= + // support verbose debug mode DBUS_ENABLE_VERBOSE_MODE:BOOL=ON diff --git a/bus/CMakeLists.txt b/bus/CMakeLists.txt index 84d86125..09503966 100644 --- a/bus/CMakeLists.txt +++ b/bus/CMakeLists.txt @@ -107,16 +107,16 @@ set_target_properties(dbus-daemon PROPERTIES COMPILE_FLAGS ${DBUS_INTERNAL_CLIEN install(TARGETS dbus-daemon ${INSTALL_TARGETS_DEFAULT_ARGS}) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/session.conf DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1) -install(FILES ${CMAKE_CURRENT_BINARY_DIR}/legacy-config/session.conf DESTINATION ${CMAKE_INSTALL_SYSCONFDIR}/dbus-1) +install(FILES ${CMAKE_CURRENT_BINARY_DIR}/legacy-config/session.conf DESTINATION ${CMAKE_INSTALL_FULL_SYSCONFDIR}/dbus-1) install(DIRECTORY DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1/session.d) install(DIRECTORY DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1/services) if(NOT WIN32) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/system.conf DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1) - install(FILES ${CMAKE_CURRENT_BINARY_DIR}/legacy-config/system.conf DESTINATION ${CMAKE_INSTALL_SYSCONFDIR}/dbus-1) + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/legacy-config/system.conf DESTINATION ${CMAKE_INSTALL_FULL_SYSCONFDIR}/dbus-1) install(DIRECTORY DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1/system.d) install(DIRECTORY DESTINATION ${CMAKE_INSTALL_DATADIR}/dbus-1/system-services) - install(DIRECTORY DESTINATION ${CMAKE_INSTALL_LOCALSTATEDIR}/run/dbus) + install(DIRECTORY DESTINATION ${CMAKE_INSTALL_FULL_LOCALSTATEDIR}/run/dbus) endif() if(DBUS_SERVICE) @@ -154,18 +154,34 @@ if(MSVC) project_source_group(${GROUP_CODE} bus_test_SOURCES dummy) endif() -configure_file(example-session-disable-stats.conf.in ${CMAKE_CURRENT_BINARY_DIR}/example-session-disable-stats.conf) -set(EXAMPLES_DATA - ${CMAKE_CURRENT_BINARY_DIR}/example-session-disable-stats.conf -) +macro(install_example_in_file a) + configure_file(${a}.in ${CMAKE_CURRENT_BINARY_DIR}/${a}) + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/${a} DESTINATION ${CMAKE_INSTALL_DATADIR}/doc/dbus/examples) +endmacro() + +macro(install_example_file a) + install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/${a} DESTINATION ${CMAKE_INSTALL_DATADIR}/doc/dbus/examples) +endmacro() + +install_example_in_file(example-session-disable-stats.conf) if(NOT WIN32) - configure_file(example-system-enable-stats.conf.in ${CMAKE_CURRENT_BINARY_DIR}/example-system-enable-stats.conf) - list(APPEND EXAMPLES_DATA - ${CMAKE_CURRENT_BINARY_DIR}/example-system-enable-stats.conf - ) + install_example_in_file(example-system-enable-stats.conf) + install_example_file(example-system-hardening-without-traditional-activation.conf) endif() -install(FILES ${EXAMPLES_DATA} DESTINATION ${CMAKE_INSTALL_DATADIR}/doc/dbus/examples) +if(DBUS_BUS_ENABLE_SYSTEMD) + configure_file(dbus.socket.in ${CMAKE_CURRENT_BINARY_DIR}/dbus.socket) + configure_file(dbus.service.in ${CMAKE_CURRENT_BINARY_DIR}/dbus.service) + add_systemd_service(${CMAKE_CURRENT_BINARY_DIR}/dbus.socket PATH ${DBUS_SYSTEMD_SYSTEMUNITDIR} LINKS sockets.target.wants) + add_systemd_service(${CMAKE_CURRENT_BINARY_DIR}/dbus.service PATH ${DBUS_SYSTEMD_SYSTEMUNITDIR} LINKS multi-user.target.wants) +endif() + +if(DBUS_ENABLE_USER_SESSION) + configure_file(systemd-user/dbus.socket.in ${CMAKE_CURRENT_BINARY_DIR}/systemd-user/dbus.socket) + configure_file(systemd-user/dbus.service.in ${CMAKE_CURRENT_BINARY_DIR}/systemd-user/dbus.service) + add_systemd_service(${CMAKE_CURRENT_BINARY_DIR}/systemd-user/dbus.socket PATH ${DBUS_SYSTEMD_USERUNITDIR} LINKS sockets.target.wants) + add_systemd_service(${CMAKE_CURRENT_BINARY_DIR}/systemd-user/dbus.service PATH ${DBUS_SYSTEMD_USERUNITDIR}) +endif() ## mop up the gcov files #clean-local: diff --git a/cmake/config.h.cmake b/cmake/config.h.cmake index 1bc545a9..cbffcfa9 100644 --- a/cmake/config.h.cmake +++ b/cmake/config.h.cmake @@ -227,6 +227,7 @@ #cmakedefine HAVE_RAISE 1 #cmakedefine HAVE_SETRLIMIT 1 #cmakedefine HAVE_UNIX_FD_PASSING 1 +#cmakedefine HAVE_SYSTEMD /* Define to use epoll(4) on Linux */ #cmakedefine DBUS_HAVE_LINUX_EPOLL 1 diff --git a/cmake/modules/Macros.cmake b/cmake/modules/Macros.cmake index c594747e..caf4372c 100644 --- a/cmake/modules/Macros.cmake +++ b/cmake/modules/Macros.cmake @@ -204,11 +204,92 @@ endmacro() # # provide option with three states AUTO, ON, OFF # -macro(tristateoption _name _default _text) +macro(add_auto_option _name _text _default) if(NOT DEFINED ${_name}) set(${_name} ${_default} CACHE STRING "${_text}" FORCE) else() set(${_name} ${_default} CACHE STRING "${_text}") endif() set_property(CACHE ${_name} PROPERTY STRINGS AUTO ON OFF) -endmacro(tristateoption) +endmacro() + + +# +# Ensure that if a tristate ON/OFF/AUTO feature is set to ON, +# its requirements have been met. Fail with a fatal error if not. +# +# _name: name of a variable ENABLE_FOO representing a tristate ON/OFF/AUTO feature +# _text: human-readable description of the feature enabled by _name, for the +# error message +# _var: name of a variable representing a system property we checked for, +# such as an executable that must exist for the feature enabled by _name to work +# _vartext: what we checked for, for the error message +# +macro(check_auto_option _name _text _var _vartext) + set(_nameval ${${_name}}) + set(_varval ${${_var}}) + #message("debug: _name ${_name} ${_nameval} _var ${_var} ${_varval}") + if(${_nameval} AND NOT ${_nameval} STREQUAL "AUTO" AND NOT ${_varval}) + message(FATAL_ERROR "${_text} requested but ${_vartext} not found") + endif() +endmacro() + +# +# Provide option that takes a path +# +macro(add_path_option _name _text _default) + if(NOT DEFINED ${_name}) + set(${_name} ${_default} CACHE STRING "${_text}" FORCE) + else() + set(${_name} ${_default} CACHE STRING "${_text}") + endif() +endmacro() + +# +# create directory on install +# +macro(install_dir filepath) + install(CODE " + set(_path \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${filepath}\") + if(NOT EXISTS \"\${_path}\") + execute_process(COMMAND ${CMAKE_COMMAND} -E make_directory \"\${_path}\") + message(\"-- Creating directory: \${_path}\") + else() + message(\"-- Up-to-date: \${_path}\") + endif() + ") +endmacro() + +# +# create symlink on install +# +macro(install_symlink filepath sympath) + install(CODE " + set(_sympath \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${sympath}\") + file(REMOVE \"\${_sympath}\") + execute_process(COMMAND ${CMAKE_COMMAND} -E create_symlink \"${filepath}\" \"\${_sympath}\" RESULT_VARIABLE result) + if(NOT result) + message(\"-- Creating symlink: \${_sympath} -> ${filepath}\") + else() + message(FATAL ERROR \"-- Failed to create symlink: \${_sympath} -> ${filepath}\") + endif() + ") +endmacro() + +# +# add system service PATH LINKS [multi-user.target.wants [...]] +# +macro(add_systemd_service file) + set(options) + set(oneValueArgs PATH) + set(multiValueArgs LINKS) + cmake_parse_arguments(_ "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN}) + set(_targetdir ${__PATH}) + install(FILES ${file} DESTINATION ${_targetdir}) + get_filename_component(_name ${file} NAME) + foreach(l ${__LINKS}) + set(_linkdir ${_targetdir}/${l}) + install_dir(${_linkdir}) + install_symlink(../${_name} ${_linkdir}/${_name}) + endforeach() +endmacro() diff --git a/dbus/CMakeLists.txt b/dbus/CMakeLists.txt index 972e05c1..63070b69 100644 --- a/dbus/CMakeLists.txt +++ b/dbus/CMakeLists.txt @@ -281,7 +281,7 @@ else(WIN32) if(DEFINED DBUS_LIBRARY_REVISION) set_target_properties(dbus-1 PROPERTIES VERSION ${DBUS_LIBRARY_MAJOR}.${DBUS_LIBRARY_AGE}.${DBUS_LIBRARY_REVISION} SOVERSION ${DBUS_LIBRARY_MAJOR}) endif() - target_link_libraries(dbus-1 ${CMAKE_THREAD_LIBS_INIT}) + target_link_libraries(dbus-1 ${CMAKE_THREAD_LIBS_INIT} ${SYSTEMD_LIBRARIES}) if(LIBRT) target_link_libraries(dbus-1 ${LIBRT}) endif() diff --git a/doc/CMakeLists.txt b/doc/CMakeLists.txt index 1f47fa2a..8239c8e8 100644 --- a/doc/CMakeLists.txt +++ b/doc/CMakeLists.txt @@ -8,7 +8,7 @@ add_custom_target(doc ALL) if(DOXYGEN_EXECUTABLE) option(DBUS_ENABLE_DOXYGEN_DOCS "build DOXYGEN documentation (requires Doxygen)" ON) - tristateoption(ENABLE_QT_HELP AUTO "build qt help documentation (requires qhelpgenerator(-qt5)); set INSTALL_QCH_DIR for custom qch installation path") + add_auto_option(ENABLE_QT_HELP "build qt help documentation (requires qhelpgenerator(-qt5)); set INSTALL_QCH_DIR for custom qch installation path" AUTO) endif() if(DBUS_ENABLE_DOXYGEN_DOCS) @@ -23,9 +23,7 @@ if(DBUS_ENABLE_DOXYGEN_DOCS) set(INSTALL_QCH_DIR ${CMAKE_INSTALL_DATADIR}/doc/dbus) endif() find_program(QHELPGENERATOR_EXECUTABLE NAMES qhelpgenerator qhelpgenerator-qt5) - if(ENABLE_QT_HELP AND NOT ENABLE_QT_HELP STREQUAL "AUTO" AND NOT QHELPGENERATOR_EXECUTABLE) - message(FATAL_ERROR "Qt help requested but qhelpgenerator not found") - endif() + check_auto_option(ENABLE_QT_HELP "Qt help" QHELPGENERATOR_EXECUTABLE "qhelpgenerator") if(ENABLE_QT_HELP AND QHELPGENERATOR_EXECUTABLE) message(STATUS "${QHELPGENERATOR_EXECUTABLE} found") set(DOXYGEN_GENERATE_QHP YES) diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt index 23f567b5..43d4df43 100644 --- a/tools/CMakeLists.txt +++ b/tools/CMakeLists.txt @@ -129,7 +129,7 @@ if(NOT WIN32) endif() # create the /var/lib/dbus directory for dbus-uuidgen -install(DIRECTORY DESTINATION ${CMAKE_INSTALL_LOCALSTATEDIR}/lib/dbus) +install(DIRECTORY DESTINATION ${CMAKE_INSTALL_FULL_LOCALSTATEDIR}/lib/dbus) set(EXAMPLES_SCRIPTS GetAllMatchRules.py