aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorVsevolod Stakhov <vsevolod@rspamd.com>2025-03-29 10:17:13 +0000
committerVsevolod Stakhov <vsevolod@rspamd.com>2025-03-29 10:17:13 +0000
commit39caa76911f19a472eab9fb21d19b43ca63f79ee (patch)
tree2b9067612ac71f77b3a63ffd73c35ab32acb547e
parent4c98aab6f670c659dff4c7e0cf392576f7850732 (diff)
downloadrspamd-39caa76911f19a472eab9fb21d19b43ca63f79ee.tar.gz
rspamd-39caa76911f19a472eab9fb21d19b43ca63f79ee.zip
[Project] Modernize cmake
-rw-r--r--CMakeLists.txt803
-rw-r--r--cmake/AddDependencySubdirectories.cmake114
-rw-r--r--cmake/CheckSymbols.cmake146
-rw-r--r--cmake/CheckSystemFeatures.cmake207
-rw-r--r--cmake/CheckSystemHeaders.cmake139
-rw-r--r--cmake/CheckURLInclude.cmake51
-rw-r--r--cmake/InstallRspamdFiles.cmake104
-rw-r--r--cmake/SetupPVSStudio.cmake56
-rw-r--r--contrib/xxhash/CMakeLists.txt18
-rw-r--r--src/CMakeLists.txt532
-rw-r--r--src/rspamadm/lua_repl.c4
11 files changed, 1281 insertions, 893 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index f3fa193cc..87f106425 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -5,107 +5,116 @@
#
############################# INITIAL SECTION #############################################
-CMAKE_MINIMUM_REQUIRED(VERSION 3.15 FATAL_ERROR)
+cmake_minimum_required(VERSION 3.15 FATAL_ERROR)
-SET(RSPAMD_VERSION_MAJOR 3)
-SET(RSPAMD_VERSION_MINOR 11)
-SET(RSPAMD_VERSION_PATCH 2)
+# Define version variables
+set(RSPAMD_VERSION_MAJOR 3)
+set(RSPAMD_VERSION_MINOR 11)
+set(RSPAMD_VERSION_PATCH 2)
# Keep two digits all the time
-SET(RSPAMD_VERSION_MAJOR_NUM ${RSPAMD_VERSION_MAJOR}0)
-SET(RSPAMD_VERSION_MINOR_NUM ${RSPAMD_VERSION_MINOR}0)
-SET(RSPAMD_VERSION_PATCH_NUM ${RSPAMD_VERSION_PATCH}0)
+set(RSPAMD_VERSION_MAJOR_NUM ${RSPAMD_VERSION_MAJOR}0)
+set(RSPAMD_VERSION_MINOR_NUM ${RSPAMD_VERSION_MINOR}0)
+set(RSPAMD_VERSION_PATCH_NUM ${RSPAMD_VERSION_PATCH}0)
-IF (GIT_ID)
- SET(GIT_VERSION 1)
- SET(RSPAMD_ID "${GIT_ID}")
-ENDIF ()
+if (GIT_ID)
+ set(GIT_VERSION 1)
+ set(RSPAMD_ID "${GIT_ID}")
+endif ()
+
+set(RSPAMD_VERSION "${RSPAMD_VERSION_MAJOR}.${RSPAMD_VERSION_MINOR}.${RSPAMD_VERSION_PATCH}")
-SET(RSPAMD_VERSION "${RSPAMD_VERSION_MAJOR}.${RSPAMD_VERSION_MINOR}.${RSPAMD_VERSION_PATCH}")
+project(rspamd
+ VERSION "${RSPAMD_VERSION}"
+ LANGUAGES C CXX ASM
+ DESCRIPTION "Rapid spam filtering system"
+ HOMEPAGE_URL "https://rspamd.com"
+)
-PROJECT(rspamd VERSION "${RSPAMD_VERSION}" LANGUAGES C CXX ASM)
+cmake_policy(SET CMP0075 NEW)
-CMAKE_POLICY(SET CMP0075 NEW)
+# Language standards
+set(CMAKE_C_STANDARD 11)
+set(CMAKE_CXX_STANDARD 20)
+set(CMAKE_C_STANDARD_REQUIRED ON)
+set(CMAKE_CXX_STANDARD_REQUIRED ON)
+set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
-# This is supported merely with cmake 3.1
-SET(CMAKE_C_STANDARD 11)
-SET(CMAKE_CXX_STANDARD 20)
-SET(CMAKE_C_STANDARD_REQUIRED ON)
-SET(CMAKE_CXX_STANDARD_REQUIRED ON)
-LIST(APPEND CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake/")
+list(APPEND CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake/")
-SET(RSPAMD_MASTER_SITE_URL "https://rspamd.com")
+set(RSPAMD_MASTER_SITE_URL "https://rspamd.com")
-IF (NOT RSPAMD_USER)
- SET(RSPAMD_USER "nobody")
- SET(RSPAMD_GROUP "nobody")
-ENDIF (NOT RSPAMD_USER)
+if (NOT RSPAMD_USER)
+ set(RSPAMD_USER "nobody")
+ set(RSPAMD_GROUP "nobody")
+endif ()
# Default for SysV Init
-SET(RSPAMD_WORKER_NORMAL "*:11333")
-SET(RSPAMD_WORKER_CONTROLLER "*:11334")
+set(RSPAMD_WORKER_NORMAL "*:11333")
+set(RSPAMD_WORKER_CONTROLLER "*:11334")
############################# OPTIONS SECTION #############################################
-OPTION(ENABLE_LUAJIT "Link with libluajit [default: ON]" ON)
-OPTION(ENABLE_URL_INCLUDE "Enable urls in ucl includes (requires libcurl or libfetch) [default: OFF]" OFF)
-OPTION(NO_SHARED "Build internal libs static [default: ON]" ON)
-OPTION(INSTALL_WEBUI "Install web interface [default: ON]" ON)
-OPTION(INSTALL_EXAMPLES "Install examples of the configuration and Lua [default: ON]" ON)
-OPTION(WANT_SYSTEMD_UNITS "Install systemd unit files on Linux [default: OFF]" OFF)
-OPTION(ENABLE_SNOWBALL "Enable snowball stemmer [default: ON]" ON)
-OPTION(ENABLE_CLANG_PLUGIN "Enable clang static analysing plugin [default: OFF]" OFF)
-OPTION(ENABLE_PCRE2 "Enable pcre2 instead of pcre [default: ON]" ON)
-OPTION(ENABLE_JEMALLOC "Build rspamd with jemalloc allocator [default: OFF]" OFF)
-OPTION(ENABLE_UTILS "Build rspamd internal utils [default: OFF]" OFF)
-OPTION(ENABLE_LIBUNWIND "Obsoleted [default: OFF]" OFF)
-OPTION(ENABLE_LUA_TRACE "Trace all Lua C API invocations [default: OFF]" OFF)
-OPTION(ENABLE_LUA_REPL "Enables Lua repl (requires C++11 compiler) [default: ON]" ON)
-OPTION(ENABLE_FASTTEXT "Link with FastText library [default: OFF]" OFF)
-OPTION(ENABLE_BACKWARD "Build rspamd with backward-cpp stacktrace [default: ON]" ON)
-OPTION(SYSTEM_ZSTD "Use system zstd instead of bundled one [default: OFF]" OFF)
-OPTION(SYSTEM_DOCTEST "Use system doctest instead of bundled one [default: OFF]" OFF)
-OPTION(SYSTEM_XXHASH "Use system xxhash instead of bundled one [default: OFF]" OFF)
+option(ENABLE_LUAJIT "Link with libluajit" ON)
+option(ENABLE_URL_INCLUDE "Enable URLs in UCL includes (requires libcurl or libfetch)" OFF)
+option(NO_SHARED "Build internal libs static" ON)
+option(INSTALL_WEBUI "Install web interface" ON)
+option(INSTALL_EXAMPLES "Install examples of the configuration and Lua" ON)
+option(WANT_SYSTEMD_UNITS "Install systemd unit files on Linux" OFF)
+option(ENABLE_SNOWBALL "Enable snowball stemmer" ON)
+option(ENABLE_CLANG_PLUGIN "Enable clang static analysing plugin" OFF)
+option(ENABLE_PCRE2 "Enable pcre2 instead of pcre" ON)
+option(ENABLE_JEMALLOC "Build rspamd with jemalloc allocator" OFF)
+option(ENABLE_UTILS "Build rspamd internal utils" OFF)
+option(ENABLE_LIBUNWIND "Obsoleted" OFF) # Deprecated option
+option(ENABLE_LUA_TRACE "Trace all Lua C API invocations" OFF)
+option(ENABLE_FASTTEXT "Link with FastText library" OFF)
+option(ENABLE_BACKWARD "Build rspamd with backward-cpp stacktrace" ON)
+option(SYSTEM_ZSTD "Use system zstd instead of bundled one" OFF)
+option(SYSTEM_DOCTEST "Use system doctest instead of bundled one" OFF)
+option(SYSTEM_XXHASH "Use system xxhash instead of bundled one" OFF)
############################# INCLUDE SECTION #############################################
-INCLUDE(CheckIncludeFiles)
-INCLUDE(CheckFunctionExists)
-INCLUDE(CheckSymbolExists)
-INCLUDE(CheckCSourceCompiles)
-INCLUDE(CheckCSourceRuns)
-INCLUDE(CheckLibraryExists)
-INCLUDE(CheckCCompilerFlag)
-INCLUDE(CMakeParseArguments)
-INCLUDE(FindArch)
-INCLUDE(AsmOp)
-INCLUDE(FindRagel)
-INCLUDE(ProcessPackage)
-
-IF (NOT RAGEL_FOUND)
- MESSAGE(FATAL_ERROR "Ragel is required to build rspamd")
-ENDIF ()
-
-FIND_PACKAGE(PkgConfig REQUIRED)
-FIND_PACKAGE(Perl REQUIRED)
+include(CheckIncludeFiles)
+include(CheckFunctionExists)
+include(CheckSymbolExists)
+include(CheckCSourceCompiles)
+include(CheckCSourceRuns)
+include(CheckLibraryExists)
+include(CheckCCompilerFlag)
+include(CMakeParseArguments)
+include(FindArch)
+include(AsmOp)
+include(FindRagel)
+include(ProcessPackage)
+
+if (NOT RAGEL_FOUND)
+ message(FATAL_ERROR "Ragel is required to build rspamd")
+endif ()
+# Find required packages
+find_package(PkgConfig REQUIRED)
+find_package(Perl REQUIRED)
+# Sanitizer setup
option(SANITIZE "Enable sanitizer: address, memory, undefined, leak (comma separated list)" "")
-INCLUDE(Toolset)
-INCLUDE(Sanitizer)
+include(Toolset)
+include(Sanitizer)
-INCLUDE(ArchDep)
-INCLUDE(Paths)
+include(ArchDep)
+include(Paths)
-IF (ENABLE_PCRE2 MATCHES "ON")
- SET(WITH_PCRE2 1)
+if (ENABLE_PCRE2)
+ set(WITH_PCRE2 1)
# For utf8 API
- LIST(APPEND CMAKE_REQUIRED_DEFINITIONS "-DPCRE2_CODE_UNIT_WIDTH=8")
-ENDIF ()
-############################# CONFIG SECTION #############################################
-# Initial set
+ list(APPEND CMAKE_REQUIRED_DEFINITIONS "-DPCRE2_CODE_UNIT_WIDTH=8")
+endif ()
+############################# CONFIG SECTION #############################################
+# Include directories
# Prefer local include dirs to system ones
-INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/"
+include_directories(
+ "${CMAKE_SOURCE_DIR}/"
"${CMAKE_SOURCE_DIR}/src"
"${CMAKE_SOURCE_DIR}/src/libutil"
"${CMAKE_SOURCE_DIR}/src/libserver"
@@ -126,17 +135,19 @@ INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/"
"${CMAKE_SOURCE_DIR}/contrib/lua-lpeg"
"${CMAKE_SOURCE_DIR}/contrib/frozen/include"
"${CMAKE_SOURCE_DIR}/contrib/fu2/include"
- "${CMAKE_BINARY_DIR}/src" #Stored in the binary dir
- "${CMAKE_BINARY_DIR}/src/libcryptobox")
+ "${CMAKE_BINARY_DIR}/src" # Stored in the binary dir
+ "${CMAKE_BINARY_DIR}/src/libcryptobox"
+)
-SET(TAR "tar")
-INCLUDE(OSDep)
+set(TAR "tar")
+include(OSDep)
# Now find libraries and headers
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES "m")
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES "pthread")
+list(APPEND RSPAMD_REQUIRED_LIBRARIES "m")
+list(APPEND RSPAMD_REQUIRED_LIBRARIES "pthread")
-IF (ENABLE_LUAJIT MATCHES "ON")
+# Lua setup
+if (ENABLE_LUAJIT)
ProcessPackage(LIBLUAJIT LIBRARY "luajit"
"luajit-2.1"
"luajit2.1"
@@ -149,9 +160,9 @@ IF (ENABLE_LUAJIT MATCHES "ON")
"include/luajit"
ROOT ${LUA_ROOT}
MODULES luajit)
- SET(WITH_LUAJIT 1)
-ELSE (ENABLE_LUAJIT MATCHES "ON")
-
+ set(WITH_LUAJIT 1)
+else ()
+ # Try to find Lua (5.3, 5.4, 5.2, or 5.1 in that order)
ProcessPackage(LIBLUA LIBRARY "lua"
"lua-5.3"
LIB_SUFFIXES "lua5.3"
@@ -164,7 +175,7 @@ ELSE (ENABLE_LUAJIT MATCHES "ON")
MODULES lua53
OPTIONAL)
- IF (NOT WITH_LIBLUA)
+ if (NOT WITH_LIBLUA)
ProcessPackage(LIBLUA LIBRARY "lua"
"lua-5.4"
LIB_SUFFIXES "lua5.4"
@@ -176,7 +187,7 @@ ELSE (ENABLE_LUAJIT MATCHES "ON")
ROOT ${LUA_ROOT}
MODULES lua54
OPTIONAL)
- IF (NOT WITH_LIBLUA)
+ if (NOT WITH_LIBLUA)
ProcessPackage(LIBLUA LIBRARY "lua"
"lua-5.2"
LIB_SUFFIXES "lua5.2"
@@ -189,7 +200,7 @@ ELSE (ENABLE_LUAJIT MATCHES "ON")
MODULES lua52
OPTIONAL)
- IF (NOT WITH_LIBLUA)
+ if (NOT WITH_LIBLUA)
ProcessPackage(LIBLUA LIBRARY "lua"
"lua-5.1"
INCLUDE lua.h INCLUDE_SUFFIXES
@@ -199,29 +210,33 @@ ELSE (ENABLE_LUAJIT MATCHES "ON")
"include/lua"
ROOT ${LUA_ROOT}
MODULES lua51)
- ENDIF ()
- ENDIF ()
- ENDIF ()
-ENDIF (ENABLE_LUAJIT MATCHES "ON")
+ endif ()
+ endif ()
+ endif ()
+endif ()
-IF (ENABLE_JEMALLOC MATCHES "ON" AND NOT SANITIZE)
+# Memory allocator
+if (ENABLE_JEMALLOC AND NOT SANITIZE)
ProcessPackage(JEMALLOC LIBRARY jemalloc_pic jemalloc INCLUDE jemalloc/jemalloc.h
ROOT ${JEMALLOC_ROOT_DIR})
- SET(WITH_JEMALLOC "1")
-ENDIF ()
+ set(WITH_JEMALLOC "1")
+endif ()
+# Required libraries
ProcessPackage(GLIB2 LIBRARY glib-2.0 INCLUDE glib.h
INCLUDE_SUFFIXES include/glib include/glib-2.0
ROOT ${GLIB_ROOT_DIR} MODULES glib-2.0>=2.28)
-IF (ENABLE_PCRE2 MATCHES "ON")
+# PCRE setup
+if (ENABLE_PCRE2)
ProcessPackage(PCRE LIBRARY pcre2 pcre2-8 INCLUDE pcre2.h INCLUDE_SUFFIXES include/pcre2
ROOT ${PCRE_ROOT_DIR} MODULES pcre2 pcre2-8 libpcre2 libpcre2-8)
-ELSE ()
+else ()
ProcessPackage(PCRE LIBRARY pcre INCLUDE pcre.h INCLUDE_SUFFIXES include/pcre
ROOT ${PCRE_ROOT_DIR} MODULES pcre libpcre pcre3 libpcre3)
-ENDIF ()
+endif ()
+# Other dependencies
ProcessPackage(SQLITE3 LIBRARY sqlite3 INCLUDE sqlite3.h INCLUDE_SUFFIXES include/sqlite3 include/sqlite
ROOT ${SQLITE3_ROOT_DIR} MODULES sqlite3 sqlite)
ProcessPackage(ICUDATA LIBRARY icudata INCLUDE unicode/ucnv.h
@@ -244,573 +259,89 @@ ProcessPackage(SODIUM LIBRARY sodium INCLUDE sodium.h
ProcessPackage(LIBARCHIVE LIBRARY archive INCLUDE archive.h
ROOT ${LIBARCHIVE_ROOT_DIR} MODULES libarchive>=3.0.0)
-if (ENABLE_FASTTEXT MATCHES "ON")
+if (ENABLE_FASTTEXT)
ProcessPackage(FASTTEXT LIBRARY fasttext INCLUDE fasttext/fasttext.h
ROOT ${FASTTEXT_ROOT_DIR} MODULES fasttext)
- SET(WITH_FASTTEXT "1")
+ set(WITH_FASTTEXT "1")
endif ()
+# Include common compiler and platform specific configurations
include(CompilerWarnings)
include(Hyperscan)
include(Openblas)
-IF (ENABLE_LUA_TRACE)
- SET(WITH_LUA_TRACE 1)
-ENDIF (ENABLE_LUA_TRACE)
+# Lua tracing
+if (ENABLE_LUA_TRACE)
+ set(WITH_LUA_TRACE 1)
+endif ()
-SET(CMAKE_C_FLAGS "${CMAKE_C_OPT_FLAGS} ${CMAKE_C_FLAGS}")
-SET(CMAKE_CXX_FLAGS "${CMAKE_C_OPT_FLAGS} ${CMAKE_CXX_FLAGS}")
+# Configure compiler flags
+set(CMAKE_C_FLAGS "${CMAKE_C_OPT_FLAGS} ${CMAKE_C_FLAGS}")
+set(CMAKE_CXX_FLAGS "${CMAKE_C_OPT_FLAGS} ${CMAKE_CXX_FLAGS}")
-ADD_DEFINITIONS(-DHAVE_CONFIG_H)
-ADD_DEFINITIONS(-DDOCTEST_CONFIG_NO_MULTI_LANE_ATOMICS)
-ADD_DEFINITIONS(-DFMT_HEADER_ONLY)
+# Define macros for compilation
+add_definitions(-DHAVE_CONFIG_H)
+add_definitions(-DDOCTEST_CONFIG_NO_MULTI_LANE_ATOMICS)
+add_definitions(-DFMT_HEADER_ONLY)
# Workaround for https://github.com/onqtam/doctest/issues/356
-ADD_DEFINITIONS(-DDOCTEST_CONFIG_USE_STD_HEADERS)
-ADD_DEFINITIONS(-DU_CHARSET_IS_UTF8)
+add_definitions(-DDOCTEST_CONFIG_USE_STD_HEADERS)
+add_definitions(-DU_CHARSET_IS_UTF8)
# Disable zstd deprecation warnings, as they are not relevant for us
-ADD_DEFINITIONS(-DZSTD_DISABLE_DEPRECATE_WARNINGS)
+add_definitions(-DZSTD_DISABLE_DEPRECATE_WARNINGS)
# Check platform specific includes
-CHECK_INCLUDE_FILES(sys/types.h HAVE_SYS_TYPES_H)
-CHECK_INCLUDE_FILES(sys/uio.h HAVE_SYS_UIO_H)
-
-CHECK_INCLUDE_FILES(fcntl.h HAVE_FCNTL_H)
-CHECK_INCLUDE_FILES(math.h HAVE_MATH_H)
-CHECK_INCLUDE_FILES(stdio.h HAVE_STDIO_H)
-CHECK_INCLUDE_FILES(stdlib.h HAVE_STDLIB_H)
-CHECK_INCLUDE_FILES(string.h HAVE_STRING_H)
-CHECK_INCLUDE_FILES(strings.h HAVE_STRINGS_H)
-CHECK_INCLUDE_FILES(time.h HAVE_TIME_H)
-CHECK_INCLUDE_FILES(unistd.h HAVE_UNISTD_H)
-CHECK_INCLUDE_FILES(stdint.h HAVE_STDINT_H)
-CHECK_INCLUDE_FILES(inttypes.h HAVE_INTTYPES_H)
-CHECK_INCLUDE_FILES(stdbool.h HAVE_STDBOOL_H)
-CHECK_INCLUDE_FILES(endian.h HAVE_ENDIAN_H)
-CHECK_INCLUDE_FILES(sys/endian.h HAVE_SYS_ENDIAN_H)
-CHECK_INCLUDE_FILES(machine/endian.h HAVE_MACHINE_ENDIAN_H)
-CHECK_INCLUDE_FILES(sys/socket.h HAVE_SYS_SOCKET_H)
-CHECK_INCLUDE_FILES(sys/mman.h HAVE_SYS_MMAN_H)
-CHECK_INCLUDE_FILES(sys/un.h HAVE_SYS_UN_H)
-CHECK_INCLUDE_FILES(sys/stat.h HAVE_SYS_STAT_H)
-CHECK_INCLUDE_FILES(sys/wait.h HAVE_SYS_WAIT_H)
-CHECK_INCLUDE_FILES(sys/param.h HAVE_SYS_PARAM_H)
-CHECK_INCLUDE_FILES(sys/file.h HAVE_SYS_FILE_H)
-CHECK_INCLUDE_FILES(sys/resource.h HAVE_SYS_RESOURCE_H)
-CHECK_INCLUDE_FILES(netinet/in.h HAVE_NETINET_IN_H)
-CHECK_INCLUDE_FILES(netinet/tcp.h HAVE_NETINET_TCP_H)
-CHECK_INCLUDE_FILES(arpa/inet.h HAVE_ARPA_INET_H)
-CHECK_INCLUDE_FILES(netdb.h HAVE_NETDB_H)
-CHECK_INCLUDE_FILES(syslog.h HAVE_SYSLOG_H)
-CHECK_INCLUDE_FILES(siginfo.h HAVE_SIGINFO_H)
-CHECK_INCLUDE_FILES(locale.h HAVE_LOCALE_H)
-CHECK_INCLUDE_FILES(libgen.h HAVE_LIBGEN_H)
-CHECK_INCLUDE_FILES(pwd.h HAVE_PWD_H)
-CHECK_INCLUDE_FILES(grp.h HAVE_GRP_H)
-CHECK_INCLUDE_FILES(glob.h HAVE_GLOB_H)
-CHECK_INCLUDE_FILES(poll.h HAVE_POLL_H)
-CHECK_INCLUDE_FILES(readpassphrase.h HAVE_READPASSPHRASE_H)
-CHECK_INCLUDE_FILES(termios.h HAVE_TERMIOS_H)
-CHECK_INCLUDE_FILES(paths.h HAVE_PATHS_H)
-CHECK_INCLUDE_FILES(ctype.h HAVE_CTYPE_H)
-CHECK_INCLUDE_FILES(unistd.h HAVE_UNISTD_H)
-CHECK_INCLUDE_FILES(cpuid.h HAVE_CPUID_H)
-CHECK_INCLUDE_FILES(dirent.h HAVE_DIRENT_H)
-CHECK_INCLUDE_FILES(ucontext.h HAVE_UCONTEXT_H)
-CHECK_INCLUDE_FILES(sys/ucontext.h HAVE_SYS_UCONTEXT_H) # OSX specific
-
-# Check platform API
-IF (NOT CMAKE_SYSTEM_NAME STREQUAL "Linux")
- # setproctitle is broken badly in Linux, never try it
- CHECK_FUNCTION_EXISTS(setproctitle HAVE_SETPROCTITLE)
-ENDIF ()
-CHECK_FUNCTION_EXISTS(getpagesize HAVE_GETPAGESIZE)
-CHECK_FUNCTION_EXISTS(nanosleep HAVE_NANOSLEEP)
-CHECK_FUNCTION_EXISTS(flock HAVE_FLOCK)
-CHECK_LIBRARY_EXISTS(m tanh "" HAVE_TANH)
-CHECK_FUNCTION_EXISTS(mkstemp HAVE_MKSTEMP)
-CHECK_FUNCTION_EXISTS(clock_gettime HAVE_CLOCK_GETTIME)
-
-# Check macros
-CHECK_SYMBOL_EXISTS(PATH_MAX limits.h HAVE_PATH_MAX)
-CHECK_SYMBOL_EXISTS(MAXPATHLEN sys/param.h HAVE_MAXPATHLEN)
-CHECK_SYMBOL_EXISTS(MAP_ANON sys/mman.h HAVE_MMAP_ANON)
-CHECK_SYMBOL_EXISTS(IPV6_V6ONLY "sys/socket.h;netinet/in.h" HAVE_IPV6_V6ONLY)
-CHECK_SYMBOL_EXISTS(posix_fallocate fcntl.h HAVE_POSIX_FALLOCATE)
-CHECK_SYMBOL_EXISTS(fallocate fcntl.h HAVE_FALLOCATE)
-CHECK_SYMBOL_EXISTS(_SC_NPROCESSORS_ONLN unistd.h HAVE_SC_NPROCESSORS_ONLN)
-CHECK_SYMBOL_EXISTS(setbit sys/param.h PARAM_H_HAS_BITSET)
-CHECK_SYMBOL_EXISTS(getaddrinfo "sys/types.h;sys/socket.h;netdb.h" HAVE_GETADDRINFO)
-CHECK_SYMBOL_EXISTS(sched_yield "sched.h" HAVE_SCHED_YIELD)
-CHECK_SYMBOL_EXISTS(nftw "sys/types.h;ftw.h" HAVE_NFTW)
-CHECK_SYMBOL_EXISTS(memrchr "string.h" HAVE_MEMRCHR)
-IF (ENABLE_PCRE2 MATCHES "ON")
- LIST(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
- CHECK_SYMBOL_EXISTS(PCRE2_CONFIG_JIT "pcre2.h" HAVE_PCRE_JIT)
-ELSE ()
- LIST(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
- CHECK_SYMBOL_EXISTS(PCRE_CONFIG_JIT "pcre.h" HAVE_PCRE_JIT)
-ENDIF ()
-CHECK_SYMBOL_EXISTS(SOCK_SEQPACKET "sys/types.h;sys/socket.h" HAVE_SOCK_SEQPACKET)
-CHECK_SYMBOL_EXISTS(O_NOFOLLOW "sys/types.h;sys/fcntl.h" HAVE_ONOFOLLOW)
-CHECK_SYMBOL_EXISTS(O_CLOEXEC "sys/types.h;sys/fcntl.h" HAVE_OCLOEXEC)
-
-# OpenSSL specific stuff
-LIST(APPEND CMAKE_REQUIRED_INCLUDES "${LIBSSL_INCLUDE}")
-IF (LIBCRYPT_LIBRARY_PATH)
- SET(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${LIBCRYPT_LIBRARY_PATH};${LIBCRYPT_LIBRARY}")
- SET(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${LIBSSL_LIBRARY_PATH};${LIBSSL_LIBRARY}")
-ELSE ()
- SET(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-lcrypt;-lssl")
-ENDIF ()
-
-CHECK_SYMBOL_EXISTS(SSL_set_tlsext_host_name "openssl/ssl.h" HAVE_SSL_TLSEXT_HOSTNAME)
-CHECK_SYMBOL_EXISTS(FIPS_mode "openssl/crypto.h" HAVE_FIPS_MODE)
-
-CHECK_SYMBOL_EXISTS(dirfd "sys/types.h;unistd.h;dirent.h" HAVE_DIRFD)
-CHECK_SYMBOL_EXISTS(fpathconf "sys/types.h;unistd.h" HAVE_FPATHCONF)
-CHECK_SYMBOL_EXISTS(sigaltstack "signal.h" HAVE_SIGALTSTACK)
-CHECK_SYMBOL_EXISTS(open_memstream "stdio.h" HAVE_OPENMEMSTREAM)
-CHECK_SYMBOL_EXISTS(fmemopen "stdio.h" HAVE_FMEMOPEN)
-CHECK_SYMBOL_EXISTS(clock_getcpuclockid "sys/types.h;time.h" HAVE_CLOCK_GETCPUCLOCKID)
-CHECK_SYMBOL_EXISTS(RUSAGE_SELF "sys/types.h;sys/resource.h" HAVE_RUSAGE_SELF)
-CHECK_SYMBOL_EXISTS(ffsll "strings.h" HAVE_FFSLL)
-
-IF (ENABLE_PCRE2 MATCHES "ON")
- IF (HAVE_PCRE_JIT)
- SET(HAVE_PCRE_JIT_FAST 1)
- ENDIF ()
-ELSE ()
- LIST(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
- IF (PCRE_LIBRARY_PATH)
- SET(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${PCRE_LIBRARY_PATH};${PCRE_LIBRARY}")
- ELSE (PCRE_LIBRARY_PATH)
- SET(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-lpcre")
- ENDIF (PCRE_LIBRARY_PATH)
- # Some PCRE implementations are lacking of pcre_jit_exec fast path
- SET(_PCRE_FAST_TEST "
-#include \"pcre.h\"
-int main (void)
-{
- int rc;
- int ovector[30];
- pcre *re;
- pcre_extra *extra;
- pcre_jit_stack *jit_stack;
-
- re = pcre_compile(\"abc\", 0, NULL, NULL, NULL);
- extra = pcre_study(re, PCRE_STUDY_JIT_COMPILE, NULL);
- jit_stack = pcre_jit_stack_alloc(32*1024, 512*1024);
- pcre_assign_jit_stack(extra, NULL, jit_stack);
- rc = pcre_jit_exec(re, extra, \"abc\", 3, 0, 0, ovector, 30, jit_stack);
-
- return rc;
-}
-")
- CHECK_C_SOURCE_COMPILES("${_PCRE_FAST_TEST}" HAVE_PCRE_JIT_FAST)
- IF (HAVE_PCRE_JIT_FAST)
- MESSAGE(STATUS "pcre_jit_exec is supported")
- ELSE (HAVE_PCRE_JIT_FAST)
- MESSAGE(STATUS "pcre_jit_exec is -NOT- supported")
- ENDIF (HAVE_PCRE_JIT_FAST)
-ENDIF ()
-
-CHECK_C_COMPILER_FLAG(-fPIC SUPPORT_FPIC)
-IF (SUPPORT_FPIC)
- ADD_COMPILE_OPTIONS("-fPIC")
-ENDIF (SUPPORT_FPIC)
-
-FILE(WRITE ${CMAKE_BINARY_DIR}/pthread_setpshared.c "
-#include <pthread.h>
-#include <stdlib.h>
-int main (void)
-{
- pthread_mutexattr_t mattr;
- if (pthread_mutexattr_init(&mattr) != 0) return 0;
- if (pthread_mutexattr_setpshared(&mattr, PTHREAD_PROCESS_SHARED) != 0) return 0;
- if (pthread_mutexattr_setrobust(&mattr, PTHREAD_MUTEX_ROBUST) != 0) return 0;
- return 1;
-}
-")
-TRY_RUN(_CAN_RUN _CAN_COMPILE
- "${CMAKE_BINARY_DIR}" "${CMAKE_BINARY_DIR}/pthread_setpshared.c"
- CMAKE_FLAGS CMAKE_C_FLAGS="-pthread")
-IF (_CAN_RUN EQUAL 1)
- SET(HAVE_PTHREAD_PROCESS_SHARED 1 CACHE INTERNAL "")
-ENDIF (_CAN_RUN EQUAL 1)
-IF (HAVE_PTHREAD_PROCESS_SHARED)
- MESSAGE(STATUS "pthread_mutexattr_setpshared is supported")
-ELSE (HAVE_PTHREAD_PROCESS_SHARED)
- MESSAGE(STATUS "pthread_mutexattr_setpshared is -NOT- supported")
-ENDIF (HAVE_PTHREAD_PROCESS_SHARED)
-
-IF (NOT HAVE_GETADDRINFO)
- MESSAGE(FATAL_ERROR "Your system does not support getaddrinfo call, please consider upgrading it to run rspamd")
-ENDIF (NOT HAVE_GETADDRINFO)
-IF (HAVE_SIGINFO_H)
- CHECK_SYMBOL_EXISTS(SA_SIGINFO "signal.h;siginfo.h" HAVE_SA_SIGINFO)
-ELSE (HAVE_SIGINFO_H)
- CHECK_SYMBOL_EXISTS(SA_SIGINFO "signal.h" HAVE_SA_SIGINFO)
-ENDIF (HAVE_SIGINFO_H)
-
-IF (NOT CMAKE_SYSTEM_NAME STREQUAL "SunOS")
- IF (HAVE_CLOCK_GETTIME)
- CHECK_SYMBOL_EXISTS(CLOCK_PROCESS_CPUTIME_ID time.h HAVE_CLOCK_PROCESS_CPUTIME_ID)
- CHECK_SYMBOL_EXISTS(CLOCK_VIRTUAL time.h HAVE_CLOCK_VIRTUAL)
- ELSE (HAVE_CLOCK_GETTIME)
- CHECK_INCLUDE_FILES(sys/timeb.h HAVE_SYS_TIMEB_H)
- ENDIF (HAVE_CLOCK_GETTIME)
-ENDIF (NOT CMAKE_SYSTEM_NAME STREQUAL "SunOS")
-
-CHECK_C_SOURCE_RUNS("
-#include <stdbool.h>
-int main(int argc, char **argv) {
- int a = 0, b = 0;
- if (__atomic_compare_exchange_n(&a, &b, 1, false, __ATOMIC_RELEASE, __ATOMIC_RELAXED)) {
- return 0;
- }
- return -1;
-}
-" HAVE_ATOMIC_BUILTINS)
-
-CHECK_C_SOURCE_RUNS("#include <stdio.h>
-int main() {
- __builtin_cpu_init();
- printf(\"%d\", __builtin_cpu_supports(\"avx\"));
- return 0;
-}" HAVE_BUILTIN_CPU_SUPPORTS)
-
-IF (NOT HAVE_ATOMIC_BUILTINS)
- MESSAGE(STATUS "atomic builtins are -NOT- supported")
-ELSE ()
- MESSAGE(STATUS "atomic builtins are supported")
-ENDIF ()
-
-CHECK_LIBRARY_EXISTS(atomic __atomic_fetch_add_4 "" HAVE_LIBATOMIC)
-IF (HAVE_LIBATOMIC)
- list(APPEND CMAKE_REQUIRED_LIBRARIES "atomic")
-endif ()
+include(CheckSystemHeaders)
+# Check macros, functions, and features
+include(CheckSystemFeatures)
-CHECK_C_SOURCE_RUNS("
-#include <x86intrin.h>
-int main(int argc, char **argv) {
- __builtin_ia32_lfence ();
- if (__builtin_ia32_rdtsc()) {
- return 0;
- }
- return -1;
-}
-" HAVE_RDTSC)
-
-IF (NOT HAVE_RDTSC)
- MESSAGE(STATUS "rdtsc intrinsic is -NOT- supported")
-ELSE ()
- MESSAGE(STATUS "rdtsc intrinsic is supported")
-ENDIF ()
-
-IF (CMAKE_SYSTEM_NAME STREQUAL "Linux")
- # In linux, we need to mount /run/shm to test which could be unavailable
- # on a build system. On the other hand, we know that linux has stupid
- # but compatible shmem support, so we assume this macro as true
- SET(HAVE_SANE_SHMEM 1)
- CHECK_C_SOURCE_COMPILES("#define _GNU_SOURCE
- #include <sys/socket.h>
- int main (int argc, char **argv) {
- return ((int*)(&recvmmsg))[argc];
- }" HAVE_RECVMMSG)
- CHECK_C_SOURCE_COMPILES("#define _GNU_SOURCE
- #include <fcntl.h>
- int main (int argc, char **argv) {
- return ((int*)(&readahead))[argc];
- }" HAVE_READAHEAD)
-ELSE ()
- CHECK_C_SOURCE_RUNS("
- #include <sys/mman.h>
- #include <fcntl.h>
- #include <unistd.h>
- #define TEST_NAME \"/test-shmem-work\"
- int
- main (int argc, char **argv)
- {
- int fd;
-
- fd = shm_open (TEST_NAME, O_RDWR | O_CREAT | O_EXCL, 00600);
- if (fd == -1) {
- return -1;
- }
- if (ftruncate (fd, 100) == -1) {
- shm_unlink (TEST_NAME);
- close (fd);
- return -1;
- }
-
- if (ftruncate (fd, 200) == -1) {
- shm_unlink (TEST_NAME);
- close (fd);
- return -1;
- }
- if (ftruncate (fd, 300) == -1) {
- shm_unlink (TEST_NAME);
- close (fd);
- return -1;
- }
-
- close (fd);
- shm_unlink (TEST_NAME);
- return 0;
- }
- " HAVE_SANE_SHMEM)
- IF (NOT HAVE_SANE_SHMEM)
- MESSAGE(STATUS "shmem support is NOT compatible with POSIX")
- ELSE ()
- MESSAGE(STATUS "shmem support is compatible with POSIX")
- ENDIF ()
-ENDIF ()
-
-IF (ENABLE_URL_INCLUDE MATCHES "ON")
- FIND_LIBRARY(LIBFETCH_LIBRARY HINTS "${RSPAMD_SEARCH_PATH}"
- NAMES fetch PATHS PATH_SUFFIXES lib64 lib
- PATHS ${RSPAMD_DEFAULT_LIBRARY_PATHS}
- DOC "Path where the libfetch library can be found")
- IF (LIBFETCH_LIBRARY)
- FIND_FILE(HAVE_FETCH_H HINTS "${RSPAMD_SEARCH_PATH}"
- NAMES fetch.h
- PATH_SUFFIXES include
- PATHS ${RSPAMD_DEFAULT_INCLUDE_PATHS}
- DOC "Path to libfetch header")
- ELSE (LIBFETCH_LIBRARY)
- # Try to find libcurl
- ProcessPackage(CURL LIBRARY curl INCLUDE curl.h INCLUDE_SUFFIXES include/curl
- ROOT ${CURL_ROOT})
- IF (NOT WITH_CURL)
- MESSAGE(WARNING "Neither libcurl nor libfetch were found, no support of URL includes in configuration")
- ENDIF (NOT WITH_CURL)
- ENDIF (LIBFETCH_LIBRARY)
-ENDIF (ENABLE_URL_INCLUDE MATCHES "ON")
-
-IF (NOT DESTDIR)
- SET(DESTDIR $ENV{DESTDIR})
-ENDIF (NOT DESTDIR)
+# Check symbols and functions
+include(CheckSymbols)
+# Configure PIC support
+check_c_compiler_flag(-fPIC SUPPORT_FPIC)
+if (SUPPORT_FPIC)
+ add_compile_options("-fPIC")
+endif ()
+
+# Support for URL includes
+include(CheckURLInclude)
+if (ENABLE_URL_INCLUDE)
+ CheckURLIncludeSupport()
+endif ()
+
+# Ensure DESTDIR is set
+if (NOT DESTDIR)
+ set(DESTDIR $ENV{DESTDIR})
+endif ()
################################ SUBDIRS SECTION ###########################
-ADD_SUBDIRECTORY(contrib/hiredis)
-INCLUDE_DIRECTORIES(BEFORE "${CMAKE_SOURCE_DIR}/contrib/hiredis")
-
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES}")
-IF (HAVE_FETCH_H)
- LIST(APPEND RSPAMD_REQUIRED_LIBRARIES fetch)
-ENDIF (HAVE_FETCH_H)
-
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES "${LUA_LIBRARY}")
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES ucl)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rdns)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES ottery)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES xxhash)
-
-IF (SYSTEM_XXHASH MATCHES "OFF")
- ADD_SUBDIRECTORY(contrib/xxhash)
- INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/contrib/xxhash")
-ELSE ()
- ProcessPackage(XXHASH LIBRARY xxhash INCLUDE xxhash.h
- ROOT ${LIBXXHASH_ROOT_DIR} MODULES xxhash libxxhash)
-ENDIF ()
-ADD_SUBDIRECTORY(contrib/cdb)
-ADD_SUBDIRECTORY(contrib/http-parser)
-ADD_SUBDIRECTORY(contrib/fpconv)
-ADD_SUBDIRECTORY(contrib/lc-btrie)
-ADD_SUBDIRECTORY(contrib/libottery)
-ADD_SUBDIRECTORY(contrib/simdutf)
-INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/contrib/simdutf/include")
-IF (SYSTEM_ZSTD MATCHES "OFF")
- ADD_SUBDIRECTORY(contrib/zstd)
-ELSE ()
- ProcessPackage(LIBZSTD LIBRARY zstd INCLUDE zstd.h
- ROOT ${LIBZSTD_ROOT_DIR} MODULES zstd libzstd)
- ADD_DEFINITIONS(-DSYS_ZSTD)
-ENDIF ()
-IF (ENABLE_SNOWBALL MATCHES "ON")
- ADD_SUBDIRECTORY(contrib/snowball)
- SET(WITH_SNOWBALL 1)
-ENDIF ()
-ADD_SUBDIRECTORY(contrib/libucl)
-ADD_SUBDIRECTORY(contrib/librdns)
-ADD_SUBDIRECTORY(contrib/aho-corasick)
-ADD_SUBDIRECTORY(contrib/lua-lpeg)
-ADD_SUBDIRECTORY(contrib/t1ha)
-ADD_SUBDIRECTORY(contrib/libev)
-ADD_SUBDIRECTORY(contrib/kann)
-ADD_SUBDIRECTORY(contrib/google-ced)
-IF (ENABLE_BACKWARD MATCHES "ON")
- ADD_SUBDIRECTORY(contrib/backward-cpp)
- message(STATUS "Backward-cpp config: ${BACKWARD_DEFINITIONS}")
-ELSE ()
- set(BACKWARD_ENABLE)
- macro(add_backward target)
- # do nothing
- endmacro()
-ENDIF ()
-IF (BACKWARD_LIBRARIES)
- message(STATUS "Backward-cpp libraries: ${BACKWARD_LIBRARIES}")
-ENDIF ()
-
-IF (SYSTEM_DOCTEST MATCHES "OFF")
- ADD_SUBDIRECTORY(contrib/doctest)
- INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/contrib/doctest")
-ELSE ()
- find_package(doctest)
-ENDIF ()
-
-IF (NOT WITH_LUAJIT)
- ADD_SUBDIRECTORY(contrib/lua-bit)
-ENDIF ()
-
-IF (ENABLE_LUA_REPL MATCHES "ON")
- ADD_SUBDIRECTORY(contrib/replxx)
- SET(WITH_LUA_REPL 1)
- LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-replxx)
-ENDIF ()
-
-IF (ENABLE_SNOWBALL MATCHES "ON")
- LIST(APPEND RSPAMD_REQUIRED_LIBRARIES stemmer)
-ENDIF ()
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-hiredis)
-
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-actrie)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-t1ha)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-ev)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-kann)
-LIST(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-ced)
-
-IF (ENABLE_CLANG_PLUGIN MATCHES "ON")
- ADD_SUBDIRECTORY(clang-plugin)
-ENDIF ()
-
-ADD_SUBDIRECTORY(src)
-enable_testing()
-ADD_SUBDIRECTORY(test)
-ADD_SUBDIRECTORY(utils)
+# Add required subdirectories for dependencies
+include(AddDependencySubdirectories)
+AddDependencySubdirectories()
############################ TARGETS SECTION ###############################
-CONFIGURE_FILE(config.h.in src/config.h)
+# Generate config.h
+configure_file(config.h.in src/config.h)
##################### INSTALLATION ##########################################
+# Setup installation targets
+include(InstallRspamdFiles)
+InstallRspamdFiles()
-# Binaries
-
-# Configs
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${CONFDIR})")
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${SHAREDIR})")
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${LUALIBDIR})")
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${PLUGINSDIR})")
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${RULESDIR})")
-
-# Install configs only if they are unchanged
-LIST(LENGTH CONFFILES CONFLIST_COUNT)
-MATH(EXPR CONFLIST_MAX ${CONFLIST_COUNT}-1)
-
-SET(GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.conf;${CMAKE_SOURCE_DIR}/conf/*.inc")
-IF (INSTALL_EXAMPLES MATCHES "ON")
- LIST(APPEND GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.lua.example")
- LIST(APPEND GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.conf.example")
-ENDIF ()
-
-FILE(GLOB_RECURSE CONF_FILES RELATIVE "${CMAKE_SOURCE_DIR}/conf" CONFIGURE_DEPENDS
- ${GLOB_PATTERNS})
-FOREACH (CONF_FILE ${CONF_FILES})
- GET_FILENAME_COMPONENT(_rp ${CONF_FILE} PATH)
- INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${CONFDIR}/${_rp})")
- INSTALL(FILES "${CMAKE_CURRENT_SOURCE_DIR}/conf/${CONF_FILE}"
- DESTINATION ${CONFDIR}/${_rp})
-ENDFOREACH (CONF_FILE)
-
-# Lua plugins
-
-FILE(GLOB LUA_PLUGINS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/src/plugins/lua" CONFIGURE_DEPENDS
- "${CMAKE_CURRENT_SOURCE_DIR}/src/plugins/lua/*.lua")
-FOREACH (LUA_PLUGIN ${LUA_PLUGINS})
- GET_FILENAME_COMPONENT(_rp ${LUA_PLUGIN} PATH)
- INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${PLUGINSDIR}/${_rp})")
- INSTALL(FILES "src/plugins/lua/${LUA_PLUGIN}" DESTINATION ${PLUGINSDIR}/${_rp})
-ENDFOREACH (LUA_PLUGIN)
-
-
-# Install TLD list
-INSTALL(FILES "contrib/publicsuffix/effective_tld_names.dat" DESTINATION
- "${SHAREDIR}")
-
-# Install languages data
-INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${SHAREDIR}/languages)")
-FILE(GLOB LANGUAGES CONFIGURE_DEPENDS "${CMAKE_CURRENT_SOURCE_DIR}/contrib/languages-data/*.json")
-FOREACH (_LANG ${LANGUAGES})
- INSTALL(FILES "${_LANG}" DESTINATION ${SHAREDIR}/languages)
-ENDFOREACH ()
-INSTALL(FILES "${CMAKE_CURRENT_SOURCE_DIR}/contrib/languages-data/stop_words" DESTINATION ${SHAREDIR}/languages)
-
-# Lua config
-FILE(GLOB_RECURSE LUA_CONFIGS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/rules" CONFIGURE_DEPENDS
- "${CMAKE_CURRENT_SOURCE_DIR}/rules/*.lua")
-FOREACH (LUA_CONF ${LUA_CONFIGS})
- GET_FILENAME_COMPONENT(_rp ${LUA_CONF} PATH)
- INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${RULESDIR}/${_rp})")
- INSTALL(FILES "rules/${LUA_CONF}" DESTINATION ${RULESDIR}/${_rp})
-ENDFOREACH (LUA_CONF)
-
-# Lua libs
-FILE(GLOB_RECURSE LUA_LIBS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/lualib" CONFIGURE_DEPENDS
- "${CMAKE_CURRENT_SOURCE_DIR}/lualib/*.lua")
-FOREACH (LUA_LIB ${LUA_LIBS})
- GET_FILENAME_COMPONENT(_rp ${LUA_LIB} PATH)
- INSTALL(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${LUALIBDIR}/${_rp})")
- INSTALL(FILES "lualib/${LUA_LIB}" DESTINATION ${LUALIBDIR}/${_rp})
-ENDFOREACH (LUA_LIB)
-
-# Install lua fun library
-INSTALL(FILES "contrib/lua-fun/fun.lua" DESTINATION ${LUALIBDIR})
-INSTALL(FILES "contrib/lua-argparse/argparse.lua" DESTINATION ${LUALIBDIR})
-INSTALL(FILES "contrib/lua-tableshape/tableshape.lua" DESTINATION ${LUALIBDIR})
-INSTALL(FILES "contrib/lua-lupa/lupa.lua" DESTINATION ${LUALIBDIR})
-INSTALL(FILES "contrib/lua-lpeg/lpegre.lua" DESTINATION ${LUALIBDIR})
-
-# systemd unit
-IF (CMAKE_SYSTEM_NAME STREQUAL "Linux" AND WANT_SYSTEMD_UNITS MATCHES "ON")
- INSTALL(FILES "rspamd.service" DESTINATION ${SYSTEMDDIR})
-ENDIF (CMAKE_SYSTEM_NAME STREQUAL "Linux" AND WANT_SYSTEMD_UNITS MATCHES "ON")
-
-# Manual pages
-INSTALL(FILES "doc/rspamd.8" DESTINATION ${MANDIR}/man8)
-INSTALL(FILES "doc/rspamc.1" DESTINATION ${MANDIR}/man1)
-INSTALL(FILES "doc/rspamadm.1" DESTINATION ${MANDIR}/man1)
-
-# Utils
-INSTALL(PROGRAMS "utils/rspamd_stats.pl" RENAME rspamd_stats DESTINATION bin)
-
-# Install webui
-IF (INSTALL_WEBUI MATCHES "ON")
- INSTALL(DIRECTORY "interface/" DESTINATION ${WWWDIR} PATTERN ".git" EXCLUDE)
-ENDIF (INSTALL_WEBUI MATCHES "ON")
-
-
-ADD_CUSTOM_TARGET(dist ${CMAKE_SOURCE_DIR}/dist.sh
+# Build distribution and testing targets
+add_custom_target(dist ${CMAKE_SOURCE_DIR}/dist.sh
"${CMAKE_BINARY_DIR}/rspamd-${RSPAMD_VERSION}.tar.xz" "${TAR}"
COMMENT "Create source distribution"
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR})
-ADD_CUSTOM_TARGET(check DEPENDS rspamd-test-cxx rspamd-test)
-ADD_CUSTOM_TARGET(run-test DEPENDS check
+add_custom_target(check DEPENDS rspamd-test-cxx rspamd-test)
+add_custom_target(run-test DEPENDS check
COMMAND test/rspamd-test-cxx
COMMAND sh -c 'LUA_PATH="${CMAKE_SOURCE_DIR}/lualib/?.lua\;${CMAKE_SOURCE_DIR}/lualib/?/?.lua\;${CMAKE_SOURCE_DIR}/lualib/?/init.lua\;${CMAKE_SOURCE_DIR}/contrib/lua-?/?.lua"
test/rspamd-test -p /rspamd/lua')
-
-# PVS Studio
-find_program(_PVS_STUDIO "pvs-studio-analyzer")
-
-if (_PVS_STUDIO)
- include(PVS-Studio)
- pvs_studio_add_target(TARGET ${PROJECT_NAME}.analyze
- ANALYZE ${PROJECT_NAME} rspamd-server rspamadm rspamc
- OUTPUT FORMAT errorfile
- LOG target_${PROJECT_NAME}.err)
-endif ()
+# Setup PVS Studio if available
+include(SetupPVSStudio)
+SetupPVSStudio()
diff --git a/cmake/AddDependencySubdirectories.cmake b/cmake/AddDependencySubdirectories.cmake
new file mode 100644
index 000000000..9c252187c
--- /dev/null
+++ b/cmake/AddDependencySubdirectories.cmake
@@ -0,0 +1,114 @@
+function(AddDependencySubdirectories)
+ # Core dependencies
+ add_subdirectory(contrib/hiredis)
+ include_directories(BEFORE "${CMAKE_SOURCE_DIR}/contrib/hiredis")
+
+ # Configure xxhash
+ if (SYSTEM_XXHASH MATCHES "OFF")
+ add_subdirectory(contrib/xxhash)
+ include_directories("${CMAKE_SOURCE_DIR}/contrib/xxhash")
+ else ()
+ ProcessPackage(XXHASH LIBRARY xxhash INCLUDE xxhash.h
+ ROOT ${LIBXXHASH_ROOT_DIR} MODULES xxhash libxxhash)
+ endif ()
+
+ # Add essential dependencies
+ add_subdirectory(contrib/cdb)
+ add_subdirectory(contrib/http-parser)
+ add_subdirectory(contrib/fpconv)
+ add_subdirectory(contrib/lc-btrie)
+ add_subdirectory(contrib/libottery)
+ add_subdirectory(contrib/simdutf)
+ include_directories("${CMAKE_SOURCE_DIR}/contrib/simdutf/include")
+
+ # Configure zstd
+ if (SYSTEM_ZSTD MATCHES "OFF")
+ add_subdirectory(contrib/zstd)
+ else ()
+ ProcessPackage(LIBZSTD LIBRARY zstd INCLUDE zstd.h
+ ROOT ${LIBZSTD_ROOT_DIR} MODULES zstd libzstd)
+ add_definitions(-DSYS_ZSTD)
+ endif ()
+
+ # Optional dependencies based on configuration
+ if (ENABLE_SNOWBALL)
+ add_subdirectory(contrib/snowball)
+ set(WITH_SNOWBALL 1 PARENT_SCOPE)
+ endif ()
+
+ # Core libraries
+ add_subdirectory(contrib/libucl)
+ add_subdirectory(contrib/librdns)
+ add_subdirectory(contrib/aho-corasick)
+ add_subdirectory(contrib/lua-lpeg)
+ add_subdirectory(contrib/t1ha)
+ add_subdirectory(contrib/libev)
+ add_subdirectory(contrib/kann)
+ add_subdirectory(contrib/google-ced)
+
+ # Backward-cpp for stacktraces
+ if (ENABLE_BACKWARD)
+ add_subdirectory(contrib/backward-cpp)
+ message(STATUS "Backward-cpp config: ${BACKWARD_DEFINITIONS}")
+ else ()
+ set(BACKWARD_ENABLE)
+ macro(add_backward target)
+ # do nothing
+ endmacro()
+ endif ()
+
+ if (BACKWARD_LIBRARIES)
+ message(STATUS "Backward-cpp libraries: ${BACKWARD_LIBRARIES}")
+ endif ()
+
+ # Doctest for testing
+ if (SYSTEM_DOCTEST MATCHES "OFF")
+ add_subdirectory(contrib/doctest)
+ include_directories("${CMAKE_SOURCE_DIR}/contrib/doctest")
+ else ()
+ find_package(doctest)
+ endif ()
+
+ # Lua-specific dependencies
+ if (NOT WITH_LUAJIT)
+ add_subdirectory(contrib/lua-bit)
+ endif ()
+
+ # Lua REPL support
+ add_subdirectory(contrib/replxx)
+ set(WITH_LUA_REPL 1 PARENT_SCOPE)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-replxx)
+
+ # Update the required libraries list based on dependencies
+ if (ENABLE_SNOWBALL)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES stemmer)
+ endif ()
+
+ # Add core required libraries
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-hiredis)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-actrie)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-t1ha)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-ev)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-kann)
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES rspamd-ced)
+
+ # Clang plugin (optional)
+ if (ENABLE_CLANG_PLUGIN)
+ add_subdirectory(clang-plugin)
+ endif ()
+
+ # Main source code
+ add_subdirectory(src)
+
+ # Enable testing
+ enable_testing()
+ add_subdirectory(test)
+
+ # Utilities
+ add_subdirectory(utils)
+
+ # Propagate variables to parent scope
+ set(RSPAMD_REQUIRED_LIBRARIES ${RSPAMD_REQUIRED_LIBRARIES} PARENT_SCOPE)
+ set(WITH_SNOWBALL ${WITH_SNOWBALL} PARENT_SCOPE)
+ set(WITH_LUA_REPL ${WITH_LUA_REPL} PARENT_SCOPE)
+endfunction()
diff --git a/cmake/CheckSymbols.cmake b/cmake/CheckSymbols.cmake
new file mode 100644
index 000000000..10207dd5b
--- /dev/null
+++ b/cmake/CheckSymbols.cmake
@@ -0,0 +1,146 @@
+# Function to check for atomic builtins, CPU features, and other specialized symbols
+function(CheckSymbols)
+ # Check for atomic builtins
+ check_c_source_runs("
+ #include <stdbool.h>
+ int main(int argc, char **argv) {
+ int a = 0, b = 0;
+ if (__atomic_compare_exchange_n(&a, &b, 1, false, __ATOMIC_RELEASE, __ATOMIC_RELAXED)) {
+ return 0;
+ }
+ return -1;
+ }
+ " HAVE_ATOMIC_BUILTINS)
+
+ if (NOT HAVE_ATOMIC_BUILTINS)
+ message(STATUS "atomic builtins are -NOT- supported")
+ else ()
+ message(STATUS "atomic builtins are supported")
+ endif ()
+
+ # Check for libatomic
+ check_library_exists(atomic __atomic_fetch_add_4 "" HAVE_LIBATOMIC)
+ if (HAVE_LIBATOMIC)
+ list(APPEND CMAKE_REQUIRED_LIBRARIES "atomic")
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES "atomic")
+ set(RSPAMD_REQUIRED_LIBRARIES "${RSPAMD_REQUIRED_LIBRARIES}" PARENT_SCOPE)
+ endif ()
+
+ # Check for CPU feature intrinsics
+ check_c_source_runs("
+ #include <stdio.h>
+ int main() {
+ __builtin_cpu_init();
+ printf(\"%d\", __builtin_cpu_supports(\"avx\"));
+ return 0;
+ }" HAVE_BUILTIN_CPU_SUPPORTS)
+
+ if (HAVE_BUILTIN_CPU_SUPPORTS)
+ message(STATUS "CPU feature detection via __builtin_cpu_supports is supported")
+ else ()
+ message(STATUS "CPU feature detection via __builtin_cpu_supports is NOT supported")
+ endif ()
+
+ # Check for RDTSC
+ check_c_source_runs("
+ #include <x86intrin.h>
+ int main(int argc, char **argv) {
+ __builtin_ia32_lfence();
+ if (__builtin_ia32_rdtsc()) {
+ return 0;
+ }
+ return -1;
+ }
+ " HAVE_RDTSC)
+
+ if (NOT HAVE_RDTSC)
+ message(STATUS "rdtsc intrinsic is -NOT- supported")
+ else ()
+ message(STATUS "rdtsc intrinsic is supported")
+ endif ()
+
+ # Check for POSIX shared memory support
+ if (NOT CMAKE_SYSTEM_NAME STREQUAL "Linux")
+ # For non-Linux systems, test shmem capability
+ check_c_source_runs("
+ #include <sys/mman.h>
+ #include <fcntl.h>
+ #include <unistd.h>
+ #define TEST_NAME \"/test-shmem-work\"
+ int
+ main(int argc, char **argv)
+ {
+ int fd;
+
+ fd = shm_open(TEST_NAME, O_RDWR | O_CREAT | O_EXCL, 00600);
+ if (fd == -1) {
+ return -1;
+ }
+ if (ftruncate(fd, 100) == -1) {
+ shm_unlink(TEST_NAME);
+ close(fd);
+ return -1;
+ }
+
+ if (ftruncate(fd, 200) == -1) {
+ shm_unlink(TEST_NAME);
+ close(fd);
+ return -1;
+ }
+ if (ftruncate(fd, 300) == -1) {
+ shm_unlink(TEST_NAME);
+ close(fd);
+ return -1;
+ }
+
+ close(fd);
+ shm_unlink(TEST_NAME);
+ return 0;
+ }
+ " HAVE_SANE_SHMEM)
+
+ if (NOT HAVE_SANE_SHMEM)
+ message(STATUS "shmem support is NOT compatible with POSIX")
+ else ()
+ message(STATUS "shmem support is compatible with POSIX")
+ endif ()
+ endif ()
+
+ # Check for pthread shared mutexes and robust mutexes
+ file(WRITE ${CMAKE_BINARY_DIR}/pthread_setpshared.c "
+ #include <pthread.h>
+ #include <stdlib.h>
+ int main(void)
+ {
+ pthread_mutexattr_t mattr;
+ if (pthread_mutexattr_init(&mattr) != 0) return 0;
+ if (pthread_mutexattr_setpshared(&mattr, PTHREAD_PROCESS_SHARED) != 0) return 0;
+ if (pthread_mutexattr_setrobust(&mattr, PTHREAD_MUTEX_ROBUST) != 0) return 0;
+ return 1;
+ }
+ ")
+
+ try_run(_CAN_RUN _CAN_COMPILE
+ "${CMAKE_BINARY_DIR}" "${CMAKE_BINARY_DIR}/pthread_setpshared.c"
+ CMAKE_FLAGS CMAKE_C_FLAGS="-pthread")
+
+ if (_CAN_RUN EQUAL 1)
+ set(HAVE_PTHREAD_PROCESS_SHARED 1 CACHE INTERNAL "")
+ endif ()
+
+ if (HAVE_PTHREAD_PROCESS_SHARED)
+ message(STATUS "pthread_mutexattr_setpshared is supported")
+ else ()
+ message(STATUS "pthread_mutexattr_setpshared is -NOT- supported")
+ endif ()
+
+ # Propagate variables to parent scope
+ set(HAVE_ATOMIC_BUILTINS ${HAVE_ATOMIC_BUILTINS} PARENT_SCOPE)
+ set(HAVE_LIBATOMIC ${HAVE_LIBATOMIC} PARENT_SCOPE)
+ set(HAVE_BUILTIN_CPU_SUPPORTS ${HAVE_BUILTIN_CPU_SUPPORTS} PARENT_SCOPE)
+ set(HAVE_RDTSC ${HAVE_RDTSC} PARENT_SCOPE)
+ set(HAVE_SANE_SHMEM ${HAVE_SANE_SHMEM} PARENT_SCOPE)
+ set(HAVE_PTHREAD_PROCESS_SHARED ${HAVE_PTHREAD_PROCESS_SHARED} PARENT_SCOPE)
+endfunction()
+
+CheckSymbols() \ No newline at end of file
diff --git a/cmake/CheckSystemFeatures.cmake b/cmake/CheckSystemFeatures.cmake
new file mode 100644
index 000000000..0a15749fd
--- /dev/null
+++ b/cmake/CheckSystemFeatures.cmake
@@ -0,0 +1,207 @@
+# CheckSystemFeatures.cmake
+# Checks for various system features, functions, and functionality
+
+# Check platform API and features
+function(CheckSystemFeatures)
+ # Process-related functions
+ if (NOT CMAKE_SYSTEM_NAME STREQUAL "Linux")
+ # setproctitle is broken badly in Linux, never try it
+ check_function_exists(setproctitle HAVE_SETPROCTITLE)
+ endif ()
+
+ # Memory and file management
+ check_function_exists(getpagesize HAVE_GETPAGESIZE)
+ check_function_exists(nanosleep HAVE_NANOSLEEP)
+ check_function_exists(flock HAVE_FLOCK)
+ check_library_exists(m tanh "" HAVE_TANH)
+ check_function_exists(mkstemp HAVE_MKSTEMP)
+ check_function_exists(clock_gettime HAVE_CLOCK_GETTIME)
+
+ # Check macros and constants
+ check_symbol_exists(PATH_MAX limits.h HAVE_PATH_MAX)
+ check_symbol_exists(MAXPATHLEN sys/param.h HAVE_MAXPATHLEN)
+ check_symbol_exists(MAP_ANON sys/mman.h HAVE_MMAP_ANON)
+ check_symbol_exists(IPV6_V6ONLY "sys/socket.h;netinet/in.h" HAVE_IPV6_V6ONLY)
+ check_symbol_exists(posix_fallocate fcntl.h HAVE_POSIX_FALLOCATE)
+ check_symbol_exists(fallocate fcntl.h HAVE_FALLOCATE)
+ check_symbol_exists(_SC_NPROCESSORS_ONLN unistd.h HAVE_SC_NPROCESSORS_ONLN)
+ check_symbol_exists(setbit sys/param.h PARAM_H_HAS_BITSET)
+ check_symbol_exists(getaddrinfo "sys/types.h;sys/socket.h;netdb.h" HAVE_GETADDRINFO)
+ check_symbol_exists(sched_yield "sched.h" HAVE_SCHED_YIELD)
+ check_symbol_exists(nftw "sys/types.h;ftw.h" HAVE_NFTW)
+ check_symbol_exists(memrchr "string.h" HAVE_MEMRCHR)
+
+ # Check if PCRE has JIT support
+ if (ENABLE_PCRE2)
+ list(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
+ check_symbol_exists(PCRE2_CONFIG_JIT "pcre2.h" HAVE_PCRE_JIT)
+ else ()
+ list(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
+ check_symbol_exists(PCRE_CONFIG_JIT "pcre.h" HAVE_PCRE_JIT)
+ endif ()
+
+ # Socket features
+ check_symbol_exists(SOCK_SEQPACKET "sys/types.h;sys/socket.h" HAVE_SOCK_SEQPACKET)
+
+ # File handling features
+ check_symbol_exists(O_NOFOLLOW "sys/types.h;sys/fcntl.h" HAVE_ONOFOLLOW)
+ check_symbol_exists(O_CLOEXEC "sys/types.h;sys/fcntl.h" HAVE_OCLOEXEC)
+
+ # OpenSSL specific stuff
+ list(APPEND CMAKE_REQUIRED_INCLUDES "${LIBSSL_INCLUDE}")
+ if (LIBCRYPT_LIBRARY_PATH)
+ set(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${LIBCRYPT_LIBRARY_PATH};${LIBCRYPT_LIBRARY}")
+ set(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${LIBSSL_LIBRARY_PATH};${LIBSSL_LIBRARY}")
+ else ()
+ set(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-lcrypt;-lssl")
+ endif ()
+
+ check_symbol_exists(SSL_set_tlsext_host_name "openssl/ssl.h" HAVE_SSL_TLSEXT_HOSTNAME)
+ check_symbol_exists(FIPS_mode "openssl/crypto.h" HAVE_FIPS_MODE)
+
+ # Directory and file path operations
+ check_symbol_exists(dirfd "sys/types.h;unistd.h;dirent.h" HAVE_DIRFD)
+ check_symbol_exists(fpathconf "sys/types.h;unistd.h" HAVE_FPATHCONF)
+
+ # Signal handling and memory operations
+ check_symbol_exists(sigaltstack "signal.h" HAVE_SIGALTSTACK)
+ check_symbol_exists(open_memstream "stdio.h" HAVE_OPENMEMSTREAM)
+ check_symbol_exists(fmemopen "stdio.h" HAVE_FMEMOPEN)
+ check_symbol_exists(clock_getcpuclockid "sys/types.h;time.h" HAVE_CLOCK_GETCPUCLOCKID)
+ check_symbol_exists(RUSAGE_SELF "sys/types.h;sys/resource.h" HAVE_RUSAGE_SELF)
+ check_symbol_exists(ffsll "strings.h" HAVE_FFSLL)
+
+ # Check for PCRE JIT fast path
+ if (ENABLE_PCRE2)
+ if (HAVE_PCRE_JIT)
+ set(HAVE_PCRE_JIT_FAST 1)
+ message(STATUS "PCRE2 JIT is supported")
+ else ()
+ message(STATUS "PCRE2 JIT is NOT supported")
+ endif ()
+ else ()
+ list(APPEND CMAKE_REQUIRED_INCLUDES "${PCRE_INCLUDE}")
+ if (PCRE_LIBRARY_PATH)
+ set(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-L${PCRE_LIBRARY_PATH};${PCRE_LIBRARY}")
+ else ()
+ set(CMAKE_REQUIRED_LIBRARIES "${CMAKE_REQUIRED_LIBRARIES};-lpcre")
+ endif ()
+
+ # Check for PCRE JIT fast path
+ set(_PCRE_FAST_TEST "
+#include \"pcre.h\"
+int main (void)
+{
+ int rc;
+ int ovector[30];
+ pcre *re;
+ pcre_extra *extra;
+ pcre_jit_stack *jit_stack;
+
+ re = pcre_compile(\"abc\", 0, NULL, NULL, NULL);
+ extra = pcre_study(re, PCRE_STUDY_JIT_COMPILE, NULL);
+ jit_stack = pcre_jit_stack_alloc(32*1024, 512*1024);
+ pcre_assign_jit_stack(extra, NULL, jit_stack);
+ rc = pcre_jit_exec(re, extra, \"abc\", 3, 0, 0, ovector, 30, jit_stack);
+
+ return rc;
+}
+")
+ check_c_source_compiles("${_PCRE_FAST_TEST}" HAVE_PCRE_JIT_FAST)
+ if (HAVE_PCRE_JIT_FAST)
+ message(STATUS "pcre_jit_exec is supported")
+ else ()
+ message(STATUS "pcre_jit_exec is NOT supported")
+ endif ()
+ endif ()
+
+ # Critical checks
+ if (NOT HAVE_GETADDRINFO)
+ message(FATAL_ERROR "Your system does not support getaddrinfo call, please consider upgrading it to run rspamd")
+ endif ()
+
+ # Check for signal information
+ if (HAVE_SIGINFO_H)
+ check_symbol_exists(SA_SIGINFO "signal.h;siginfo.h" HAVE_SA_SIGINFO)
+ else ()
+ check_symbol_exists(SA_SIGINFO "signal.h" HAVE_SA_SIGINFO)
+ endif ()
+
+ # Clock and timer features
+ if (NOT CMAKE_SYSTEM_NAME STREQUAL "SunOS")
+ if (HAVE_CLOCK_GETTIME)
+ check_symbol_exists(CLOCK_PROCESS_CPUTIME_ID time.h HAVE_CLOCK_PROCESS_CPUTIME_ID)
+ check_symbol_exists(CLOCK_VIRTUAL time.h HAVE_CLOCK_VIRTUAL)
+ else ()
+ check_include_files(sys/timeb.h HAVE_SYS_TIMEB_H)
+ endif ()
+ endif ()
+
+ # Linux-specific features
+ if (CMAKE_SYSTEM_NAME STREQUAL "Linux")
+ # In linux, we need to mount /run/shm to test which could be unavailable
+ # on a build system. On the other hand, we know that linux has stupid
+ # but compatible shmem support, so we assume this macro as true
+ set(HAVE_SANE_SHMEM 1)
+
+ check_c_source_compiles("#define _GNU_SOURCE
+ #include <sys/socket.h>
+ int main (int argc, char **argv) {
+ return ((int*)(&recvmmsg))[argc];
+ }" HAVE_RECVMMSG)
+
+ check_c_source_compiles("#define _GNU_SOURCE
+ #include <fcntl.h>
+ int main (int argc, char **argv) {
+ return ((int*)(&readahead))[argc];
+ }" HAVE_READAHEAD)
+ endif ()
+
+ # Propagate variables to parent scope
+ set(HAVE_PCRE_JIT_FAST ${HAVE_PCRE_JIT_FAST} PARENT_SCOPE)
+ set(HAVE_SANE_SHMEM ${HAVE_SANE_SHMEM} PARENT_SCOPE)
+ set(HAVE_GETPAGESIZE ${HAVE_GETPAGESIZE} PARENT_SCOPE)
+ set(HAVE_NANOSLEEP ${HAVE_NANOSLEEP} PARENT_SCOPE)
+ set(HAVE_FLOCK ${HAVE_FLOCK} PARENT_SCOPE)
+ set(HAVE_TANH ${HAVE_TANH} PARENT_SCOPE)
+ set(HAVE_MKSTEMP ${HAVE_MKSTEMP} PARENT_SCOPE)
+ set(HAVE_CLOCK_GETTIME ${HAVE_CLOCK_GETTIME} PARENT_SCOPE)
+ set(HAVE_PATH_MAX ${HAVE_PATH_MAX} PARENT_SCOPE)
+ set(HAVE_MAXPATHLEN ${HAVE_MAXPATHLEN} PARENT_SCOPE)
+ set(HAVE_MMAP_ANON ${HAVE_MMAP_ANON} PARENT_SCOPE)
+ set(HAVE_IPV6_V6ONLY ${HAVE_IPV6_V6ONLY} PARENT_SCOPE)
+ set(HAVE_POSIX_FALLOCATE ${HAVE_POSIX_FALLOCATE} PARENT_SCOPE)
+ set(HAVE_FALLOCATE ${HAVE_FALLOCATE} PARENT_SCOPE)
+ set(HAVE_SC_NPROCESSORS_ONLN ${HAVE_SC_NPROCESSORS_ONLN} PARENT_SCOPE)
+ set(PARAM_H_HAS_BITSET ${PARAM_H_HAS_BITSET} PARENT_SCOPE)
+ set(HAVE_GETADDRINFO ${HAVE_GETADDRINFO} PARENT_SCOPE)
+ set(HAVE_SCHED_YIELD ${HAVE_SCHED_YIELD} PARENT_SCOPE)
+ set(HAVE_NFTW ${HAVE_NFTW} PARENT_SCOPE)
+ set(HAVE_MEMRCHR ${HAVE_MEMRCHR} PARENT_SCOPE)
+ set(HAVE_PCRE_JIT ${HAVE_PCRE_JIT} PARENT_SCOPE)
+ set(HAVE_SOCK_SEQPACKET ${HAVE_SOCK_SEQPACKET} PARENT_SCOPE)
+ set(HAVE_ONOFOLLOW ${HAVE_ONOFOLLOW} PARENT_SCOPE)
+ set(HAVE_OCLOEXEC ${HAVE_OCLOEXEC} PARENT_SCOPE)
+ set(HAVE_SSL_TLSEXT_HOSTNAME ${HAVE_SSL_TLSEXT_HOSTNAME} PARENT_SCOPE)
+ set(HAVE_FIPS_MODE ${HAVE_FIPS_MODE} PARENT_SCOPE)
+ set(HAVE_DIRFD ${HAVE_DIRFD} PARENT_SCOPE)
+ set(HAVE_FPATHCONF ${HAVE_FPATHCONF} PARENT_SCOPE)
+ set(HAVE_SIGALTSTACK ${HAVE_SIGALTSTACK} PARENT_SCOPE)
+ set(HAVE_OPENMEMSTREAM ${HAVE_OPENMEMSTREAM} PARENT_SCOPE)
+ set(HAVE_FMEMOPEN ${HAVE_FMEMOPEN} PARENT_SCOPE)
+ set(HAVE_CLOCK_GETCPUCLOCKID ${HAVE_CLOCK_GETCPUCLOCKID} PARENT_SCOPE)
+ set(HAVE_RUSAGE_SELF ${HAVE_RUSAGE_SELF} PARENT_SCOPE)
+ set(HAVE_FFSLL ${HAVE_FFSLL} PARENT_SCOPE)
+ set(HAVE_SA_SIGINFO ${HAVE_SA_SIGINFO} PARENT_SCOPE)
+ set(HAVE_CLOCK_PROCESS_CPUTIME_ID ${HAVE_CLOCK_PROCESS_CPUTIME_ID} PARENT_SCOPE)
+ set(HAVE_CLOCK_VIRTUAL ${HAVE_CLOCK_VIRTUAL} PARENT_SCOPE)
+
+ # Linux-specific features propagation
+ if (CMAKE_SYSTEM_NAME STREQUAL "Linux")
+ set(HAVE_RECVMMSG ${HAVE_RECVMMSG} PARENT_SCOPE)
+ set(HAVE_READAHEAD ${HAVE_READAHEAD} PARENT_SCOPE)
+ endif ()
+endfunction()
+
+# Execute the function
+CheckSystemFeatures()
diff --git a/cmake/CheckSystemHeaders.cmake b/cmake/CheckSystemHeaders.cmake
new file mode 100644
index 000000000..232814eba
--- /dev/null
+++ b/cmake/CheckSystemHeaders.cmake
@@ -0,0 +1,139 @@
+# CheckSystemHeaders.cmake
+# Checks for the existence of system headers
+
+# Check platform specific includes
+function(CheckSystemHeaders)
+ # Basic system headers
+ check_include_files(sys/types.h HAVE_SYS_TYPES_H)
+ check_include_files(sys/uio.h HAVE_SYS_UIO_H)
+
+ # Standard C headers
+ check_include_files(fcntl.h HAVE_FCNTL_H)
+ check_include_files(math.h HAVE_MATH_H)
+ check_include_files(stdio.h HAVE_STDIO_H)
+ check_include_files(stdlib.h HAVE_STDLIB_H)
+ check_include_files(string.h HAVE_STRING_H)
+ check_include_files(strings.h HAVE_STRINGS_H)
+ check_include_files(time.h HAVE_TIME_H)
+ check_include_files(unistd.h HAVE_UNISTD_H)
+
+ # Data type headers
+ check_include_files(stdint.h HAVE_STDINT_H)
+ check_include_files(inttypes.h HAVE_INTTYPES_H)
+ check_include_files(stdbool.h HAVE_STDBOOL_H)
+
+ # Endian-related headers
+ check_include_files(endian.h HAVE_ENDIAN_H)
+ check_include_files(sys/endian.h HAVE_SYS_ENDIAN_H)
+ check_include_files(machine/endian.h HAVE_MACHINE_ENDIAN_H)
+
+ # System utility headers
+ check_include_files(sys/socket.h HAVE_SYS_SOCKET_H)
+ check_include_files(sys/mman.h HAVE_SYS_MMAN_H)
+ check_include_files(sys/un.h HAVE_SYS_UN_H)
+ check_include_files(sys/stat.h HAVE_SYS_STAT_H)
+ check_include_files(sys/wait.h HAVE_SYS_WAIT_H)
+ check_include_files(sys/param.h HAVE_SYS_PARAM_H)
+ check_include_files(sys/file.h HAVE_SYS_FILE_H)
+ check_include_files(sys/resource.h HAVE_SYS_RESOURCE_H)
+
+ # Network-related headers
+ check_include_files(netinet/in.h HAVE_NETINET_IN_H)
+ check_include_files(netinet/tcp.h HAVE_NETINET_TCP_H)
+ check_include_files(arpa/inet.h HAVE_ARPA_INET_H)
+ check_include_files(netdb.h HAVE_NETDB_H)
+
+ # System logging and signal handling
+ check_include_files(syslog.h HAVE_SYSLOG_H)
+ check_include_files(siginfo.h HAVE_SIGINFO_H)
+
+ # Internationalization and user/groups
+ check_include_files(locale.h HAVE_LOCALE_H)
+ check_include_files(libgen.h HAVE_LIBGEN_H)
+ check_include_files(pwd.h HAVE_PWD_H)
+ check_include_files(grp.h HAVE_GRP_H)
+
+ # File and path handling
+ check_include_files(glob.h HAVE_GLOB_H)
+ check_include_files(poll.h HAVE_POLL_H)
+ check_include_files(readpassphrase.h HAVE_READPASSPHRASE_H)
+ check_include_files(termios.h HAVE_TERMIOS_H)
+ check_include_files(paths.h HAVE_PATHS_H)
+
+ # Other utilities
+ check_include_files(ctype.h HAVE_CTYPE_H)
+ check_include_files(cpuid.h HAVE_CPUID_H)
+ check_include_files(dirent.h HAVE_DIRENT_H)
+
+ # Context-related headers
+ check_include_files(ucontext.h HAVE_UCONTEXT_H)
+ check_include_files(sys/ucontext.h HAVE_SYS_UCONTEXT_H) # OSX specific
+
+ # Time and memory
+ check_include_files(sys/timeb.h HAVE_SYS_TIMEB_H)
+
+ # Log the results for important headers
+ if (NOT HAVE_SYS_TYPES_H)
+ message(WARNING "sys/types.h not found - this may cause problems")
+ endif ()
+
+ if (NOT HAVE_SYS_SOCKET_H)
+ message(WARNING "sys/socket.h not found - networking functionality may be limited")
+ endif ()
+
+ # Return results to parent scope
+ foreach (var
+ HAVE_SYS_TYPES_H
+ HAVE_SYS_UIO_H
+ HAVE_FCNTL_H
+ HAVE_MATH_H
+ HAVE_STDIO_H
+ HAVE_STDLIB_H
+ HAVE_STRING_H
+ HAVE_STRINGS_H
+ HAVE_TIME_H
+ HAVE_UNISTD_H
+ HAVE_STDINT_H
+ HAVE_INTTYPES_H
+ HAVE_STDBOOL_H
+ HAVE_ENDIAN_H
+ HAVE_SYS_ENDIAN_H
+ HAVE_MACHINE_ENDIAN_H
+ HAVE_SYS_SOCKET_H
+ HAVE_SYS_MMAN_H
+ HAVE_SYS_UN_H
+ HAVE_SYS_STAT_H
+ HAVE_SYS_WAIT_H
+ HAVE_SYS_PARAM_H
+ HAVE_SYS_FILE_H
+ HAVE_SYS_RESOURCE_H
+ HAVE_NETINET_IN_H
+ HAVE_NETINET_TCP_H
+ HAVE_ARPA_INET_H
+ HAVE_NETDB_H
+ HAVE_SYSLOG_H
+ HAVE_SIGINFO_H
+ HAVE_LOCALE_H
+ HAVE_LIBGEN_H
+ HAVE_PWD_H
+ HAVE_GRP_H
+ HAVE_GLOB_H
+ HAVE_POLL_H
+ HAVE_READPASSPHRASE_H
+ HAVE_TERMIOS_H
+ HAVE_PATHS_H
+ HAVE_CTYPE_H
+ HAVE_UNISTD_H
+ HAVE_CPUID_H
+ HAVE_DIRENT_H
+ HAVE_UCONTEXT_H
+ HAVE_SYS_UCONTEXT_H
+ HAVE_SYS_TIMEB_H)
+ if (${var})
+ set(${var} ${${var}} PARENT_SCOPE)
+ endif ()
+ endforeach ()
+endfunction()
+
+# Execute the function
+CheckSystemHeaders()
diff --git a/cmake/CheckURLInclude.cmake b/cmake/CheckURLInclude.cmake
new file mode 100644
index 000000000..12cecacd9
--- /dev/null
+++ b/cmake/CheckURLInclude.cmake
@@ -0,0 +1,51 @@
+include(CheckIncludeFiles)
+include(CheckLibraryExists)
+
+# Function to check for URL include support (libcurl or libfetch)
+function(CheckURLIncludeSupport)
+ # First try to find libfetch
+ find_library(LIBFETCH_LIBRARY HINTS "${RSPAMD_SEARCH_PATH}"
+ NAMES fetch PATHS PATH_SUFFIXES lib64 lib
+ PATHS ${RSPAMD_DEFAULT_LIBRARY_PATHS}
+ DOC "Path where the libfetch library can be found")
+
+ if (LIBFETCH_LIBRARY)
+ # Found libfetch library, now check for header
+ find_file(HAVE_FETCH_H HINTS "${RSPAMD_SEARCH_PATH}"
+ NAMES fetch.h
+ PATH_SUFFIXES include
+ PATHS ${RSPAMD_DEFAULT_INCLUDE_PATHS}
+ DOC "Path to libfetch header")
+
+ if (HAVE_FETCH_H)
+ message(STATUS "Found libfetch: ${LIBFETCH_LIBRARY}")
+ list(APPEND RSPAMD_REQUIRED_LIBRARIES "fetch")
+ set(WITH_FETCH 1)
+ set(WITH_FETCH ${WITH_FETCH} PARENT_SCOPE)
+ else ()
+ message(STATUS "Found libfetch library but missing fetch.h header")
+ endif ()
+ else ()
+ # Try to find libcurl as an alternative
+ ProcessPackage(CURL LIBRARY curl INCLUDE curl.h INCLUDE_SUFFIXES include/curl
+ ROOT ${CURL_ROOT})
+
+ if (WITH_CURL)
+ message(STATUS "Found libcurl for URL includes")
+ set(WITH_CURL ${WITH_CURL} PARENT_SCOPE)
+ else ()
+ message(WARNING "Neither libcurl nor libfetch were found, no support of URL includes in configuration")
+ endif ()
+ endif ()
+
+ # Propagate variables to parent scope
+ if (HAVE_FETCH_H)
+ set(HAVE_FETCH_H ${HAVE_FETCH_H} PARENT_SCOPE)
+ set(LIBFETCH_LIBRARY ${LIBFETCH_LIBRARY} PARENT_SCOPE)
+ endif ()
+
+ # Update the global RSPAMD_REQUIRED_LIBRARIES list
+ if (HAVE_FETCH_H)
+ set(RSPAMD_REQUIRED_LIBRARIES ${RSPAMD_REQUIRED_LIBRARIES} PARENT_SCOPE)
+ endif ()
+endfunction()
diff --git a/cmake/InstallRspamdFiles.cmake b/cmake/InstallRspamdFiles.cmake
new file mode 100644
index 000000000..b6b631cdc
--- /dev/null
+++ b/cmake/InstallRspamdFiles.cmake
@@ -0,0 +1,104 @@
+# InstallRspamdFiles.cmake
+# Manages the installation of Rspamd files, configurations, and components
+
+function(InstallRspamdFiles)
+ # Create necessary directories
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${CONFDIR})")
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${SHAREDIR})")
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${LUALIBDIR})")
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${PLUGINSDIR})")
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${RULESDIR})")
+
+ # Install configuration files
+ set(GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.conf;${CMAKE_SOURCE_DIR}/conf/*.inc")
+ if (INSTALL_EXAMPLES)
+ list(APPEND GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.lua.example")
+ list(APPEND GLOB_PATTERNS "${CMAKE_SOURCE_DIR}/conf/*.conf.example")
+ endif ()
+
+ file(GLOB_RECURSE CONF_FILES RELATIVE "${CMAKE_SOURCE_DIR}/conf" CONFIGURE_DEPENDS
+ ${GLOB_PATTERNS})
+ foreach (CONF_FILE ${CONF_FILES})
+ get_filename_component(_rp ${CONF_FILE} PATH)
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${CONFDIR}/${_rp})")
+ install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/conf/${CONF_FILE}"
+ DESTINATION ${CONFDIR}/${_rp})
+ endforeach ()
+
+ # Install Lua plugins
+ file(GLOB LUA_PLUGINS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/src/plugins/lua" CONFIGURE_DEPENDS
+ "${CMAKE_CURRENT_SOURCE_DIR}/src/plugins/lua/*.lua")
+ foreach (LUA_PLUGIN ${LUA_PLUGINS})
+ get_filename_component(_rp ${LUA_PLUGIN} PATH)
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${PLUGINSDIR}/${_rp})")
+ install(FILES "src/plugins/lua/${LUA_PLUGIN}" DESTINATION ${PLUGINSDIR}/${_rp})
+ endforeach ()
+
+ # Install TLD list
+ install(FILES "contrib/publicsuffix/effective_tld_names.dat" DESTINATION
+ "${SHAREDIR}")
+
+ # Install language data
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${SHAREDIR}/languages)")
+ file(GLOB LANGUAGES CONFIGURE_DEPENDS "${CMAKE_CURRENT_SOURCE_DIR}/contrib/languages-data/*.json")
+ foreach (_LANG ${LANGUAGES})
+ install(FILES "${_LANG}" DESTINATION ${SHAREDIR}/languages)
+ endforeach ()
+ install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/contrib/languages-data/stop_words"
+ DESTINATION ${SHAREDIR}/languages)
+
+ # Install Lua rules
+ file(GLOB_RECURSE LUA_CONFIGS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/rules" CONFIGURE_DEPENDS
+ "${CMAKE_CURRENT_SOURCE_DIR}/rules/*.lua")
+ foreach (LUA_CONF ${LUA_CONFIGS})
+ get_filename_component(_rp ${LUA_CONF} PATH)
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${RULESDIR}/${_rp})")
+ install(FILES "rules/${LUA_CONF}" DESTINATION ${RULESDIR}/${_rp})
+ endforeach ()
+
+ # Install Lua libraries
+ file(GLOB_RECURSE LUA_LIBS RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}/lualib" CONFIGURE_DEPENDS
+ "${CMAKE_CURRENT_SOURCE_DIR}/lualib/*.lua")
+ foreach (LUA_LIB ${LUA_LIBS})
+ get_filename_component(_rp ${LUA_LIB} PATH)
+ install(CODE "FILE(MAKE_DIRECTORY \$ENV{DESTDIR}${LUALIBDIR}/${_rp})")
+ install(FILES "lualib/${LUA_LIB}" DESTINATION ${LUALIBDIR}/${_rp})
+ endforeach ()
+
+ # Install third-party Lua libraries
+ install(FILES "contrib/lua-fun/fun.lua" DESTINATION ${LUALIBDIR})
+ install(FILES "contrib/lua-argparse/argparse.lua" DESTINATION ${LUALIBDIR})
+ install(FILES "contrib/lua-tableshape/tableshape.lua" DESTINATION ${LUALIBDIR})
+ install(FILES "contrib/lua-lupa/lupa.lua" DESTINATION ${LUALIBDIR})
+ install(FILES "contrib/lua-lpeg/lpegre.lua" DESTINATION ${LUALIBDIR})
+
+ # Install systemd unit if on Linux and requested
+ if (CMAKE_SYSTEM_NAME STREQUAL "Linux" AND WANT_SYSTEMD_UNITS)
+ install(FILES "rspamd.service" DESTINATION ${SYSTEMDDIR})
+ endif ()
+
+ # Install man pages
+ install(FILES "doc/rspamd.8" DESTINATION ${MANDIR}/man8)
+ install(FILES "doc/rspamc.1" DESTINATION ${MANDIR}/man1)
+ install(FILES "doc/rspamadm.1" DESTINATION ${MANDIR}/man1)
+
+ # Install utilities
+ install(PROGRAMS "utils/rspamd_stats.pl" RENAME rspamd_stats DESTINATION bin)
+
+ # Install web UI if requested
+ if (INSTALL_WEBUI)
+ install(DIRECTORY "interface/" DESTINATION ${WWWDIR} PATTERN ".git" EXCLUDE)
+ endif ()
+
+ # Log installation paths
+ message(STATUS "Rspamd will be installed in the following directories:")
+ message(STATUS " - Binaries: ${CMAKE_INSTALL_PREFIX}/bin")
+ message(STATUS " - Configuration: ${CONFDIR}")
+ message(STATUS " - Rules: ${RULESDIR}")
+ message(STATUS " - Lua libraries: ${LUALIBDIR}")
+ message(STATUS " - Plugins: ${PLUGINSDIR}")
+ message(STATUS " - Shared data: ${SHAREDIR}")
+ if (INSTALL_WEBUI)
+ message(STATUS " - Web UI: ${WWWDIR}")
+ endif ()
+endfunction()
diff --git a/cmake/SetupPVSStudio.cmake b/cmake/SetupPVSStudio.cmake
new file mode 100644
index 000000000..92fa560f0
--- /dev/null
+++ b/cmake/SetupPVSStudio.cmake
@@ -0,0 +1,56 @@
+# SetupPVSStudio.cmake
+# Configures PVS-Studio static code analysis if available
+
+function(SetupPVSStudio)
+ # Try to find PVS-Studio analyzer
+ find_program(_PVS_STUDIO "pvs-studio-analyzer")
+
+ if (_PVS_STUDIO)
+ message(STATUS "Found PVS-Studio analyzer: ${_PVS_STUDIO}")
+
+ # Include the PVS-Studio module
+ include(PVS-Studio)
+
+ # Get a list of source directories to analyze
+ set(_ANALYZE_TARGETS
+ ${PROJECT_NAME} # Main project
+ rspamd-server # Server component
+ rspamadm # Admin utility
+ rspamc # Client utility
+ )
+
+ # Setup analysis target
+ pvs_studio_add_target(
+ TARGET ${PROJECT_NAME}.analyze # Target name for running analysis
+ ANALYZE ${_ANALYZE_TARGETS} # What to analyze
+ OUTPUT FORMAT errorfile # Output format
+ LOG target_${PROJECT_NAME}.err # Log file path
+ ARGS
+ # Additional pvs-studio-analyzer arguments
+ --exclude-path "${CMAKE_SOURCE_DIR}/contrib" # Exclude third-party code
+ )
+
+ # Add a help message for the target
+ add_custom_command(
+ TARGET ${PROJECT_NAME}.analyze
+ POST_BUILD
+ COMMAND ${CMAKE_COMMAND} -E echo "PVS-Studio analysis complete. Results in target_${PROJECT_NAME}.err"
+ )
+
+ # Create a report target that converts the error file to a more readable format
+ add_custom_target(${PROJECT_NAME}.analyze-report
+ COMMAND ${CMAKE_COMMAND} -E echo "Generating HTML report from PVS-Studio results..."
+ COMMAND plog-converter -a GA:1,2,3 -t fullhtml -o pvs-report target_${PROJECT_NAME}.err
+ COMMAND ${CMAKE_COMMAND} -E echo "Report generated in pvs-report/ directory"
+ DEPENDS ${PROJECT_NAME}.analyze
+ COMMENT "Converting PVS-Studio output to HTML report"
+ VERBATIM
+ )
+
+ message(STATUS "PVS-Studio targets added:")
+ message(STATUS " - ${PROJECT_NAME}.analyze: Run the analysis")
+ message(STATUS " - ${PROJECT_NAME}.analyze-report: Generate HTML report from analysis results")
+ else ()
+ message(STATUS "PVS-Studio analyzer not found. Static analysis disabled.")
+ endif ()
+endfunction()
diff --git a/contrib/xxhash/CMakeLists.txt b/contrib/xxhash/CMakeLists.txt
index fa69efbe0..5091d261d 100644
--- a/contrib/xxhash/CMakeLists.txt
+++ b/contrib/xxhash/CMakeLists.txt
@@ -1,13 +1,13 @@
SET(XXHASHSRC xxhash.c)
-ADD_LIBRARY(xxhash STATIC ${XXHASHSRC})
+ADD_LIBRARY(rspamd-xxhash STATIC ${XXHASHSRC})
-IF(ENABLE_FULL_DEBUG MATCHES "OFF")
-if ("${CMAKE_C_COMPILER_ID}" STREQUAL "Clang" OR "${CMAKE_C_COMPILER_ID}" STREQUAL "GNU")
- SET_TARGET_PROPERTIES(xxhash PROPERTIES COMPILE_FLAGS "-O3")
-endif ()
-else()
-ADD_DEFINITIONS(-DXXH_NO_INLINE_HINTS=1)
-ENDIF()
+IF (ENABLE_FULL_DEBUG MATCHES "OFF")
+ if ("${CMAKE_C_COMPILER_ID}" STREQUAL "Clang" OR "${CMAKE_C_COMPILER_ID}" STREQUAL "GNU")
+ SET_TARGET_PROPERTIES(rspamd-xxhash PROPERTIES COMPILE_FLAGS "-O3")
+ endif ()
+else ()
+ ADD_DEFINITIONS(-DXXH_NO_INLINE_HINTS=1)
+ENDIF ()
-set (CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DXXH_NO_INLINE_HINTS=1" PARENT_SCOPE)
+set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DXXH_NO_INLINE_HINTS=1" PARENT_SCOPE)
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 92edb0b6a..e4d3c7d81 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -1,246 +1,286 @@
-MACRO(_AddModulesForced MLIST)
-# Generate unique string for this build
- SET(MODULES_C "${CMAKE_CURRENT_BINARY_DIR}/modules.c")
- FILE(WRITE "${MODULES_C}"
- "#include \"rspamd.h\"\n")
-
- # Handle even old cmake
- LIST(LENGTH ${MLIST} MLIST_COUNT)
- MATH(EXPR MLIST_MAX ${MLIST_COUNT}-1)
-
- FOREACH(MOD_IDX RANGE ${MLIST_MAX})
- LIST(GET ${MLIST} ${MOD_IDX} MOD)
- FILE(APPEND "${MODULES_C}" "extern module_t ${MOD}_module;\n")
- ENDFOREACH(MOD_IDX RANGE ${MLIST_MAX})
-
- FILE(APPEND "${MODULES_C}" "\n\nmodule_t *modules[] = {\n")
-
- FOREACH(MOD_IDX RANGE ${MLIST_MAX})
- LIST(GET ${MLIST} ${MOD_IDX} MOD)
- FILE(APPEND "${MODULES_C}" "&${MOD}_module,\n")
- ENDFOREACH(MOD_IDX RANGE ${MLIST_MAX})
-
- FILE(APPEND "${MODULES_C}" "NULL\n};\n")
-ENDMACRO(_AddModulesForced MLIST)
-
-MACRO(_AddWorkersForced WLIST)
- SET(WORKERS_C "${CMAKE_CURRENT_BINARY_DIR}/workers.c")
- FILE(WRITE "${WORKERS_C}"
- "#include \"rspamd.h\"\n")
-
- # Handle even old cmake
- LIST(LENGTH ${WLIST} WLIST_COUNT)
- MATH(EXPR WLIST_MAX ${WLIST_COUNT}-1)
- FOREACH(MOD_IDX RANGE ${WLIST_MAX})
- LIST(GET ${WLIST} ${MOD_IDX} WRK)
- FILE(APPEND "${WORKERS_C}" "extern worker_t ${WRK}_worker;\n")
- ENDFOREACH(MOD_IDX RANGE ${WLIST_MAX})
-
- FILE(APPEND "${WORKERS_C}" "\n\nworker_t *workers[] = {\n")
-
- FOREACH(MOD_IDX RANGE ${WLIST_MAX})
- LIST(GET ${WLIST} ${MOD_IDX} WRK)
- FILE(APPEND "${WORKERS_C}" "&${WRK}_worker,\n")
- ENDFOREACH(MOD_IDX RANGE ${WLIST_MAX})
- FILE(APPEND "${WORKERS_C}" "NULL\n};\n")
-ENDMACRO(_AddWorkersForced WLIST)
-
-MACRO(AddModules MLIST WLIST)
- _AddModulesForced(${MLIST})
- _AddWorkersForced(${WLIST})
- #IF(NOT EXISTS "modules.c")
- # _AddModulesForced(${MLIST} ${WLIST})
- #ELSE(NOT EXISTS "modules.c")
- # FILE(STRINGS "modules.c" FILE_ID_RAW REGEX "^/.*[a-zA-Z0-9]+.*/$")
- # STRING(REGEX MATCH "[a-zA-Z0-9]+" FILE_ID "${FILE_ID_RAW}")
- # IF(NOT FILE_ID STREQUAL MODULES_ID)
- # MESSAGE("Regenerate modules info")
- # _AddModulesForced(${MLIST} ${WLIST})
- # ENDIF(NOT FILE_ID STREQUAL MODULES_ID)
- #ENDIF(NOT EXISTS "modules.c")
-ENDMACRO(AddModules MLIST WLIST)
-
-# Rspamd core components
-IF (ENABLE_CLANG_PLUGIN MATCHES "ON")
- SET(CMAKE_C_FLAGS
- "${CMAKE_C_FLAGS} -Xclang -load -Xclang ${CMAKE_CURRENT_BINARY_DIR}/../clang-plugin/librspamd-clang${CMAKE_SHARED_LIBRARY_SUFFIX} -Xclang -add-plugin -Xclang rspamd-ast")
- IF(CLANG_EXTRA_PLUGINS_LIBS)
- FOREACH(_lib ${CLANG_EXTRA_PLUGINS_LIBS})
- SET(CMAKE_C_FLAGS
- "${CMAKE_C_FLAGS} -Xclang -load -Xclang ${_lib}")
- SET(CMAKE_CXX_FLAGS
- "${CMAKE_CXX_FLAGS} -Xclang -load -Xclang ${_lib}")
- ENDFOREACH()
- ENDIF()
- IF(CLANG_EXTRA_PLUGINS)
- FOREACH(_plug ${CLANG_EXTRA_PLUGINS})
- SET(CMAKE_C_FLAGS
- "${CMAKE_C_FLAGS} -Xclang -add-plugin -Xclang ${_plug}")
- SET(CMAKE_CXX_FLAGS
- "${CMAKE_C_FLAGS} -Xclang -add-plugin -Xclang ${_plug}")
- ENDFOREACH()
- ENDIF()
-ENDIF ()
-
-ADD_SUBDIRECTORY(lua)
-ADD_SUBDIRECTORY(libcryptobox)
-ADD_SUBDIRECTORY(libutil)
-ADD_SUBDIRECTORY(libserver)
-ADD_SUBDIRECTORY(libmime)
-ADD_SUBDIRECTORY(libstat)
-ADD_SUBDIRECTORY(client)
-ADD_SUBDIRECTORY(rspamadm)
-
-SET(RSPAMDSRC controller.c
- fuzzy_storage.c
- rspamd.c
- worker.c
- rspamd_proxy.c)
-
-SET(PLUGINSSRC plugins/regexp.c
- plugins/chartable.cxx
- plugins/fuzzy_check.c
- plugins/dkim_check.c
- libserver/rspamd_control.c)
-
-SET(MODULES_LIST regexp chartable fuzzy_check dkim)
-SET(WORKERS_LIST normal controller fuzzy rspamd_proxy)
-IF (ENABLE_HYPERSCAN MATCHES "ON")
- LIST(APPEND WORKERS_LIST "hs_helper")
- LIST(APPEND RSPAMDSRC "hs_helper.c")
-ENDIF()
-
-AddModules(MODULES_LIST WORKERS_LIST)
-LIST(LENGTH PLUGINSSRC RSPAMD_MODULES_NUM)
-
-SET(RAGEL_DEPENDS "${CMAKE_SOURCE_DIR}/src/ragel/smtp_address.rl"
- "${CMAKE_SOURCE_DIR}/src/ragel/smtp_date.rl"
- "${CMAKE_SOURCE_DIR}/src/ragel/smtp_ip.rl"
- "${CMAKE_SOURCE_DIR}/src/ragel/smtp_base.rl"
- "${CMAKE_SOURCE_DIR}/src/ragel/content_disposition.rl")
-RAGEL_TARGET(ragel_smtp_addr
- INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_addr_parser.rl
- DEPENDS ${RAGEL_DEPENDS}
- COMPILE_FLAGS -T1
- OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/smtp_addr_parser.rl.c)
-RAGEL_TARGET(ragel_content_disposition
- INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/content_disposition_parser.rl
- DEPENDS ${RAGEL_DEPENDS}
- COMPILE_FLAGS -G2
- OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/content_disposition.rl.c)
-RAGEL_TARGET(ragel_rfc2047
- INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/rfc2047_parser.rl
- DEPENDS ${RAGEL_DEPENDS}
- COMPILE_FLAGS -G2
- OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/rfc2047.rl.c)
-RAGEL_TARGET(ragel_smtp_date
- INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_date_parser.rl
- DEPENDS ${RAGEL_DEPENDS}
- COMPILE_FLAGS -G2
- OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/date_parser.rl.c)
-RAGEL_TARGET(ragel_smtp_ip
- INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_ip_parser.rl
- DEPENDS ${RAGEL_DEPENDS}
- COMPILE_FLAGS -G2
- OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/ip_parser.rl.c)
-# Fucking cmake...
-FOREACH(_GEN ${LIBSERVER_GENERATED})
- set_source_files_properties(${_GEN} PROPERTIES GENERATED TRUE)
-ENDFOREACH()
-######################### LINK SECTION ###############################
-
-IF(ENABLE_STATIC MATCHES "ON")
- ADD_LIBRARY(rspamd-server STATIC
- ${RSPAMD_CRYPTOBOX}
- ${RSPAMD_UTIL}
- ${RSPAMD_LUA}
- ${RSPAMD_SERVER}
- ${RSPAMD_STAT}
- ${RSPAMD_MIME}
- ${CMAKE_CURRENT_BINARY_DIR}/modules.c
- ${PLUGINSSRC}
- "${RAGEL_ragel_smtp_addr_OUTPUTS}"
- "${RAGEL_ragel_newlines_strip_OUTPUTS}"
- "${RAGEL_ragel_content_type_OUTPUTS}"
- "${RAGEL_ragel_content_disposition_OUTPUTS}"
- "${RAGEL_ragel_rfc2047_OUTPUTS}"
- "${RAGEL_ragel_smtp_date_OUTPUTS}"
- "${RAGEL_ragel_smtp_ip_OUTPUTS}"
- ${BACKWARD_ENABLE})
-ELSE()
- ADD_LIBRARY(rspamd-server SHARED
- ${RSPAMD_CRYPTOBOX}
- ${RSPAMD_UTIL}
- ${RSPAMD_SERVER}
- ${RSPAMD_STAT}
- ${RSPAMD_MIME}
- ${RSPAMD_LUA}
- ${CMAKE_CURRENT_BINARY_DIR}/modules.c
- ${PLUGINSSRC}
- "${RAGEL_ragel_smtp_addr_OUTPUTS}"
- "${RAGEL_ragel_newlines_strip_OUTPUTS}"
- "${RAGEL_ragel_content_type_OUTPUTS}"
- "${RAGEL_ragel_content_disposition_OUTPUTS}"
- "${RAGEL_ragel_rfc2047_OUTPUTS}"
- "${RAGEL_ragel_smtp_date_OUTPUTS}"
- "${RAGEL_ragel_smtp_ip_OUTPUTS}"
- ${BACKWARD_ENABLE})
-ENDIF()
-
-FOREACH(_DEP ${LIBSERVER_DEPENDS})
- ADD_DEPENDENCIES(rspamd-server "${_DEP}")
-ENDFOREACH()
-
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-http-parser)
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-fpconv)
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-cdb)
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-lpeg)
-TARGET_LINK_LIBRARIES(rspamd-server lcbtrie)
-IF(SYSTEM_ZSTD MATCHES "OFF")
- TARGET_LINK_LIBRARIES(rspamd-server rspamd-zstd)
-ELSE()
- TARGET_LINK_LIBRARIES(rspamd-server zstd)
-ENDIF()
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-simdutf)
-
-IF (ENABLE_CLANG_PLUGIN MATCHES "ON")
- ADD_DEPENDENCIES(rspamd-server rspamd-clang)
-ENDIF()
-
-IF (NOT WITH_LUAJIT)
- TARGET_LINK_LIBRARIES(rspamd-server rspamd-bit)
-ENDIF()
-
-IF (ENABLE_SNOWBALL MATCHES "ON")
- TARGET_LINK_LIBRARIES(rspamd-server stemmer)
-ENDIF()
-TARGET_LINK_LIBRARIES(rspamd-server rspamd-hiredis)
-
-IF (ENABLE_FANN MATCHES "ON")
- TARGET_LINK_LIBRARIES(rspamd-server fann)
-ENDIF ()
-
-IF (ENABLE_HYPERSCAN MATCHES "ON")
- TARGET_LINK_LIBRARIES(rspamd-server hs)
-ENDIF()
-
-IF(WITH_BLAS)
- TARGET_LINK_LIBRARIES(rspamd-server ${BLAS_REQUIRED_LIBRARIES})
-ENDIF()
-
-TARGET_LINK_LIBRARIES(rspamd-server ${RSPAMD_REQUIRED_LIBRARIES})
-ADD_BACKWARD(rspamd-server)
-
-ADD_EXECUTABLE(rspamd ${RSPAMDSRC} ${CMAKE_CURRENT_BINARY_DIR}/workers.c ${CMAKE_CURRENT_BINARY_DIR}/config.h)
-ADD_BACKWARD(rspamd)
-SET_TARGET_PROPERTIES(rspamd PROPERTIES LINKER_LANGUAGE CXX)
-SET_TARGET_PROPERTIES(rspamd-server PROPERTIES LINKER_LANGUAGE CXX)
-IF(NOT NO_TARGET_VERSIONS)
- SET_TARGET_PROPERTIES(rspamd PROPERTIES VERSION ${RSPAMD_VERSION})
-ENDIF()
-
-#TARGET_LINK_LIBRARIES(rspamd ${RSPAMD_REQUIRED_LIBRARIES})
-TARGET_LINK_LIBRARIES(rspamd rspamd-server)
-
-INSTALL(TARGETS rspamd RUNTIME DESTINATION bin)
-INSTALL(TARGETS rspamd-server LIBRARY DESTINATION ${RSPAMD_LIBDIR}) \ No newline at end of file
+# Function to generate module registrations
+function(generate_modules_list MODULE_LIST)
+ # Generate unique string for this build
+ set(MODULES_C "${CMAKE_CURRENT_BINARY_DIR}/modules.c")
+ file(WRITE "${MODULES_C}"
+ "#include \"rspamd.h\"\n")
+
+ # Process each module
+ foreach (MOD IN LISTS ${MODULE_LIST})
+ file(APPEND "${MODULES_C}" "extern module_t ${MOD}_module;\n")
+ endforeach ()
+
+ file(APPEND "${MODULES_C}" "\n\nmodule_t *modules[] = {\n")
+
+ foreach (MOD IN LISTS ${MODULE_LIST})
+ file(APPEND "${MODULES_C}" "&${MOD}_module,\n")
+ endforeach ()
+
+ file(APPEND "${MODULES_C}" "NULL\n};\n")
+
+ # Return the generated file path
+ set(MODULES_C_PATH "${MODULES_C}" PARENT_SCOPE)
+endfunction()
+
+# Function to generate worker registrations
+function(generate_workers_list WORKER_LIST)
+ set(WORKERS_C "${CMAKE_CURRENT_BINARY_DIR}/workers.c")
+ file(WRITE "${WORKERS_C}"
+ "#include \"rspamd.h\"\n")
+
+ # Process each worker
+ foreach (WRK IN LISTS ${WORKER_LIST})
+ file(APPEND "${WORKERS_C}" "extern worker_t ${WRK}_worker;\n")
+ endforeach ()
+
+ file(APPEND "${WORKERS_C}" "\n\nworker_t *workers[] = {\n")
+
+ foreach (WRK IN LISTS ${WORKER_LIST})
+ file(APPEND "${WORKERS_C}" "&${WRK}_worker,\n")
+ endforeach ()
+
+ file(APPEND "${WORKERS_C}" "NULL\n};\n")
+
+ # Return the generated file path
+ set(WORKERS_C_PATH "${WORKERS_C}" PARENT_SCOPE)
+endfunction()
+
+# Function to generate both modules and workers
+function(generate_registration_code MODULE_LIST WORKER_LIST)
+ generate_modules_list(${MODULE_LIST})
+ generate_workers_list(${WORKER_LIST})
+
+ # Set parent scope variables
+ set(MODULES_C_PATH ${MODULES_C_PATH} PARENT_SCOPE)
+ set(WORKERS_C_PATH ${WORKERS_C_PATH} PARENT_SCOPE)
+endfunction()
+
+# Configure Clang Plugin if enabled
+if (ENABLE_CLANG_PLUGIN)
+ set(CLANG_PLUGIN_FLAGS "-Xclang -load -Xclang ${CMAKE_CURRENT_BINARY_DIR}/../clang-plugin/librspamd-clang${CMAKE_SHARED_LIBRARY_SUFFIX} -Xclang -add-plugin -Xclang rspamd-ast")
+
+ # Apply to both C and C++ compiler flags
+ add_compile_options(${CLANG_PLUGIN_FLAGS})
+
+ # Add any extra clang plugins
+ if (CLANG_EXTRA_PLUGINS_LIBS)
+ foreach (lib ${CLANG_EXTRA_PLUGINS_LIBS})
+ add_compile_options("-Xclang" "-load" "-Xclang" "${lib}")
+ endforeach ()
+ endif ()
+
+ if (CLANG_EXTRA_PLUGINS)
+ foreach (plug ${CLANG_EXTRA_PLUGINS})
+ add_compile_options("-Xclang" "-add-plugin" "-Xclang" "${plug}")
+ endforeach ()
+ endif ()
+endif ()
+
+# Add subdirectories for components
+add_subdirectory(lua)
+add_subdirectory(libcryptobox)
+add_subdirectory(libutil)
+add_subdirectory(libserver)
+add_subdirectory(libmime)
+add_subdirectory(libstat)
+add_subdirectory(client)
+add_subdirectory(rspamadm)
+
+# Define source files
+set(RSPAMD_SOURCES
+ controller.c
+ fuzzy_storage.c
+ rspamd.c
+ worker.c
+ rspamd_proxy.c)
+
+set(PLUGIN_SOURCES
+ plugins/regexp.c
+ plugins/chartable.cxx
+ plugins/fuzzy_check.c
+ plugins/dkim_check.c
+ libserver/rspamd_control.c)
+
+# Define module and worker lists
+set(MODULES_LIST regexp chartable fuzzy_check dkim)
+set(WORKERS_LIST normal controller fuzzy rspamd_proxy)
+
+# Add hyperscan worker if enabled
+if (ENABLE_HYPERSCAN)
+ list(APPEND WORKERS_LIST hs_helper)
+ list(APPEND RSPAMD_SOURCES hs_helper.c)
+endif ()
+
+# Generate modules and workers registration code
+generate_registration_code(MODULES_LIST WORKERS_LIST)
+
+# Count the number of modules
+list(LENGTH PLUGIN_SOURCES RSPAMD_MODULES_NUM)
+
+# Configure Ragel for parsers
+set(RAGEL_DEPENDS
+ "${CMAKE_SOURCE_DIR}/src/ragel/smtp_address.rl"
+ "${CMAKE_SOURCE_DIR}/src/ragel/smtp_date.rl"
+ "${CMAKE_SOURCE_DIR}/src/ragel/smtp_ip.rl"
+ "${CMAKE_SOURCE_DIR}/src/ragel/smtp_base.rl"
+ "${CMAKE_SOURCE_DIR}/src/ragel/content_disposition.rl")
+
+# Generate parsers with Ragel
+ragel_target(ragel_smtp_addr
+ INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_addr_parser.rl
+ DEPENDS ${RAGEL_DEPENDS}
+ COMPILE_FLAGS -T1
+ OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/smtp_addr_parser.rl.c)
+
+ragel_target(ragel_content_disposition
+ INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/content_disposition_parser.rl
+ DEPENDS ${RAGEL_DEPENDS}
+ COMPILE_FLAGS -G2
+ OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/content_disposition.rl.c)
+
+ragel_target(ragel_rfc2047
+ INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/rfc2047_parser.rl
+ DEPENDS ${RAGEL_DEPENDS}
+ COMPILE_FLAGS -G2
+ OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/rfc2047.rl.c)
+
+ragel_target(ragel_smtp_date
+ INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_date_parser.rl
+ DEPENDS ${RAGEL_DEPENDS}
+ COMPILE_FLAGS -G2
+ OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/date_parser.rl.c)
+
+ragel_target(ragel_smtp_ip
+ INPUTS ${CMAKE_SOURCE_DIR}/src/ragel/smtp_ip_parser.rl
+ DEPENDS ${RAGEL_DEPENDS}
+ COMPILE_FLAGS -G2
+ OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/ip_parser.rl.c)
+
+# Mark generated files correctly
+foreach (_gen ${LIBSERVER_GENERATED})
+ set_source_files_properties(${_gen} PROPERTIES GENERATED TRUE)
+endforeach ()
+
+# Collection of all generated Ragel outputs
+set(RAGEL_OUTPUTS
+ ${RAGEL_ragel_smtp_addr_OUTPUTS}
+ ${RAGEL_ragel_newlines_strip_OUTPUTS}
+ ${RAGEL_ragel_content_type_OUTPUTS}
+ ${RAGEL_ragel_content_disposition_OUTPUTS}
+ ${RAGEL_ragel_rfc2047_OUTPUTS}
+ ${RAGEL_ragel_smtp_date_OUTPUTS}
+ ${RAGEL_ragel_smtp_ip_OUTPUTS})
+
+# Common sources for rspamd-server
+set(SERVER_COMMON_SOURCES
+ ${RSPAMD_CRYPTOBOX}
+ ${RSPAMD_UTIL}
+ ${RSPAMD_LUA}
+ ${RSPAMD_SERVER}
+ ${RSPAMD_STAT}
+ ${RSPAMD_MIME}
+ ${MODULES_C_PATH}
+ ${PLUGIN_SOURCES}
+ ${RAGEL_OUTPUTS}
+ ${BACKWARD_ENABLE})
+
+# Build rspamd-server as static or shared library based on configuration
+if (ENABLE_STATIC)
+ add_library(rspamd-server STATIC ${SERVER_COMMON_SOURCES})
+else ()
+ add_library(rspamd-server SHARED ${SERVER_COMMON_SOURCES})
+endif ()
+
+# Set dependencies for rspamd-server
+foreach (_dep ${LIBSERVER_DEPENDS})
+ add_dependencies(rspamd-server "${_dep}")
+endforeach ()
+
+# Link dependencies
+target_link_libraries(rspamd-server
+ PRIVATE
+ rspamd-http-parser
+ rspamd-fpconv
+ rspamd-cdb
+ rspamd-lpeg
+ ottery
+ lcbtrie
+ rspamd-simdutf
+ rdns
+ ucl)
+
+# Handle xxhash dependency
+if (SYSTEM_XXHASH)
+ target_link_libraries(rspamd-server PUBLIC xxhash)
+else ()
+ target_link_libraries(rspamd-server PRIVATE rspamd-xxhash)
+endif ()
+
+# Handle zstd dependency
+if (SYSTEM_ZSTD)
+ target_link_libraries(rspamd-server PUBLIC zstd)
+else ()
+ target_link_libraries(rspamd-server PRIVATE rspamd-zstd)
+endif ()
+
+# Handle clang plugin dependency
+if (ENABLE_CLANG_PLUGIN)
+ add_dependencies(rspamd-server rspamd-clang)
+endif ()
+
+# Handle Lua JIT/Lua dependency
+if (NOT WITH_LUAJIT)
+ target_link_libraries(rspamd-server PRIVATE rspamd-bit)
+endif ()
+
+# Link additional optional dependencies
+if (ENABLE_SNOWBALL)
+ target_link_libraries(rspamd-server PRIVATE stemmer)
+endif ()
+
+target_link_libraries(rspamd-server PRIVATE rspamd-hiredis)
+
+if (ENABLE_FANN)
+ target_link_libraries(rspamd-server PRIVATE fann)
+endif ()
+
+if (ENABLE_HYPERSCAN)
+ target_link_libraries(rspamd-server PUBLIC hs)
+endif ()
+
+if (WITH_BLAS)
+ target_link_libraries(rspamd-server PRIVATE ${BLAS_REQUIRED_LIBRARIES})
+endif ()
+
+# Link all required system libraries
+target_link_libraries(rspamd-server PUBLIC ${RSPAMD_REQUIRED_LIBRARIES})
+
+# Add Backward support for stacktrace
+add_backward(rspamd-server)
+
+# Build main rspamd executable
+add_executable(rspamd
+ ${RSPAMD_SOURCES}
+ ${WORKERS_C_PATH}
+ ${CMAKE_CURRENT_BINARY_DIR}/config.h)
+
+# Configure rspamd executable
+add_backward(rspamd)
+set_target_properties(rspamd PROPERTIES LINKER_LANGUAGE CXX)
+set_target_properties(rspamd-server PROPERTIES LINKER_LANGUAGE CXX)
+
+if (NOT NO_TARGET_VERSIONS)
+ set_target_properties(rspamd PROPERTIES VERSION ${RSPAMD_VERSION})
+endif ()
+
+# Link rspamd executable with the server library
+target_link_libraries(rspamd PRIVATE rspamd-server)
+
+# Install targets
+install(TARGETS rspamd
+ RUNTIME
+ DESTINATION bin)
+
+install(TARGETS rspamd-server
+ LIBRARY
+ DESTINATION ${RSPAMD_LIBDIR})
diff --git a/src/rspamadm/lua_repl.c b/src/rspamadm/lua_repl.c
index 41a319de9..9ad790d20 100644
--- a/src/rspamadm/lua_repl.c
+++ b/src/rspamadm/lua_repl.c
@@ -1,5 +1,5 @@
/*
- * Copyright 2024 Vsevolod Stakhov
+ * Copyright 2025 Vsevolod Stakhov
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -701,8 +701,8 @@ rspamadm_lua_run_repl(lua_State *L, bool is_batch)
g_string_append(tb, " \n");
}
}
- }
#endif
+ }
}
}