diff --git a/.cirrus.yml b/.cirrus.yml index 2c5648a0fd..85902c4d81 100644 --- a/.cirrus.yml +++ b/.cirrus.yml @@ -357,3 +357,23 @@ ubsan_sanitizer_task: # CXXFLAGS: -DZEEK_DICT_DEBUG # ZEEK_CI_CONFIGURE_FLAGS: *TSAN_SANITIZER_CONFIG # ZEEK_CI_DISABLE_SCRIPT_PROFILING: 1 + +windows_task: + # 2 hour timeout just for potential of building Docker image taking a while + timeout_in: 120m + windows_container: + # image: cirrusci/windowsservercore:cmake + # image: zeekurity/broker-ci-windows:latest + dockerfile: ci/windows/Dockerfile + os_version: 2019 + cpu: 8 + # Not allowed to request less than 8GB for an 8 CPU Windows VM. + memory: 8GB + sync_submodules_script: git submodule update --recursive --init + prepare_script: ci/windows/prepare.cmd + build_script: ci/windows/build.cmd + test_script: ci/windows/test.cmd + env: + ZEEK_CI_CPUS: 8 + # Give verbose error output on a test failure. + CTEST_OUTPUT_ON_FAILURE: 1 diff --git a/.gitignore b/.gitignore index 47d737f573..6a31b11bd7 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,7 @@ # Ignore anything prefixed with build since people # tend to name all of their build directories prefixed that way. build* +!ci/windows/build.cmd tmp *.gcov @@ -17,3 +18,12 @@ cmake-build-* # clangd .cache + +out/ + +# Visual Studio +.vs/ +.vscode/ +CMakeSettings.json + +src/include \ No newline at end of file diff --git a/.gitmodules b/.gitmodules index 72c078326f..13774cbbfd 100644 --- a/.gitmodules +++ b/.gitmodules @@ -70,3 +70,6 @@ [submodule "auxil/zeek-af_packet-plugin"] path = auxil/zeek-af_packet-plugin url = https://github.com/zeek/zeek-af_packet-plugin.git +[submodule "auxil/libunistd"] + path = auxil/libunistd + url = https://github.com/zeek/libunistd diff --git a/CHANGES b/CHANGES index b189c7c50b..0f99bc6931 100644 --- a/CHANGES +++ b/CHANGES @@ -1,3 +1,7 @@ +5.2.0-dev.307 | 2022-11-11 15:13:47 -0700 + + * Merged support for Microsoft Windows (Tomer Lev, Elad Solomon, Microsoft) + 5.2.0-dev.234 | 2022-11-11 12:48:20 -0700 * Spelling src (Josh Soref) diff --git a/CMakeLists.txt b/CMakeLists.txt index a2061b010c..2b960d522b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,9 +2,110 @@ # auxil/zeek-aux/plugin-support/skeleton/CMakeLists.txt cmake_minimum_required(VERSION 3.15.0 FATAL_ERROR) +if ( WIN32 ) + # Enable usage of CMAKE_MSVC_RUNTIME_LIBRARY variable + cmake_policy(SET CMP0091 NEW) +endif() + project(Zeek C CXX) -include(GNUInstallDirs) +option(ZEEK_STANDALONE "Is Zeek compiled stand-alone or embedded in a parent project." ON) +option(ENABLE_ZEEK_UNIT_TESTS "Should the doctest unit tests be built?" ON) + +list(APPEND CMAKE_MODULE_PATH ${CMAKE_BINARY_DIR}) +list(APPEND CMAKE_PREFIX_PATH ${CMAKE_BINARY_DIR}) + +# Windows: Configure runtime and dependencies +if ( MSVC ) + # Remove existing runtime flags + set(CompilerFlags + CMAKE_CXX_FLAGS + CMAKE_CXX_FLAGS_DEBUG + CMAKE_CXX_FLAGS_RELEASE + CMAKE_CXX_FLAGS_RELWITHDEBINFO + CMAKE_C_FLAGS + CMAKE_C_FLAGS_DEBUG + CMAKE_C_FLAGS_RELEASE + CMAKE_C_FLAGS_RELWITHDEBINFO + ) + foreach(CompilerFlag ${CompilerFlags}) + string(REGEX REPLACE "[/|-]MDd" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]MD" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]MTd" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]MT" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]Zi" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]W3" "" ${CompilerFlag} "${${CompilerFlag}}") + string(REGEX REPLACE "[/|-]W4" "" ${CompilerFlag} "${${CompilerFlag}}") + endforeach() + + # Set compilation flags for Windows + add_compile_options( + /guard:cf # required by CheckCFlags + /Z7) # required by CheckCFlags + + add_link_options( + /debug:full # required by CheckCFlags + ) + + # Set always to static runtime + set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} /MT") + set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} /MTd") + if (CMAKE_BUILD_TYPE STREQUAL "Debug") + set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreadedDebug") + set(CMAKE_MSVC_RUNTIME_LIBRARY_FLAG "MTd") + else () + set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded") + set(CMAKE_MSVC_RUNTIME_LIBRARY_FLAG "MT") + endif () + + set(OPENSSL_USE_STATIC_LIBS true) + set(OPENSSL_MSVC_STATIC_RT true) + + if ( ZEEK_STANDALONE ) + include(${CMAKE_SOURCE_DIR}/cmake/conan.cmake) + conan_cmake_autodetect(settings) + # Install packages from conanfile + conan_cmake_install(PATH_OR_REFERENCE ${CMAKE_SOURCE_DIR}/ci/windows/conanfile_windows.txt + BUILD missing + SETTINGS ${settings}) + endif() + + # Set LibPCAP to point to libpcap binaries. + find_package(libpcap) + set(PCAP_ROOT_DIR "${libpcap_LIB_DIRS}/../") + set(PCAP_INCLUDE_DIR ${libpcap_INCLUDES}) + set(PCAP_LIBRARY ${libpcap_LIBS}) + set(LIBPCAP_PCAP_COMPILE_NOPCAP_HAS_ERROR_PARAMETER false) + + # Set ZLib to point at the right variable. + find_package(ZLIB) + set(ZLIB_LIBRARY ${ZLIB_LIBRARIES}) + + # Set CAres + find_package(c-ares) + set(HAVE_CARES true) # Disable FindCAres cmake file + include_directories(BEFORE ${c-ares_INCLUDE_DIRS}) + set(zeekdeps ${zeekdeps} ${c-ares_LIBRARIES}) + add_definitions(-DCARES_STATICLIB) + + add_subdirectory(auxil/libunistd) + set(UNISTD_INCLUDES ${CMAKE_SOURCE_DIR}/auxil/libunistd/unistd ${CMAKE_SOURCE_DIR}/auxil/libunistd/regex) + include_directories(BEFORE ${UNISTD_INCLUDES}) + # Required for `check_include_files` to operate correctly + list(APPEND CMAKE_REQUIRED_INCLUDES ${UNISTD_INCLUDES}) + list(APPEND zeekdeps libunistd libregex) + + # Set CMAKE flags for supported windows build. + set(DISABLE_PYTHON_BINDINGS true) + set(BROKER_DISABLE_TESTS true) + set(BROKER_DISABLE_DOC_EXAMPLES true) + add_definitions(-DDOCTEST_CONFIG_NO_MULTITHREADING) + + # Disable Spicy as it is not yet supported in Windows. + set(DISABLE_SPICY true) +else () + include(GNUInstallDirs) +endif () include(cmake/CommonCMakeConfig.cmake) include(cmake/FindClangTidy.cmake) @@ -63,6 +164,21 @@ if (ZEEK_PLUGIN_DIR) else () set(BRO_PLUGIN_INSTALL_PATH ${ZEEK_LIBDIR_PATH}/plugins CACHE STRING "Installation path for plugins" FORCE) +endif() + +set(bro_plugin_install_path "${BRO_PLUGIN_INSTALL_PATH}") +set(cmake_binary_dir "${CMAKE_BINARY_DIR}") +set(cmake_current_binary_dir "${CMAKE_CURRENT_BINARY_DIR}") +set(cmake_install_prefix "${CMAKE_INSTALL_PREFIX}") +set(cmake_source_dir "${CMAKE_SOURCE_DIR}") +set(zeek_script_install_path "${ZEEK_SCRIPT_INSTALL_PATH}") +if ( MSVC ) + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" bro_plugin_install_path "${bro_plugin_install_path}") + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" cmake_binary_dir "${cmake_binary_dir}") + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" cmake_current_binary_dir "${cmake_current_binary_dir}") + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" cmake_install_prefix "${cmake_install_prefix}") + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" cmake_source_dir "${cmake_source_dir}") + string(REGEX REPLACE "^([A-Za-z]):/(.*)" "/\\1/\\2" zeek_script_install_path "${zeek_script_install_path}") endif () if ( NOT ZEEK_ETC_INSTALL_DIR ) @@ -81,6 +197,10 @@ if ( NOT ZEEK_LOG_DIR ) set(ZEEK_LOG_DIR ${ZEEK_ROOT_DIR}/logs) endif () +if ( NOT MSVC ) + set(HAVE_SUPERVISOR true) +endif () + install(DIRECTORY DESTINATION ${ZEEK_ETC_INSTALL_DIR}) install(DIRECTORY DESTINATION ${ZEEK_STATE_DIR}) install(DIRECTORY DESTINATION ${ZEEK_SPOOL_DIR}) @@ -300,7 +420,9 @@ FindRequiredPackage(FLEX) FindRequiredPackage(BISON) FindRequiredPackage(PCAP) FindRequiredPackage(OpenSSL) -FindRequiredPackage(BIND) +if ( NOT MSVC ) + FindRequiredPackage(BIND) +endif () FindRequiredPackage(ZLIB) # Installation directory for the distribution's Python modules. An @@ -325,6 +447,9 @@ set(PY_MOD_INSTALL_DIR ${py_mod_install_dir} if (EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/auxil/binpac/CMakeLists.txt) set(ENABLE_STATIC_ONLY_SAVED ${ENABLE_STATIC_ONLY}) + if ( MSVC ) + set(BUILD_STATIC_BINPAC true) + endif() if ( BUILD_STATIC_BINPAC ) set(ENABLE_STATIC_ONLY true) @@ -381,6 +506,11 @@ if ( PYTHON_VERSION_STRING VERSION_LESS ${ZEEK_PYTHON_MIN} ) endif () add_subdirectory(auxil/paraglob) +if ( MSVC ) + cmake_policy(SET CMP0079 NEW) + target_link_libraries(paraglob shlwapi) + set(BROKER_DISABLE_TOOLS true) +endif () set(zeekdeps ${zeekdeps} paraglob) if ( Broker_ROOT ) @@ -397,6 +527,9 @@ else () endif () set(ENABLE_STATIC_ONLY_SAVED ${ENABLE_STATIC_ONLY}) + if ( MSVC ) + set(BUILD_STATIC_BROKER true) + endif() if ( BUILD_STATIC_BROKER ) set(ENABLE_STATIC_ONLY true) @@ -599,7 +732,12 @@ if ( ${CMAKE_SYSTEM_NAME} MATCHES Linux ) endif () endif () -set(DEFAULT_ZEEKPATH .:${ZEEK_SCRIPT_INSTALL_PATH}:${ZEEK_SCRIPT_INSTALL_PATH}/policy:${ZEEK_SCRIPT_INSTALL_PATH}/site:${ZEEK_SCRIPT_INSTALL_PATH}/builtin-plugins) +set(DEFAULT_ZEEKPATH_PATHS . ${ZEEK_SCRIPT_INSTALL_PATH} ${ZEEK_SCRIPT_INSTALL_PATH}/policy ${ZEEK_SCRIPT_INSTALL_PATH}/site ${ZEEK_SCRIPT_INSTALL_PATH}/builtin-plugins) +if ( MSVC ) + list(JOIN DEFAULT_ZEEKPATH_PATHS ";" DEFAULT_ZEEKPATH) +else () + list(JOIN DEFAULT_ZEEKPATH_PATHS ":" DEFAULT_ZEEKPATH) +endif () if ( NOT BINARY_PACKAGING_MODE ) set(ZEEK_DIST ${PROJECT_SOURCE_DIR}) @@ -653,11 +791,13 @@ install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/cmake DESTINATION share/zeek USE_SOURCE_PERMISSIONS PATTERN ".git" EXCLUDE) -# Install wrapper script for Bro-to-Zeek renaming. -include(InstallShellScript) -include(InstallSymlink) -InstallShellScript("bin" "zeek-wrapper.in" "zeek-wrapper") -InstallSymlink("${CMAKE_INSTALL_PREFIX}/bin/zeek-wrapper" "${CMAKE_INSTALL_PREFIX}/bin/bro-config") +if ( NOT MSVC ) + # Install wrapper script for Bro-to-Zeek renaming. + include(InstallShellScript) + include(InstallSymlink) + InstallShellScript("bin" "zeek-wrapper.in" "zeek-wrapper") + InstallSymlink("${CMAKE_INSTALL_PREFIX}/bin/zeek-wrapper" "${CMAKE_INSTALL_PREFIX}/bin/bro-config") +endif () ######################################################################## ## zkg configuration diff --git a/COPYING.3rdparty b/COPYING.3rdparty index e984d6eb40..a023dc9efc 100644 --- a/COPYING.3rdparty +++ b/COPYING.3rdparty @@ -754,3 +754,31 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +============================================================================== + +%%% auxil/libunistd + +============================================================================== + +The MIT License (MIT) + +Copyright (c) 2015 Robin Rowe + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/NEWS b/NEWS index d8ffd1bf9a..0360e1f136 100644 --- a/NEWS +++ b/NEWS @@ -23,6 +23,17 @@ Breaking Changes New Functionality ----------------- +- Experimental support added for building and running Zeek on Microsoft Windows + environments. This is considered experimental due to the fact that our + standard testing setup (btest) doesn't run properly on Windows. This will be + fixed in the future. In the meantime we have done some basic testing against + builds done with Visual Studio 2019. Information on how to build on Windows is + available in the Zeek documentation. Note also that Spicy is currently + unsupported and will be fixed in the future. + + The Zeek team wants to give a huge thank you to the team at Microsoft for all + of their effort in completing this port. + - New ``analyzer_confirmation_info`` and ``analyzer_violation_info`` events with accompanying record types ``AnalyzerConfirmationInfo`` and ``AnalyzerViolationInfo`` have been added. These supersede diff --git a/VERSION b/VERSION index 57ee858b28..b3c0a982bf 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -5.2.0-dev.234 +5.2.0-dev.307 diff --git a/auxil/libunistd b/auxil/libunistd new file mode 160000 index 0000000000..2c290dc3c7 --- /dev/null +++ b/auxil/libunistd @@ -0,0 +1 @@ +Subproject commit 2c290dc3c7c9c706b5c0abbe06158bfb8a2721fe diff --git a/auxil/spicy/hilti-cxx-include-dirs.in b/auxil/spicy/hilti-cxx-include-dirs.in index 06ae06a806..6c4a140be9 100755 --- a/auxil/spicy/hilti-cxx-include-dirs.in +++ b/auxil/spicy/hilti-cxx-include-dirs.in @@ -14,6 +14,7 @@ PATHS=$PATHS:@CMAKE_BINARY_DIR@ PATHS=$PATHS:@CMAKE_BINARY_DIR@/src PATHS=$PATHS:@CMAKE_BINARY_DIR@/src/include PATHS=$PATHS:@CMAKE_SOURCE_DIR@/src +PATHS=$PATHS:@CMAKE_SOURCE_DIR@/src/include PATHS=$PATHS:@CMAKE_SOURCE_DIR@/auxil/broker/include/ echo $PATHS diff --git a/ci/windows/Dockerfile b/ci/windows/Dockerfile new file mode 100644 index 0000000000..af632901db --- /dev/null +++ b/ci/windows/Dockerfile @@ -0,0 +1,30 @@ +# escape=` +FROM mcr.microsoft.com/dotnet/framework/sdk:4.8-windowsservercore-ltsc2019 + +SHELL [ "powershell" ] + +RUN Set-ExecutionPolicy Unrestricted -Force + +# Install Chocolatey +RUN [System.Net.ServicePointManager]::SecurityProtocol = [System.Net.ServicePointManager]::SecurityProtocol -bor 3072; ` + iex ((New-Object System.Net.WebClient).DownloadString('https://chocolatey.org/install.ps1')) + +# Install prerequisites +RUN choco install -y --no-progress visualstudio2019buildtools --version=16.11.11.0 +RUN choco install -y --no-progress visualstudio2019-workload-vctools --version=1.0.0 --package-parameters '--add Microsoft.VisualStudio.Component.VC.ATLMFC' +RUN choco install -y --no-progress conan +RUN choco install -y --no-progress sed +RUN choco install -y --no-progress winflexbison3 +RUN choco install -y --no-progress msysgit +RUN choco install -y --no-progress python +RUN choco install -y --no-progress openssl + +# Set working environment. +SHELL [ "cmd", "/c" ] +RUN setx /M PATH "%PATH%;C:\\Program Files\\Git\\bin" +RUN setx /M CONAN_SKIP_BROKEN_SYMLINKS_CHECK 1 +RUN mkdir C:\build +WORKDIR C:\build + +# This entry point starts the developer command prompt and launches the PowerShell shell. +ENTRYPOINT ["C:\\Program Files (x86)\\Microsoft Visual Studio\\2019\\BuildTools\\Common7\\Tools\\VsDevCmd.bat", "-arch=x64", "&&", "powershell.exe", "-NoLogo", "-ExecutionPolicy", "Unrestricted"] \ No newline at end of file diff --git a/ci/windows/build.cmd b/ci/windows/build.cmd new file mode 100644 index 0000000000..b64396a417 --- /dev/null +++ b/ci/windows/build.cmd @@ -0,0 +1,11 @@ +:: Import the visual studio compiler environment into the one running in the +:: cmd current shell. This path is hard coded to the one on the CI image, but +:: can be adjusted if running builds locally. Unfortunately, the initial path +:: isn't in the environment so we have to hardcode the whole path. +call "c:\Program Files (x86)\Microsoft Visual Studio\2019\BuildTools\VC\Auxiliary\Build\vcvarsall.bat" x86_amd64 + +mkdir build +cd build + +cmake.exe .. -DCMAKE_BUILD_TYPE=release -DENABLE_ZEEK_UNIT_TESTS=yes -G Ninja +cmake.exe --build . diff --git a/ci/windows/conanfile_windows.txt b/ci/windows/conanfile_windows.txt new file mode 100644 index 0000000000..cb4bc35ada --- /dev/null +++ b/ci/windows/conanfile_windows.txt @@ -0,0 +1,8 @@ +[requires] +zlib/1.2.11 +libpcap/1.10.1 +c-ares/1.18.1 + +[generators] +cmake_find_package +cmake diff --git a/ci/windows/prepare.cmd b/ci/windows/prepare.cmd new file mode 100644 index 0000000000..162381367e --- /dev/null +++ b/ci/windows/prepare.cmd @@ -0,0 +1,7 @@ +@echo on + +echo %ZEEK_CI_CPUS% +wmic cpu get NumberOfCores, NumberOfLogicalProcessors/Format:List +systeminfo +dir C: +choco list --localonly diff --git a/ci/windows/test.cmd b/ci/windows/test.cmd new file mode 100644 index 0000000000..aae40887d9 --- /dev/null +++ b/ci/windows/test.cmd @@ -0,0 +1,7 @@ +:: See build.cmd for documentation on this call. +call "c:\Program Files (x86)\Microsoft Visual Studio\2019\BuildTools\VC\Auxiliary\Build\vcvarsall.bat" x86_amd64 + +:: We currently don't have any tests to run on Windows, so this is just commented out. +:: We'll expand on this later. +:: cd build +:: ctest -C release || exit \b 1 diff --git a/scripts/base/init-bare.zeek b/scripts/base/init-bare.zeek index 519db3922d..767c33cb1a 100644 --- a/scripts/base/init-bare.zeek +++ b/scripts/base/init-bare.zeek @@ -792,6 +792,17 @@ type ReporterStats: record { weirds_by_type: table[string] of count; }; +## Statistics about how many times each event name is queued. +## +## .. zeek:see:: get_event_handler_call_counts +type EventNameCounter: record { + ## Name of the zeek event. + name: string &log; + ## Times it was queued, as captured by event hook. + times_queued: count &log; +} &log; +type EventNameStats: vector of EventNameCounter; + ## Table type used to map variable names to their memory allocation. ## ## .. todo:: We need this type definition only for declaring builtin functions diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 8c6ad63ba5..91c7e6a7f6 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,9 +1,18 @@ include_directories(BEFORE ${CMAKE_CURRENT_SOURCE_DIR} + ${CMAKE_CURRENT_SOURCE_DIR}/include ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/include ) +# Force creation of includes symlink. This can't just be in the src directory +# because MSVC will end up with an include loop. +execute_process(COMMAND "${CMAKE_COMMAND}" -E make_directory + "${CMAKE_CURRENT_SOURCE_DIR}/include") +execute_process(COMMAND "${CMAKE_COMMAND}" -E create_symlink + ".." + "${CMAKE_CURRENT_SOURCE_DIR}/include/zeek") + # Allows header file inclusion via zeek/ within the build tree execute_process(COMMAND "${CMAKE_COMMAND}" -E make_directory "${CMAKE_CURRENT_BINARY_DIR}/include") @@ -31,9 +40,9 @@ configure_file(util-config.h.in ${CMAKE_CURRENT_BINARY_DIR}/util-config.h) # - deletes instances of 'extern char.*getenv' in inFile # - writes results to outFile and adds it to list TRANSFORMED_BISON_OUTPUTS macro(REPLACE_YY_PREFIX_TARGET inFile outFile yylexPrefix yyPrefix) - set(args "'/extern char.*getenv/d") + set(args "\"/extern char.*getenv/d") set(args "${args}\;s/yylex/${yylexPrefix}lex/") - set(args "${args}\;s/yy/${yyPrefix}/g'" < ${inFile} > ${outFile}) + set(args "${args}\;s/yy/${yyPrefix}/g\"" < ${inFile} > ${outFile}) add_custom_command(OUTPUT ${outFile} COMMAND ${SED_EXE} ARGS ${args} @@ -48,6 +57,12 @@ endmacro(REPLACE_YY_PREFIX_TARGET) set(BISON_FLAGS "--debug") +if ( MSVC ) + set(SIGN_COMPARE_FLAG "/wd4018") +else() + set(SIGN_COMPARE_FLAG "-Wno-sign-compare") +endif() + # BIF parser/scanner bison_target(BIFParser builtin-func.y ${CMAKE_CURRENT_BINARY_DIR}/bif_parse.cc @@ -56,7 +71,7 @@ bison_target(BIFParser builtin-func.y COMPILE_FLAGS "${BISON_FLAGS}") flex_target(BIFScanner builtin-func.l ${CMAKE_CURRENT_BINARY_DIR}/bif_lex.cc) add_flex_bison_dependency(BIFScanner BIFParser) -set_property(SOURCE bif_lex.cc APPEND_STRING PROPERTY COMPILE_FLAGS "-Wno-sign-compare") +set_property(SOURCE bif_lex.cc APPEND_STRING PROPERTY COMPILE_FLAGS "${SIGN_COMPARE_FLAG}") # Rule parser/scanner bison_target(RuleParser rule-parse.y @@ -72,7 +87,7 @@ replace_yy_prefix_target(${CMAKE_CURRENT_BINARY_DIR}/rup.h rules_ rules_) flex_target(RuleScanner rule-scan.l ${CMAKE_CURRENT_BINARY_DIR}/rule-scan.cc COMPILE_FLAGS "-Prules_") -set_property(SOURCE rule-scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "-Wno-sign-compare") +set_property(SOURCE rule-scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "${SIGN_COMPARE_FLAG}") # RE parser/scanner bison_target(REParser re-parse.y @@ -86,7 +101,7 @@ replace_yy_prefix_target(${CMAKE_CURRENT_BINARY_DIR}/rep.cc flex_target(REScanner re-scan.l ${CMAKE_CURRENT_BINARY_DIR}/re-scan.cc COMPILE_FLAGS "-Pre_") add_flex_bison_dependency(REScanner REParser) -set_property(SOURCE re-scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "-Wno-sign-compare") +set_property(SOURCE re-scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "${SIGN_COMPARE_FLAG}") # Parser/Scanner bison_target(Parser parse.y @@ -99,13 +114,15 @@ replace_yy_prefix_target(${CMAKE_CURRENT_BINARY_DIR}/p.cc zeek yy) flex_target(Scanner scan.l ${CMAKE_CURRENT_BINARY_DIR}/scan.cc COMPILE_FLAGS "-Pzeek") -set_property(SOURCE scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "-Wno-sign-compare") +set_property(SOURCE scan.cc APPEND_STRING PROPERTY COMPILE_FLAGS "${SIGN_COMPARE_FLAG}") ######################################################################## ## bifcl-dependent targets include(BifCl) +set(SUPERVISOR_SRCS supervisor/Supervisor.cc Pipe.cc) + set(BIF_SRCS zeek.bif stats.bif @@ -139,9 +156,9 @@ endforeach () include(BinPAC) set(BINPAC_AUXSRC - ${PROJECT_SOURCE_DIR}/src/binpac.pac - ${PROJECT_SOURCE_DIR}/src/zeek.pac - ${PROJECT_SOURCE_DIR}/src/binpac_zeek.h + ${CMAKE_CURRENT_SOURCE_DIR}/binpac.pac + ${CMAKE_CURRENT_SOURCE_DIR}/zeek.pac + ${CMAKE_CURRENT_SOURCE_DIR}/binpac_zeek.h ) binpac_target(binpac-lib.pac) @@ -163,6 +180,8 @@ gen_zam_target(${GEN_ZAM_SRC}) ## Including subdirectories. ######################################################################## +option(USE_SQLITE "Should Zeek use SQLite?" ON) + set(bro_SUBDIR_LIBS CACHE INTERNAL "subdir libraries" FORCE) set(bro_SUBDIR_DEPS CACHE INTERNAL "subdir dependencies" FORCE) set(bro_PLUGIN_LIBS CACHE INTERNAL "plugin libraries" FORCE) @@ -258,6 +277,11 @@ set(_gen_zeek_script_cpp ${CMAKE_CURRENT_BINARY_DIR}/../CPP-gen.cc) add_custom_command(OUTPUT ${_gen_zeek_script_cpp} COMMAND ${CMAKE_COMMAND} -E touch ${_gen_zeek_script_cpp}) +if (!MSVC) + set_source_files_properties(legacy-netvar-init.cc PROPERTIES COMPILE_FLAGS + -Wno-deprecated-declarations) +endif() + set(MAIN_SRCS digest.cc net_util.cc @@ -311,7 +335,6 @@ set(MAIN_SRCS Options.cc Overflow.cc PacketFilter.cc - Pipe.cc PolicyFile.cc PrefixTable.cc PriorityQueue.cc @@ -346,7 +369,7 @@ set(MAIN_SRCS ZeekString.cc ZVal.cc - supervisor/Supervisor.cc + ${SUPERVISOR_SRCS} threading/BasicThread.cc threading/Formatter.cc @@ -422,7 +445,7 @@ set(THIRD_PARTY_SRCS 3rdparty/modp_numtoa.c 3rdparty/patricia.c 3rdparty/setsignal.c - 3rdparty/sqlite3.c + $<$:3rdparty/sqlite3.c> 3rdparty/strsep.c ) @@ -465,10 +488,19 @@ elseif (${COMPILER_ARCHITECTURE} STREQUAL "power") ../auxil/highwayhash/highwayhash/hh_vsx.cc ) elseif(${COMPILER_ARCHITECTURE} STREQUAL "x86_64") + if (MSVC) + set(_avx_flag /arch:AVX2) + # Using an undocumentd compiler flag: https://stackoverflow.com/questions/64053597/how-do-i-enable-sse4-1-and-sse3-but-not-avx-in-msvc/69328426#69328426 + set(_sse_flag /d2archSSE42) + else() + set(_avx_flag -mavx2) + set(_sse_flag -msse4.1) + endif() + set_source_files_properties(../auxil/highwayhash/highwayhash/hh_avx2.cc PROPERTIES COMPILE_FLAGS - -mavx2) + ${_avx_flag}) set_source_files_properties(../auxil/highwayhash/highwayhash/hh_sse41.cc PROPERTIES COMPILE_FLAGS - -msse4.1) + ${_sse_flag}) list(APPEND HH_SRCS ../auxil/highwayhash/highwayhash/hh_avx2.cc @@ -504,23 +536,58 @@ collect_headers(zeek_HEADERS ${zeek_SRCS}) add_library(zeek_objs OBJECT ${zeek_SRCS}) -add_executable(zeek main.cc - $ - ${zeek_HEADERS} - ${bro_SUBDIR_LIBS} - ${bro_PLUGIN_LIBS} -) -target_link_libraries(zeek ${bro_PLUGIN_LINK_LIBS} ${zeekdeps} ${CMAKE_THREAD_LIBS_INIT} ${CMAKE_DL_LIBS}) -# Export symbols from zeek executable for use by plugins -set_target_properties(zeek PROPERTIES ENABLE_EXPORTS TRUE) +if (ZEEK_STANDALONE) + add_executable(zeek main.cc + $ + ${zeek_HEADERS} + ${bro_SUBDIR_LIBS} + ${bro_PLUGIN_LIBS} + ) + target_link_libraries(zeek ${bro_PLUGIN_LINK_LIBS} ${zeekdeps} ${CMAKE_THREAD_LIBS_INIT} ${CMAKE_DL_LIBS}) -install(TARGETS zeek DESTINATION bin) + # Export symbols from zeek executable for use by plugins + set_target_properties(zeek PROPERTIES ENABLE_EXPORTS TRUE) -set(BRO_EXE zeek - CACHE STRING "Zeek executable binary" FORCE) + if ( MSVC ) + set(WINDOWS_EXPORT_ALL_SYMBOLS ON) + endif () -set(BRO_EXE_PATH ${CMAKE_CURRENT_BINARY_DIR}/zeek - CACHE STRING "Path to Zeek executable binary" FORCE) + install(TARGETS zeek RUNTIME DESTINATION bin) + + set(BRO_EXE zeek + CACHE STRING "Zeek executable binary" FORCE) + + set(BRO_EXE_PATH ${CMAKE_CURRENT_BINARY_DIR}/zeek + CACHE STRING "Path to Zeek executable binary" FORCE) +endif() + +if (NOT ZEEK_STANDALONE OR CONAN_EXPORTED) + add_library(libzeek STATIC $ + ${zeek_HEADERS} + ${bro_SUBDIR_LIBS} + ${bro_PLUGIN_LIBS}) + + target_link_libraries(libzeek PUBLIC ${zeekdeps} + ${CMAKE_THREAD_LIBS_INIT} + ${CMAKE_DL_LIBS} + ${bro_SUBDIR_LIBS} + ${bro_PLUGIN_LIBS}) + + target_include_directories(libzeek PUBLIC + ${CMAKE_SOURCE_DIR}/zeek/src + ${CMAKE_SOURCE_DIR}/zeek/src/include + ${CMAKE_BINARY_DIR} + ${CMAKE_BINARY_DIR}/zeek/src + ${CMAKE_BINARY_DIR}/zeek/src/include) + + install(TARGETS libzeek LIBRARY DESTINATION lib) +endif() + +if ( NOT WIN32 ) + # Install wrapper script for Bro-to-Zeek renaming. + include(InstallSymlink) + InstallSymlink("${CMAKE_INSTALL_PREFIX}/bin/zeek-wrapper" "${CMAKE_INSTALL_PREFIX}/bin/bro") +endif () # Target to create all the autogenerated files. add_custom_target(generate_outputs_stage1) @@ -567,7 +634,15 @@ install(CODE " # Make sure to escape a bunch of special characters in the path before trying to use it as a # regular expression below. -string(REGEX REPLACE "([][+.*()^])" "\\\\\\1" escaped_path "${CMAKE_CURRENT_SOURCE_DIR}/zeek") +string(REGEX REPLACE "([][+.*()^])" "\\\\\\1" escaped_include_path "${CMAKE_CURRENT_SOURCE_DIR}/include/*") + +if (WIN32) + install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/windows/usr.include/ + DESTINATION include/ + FILES_MATCHING + PATTERN "*.h" + ) +endif() install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/ DESTINATION include/zeek @@ -576,7 +651,7 @@ install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/ PATTERN "*.pac" PATTERN "3rdparty/*" EXCLUDE # The "zeek -> ." symlink isn't needed in the install-tree - REGEX "^${escaped_path}$" EXCLUDE + REGEX "${escaped_include_path}$" EXCLUDE # FILES_MATCHING creates empty directories: # https://gitlab.kitware.com/cmake/cmake/-/issues/17122 @@ -592,6 +667,8 @@ install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/ PATTERN "*.bif.netvar_h" PATTERN "*.bif.h" PATTERN "CMakeFiles" EXCLUDE + # The "include/zeek -> .." symlink isn't needed in the install-tree + REGEX "${escaped_include_path}$" EXCLUDE ) install(FILES @@ -602,7 +679,7 @@ install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/modp_numtoa.h ${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/patricia.h ${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/setsignal.h - ${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/sqlite3.h + $<$:${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/sqlite3.h> ${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/doctest.h DESTINATION include/zeek/3rdparty ) diff --git a/src/DNS_Mapping.cc b/src/DNS_Mapping.cc index b83983aaaa..ce9da8bb4b 100644 --- a/src/DNS_Mapping.cc +++ b/src/DNS_Mapping.cc @@ -296,6 +296,9 @@ TEST_CASE("dns_mapping init addr") TEST_CASE("dns_mapping save reload") { + // TODO: this test uses fmemopen and mkdtemp, both of which aren't available on + // Windows. We'll have to figure out another way to do this test there. +#ifndef _MSC_VER IPAddr addr("1.2.3.4"); in4_addr in4; addr.CopyIPv4(&in4); @@ -356,6 +359,7 @@ TEST_CASE("dns_mapping save reload") CHECK(svh->ToStdString() == "testing.home"); delete[] he.h_name; +#endif } TEST_CASE("dns_mapping multiple addresses") diff --git a/src/DNS_Mgr.cc b/src/DNS_Mgr.cc index addab9ed76..70fd20219e 100644 --- a/src/DNS_Mgr.cc +++ b/src/DNS_Mgr.cc @@ -540,10 +540,10 @@ static void query_cb(void* arg, int status, int timeouts, unsigned char* buf, in * some source of data (either a host file or a DNS server). This indicates that we're * able to do lookups against c-ares now and should activate the IOSource. */ -static void sock_cb(void* data, int s, int read, int write) +static void sock_cb(void* data, ares_socket_t s, int read, int write) { auto mgr = reinterpret_cast(data); - mgr->RegisterSocket(s, read == 1, write == 1); + mgr->RegisterSocket((int)s, read == 1, write == 1); } DNS_Mgr::DNS_Mgr(DNS_MgrMode arg_mode) : IOSource(true), mode(arg_mode) @@ -1613,6 +1613,8 @@ void TestDNS_Mgr::Process() TEST_CASE("dns_mgr priming" * doctest::skip(true)) { + // TODO: This test uses mkdtemp, which isn't available on Windows. +#ifndef _MSC_VER char prefix[] = "/tmp/zeek-unit-test-XXXXXX"; auto tmpdir = mkdtemp(prefix); @@ -1658,6 +1660,7 @@ TEST_CASE("dns_mgr priming" * doctest::skip(true)) // Clean up cache file and the temp directory unlink(mgr2.CacheFile().c_str()); rmdir(tmpdir); +#endif } TEST_CASE("dns_mgr alternate server" * doctest::skip(true)) diff --git a/src/DebugCmdInfoConstants.in b/src/DebugCmdInfoConstants.in index d00b6dbde6..775149301c 100644 --- a/src/DebugCmdInfoConstants.in +++ b/src/DebugCmdInfoConstants.in @@ -1,6 +1,6 @@ // This invalid entry should always be first cmd: dcInvalid -names: +names: _ resume: false help: This function should not be called repeatable: false diff --git a/src/DebugLogger.h b/src/DebugLogger.h index 158e4dc950..e8be0a71e2 100644 --- a/src/DebugLogger.h +++ b/src/DebugLogger.h @@ -13,17 +13,17 @@ #include "zeek/util.h" -#define DBG_LOG(stream, args...) \ +#define DBG_LOG(stream, ...) \ if ( ::zeek::detail::debug_logger.IsEnabled(stream) ) \ - ::zeek::detail::debug_logger.Log(stream, args) -#define DBG_LOG_VERBOSE(stream, args...) \ + ::zeek::detail::debug_logger.Log(stream, __VA_ARGS__) +#define DBG_LOG_VERBOSE(stream, ...) \ if ( ::zeek::detail::debug_logger.IsVerbose() && \ ::zeek::detail::debug_logger.IsEnabled(stream) ) \ - ::zeek::detail::debug_logger.Log(stream, args) + ::zeek::detail::debug_logger.Log(stream, __VA_ARGS__) #define DBG_PUSH(stream) ::zeek::detail::debug_logger.PushIndent(stream) #define DBG_POP(stream) ::zeek::detail::debug_logger.PopIndent(stream) -#define PLUGIN_DBG_LOG(plugin, args...) ::zeek::detail::debug_logger.Log(plugin, args) +#define PLUGIN_DBG_LOG(plugin, ...) ::zeek::detail::debug_logger.Log(plugin, __VA_ARGS__) namespace zeek { @@ -123,9 +123,9 @@ extern DebugLogger debug_logger; } // namespace zeek #else -#define DBG_LOG(args...) -#define DBG_LOG_VERBOSE(args...) +#define DBG_LOG(...) +#define DBG_LOG_VERBOSE(...) #define DBG_PUSH(stream) #define DBG_POP(stream) -#define PLUGIN_DBG_LOG(plugin, args...) +#define PLUGIN_DBG_LOG(plugin, ...) #endif diff --git a/src/EventHandler.cc b/src/EventHandler.cc index 09ba72c27d..62a616a619 100644 --- a/src/EventHandler.cc +++ b/src/EventHandler.cc @@ -52,6 +52,8 @@ void EventHandler::SetFunc(FuncPtr f) void EventHandler::Call(Args* vl, bool no_remote) { + call_count++; + if ( new_event ) NewEvent(vl); diff --git a/src/EventHandler.h b/src/EventHandler.h index 64f134786e..c8947f1082 100644 --- a/src/EventHandler.h +++ b/src/EventHandler.h @@ -38,19 +38,21 @@ public: explicit operator bool() const; void SetUsed() { used = true; } - bool Used() { return used; } + bool Used() const { return used; } // Handlers marked as error handlers will not be called recursively to // avoid infinite loops if they trigger a similar error themselves. void SetErrorHandler() { error_handler = true; } - bool ErrorHandler() { return error_handler; } + bool ErrorHandler() const { return error_handler; } void SetEnable(bool arg_enable) { enabled = arg_enable; } // Flags the event as interesting even if there is no body defined. In // particular, this will then still pass the event on to plugins. void SetGenerateAlways() { generate_always = true; } - bool GenerateAlways() { return generate_always; } + bool GenerateAlways() const { return generate_always; } + + uint64_t CallCount() const { return call_count; } private: void NewEvent(zeek::Args* vl); // Raise new_event() meta event. @@ -62,6 +64,7 @@ private: bool enabled; bool error_handler; // this handler reports error messages. bool generate_always; + uint64_t call_count = 0; std::unordered_set auto_publish; }; diff --git a/src/File.cc b/src/File.cc index b2a167740f..44c78ccd91 100644 --- a/src/File.cc +++ b/src/File.cc @@ -202,8 +202,16 @@ void File::SetBuf(bool arg_buffered) if ( ! f ) return; +#ifndef _MSC_VER if ( setvbuf(f, NULL, arg_buffered ? _IOFBF : _IOLBF, 0) != 0 ) reporter->Error("setvbuf failed"); +#else + // TODO: this turns off buffering altogether because Windows wants us to pass a valid + // buffer and length if we're going to pass one of the other modes. We need to + // investigate the performance ramifications of this. + if ( setvbuf(f, NULL, _IONBF, 0) != 0 ) + reporter->Error("setvbuf failed"); +#endif buffered = arg_buffered; } diff --git a/src/Flare.cc b/src/Flare.cc index e2f42fa34e..f2dbc60155 100644 --- a/src/Flare.cc +++ b/src/Flare.cc @@ -8,10 +8,61 @@ #include "zeek/Reporter.h" +#ifdef _MSC_VER + +#include + +#define fatalError(...) \ + do \ + { \ + if ( reporter ) \ + reporter->FatalError(__VA_ARGS__); \ + else \ + { \ + fprintf(stderr, __VA_ARGS__); \ + fprintf(stderr, "\n"); \ + _exit(1); \ + } \ + } while ( 0 ) + +#endif + namespace zeek::detail { -Flare::Flare() : pipe(FD_CLOEXEC, FD_CLOEXEC, O_NONBLOCK, O_NONBLOCK) { } +Flare::Flare() +#ifndef _MSC_VER + : pipe(FD_CLOEXEC, FD_CLOEXEC, O_NONBLOCK, O_NONBLOCK) + { + } +#else + { + WSADATA wsaData; + if ( WSAStartup(MAKEWORD(2, 2), &wsaData) != 0 ) + fatalError("WSAStartup failure: %d", WSAGetLastError()); + + recvfd = WSASocket(AF_INET, SOCK_DGRAM, IPPROTO_UDP, nullptr, 0, + WSA_FLAG_OVERLAPPED | WSA_FLAG_NO_HANDLE_INHERIT); + if ( recvfd == (int)INVALID_SOCKET ) + fatalError("WSASocket failure: %d", WSAGetLastError()); + sendfd = WSASocket(AF_INET, SOCK_DGRAM, IPPROTO_UDP, nullptr, 0, + WSA_FLAG_OVERLAPPED | WSA_FLAG_NO_HANDLE_INHERIT); + if ( sendfd == (int)INVALID_SOCKET ) + fatalError("WSASocket failure: %d", WSAGetLastError()); + + sockaddr_in sa; + memset(&sa, 0, sizeof(sa)); + sa.sin_family = AF_INET; + sa.sin_addr.s_addr = inet_addr("127.0.0.1"); + if ( bind(recvfd, (sockaddr*)&sa, sizeof(sa)) == SOCKET_ERROR ) + fatalError("bind failure: %d", WSAGetLastError()); + int salen = sizeof(sa); + if ( getsockname(recvfd, (sockaddr*)&sa, &salen) == SOCKET_ERROR ) + fatalError("getsockname failure: %d", WSAGetLastError()); + if ( connect(sendfd, (sockaddr*)&sa, sizeof(sa)) == SOCKET_ERROR ) + fatalError("connect failure: %d", WSAGetLastError()); + } +#endif [[noreturn]] static void bad_pipe_op(const char* which, bool signal_safe) { @@ -36,14 +87,22 @@ void Flare::Fire(bool signal_safe) for ( ;; ) { +#ifndef _MSC_VER int n = write(pipe.WriteFD(), &tmp, 1); +#else + int n = send(sendfd, &tmp, 1, 0); +#endif if ( n > 0 ) // Success -- wrote a byte to pipe. break; if ( n < 0 ) { +#ifdef _MSC_VER + errno = WSAGetLastError(); + bad_pipe_op("send", signal_safe); +#endif if ( errno == EAGAIN ) // Success: pipe is full and just need at least one byte in it. break; @@ -66,15 +125,23 @@ int Flare::Extinguish(bool signal_safe) for ( ;; ) { +#ifndef _MSC_VER int n = read(pipe.ReadFD(), &tmp, sizeof(tmp)); - +#else + int n = recv(recvfd, tmp, sizeof(tmp), 0); +#endif if ( n >= 0 ) { rval += n; // Pipe may not be empty yet: try again. continue; } - +#ifdef _MSC_VER + if ( WSAGetLastError() == WSAEWOULDBLOCK ) + break; + errno = WSAGetLastError(); + bad_pipe_op("recv", signal_safe); +#endif if ( errno == EAGAIN ) // Success: pipe is now empty. break; diff --git a/src/Flare.h b/src/Flare.h index e1bfe3b6af..affae42dfd 100644 --- a/src/Flare.h +++ b/src/Flare.h @@ -2,7 +2,9 @@ #pragma once -#include "zeek/Pipe.h" +#ifndef _MSC_VER +#include "Pipe.h" +#endif namespace zeek::detail { @@ -22,7 +24,16 @@ public: * @return a file descriptor that will become ready if the flare has been * Fire()'d and not yet Extinguished()'d. */ - int FD() const { return pipe.ReadFD(); } + int FD() const +#ifndef _MSC_VER + { + return pipe.ReadFD(); + } +#else + { + return recvfd; + } +#endif /** * Put the object in the "ready" state. @@ -41,7 +52,11 @@ public: int Extinguish(bool signal_safe = false); private: +#ifndef _MSC_VER Pipe pipe; +#else + int sendfd, recvfd; +#endif }; } // namespace zeek::detail diff --git a/src/Hash.cc b/src/Hash.cc index c9c9f16af2..344a9f5c22 100644 --- a/src/Hash.cc +++ b/src/Hash.cc @@ -345,7 +345,7 @@ void HashKey::Reserve(const char* tag, size_t addl_size, size_t alignment) void HashKey::Allocate() { - if ( key != nullptr and key != reinterpret_cast(&key_u) ) + if ( key != nullptr && key != reinterpret_cast(&key_u) ) { reporter->InternalWarning("usage error in HashKey::Allocate(): already allocated"); return; diff --git a/src/Hash.h b/src/Hash.h index cc5f5967be..985c71446a 100644 --- a/src/Hash.h +++ b/src/Hash.h @@ -19,6 +19,7 @@ #pragma once +#include #include #include "zeek/util.h" // for zeek_int_t diff --git a/src/IP.cc b/src/IP.cc index c85cdc1e96..4de4506387 100644 --- a/src/IP.cc +++ b/src/IP.cc @@ -66,8 +66,8 @@ RecordValPtr IPv6_Hdr::ToVal(VectorValPtr chain) const static auto ip6_hdr_type = id::find_type("ip6_hdr"); rv = make_intrusive(ip6_hdr_type); const struct ip6_hdr* ip6 = (const struct ip6_hdr*)data; - rv->Assign(0, (ntohl(ip6->ip6_flow) & 0x0ff00000) >> 20); - rv->Assign(1, ntohl(ip6->ip6_flow) & 0x000fffff); + rv->Assign(0, static_cast(ntohl(ip6->ip6_flow) & 0x0ff00000) >> 20); + rv->Assign(1, static_cast(ntohl(ip6->ip6_flow) & 0x000fffff)); rv->Assign(2, ntohs(ip6->ip6_plen)); rv->Assign(3, ip6->ip6_nxt); rv->Assign(4, ip6->ip6_hlim); @@ -127,7 +127,7 @@ RecordValPtr IPv6_Hdr::ToVal(VectorValPtr chain) const rv->Assign(2, (ntohs(frag->ip6f_offlg) & 0xfff8) >> 3); rv->Assign(3, (ntohs(frag->ip6f_offlg) & 0x0006) >> 1); rv->Assign(4, static_cast(ntohs(frag->ip6f_offlg) & 0x0001)); - rv->Assign(5, ntohl(frag->ip6f_ident)); + rv->Assign(5, static_cast(ntohl(frag->ip6f_ident))); } break; @@ -138,13 +138,13 @@ RecordValPtr IPv6_Hdr::ToVal(VectorValPtr chain) const rv->Assign(0, ((ip6_ext*)data)->ip6e_nxt); rv->Assign(1, ((ip6_ext*)data)->ip6e_len); rv->Assign(2, ntohs(((uint16_t*)data)[1])); - rv->Assign(3, ntohl(((uint32_t*)data)[1])); + rv->Assign(3, static_cast(ntohl(((uint32_t*)data)[1]))); if ( Length() >= 12 ) { // Sequence Number and ICV fields can only be extracted if // Payload Len was non-zero for this header. - rv->Assign(4, ntohl(((uint32_t*)data)[2])); + rv->Assign(4, static_cast(ntohl(((uint32_t*)data)[2]))); uint16_t off = 3 * sizeof(uint32_t); rv->Assign(5, new String(data + off, Length() - off, true)); } @@ -156,8 +156,8 @@ RecordValPtr IPv6_Hdr::ToVal(VectorValPtr chain) const static auto ip6_esp_type = id::find_type("ip6_esp"); rv = make_intrusive(ip6_esp_type); const uint32_t* esp = (const uint32_t*)data; - rv->Assign(0, ntohl(esp[0])); - rv->Assign(1, ntohl(esp[1])); + rv->Assign(0, static_cast(ntohl(esp[0]))); + rv->Assign(1, static_cast(ntohl(esp[1]))); } break; @@ -401,8 +401,8 @@ RecordValPtr IP_Hdr::ToPktHdrVal(RecordValPtr pkt_hdr, int sindex) const tcp_hdr->Assign(0, val_mgr->Port(ntohs(tp->th_sport), TRANSPORT_TCP)); tcp_hdr->Assign(1, val_mgr->Port(ntohs(tp->th_dport), TRANSPORT_TCP)); - tcp_hdr->Assign(2, ntohl(tp->th_seq)); - tcp_hdr->Assign(3, ntohl(tp->th_ack)); + tcp_hdr->Assign(2, static_cast(ntohl(tp->th_seq))); + tcp_hdr->Assign(3, static_cast(ntohl(tp->th_ack))); tcp_hdr->Assign(4, tcp_hdr_len); tcp_hdr->Assign(5, data_len); tcp_hdr->Assign(6, tp->th_x2); diff --git a/src/IP.h b/src/IP.h index 0488290b00..76f17f7237 100644 --- a/src/IP.h +++ b/src/IP.h @@ -12,6 +12,8 @@ #ifdef HAVE_NETINET_IP6_H #include +#else +#include "net_util.h" // for struct ip6_hdr #endif #include diff --git a/src/IntrusivePtr.h b/src/IntrusivePtr.h index 93efcc0a71..7d9578d29f 100644 --- a/src/IntrusivePtr.h +++ b/src/IntrusivePtr.h @@ -6,6 +6,8 @@ #include #include +#include "Obj.h" + namespace zeek { @@ -25,6 +27,12 @@ struct NewRef { }; +/** + * This has to be forward declared and known here in order for us to be able + * cast this in the `Unref` function. + */ +class OpaqueVal; + /** * An intrusive, reference counting smart pointer implementation. Much like * @c std::shared_ptr, this smart pointer models shared ownership of an object @@ -111,7 +119,14 @@ public: ~IntrusivePtr() { if ( ptr_ ) - Unref(ptr_); + { + // Specializing `OpaqueVal` as MSVC compiler does not detect it + // inheriting from `zeek::Obj` so we have to do that manually. + if constexpr ( std::is_same_v ) + Unref(reinterpret_cast(ptr_)); + else + Unref(ptr_); + } } void swap(IntrusivePtr& other) noexcept { std::swap(ptr_, other.ptr_); } diff --git a/src/Obj.cc b/src/Obj.cc index fd1b9100aa..47bbf1462d 100644 --- a/src/Obj.cc +++ b/src/Obj.cc @@ -61,10 +61,14 @@ Obj::~Obj() { if ( notify_plugins ) { +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif PLUGIN_HOOK_VOID(HOOK_BRO_OBJ_DTOR, HookBroObjDtor(this)); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif PLUGIN_HOOK_VOID(HOOK_OBJ_DTOR, HookObjDtor(this)); } diff --git a/src/OpaqueVal.h b/src/OpaqueVal.h index 619c002bd8..0e33db0d88 100644 --- a/src/OpaqueVal.h +++ b/src/OpaqueVal.h @@ -2,6 +2,10 @@ #pragma once +#ifdef _MSC_VER +#include +#endif + #include #if ( OPENSSL_VERSION_NUMBER < 0x30000000L ) || defined(LIBRESSL_VERSION_NUMBER) #include diff --git a/src/Options.cc b/src/Options.cc index c978bd31d5..e341a020e7 100644 --- a/src/Options.cc +++ b/src/Options.cc @@ -4,17 +4,17 @@ #include "zeek/zeek-config.h" -#include - -#ifdef HAVE_GETOPT_H +#if defined(HAVE_GETOPT_H) && ! defined(_MSC_VER) #include #endif +#include #include #include #include #include +#include "zeek/3rdparty/bsd-getopt-long.h" #include "zeek/ScriptProfile.h" #include "zeek/logging/writers/ascii/Ascii.h" #include "zeek/script_opt/ScriptOpt.h" diff --git a/src/PolicyFile.cc b/src/PolicyFile.cc index 31e44dcdd9..db3cf77ff2 100644 --- a/src/PolicyFile.cc +++ b/src/PolicyFile.cc @@ -117,9 +117,10 @@ bool LoadPolicyFileText(const char* policy_filename, // ### This code is not necessarily Unicode safe! // (probably fine with UTF-8) pf->filedata = new char[size + 1]; - if ( fread(pf->filedata, size, 1, f) != 1 ) + size_t n = fread(pf->filedata, 1, size, f); + if ( ferror(f) ) reporter->InternalError("Failed to fread() file data"); - pf->filedata[size] = 0; + pf->filedata[n] = 0; fclose(f); } diff --git a/src/RunState.cc b/src/RunState.cc index 315ddcd24d..6a1d4c3387 100644 --- a/src/RunState.cc +++ b/src/RunState.cc @@ -40,10 +40,12 @@ extern "C" #include "zeek/plugin/Manager.h" #include "zeek/session/Manager.h" +#ifndef _MSC_VER extern "C" { extern int select(int, fd_set*, fd_set*, fd_set*, struct timeval*); } +#endif static double last_watchdog_proc_time = 0.0; // value of above during last watchdog extern int signal_val; diff --git a/src/ScriptProfile.cc b/src/ScriptProfile.cc index 862b4c5ebe..22f09dfb63 100644 --- a/src/ScriptProfile.cc +++ b/src/ScriptProfile.cc @@ -102,7 +102,7 @@ ScriptProfileMgr::~ScriptProfileMgr() auto& fp = fs.second; auto n = func->GetBodies().size(); if ( n > 1 ) - fprintf(f, "%s\t%lu-locations\t%s\t%d\t%.06f\t%0.6f\t%" PRIu64 "\t%lld\n", + fprintf(f, "%s\t%zu-locations\t%s\t%d\t%.06f\t%0.6f\t%" PRIu64 "\t%lld\n", fp.Name().c_str(), n, func->GetType()->FlavorString().c_str(), fp.NumCalls(), fp.CPUTime(), 0.0, fp.Memory(), 0LL); } diff --git a/src/ScriptValidation.cc b/src/ScriptValidation.cc index 73942246ea..1555346985 100644 --- a/src/ScriptValidation.cc +++ b/src/ScriptValidation.cc @@ -85,7 +85,7 @@ private: bool NextStmtIsValid() { return stmt_depths[STMT_FOR] > 0 || stmt_depths[STMT_WHILE] > 0; } - std::unordered_map stmt_depths; + std::unordered_map stmt_depths; int hook_depth = 0; }; diff --git a/src/SerializationFormat.cc b/src/SerializationFormat.cc index 42cff63cdd..f8c67a3c52 100644 --- a/src/SerializationFormat.cc +++ b/src/SerializationFormat.cc @@ -386,7 +386,7 @@ bool BinarySerializationFormat::Write(const IPAddr& addr, const char* tag) for ( int i = 0; i < n; ++i ) { - if ( ! Write(ntohl(raw[i]), "addr-part") ) + if ( ! Write(static_cast(ntohl(raw[i])), "addr-part") ) return false; } @@ -402,7 +402,7 @@ bool BinarySerializationFormat::Write(const struct in_addr& addr, const char* ta { const uint32_t* bytes = (uint32_t*)&addr.s_addr; - if ( ! Write(ntohl(bytes[0]), "addr4") ) + if ( ! Write(static_cast(ntohl(bytes[0])), "addr4") ) return false; return true; @@ -414,7 +414,7 @@ bool BinarySerializationFormat::Write(const struct in6_addr& addr, const char* t for ( int i = 0; i < 4; ++i ) { - if ( ! Write(ntohl(bytes[i]), "addr6-part") ) + if ( ! Write(static_cast(ntohl(bytes[i])), "addr6-part") ) return false; } diff --git a/src/Val.cc b/src/Val.cc index 4d212539f5..cf1c2b37b6 100644 --- a/src/Val.cc +++ b/src/Val.cc @@ -3962,18 +3962,9 @@ ValManager::ValManager() for ( auto i = 0u; i < PREALLOCATED_INTS; ++i ) ints[i] = Val::MakeInt(PREALLOCATED_INT_LOWEST + i); - - for ( auto i = 0u; i < ports.size(); ++i ) - { - auto& arr = ports[i]; - auto port_type = (TransportProto)i; - - for ( auto j = 0u; j < arr.size(); ++j ) - arr[j] = IntrusivePtr{AdoptRef{}, new PortVal(PortVal::Mask(j, port_type))}; - } } -const PortValPtr& ValManager::Port(uint32_t port_num, TransportProto port_type) const +const PortValPtr& ValManager::Port(uint32_t port_num, TransportProto port_type) { if ( port_num >= 65536 ) { @@ -3981,10 +3972,15 @@ const PortValPtr& ValManager::Port(uint32_t port_num, TransportProto port_type) port_num = 0; } - return ports[port_type][port_num]; + uint32_t port_masked = PortVal::Mask(port_num, port_type); + if ( ports.find(port_masked) == ports.end() ) + ports[port_masked] = IntrusivePtr{AdoptRef{}, + new PortVal(PortVal::Mask(port_num, port_type))}; + + return ports[port_masked]; } -const PortValPtr& ValManager::Port(uint32_t port_num) const +const PortValPtr& ValManager::Port(uint32_t port_num) { auto mask = port_num & PORT_SPACE_MASK; port_num &= ~PORT_SPACE_MASK; diff --git a/src/Val.h b/src/Val.h index 2bf0a48c90..5db5368b66 100644 --- a/src/Val.h +++ b/src/Val.h @@ -298,9 +298,15 @@ protected: class ValManager { public: +#ifdef _MSC_VER + static constexpr zeek_uint_t PREALLOCATED_COUNTS = 1; + static constexpr zeek_uint_t PREALLOCATED_INTS = 1; + static constexpr zeek_int_t PREALLOCATED_INT_LOWEST = 0; +#else static constexpr zeek_uint_t PREALLOCATED_COUNTS = 4096; static constexpr zeek_uint_t PREALLOCATED_INTS = 512; static constexpr zeek_int_t PREALLOCATED_INT_LOWEST = -255; +#endif static constexpr zeek_int_t PREALLOCATED_INT_HIGHEST = PREALLOCATED_INT_LOWEST + PREALLOCATED_INTS - 1; @@ -327,13 +333,13 @@ public: inline const StringValPtr& EmptyString() const { return empty_string; } // Port number given in host order. - const PortValPtr& Port(uint32_t port_num, TransportProto port_type) const; + const PortValPtr& Port(uint32_t port_num, TransportProto port_type); // Host-order port number already masked with port space protocol mask. - const PortValPtr& Port(uint32_t port_num) const; + const PortValPtr& Port(uint32_t port_num); private: - std::array, NUM_PORT_SPACES> ports; + std::unordered_map ports; std::array counts; std::array ints; StringValPtr empty_string; @@ -1124,15 +1130,18 @@ public: AddedField(field); } - void Assign(int field, int new_val) + // For int types, we provide both [u]int32_t and [u]int64_t versions for + // convenience, since sometimes the caller has one rather than the other. + void Assign(int field, int32_t new_val) + { + (*record_val)[field] = ZVal(zeek_int_t(new_val)); + AddedField(field); + } + void Assign(int field, int64_t new_val) { (*record_val)[field] = ZVal(zeek_int_t(new_val)); AddedField(field); } - - // For unsigned, we provide both uint32_t and uint64_t versions - // for convenience, since sometimes the caller has one rather - // than the other. void Assign(int field, uint32_t new_val) { (*record_val)[field] = ZVal(zeek_uint_t(new_val)); diff --git a/src/analyzer/Manager.h b/src/analyzer/Manager.h index e0b997d085..5a1c23235f 100644 --- a/src/analyzer/Manager.h +++ b/src/analyzer/Manager.h @@ -402,12 +402,12 @@ extern analyzer::Manager* analyzer_mgr; DBG_LOG(zeek::DBG_ANALYZER, "%s " txt, \ fmt_conn_id(conn->OrigAddr(), ntohs(conn->OrigPort()), conn->RespAddr(), \ ntohs(conn->RespPort()))); -#define DBG_ANALYZER_ARGS(conn, fmt, args...) \ +#define DBG_ANALYZER_ARGS(conn, fmt, ...) \ DBG_LOG(zeek::DBG_ANALYZER, "%s " fmt, \ fmt_conn_id(conn->OrigAddr(), ntohs(conn->OrigPort()), conn->RespAddr(), \ ntohs(conn->RespPort())), \ - ##args); + ##__VA_ARGS__); #else #define DBG_ANALYZER(conn, txt) -#define DBG_ANALYZER_ARGS(conn, fmt, args...) +#define DBG_ANALYZER_ARGS(conn, fmt, ...) #endif diff --git a/src/analyzer/protocol/dns/DNS.cc b/src/analyzer/protocol/dns/DNS.cc index 0a7355e76d..68f33f19be 100644 --- a/src/analyzer/protocol/dns/DNS.cc +++ b/src/analyzer/protocol/dns/DNS.cc @@ -823,8 +823,7 @@ bool DNS_Interpreter::ParseRR_EDNS(detail::DNS_MsgInfo* msg, const u_char*& data case TYPE_TCP_KA: { - EDNS_TCP_KEEPALIVE edns_tcp_keepalive{.keepalive_timeout_omitted = true, - .keepalive_timeout = 0}; + EDNS_TCP_KEEPALIVE edns_tcp_keepalive{true, 0}; if ( option_len == 0 || option_len == 2 ) { // 0 bytes is permitted by RFC 7828, showing that the timeout value is @@ -1736,11 +1735,8 @@ bool DNS_Interpreter::ParseRR_SVCB(detail::DNS_MsgInfo* msg, const u_char*& data name_end = target_name + 1; } - SVCB_DATA svcb_data = { - .svc_priority = svc_priority, - .target_name = make_intrusive( - new String(target_name, name_end - target_name, true)), - }; + SVCB_DATA svcb_data = {svc_priority, make_intrusive(new String( + target_name, name_end - target_name, true))}; // TODO: parse svcparams // we consume all the remaining raw data (svc params) but do nothing. diff --git a/src/file_analysis/analyzer/extract/functions.bif b/src/file_analysis/analyzer/extract/functions.bif index 96a1b07da1..25a021449d 100644 --- a/src/file_analysis/analyzer/extract/functions.bif +++ b/src/file_analysis/analyzer/extract/functions.bif @@ -3,7 +3,7 @@ module FileExtract; %%{ -#include "zeek/zeek/file_analysis/Manager.h" +#include "zeek/file_analysis/Manager.h" #include "zeek/file_analysis/file_analysis.bif.h" %%} diff --git a/src/file_analysis/analyzer/x509/X509Common.cc b/src/file_analysis/analyzer/x509/X509Common.cc index a4dd56a50a..339894a94e 100644 --- a/src/file_analysis/analyzer/x509/X509Common.cc +++ b/src/file_analysis/analyzer/x509/X509Common.cc @@ -279,7 +279,7 @@ void X509Common::ParseExtension(X509_EXTENSION* ex, const EventHandlerPtr& h, bo auto pX509Ext = make_intrusive(BifType::Record::X509::Extension); pX509Ext->Assign(0, name); - if ( short_name and strlen(short_name) > 0 ) + if ( short_name && strlen(short_name) > 0 ) pX509Ext->Assign(1, short_name); pX509Ext->Assign(2, oid); diff --git a/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac b/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac deleted file mode 120000 index 88305ed8fd..0000000000 --- a/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac +++ /dev/null @@ -1 +0,0 @@ -../../../analyzer/protocol/ssl/tls-handshake-signed_certificate_timestamp.pac \ No newline at end of file diff --git a/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac b/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac new file mode 100644 index 0000000000..5ebb1abe9a --- /dev/null +++ b/src/file_analysis/analyzer/x509/x509-signed_certificate_timestamp.pac @@ -0,0 +1 @@ +%include ../../../analyzer/protocol/ssl/tls-handshake-signed_certificate_timestamp.pac \ No newline at end of file diff --git a/src/fuzzers/FuzzBuffer.cc b/src/fuzzers/FuzzBuffer.cc index 5529e98531..5ea074f5c3 100644 --- a/src/fuzzers/FuzzBuffer.cc +++ b/src/fuzzers/FuzzBuffer.cc @@ -4,6 +4,10 @@ #include "zeek/fuzzers/FuzzBuffer.h" +#ifdef _MSC_VER +#include +#endif + #include namespace zeek::detail diff --git a/src/fuzzers/packet-fuzzer.cc b/src/fuzzers/packet-fuzzer.cc index af199a1544..49b183bda4 100644 --- a/src/fuzzers/packet-fuzzer.cc +++ b/src/fuzzers/packet-fuzzer.cc @@ -1,3 +1,7 @@ +#ifdef _MSC_VER +#include +#endif + extern "C" { #include diff --git a/src/include/.gitkeep b/src/include/.gitkeep new file mode 100644 index 0000000000..d3f5a12faa --- /dev/null +++ b/src/include/.gitkeep @@ -0,0 +1 @@ + diff --git a/src/input/readers/CMakeLists.txt b/src/input/readers/CMakeLists.txt index d653789847..032a286052 100644 --- a/src/input/readers/CMakeLists.txt +++ b/src/input/readers/CMakeLists.txt @@ -4,4 +4,6 @@ add_subdirectory(benchmark) add_subdirectory(binary) add_subdirectory(config) add_subdirectory(raw) -add_subdirectory(sqlite) +if (USE_SQLITE) + add_subdirectory(sqlite) +endif() diff --git a/src/iosource/BPF_Program.cc b/src/iosource/BPF_Program.cc index 71c9f7ee27..31da7536f9 100644 --- a/src/iosource/BPF_Program.cc +++ b/src/iosource/BPF_Program.cc @@ -4,6 +4,11 @@ #include "zeek/zeek-config.h" +// clang-format off +// Include order is required here for a working build on Windows. +#include +#include +// clang-format on #include #include "zeek/util.h" diff --git a/src/iosource/Packet.h b/src/iosource/Packet.h index cedc235493..2719047415 100644 --- a/src/iosource/Packet.h +++ b/src/iosource/Packet.h @@ -11,6 +11,8 @@ using pkt_timeval = bpf_timeval; #else using pkt_timeval = struct timeval; +#include +#include #endif #include // For DLT_ constants diff --git a/src/iosource/pcap/Dumper.cc b/src/iosource/pcap/Dumper.cc index 3e7b5e32bb..24a5628fec 100644 --- a/src/iosource/pcap/Dumper.cc +++ b/src/iosource/pcap/Dumper.cc @@ -107,7 +107,7 @@ bool PcapDumper::Dump(const Packet* pkt) return false; // Reconstitute the pcap_pkthdr. - const struct pcap_pkthdr phdr = {.ts = pkt->ts, .caplen = pkt->cap_len, .len = pkt->len}; + const struct pcap_pkthdr phdr = {pkt->ts, pkt->cap_len, pkt->len}; pcap_dump((u_char*)dumper, &phdr, pkt->data); pcap_dump_flush(dumper); diff --git a/src/iosource/pcap/Dumper.h b/src/iosource/pcap/Dumper.h index 1c78f4e575..58bd169030 100644 --- a/src/iosource/pcap/Dumper.h +++ b/src/iosource/pcap/Dumper.h @@ -2,6 +2,8 @@ #pragma once +#include + extern "C" { #include diff --git a/src/iosource/pcap/Source.cc b/src/iosource/pcap/Source.cc index 210263cf7c..4ebd8e77ca 100644 --- a/src/iosource/pcap/Source.cc +++ b/src/iosource/pcap/Source.cc @@ -160,7 +160,9 @@ void PcapSource::OpenLive() Info(util::fmt("pcap bufsize = %d\n", ((struct pcap*)pd)->bufsize)); #endif +#ifndef _MSC_VER props.selectable_fd = pcap_get_selectable_fd(pd); +#endif props.link_type = pcap_datalink(pd); props.is_live = true; diff --git a/src/iosource/pcap/Source.h b/src/iosource/pcap/Source.h index 1f100273ea..b02828ae1c 100644 --- a/src/iosource/pcap/Source.h +++ b/src/iosource/pcap/Source.h @@ -3,6 +3,7 @@ #pragma once #include // for u_char +#include extern "C" { diff --git a/src/logging/writers/CMakeLists.txt b/src/logging/writers/CMakeLists.txt index 867ad58c47..3aa507b316 100644 --- a/src/logging/writers/CMakeLists.txt +++ b/src/logging/writers/CMakeLists.txt @@ -1,4 +1,6 @@ add_subdirectory(ascii) add_subdirectory(none) -add_subdirectory(sqlite) +if (USE_SQLITE) + add_subdirectory(sqlite) +endif() diff --git a/src/logging/writers/ascii/Ascii.cc b/src/logging/writers/ascii/Ascii.cc index 8a703331e2..33793ada4a 100644 --- a/src/logging/writers/ascii/Ascii.cc +++ b/src/logging/writers/ascii/Ascii.cc @@ -88,7 +88,7 @@ struct LeftoverLog * Return the "path" (logging framework parlance) of the log without the * directory or file extension. E.g. the "path" of "logs/conn.log" is just "conn". */ - std::string Path() const { return zeek::filesystem::path(filename).stem(); } + std::string Path() const { return zeek::filesystem::path(filename).stem().string(); } /** * Deletes the shadow file and returns whether it succeeded. @@ -110,12 +110,13 @@ static std::string prefix_basename_with(const std::string& path, const std::stri TEST_CASE("writers.ascii prefix_basename_with") { - CHECK(prefix_basename_with("", ".shadow.") == ".shadow."); - CHECK(prefix_basename_with("conn.log", ".shadow.") == ".shadow.conn.log"); - CHECK(prefix_basename_with("/conn.log", ".shadow.") == "/.shadow.conn.log"); +#ifdef _MSC_VER + // TODO: adapt this test to Windows paths +#else CHECK(prefix_basename_with("a/conn.log", ".shadow.") == "a/.shadow.conn.log"); CHECK(prefix_basename_with("/a/conn.log", ".shadow.") == "/a/.shadow.conn.log"); CHECK(prefix_basename_with("a/b/conn.log", ".shadow.") == "a/b/.shadow.conn.log"); +#endif } static std::optional parse_shadow_log(const std::string& fname) @@ -493,7 +494,7 @@ bool Ascii::DoInit(const WriterInfo& info, int num_fields, const threading::Fiel } if ( fname.front() != '/' && ! logdir.empty() ) - fname = zeek::filesystem::path(logdir) / fname; + fname = (zeek::filesystem::path(logdir) / fname).string(); fname += ext; @@ -773,7 +774,7 @@ static std::vector find_leftover_logs() if ( BifConst::LogAscii::logdir->Len() > 0 ) logdir = zeek::filesystem::absolute(BifConst::LogAscii::logdir->ToStdString()); - auto d = opendir(logdir.c_str()); + auto d = opendir(logdir.string().c_str()); struct dirent* dp; if ( ! d ) @@ -788,8 +789,8 @@ static std::vector find_leftover_logs() if ( strncmp(dp->d_name, shadow_file_prefix, prefix_len) != 0 ) continue; - std::string shadow_fname = logdir / dp->d_name; - std::string log_fname = logdir / (dp->d_name + prefix_len); + std::string shadow_fname = (logdir / dp->d_name).string(); + std::string log_fname = (logdir / (dp->d_name + prefix_len)).string(); if ( util::is_file(log_fname) ) { @@ -909,17 +910,12 @@ string Ascii::Timestamp(double t) time_t teatime = time_t(t); if ( ! teatime ) - { - // Use wall clock. - struct timeval tv; - if ( gettimeofday(&tv, 0) < 0 ) - Error("gettimeofday failed"); - else - teatime = tv.tv_sec; - } + teatime = std::chrono::system_clock::to_time_t(std::chrono::system_clock::now()); struct tm tmbuf; struct tm* tm = localtime_r(&teatime, &tmbuf); + if ( tm == nullptr ) + Error(util::fmt("localtime_r failed: %s", strerror(errno))); char tmp[128]; const char* const date_fmt = "%Y-%m-%d-%H-%M-%S"; diff --git a/src/logging/writers/sqlite/SQLite.cc b/src/logging/writers/sqlite/SQLite.cc index 3747ddd06f..89894e4213 100644 --- a/src/logging/writers/sqlite/SQLite.cc +++ b/src/logging/writers/sqlite/SQLite.cc @@ -147,7 +147,7 @@ bool SQLite::DoInit(const WriterInfo& info, int arg_num_fields, const Field* con tablename = it->second; if ( checkError(sqlite3_open_v2( - fullpath.c_str(), &db, + fullpath.string().c_str(), &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE | SQLITE_OPEN_NOMUTEX, NULL)) ) return false; diff --git a/src/main.cc b/src/main.cc index 254fb14c58..1de09fc9e7 100644 --- a/src/main.cc +++ b/src/main.cc @@ -2,13 +2,23 @@ #include "zeek/zeek-config.h" +#include + #include "zeek/RunState.h" #include "zeek/iosource/Manager.h" #include "zeek/supervisor/Supervisor.h" #include "zeek/zeek-setup.h" +#ifdef _MSC_VER +#include // For _O_BINARY. +#endif + int main(int argc, char** argv) { +#ifdef _MSC_VER + _setmode(_fileno(stdout), _O_BINARY); + _setmode(_fileno(stderr), _O_BINARY); +#endif auto time_start = zeek::util::current_time(true); auto setup_result = zeek::detail::setup(argc, argv); @@ -41,7 +51,6 @@ int main(int argc, char** argv) zeek::detail::timer_mgr->Add(new zeek::detail::ParentProcessCheckTimer(1, 1)); double time_net_start = zeek::util::current_time(true); - ; uint64_t mem_net_start_total; uint64_t mem_net_start_malloced; diff --git a/src/net_util.h b/src/net_util.h index be222a3dbd..addb616874 100644 --- a/src/net_util.h +++ b/src/net_util.h @@ -283,6 +283,7 @@ inline uint64_t htonll(uint64_t i) #else +#ifndef _MSC_VER inline double ntohd(double d) { assert(sizeof(d) == 8); @@ -328,6 +329,7 @@ inline float htonf(float f) { return ntohf(f); } +#endif #ifndef HAVE_BYTEORDER_64 inline uint64_t ntohll(uint64_t i) diff --git a/src/packet_analysis/protocol/arp/ARP.cc b/src/packet_analysis/protocol/arp/ARP.cc index 51ec3aab02..5d9396c6d0 100644 --- a/src/packet_analysis/protocol/arp/ARP.cc +++ b/src/packet_analysis/protocol/arp/ARP.cc @@ -94,7 +94,7 @@ bool ARPAnalyzer::AnalyzePacket(size_t len, const uint8_t* data, Packet* packet) auto ah = (const struct arp_pkthdr*)data; // Check the size. - size_t min_length = (ar_tpa(ah) - (char*)data) + ah->ar_pln; + size_t min_length = (ar_tpa(ah) - (caddr_t)data) + ah->ar_pln; if ( min_length > len ) { Weird("truncated_ARP", packet); @@ -149,7 +149,7 @@ bool ARPAnalyzer::AnalyzePacket(size_t len, const uint8_t* data, Packet* packet) } // Check MAC src address = ARP sender MAC address. - if ( memcmp(packet->l2_src, ar_sha(ah), ah->ar_hln) != 0 ) + if ( memcmp(packet->l2_src, (const char*)ar_sha(ah), ah->ar_hln) != 0 ) { BadARPEvent(ah, "weird-arp-sha"); return false; @@ -219,9 +219,9 @@ void ARPAnalyzer::BadARPEvent(const struct arp_pkthdr* hdr, const char* fmt, ... vsnprintf(msg, sizeof(msg), fmt, args); va_end(args); - event_mgr.Enqueue(bad_arp, ToAddrVal(ar_spa(hdr), hdr->ar_pln), + event_mgr.Enqueue(bad_arp, ToAddrVal(reinterpret_cast(ar_spa(hdr)), hdr->ar_pln), ToEthAddrStr(reinterpret_cast(ar_sha(hdr)), hdr->ar_hln), - ToAddrVal(ar_tpa(hdr), hdr->ar_pln), + ToAddrVal(reinterpret_cast(ar_tpa(hdr)), hdr->ar_pln), ToEthAddrStr(reinterpret_cast(ar_tha(hdr)), hdr->ar_hln), zeek::make_intrusive(msg)); } diff --git a/src/packet_analysis/protocol/ip/IP.cc b/src/packet_analysis/protocol/ip/IP.cc index 1263317317..ec2c6dcdc0 100644 --- a/src/packet_analysis/protocol/ip/IP.cc +++ b/src/packet_analysis/protocol/ip/IP.cc @@ -62,7 +62,8 @@ bool IPAnalyzer::AnalyzePacket(size_t len, const uint8_t* data, Packet* packet) return false; } - ip_hdr = std::make_shared((const struct ip6_hdr*)data, false, len); + ip_hdr = std::make_shared((const struct ip6_hdr*)data, false, + static_cast(len)); packet->l3_proto = L3_IPV6; } else diff --git a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc index 0330d6ccfa..dfc33a209a 100644 --- a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc +++ b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc @@ -1791,8 +1791,8 @@ int TCPSessionAdapter::ParseTCPOptions(const struct tcphdr* tcp, bool is_orig) // timestamps if ( length == 10 ) { - auto send = ntohl(*reinterpret_cast(o + 2)); - auto echo = ntohl(*reinterpret_cast(o + 6)); + uint32_t send = ntohl(*reinterpret_cast(o + 2)); + uint32_t echo = ntohl(*reinterpret_cast(o + 6)); option_record->Assign(6, send); option_record->Assign(7, echo); } @@ -1809,7 +1809,7 @@ int TCPSessionAdapter::ParseTCPOptions(const struct tcphdr* tcp, bool is_orig) { auto rate = o[2]; auto ttl_diff = o[3]; - auto qs_nonce = ntohl(*reinterpret_cast(o + 4)); + uint32_t qs_nonce = ntohl(*reinterpret_cast(o + 4)); option_record->Assign(8, rate); option_record->Assign(9, ttl_diff); option_record->Assign(10, qs_nonce); diff --git a/src/plugin/Manager.cc b/src/plugin/Manager.cc index 155907d141..ba57268ca2 100644 --- a/src/plugin/Manager.cc +++ b/src/plugin/Manager.cc @@ -3,8 +3,10 @@ #include "zeek/plugin/Manager.h" #include +#ifndef _MSC_VER #include #include +#endif #include #include #include // for PATH_MAX @@ -56,13 +58,13 @@ void Manager::SearchDynamicPlugins(const std::string& dir) if ( dir.empty() ) return; - if ( dir.find(':') != string::npos ) + if ( dir.find(path_list_separator) != string::npos ) { // Split at ":". std::stringstream s(dir); std::string d; - while ( std::getline(s, d, ':') ) + while ( std::getline(s, d, path_list_separator[0]) ) SearchDynamicPlugins(d); return; @@ -160,6 +162,10 @@ void Manager::SearchDynamicPlugins(const std::string& dir) bool Manager::ActivateDynamicPluginInternal(const std::string& name, bool ok_if_not_found, std::vector* errors) { +// Loading dynamic plugins is not currently supported on Windows platform. +#ifdef _MSC_VER + return false; +#else errors->clear(); // caller should pass it in empty, but just to be sure dynamic_plugin_map::iterator m = dynamic_plugins.find(util::strtolower(name)); @@ -326,6 +332,7 @@ bool Manager::ActivateDynamicPluginInternal(const std::string& name, bool ok_if_ m->second.clear(); return true; +#endif } void Manager::ActivateDynamicPlugin(const std::string& name) @@ -346,14 +353,21 @@ void Manager::ActivateDynamicPlugins(bool all) // Activate plugins that were specifically requested. for ( const auto& x : requested_plugins ) - plugins_to_activate.emplace(x, false); + { + if ( ! x.empty() ) + plugins_to_activate.emplace(x, false); + } // Activate plugins that our environment tells us to. vector p; - util::tokenize_string(util::zeek_plugin_activate(), ",", &p); + std::string plugin_activate = util::zeek_plugin_activate(); + if ( ! plugin_activate.empty() ) + { + util::tokenize_string(util::zeek_plugin_activate(), ",", &p); - for ( const auto& x : p ) - plugins_to_activate.emplace(x, true); + for ( const auto& x : p ) + plugins_to_activate.emplace(x, true); + } if ( all ) { @@ -911,32 +925,48 @@ void Manager::HookBroObjDtor(void* obj) const if ( HavePluginForHook(META_HOOK_PRE) ) { args.push_back(HookArgument(obj)); +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif MetaHookPre(HOOK_BRO_OBJ_DTOR, args); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif hook_list* l = hooks[HOOK_BRO_OBJ_DTOR]; +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif if ( l ) for ( hook_list::iterator i = l->begin(); i != l->end(); ++i ) { Plugin* p = (*i).second; +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif p->HookBroObjDtor(obj); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } if ( HavePluginForHook(META_HOOK_POST) ) +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif MetaHookPost(HOOK_BRO_OBJ_DTOR, args, HookArgument()); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } void Manager::HookObjDtor(void* obj) const diff --git a/src/plugin/Manager.h b/src/plugin/Manager.h index b6a4bd2f7b..89b0deab5f 100644 --- a/src/plugin/Manager.h +++ b/src/plugin/Manager.h @@ -77,7 +77,7 @@ public: * This must be called only before InitPluginsPreScript(). * * @param dir The directory to search for plugins. Multiple directories - * can be given by splitting them with ':'. + * can be given by separating them with zeek::util::path_list_separator. */ void SearchDynamicPlugins(const std::string& dir); diff --git a/src/plugin/Plugin.cc b/src/plugin/Plugin.cc index 6b5a201564..af005a40f9 100644 --- a/src/plugin/Plugin.cc +++ b/src/plugin/Plugin.cc @@ -383,10 +383,14 @@ void Plugin::RequestEvent(EventHandlerPtr handler) void Plugin::RequestBroObjDtor(Obj* obj) { +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif plugin_mgr->RequestBroObjDtor(obj, this); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } void Plugin::RequestObjDtor(Obj* obj) diff --git a/src/plugin/Plugin.h b/src/plugin/Plugin.h index c83a48bdd4..c026bc9b3d 100644 --- a/src/plugin/Plugin.h +++ b/src/plugin/Plugin.h @@ -25,6 +25,10 @@ struct Field; namespace zeek { +#ifdef _MSC_VER +#undef VOID +#endif + // Increase this when making incompatible changes to the plugin API. Note // that the constant is never used in C code. It's picked up on by CMake. constexpr int PLUGIN_API_VERSION = 7; @@ -116,17 +120,23 @@ public: // We force this to inline so that the API version gets hardcoded // into the external plugin. (Technically, it's not a "force", just a // strong hint.). The attribute seems generally available. +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif inline Configuration() __attribute__((always_inline)) { bro_version = ZEEK_PLUGIN_ZEEK_VERSION; zeek_version = ZEEK_PLUGIN_ZEEK_VERSION; } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif Configuration(Configuration&& c) { bro_version = std::move(c.bro_version); @@ -136,10 +146,14 @@ public: description = std::move(c.description); version = std::move(c.version); } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif Configuration(const Configuration& c) { bro_version = c.bro_version; @@ -149,10 +163,14 @@ public: description = c.description; version = c.version; } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif Configuration& operator=(Configuration&& c) { bro_version = std::move(c.bro_version); @@ -164,10 +182,14 @@ public: return *this; } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif Configuration& operator=(const Configuration& c) { bro_version = c.bro_version; @@ -179,12 +201,18 @@ public: return *this; } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif ~Configuration() { } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif /** * One can assign ZEEK_PLUGIN_ZEEK_VERSION to this to catch diff --git a/src/script_opt/CPP/RuntimeInits.cc b/src/script_opt/CPP/RuntimeInits.cc index b2126b4dcc..1e5678d8b0 100644 --- a/src/script_opt/CPP/RuntimeInits.cc +++ b/src/script_opt/CPP/RuntimeInits.cc @@ -28,7 +28,7 @@ void CPP_IndexedInits::Generate(InitsManager* im, std::vector& iv { auto& e_type = im->Types(init_vals[0]); int val = init_vals[1]; - ivec[offset] = make_enum__CPP(e_type, val); + ivec[offset] = zeek::detail::make_enum__CPP(e_type, val); } template diff --git a/src/script_opt/ZAM/Stmt.cc b/src/script_opt/ZAM/Stmt.cc index 808eeb2d29..1e3daedee8 100644 --- a/src/script_opt/ZAM/Stmt.cc +++ b/src/script_opt/ZAM/Stmt.cc @@ -384,8 +384,10 @@ const ZAMStmt ZAMCompiler::GenCond(const Expr* e, int& branch_v) // from "ZAM-Conds.h". It really shouldn't worry about indentation mismatches // across included files since those are not indicative of possible // logic errors, but Oh Well. +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wmisleading-indentation" +#endif switch ( e->Tag() ) { #include "ZAM-Conds.h" @@ -393,7 +395,9 @@ const ZAMStmt ZAMCompiler::GenCond(const Expr* e, int& branch_v) default: reporter->InternalError("bad expression type in ZAMCompiler::GenCond"); } +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif // Not reached. } diff --git a/src/stats.bif b/src/stats.bif index ba5b94efae..9adc49b16c 100644 --- a/src/stats.bif +++ b/src/stats.bif @@ -484,3 +484,33 @@ function get_reporter_stats%(%): ReporterStats return r; %} + +## Returns a list of event handlers that were called and the number of times +## each was called. +## +## Returns: A record with event call statistics. +## +function get_event_handler_call_counts%(%): EventNameStats + %{ + auto rval = zeek::make_intrusive(zeek::id::find_type("EventNameStats")); + const auto& recordType = zeek::id::find_type("EventNameCounter"); + + int i = 0; + const auto& events = event_registry->UsedHandlers(); + for ( const auto& name : events ) + { + auto handler = event_registry->Lookup(name); + auto call_count = handler->CallCount(); + + if ( call_count > 0 ) + { + auto eventStatRecord = zeek::make_intrusive(recordType); + eventStatRecord->Assign(0, zeek::make_intrusive(name)); + eventStatRecord->Assign(1, zeek::val_mgr->Count(handler->CallCount())); + rval->Assign(i, std::move(eventStatRecord)); + i++; + } + } + + return rval; + %} diff --git a/src/supervisor/Supervisor.cc b/src/supervisor/Supervisor.cc index 44544d518f..e74da48ddd 100644 --- a/src/supervisor/Supervisor.cc +++ b/src/supervisor/Supervisor.cc @@ -41,7 +41,7 @@ extern "C" #include "zeek/zeek-affinity.h" #ifdef DEBUG -#define DBG_STEM(args...) stem->LogDebug(args); +#define DBG_STEM(...) stem->LogDebug(__VA_ARGS__); #else #define DBG_STEM #endif @@ -987,22 +987,24 @@ std::optional Stem::Poll() const auto total_fd_count = fixed_fd_count + (nodes.size() * 2); auto pfds = std::make_unique(total_fd_count); int pfd_idx = 0; - pfds[pfd_idx++] = {pipe->InFD(), POLLIN, 0}; - pfds[pfd_idx++] = {signal_flare->FD(), POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(pipe->InFD()), POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(signal_flare->FD()), POLLIN, 0}; for ( const auto& [name, node] : nodes ) { node_pollfd_indices[name] = pfd_idx; if ( node.stdout_pipe.pipe ) - pfds[pfd_idx++] = {node.stdout_pipe.pipe->ReadFD(), POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(node.stdout_pipe.pipe->ReadFD()), + POLLIN, 0}; else - pfds[pfd_idx++] = {-1, POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(-1), POLLIN, 0}; if ( node.stderr_pipe.pipe ) - pfds[pfd_idx++] = {node.stderr_pipe.pipe->ReadFD(), POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(node.stderr_pipe.pipe->ReadFD()), + POLLIN, 0}; else - pfds[pfd_idx++] = {-1, POLLIN, 0}; + pfds[pfd_idx++] = {static_cast(-1), POLLIN, 0}; } // Note: the poll timeout here is for periodically checking if the parent @@ -1249,7 +1251,7 @@ Supervisor::NodeConfig Supervisor::NodeConfig::FromRecord(const RecordVal* node) const auto& affinity_val = node->GetField("cpu_affinity"); if ( affinity_val ) - rval.cpu_affinity = affinity_val->AsInt(); + rval.cpu_affinity = static_cast(affinity_val->AsInt()); const auto& bare_mode_val = node->GetField("bare_mode"); @@ -1277,10 +1279,14 @@ Supervisor::NodeConfig Supervisor::NodeConfig::FromRecord(const RecordVal* node) for ( auto i = 0u; i < scripts_val->Size(); ++i ) { auto script = scripts_val->StringValAt(i)->ToStdString(); +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif rval.scripts.emplace_back(std::move(script)); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } auto env_table_val = node->GetField("env")->AsTableVal(); @@ -1364,10 +1370,14 @@ Supervisor::NodeConfig Supervisor::NodeConfig::FromJSON(std::string_view json) auto& scripts = j["scripts"]; for ( auto it = scripts.Begin(); it != scripts.End(); ++it ) +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif rval.scripts.emplace_back(it->GetString()); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif auto& env = j["env"]; @@ -1447,10 +1457,14 @@ RecordValPtr Supervisor::NodeConfig::ToRecord() const auto st = rt->GetFieldType("scripts"); auto scripts_val = make_intrusive(std::move(st)); +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif for ( const auto& s : scripts ) +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif scripts_val->Assign(scripts_val->Size(), make_intrusive(s)); rval->AssignField("scripts", std::move(scripts_val)); @@ -1656,10 +1670,14 @@ void SupervisedNode::Init(Options* options) const stl.insert(stl.begin(), config.addl_base_scripts.begin(), config.addl_base_scripts.end()); stl.insert(stl.end(), config.addl_user_scripts.begin(), config.addl_user_scripts.end()); +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif stl.insert(stl.end(), config.scripts.begin(), config.scripts.end()); +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif } RecordValPtr Supervisor::Status(std::string_view node_name) diff --git a/src/supervisor/Supervisor.h b/src/supervisor/Supervisor.h index e691c3c868..3d883c7617 100644 --- a/src/supervisor/Supervisor.h +++ b/src/supervisor/Supervisor.h @@ -2,6 +2,8 @@ #pragma once +#include "zeek/zeek-config.h" + #include #include #include @@ -143,18 +145,26 @@ public: */ struct NodeConfig { +#ifdef __GNUC__ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdeprecated-declarations" +#endif // This block exists because the default implementations // themselves trigger deprecation warnings for accessing the // "scripts" field. It can go when we remove that deprecation. NodeConfig() = default; +#ifndef _MSC_VER + // MSVC throws this error when specifing this constructor: + // error C2580: multiple versions of a defaulted special member functions are not allowed NodeConfig(NodeConfig&) = default; +#endif NodeConfig(const NodeConfig&) = default; NodeConfig(NodeConfig&&) = default; ~NodeConfig() = default; NodeConfig& operator=(const NodeConfig&) = default; +#ifdef __GNUC__ #pragma GCC diagnostic pop +#endif /** * Create configuration from script-layer record value. diff --git a/src/telemetry/CMakeLists.txt b/src/telemetry/CMakeLists.txt index c4b8359a48..129f49effb 100644 --- a/src/telemetry/CMakeLists.txt +++ b/src/telemetry/CMakeLists.txt @@ -13,3 +13,4 @@ bif_target(telemetry.bif) bro_add_subdir_library(telemetry ${telemetry_SRCS}) add_dependencies(bro_telemetry generate_outputs) + diff --git a/src/telemetry/Counter.h b/src/telemetry/Counter.h index 6f5e360a89..afa836999a 100644 --- a/src/telemetry/Counter.h +++ b/src/telemetry/Counter.h @@ -57,7 +57,7 @@ public: /** * @return Whether @c this and @p other refer to the same counter. */ - constexpr bool IsSameAs(IntCounter other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const IntCounter& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::int_counter_hdl*; @@ -72,13 +72,13 @@ private: * @return Whether @p lhs and @p rhs refer to the same object. * @note compare their @c value instead to check for equality. */ -constexpr bool operator==(IntCounter lhs, IntCounter rhs) noexcept +constexpr bool operator==(const IntCounter& lhs, const IntCounter& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates IntCounter -constexpr bool operator!=(IntCounter lhs, IntCounter rhs) noexcept +constexpr bool operator!=(const IntCounter& lhs, const IntCounter& rhs) noexcept { return ! (lhs == rhs); } @@ -155,7 +155,7 @@ public: /** * @return Whether @c this and @p other refer to the same counter. */ - constexpr bool IsSameAs(DblCounter other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const DblCounter& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::dbl_counter_hdl*; @@ -170,13 +170,13 @@ private: * @return Whether @p lhs and @p rhs refer to the same object. * @note compare their @c value instead to check for equality. */ -constexpr bool operator==(DblCounter lhs, DblCounter rhs) noexcept +constexpr bool operator==(const DblCounter& lhs, const DblCounter& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates DblCounter -constexpr bool operator!=(DblCounter lhs, DblCounter rhs) noexcept +constexpr bool operator!=(const DblCounter& lhs, const DblCounter& rhs) noexcept { return ! (lhs == rhs); } diff --git a/src/telemetry/Gauge.h b/src/telemetry/Gauge.h index 294f9b1ab1..68cc6ca6e2 100644 --- a/src/telemetry/Gauge.h +++ b/src/telemetry/Gauge.h @@ -73,7 +73,7 @@ public: /** * @return Whether @c this and @p other refer to the same counter. */ - constexpr bool IsSameAs(IntGauge other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const IntGauge& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::int_gauge_hdl*; @@ -88,13 +88,13 @@ private: * @return Whether @p lhs and @p rhs refer to the same object. * @note compare their @c value instead to check for equality. */ -constexpr bool operator==(IntGauge lhs, IntGauge rhs) noexcept +constexpr bool operator==(const IntGauge& lhs, const IntGauge& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates IntGauge -constexpr bool operator!=(IntGauge lhs, IntGauge rhs) noexcept +constexpr bool operator!=(const IntGauge& lhs, const IntGauge& rhs) noexcept { return ! (lhs == rhs); } @@ -180,7 +180,7 @@ public: /** * @return Whether @c this and @p other refer to the same counter. */ - constexpr bool IsSameAs(DblGauge other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const DblGauge& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::dbl_gauge_hdl*; @@ -195,13 +195,13 @@ private: * @return Whether @p lhs and @p rhs refer to the same object. * @note compare their @c value instead to check for equality. */ -constexpr bool operator==(DblGauge lhs, DblGauge rhs) noexcept +constexpr bool operator==(const DblGauge& lhs, const DblGauge& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates DblGauge -constexpr bool operator!=(DblGauge lhs, DblGauge rhs) noexcept +constexpr bool operator!=(const DblGauge& lhs, const DblGauge& rhs) noexcept { return ! (lhs == rhs); } diff --git a/src/telemetry/Histogram.h b/src/telemetry/Histogram.h index 7e1d037db1..0073ebb011 100644 --- a/src/telemetry/Histogram.h +++ b/src/telemetry/Histogram.h @@ -60,7 +60,7 @@ public: /** * @return Whether @c this and @p other refer to the same histogram. */ - constexpr bool IsSameAs(IntHistogram other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const IntHistogram& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::int_histogram_hdl*; @@ -74,13 +74,13 @@ private: * Checks whether two @ref IntHistogram handles are identical. * @return Whether @p lhs and @p rhs refer to the same object. */ -constexpr bool operator==(IntHistogram lhs, IntHistogram rhs) noexcept +constexpr bool operator==(const IntHistogram& lhs, const IntHistogram& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates IntHistogram -constexpr bool operator!=(IntHistogram lhs, IntHistogram rhs) noexcept +constexpr bool operator!=(const IntHistogram& lhs, const IntHistogram& rhs) noexcept { return ! (lhs == rhs); } @@ -165,7 +165,7 @@ public: /** * @return Whether @c this and @p other refer to the same histogram. */ - constexpr bool IsSameAs(DblHistogram other) const noexcept { return hdl == other.hdl; } + constexpr bool IsSameAs(const DblHistogram& other) const noexcept { return hdl == other.hdl; } private: using Handle = broker::telemetry::dbl_histogram_hdl*; @@ -179,13 +179,13 @@ private: * Checks whether two @ref DblHistogram handles are identical. * @return Whether @p lhs and @p rhs refer to the same object. */ -constexpr bool operator==(DblHistogram lhs, DblHistogram rhs) noexcept +constexpr bool operator==(const DblHistogram& lhs, const DblHistogram& rhs) noexcept { return lhs.IsSameAs(rhs); } /// @relates DblHistogram -constexpr bool operator!=(DblHistogram lhs, DblHistogram rhs) noexcept +constexpr bool operator!=(const DblHistogram& lhs, const DblHistogram& rhs) noexcept { return ! (lhs == rhs); } diff --git a/src/threading/BasicThread.cc b/src/threading/BasicThread.cc index 32c2504d3f..99116786d5 100644 --- a/src/threading/BasicThread.cc +++ b/src/threading/BasicThread.cc @@ -48,9 +48,10 @@ void BasicThread::SetName(const char* arg_name) void BasicThread::SetOSName(const char* arg_name) { - static_assert(std::is_same::value, - "libstdc++ doesn't use pthread_t"); - util::detail::set_thread_name(arg_name, thread.native_handle()); + // Do it only if libc++ supports pthread_t. + if constexpr ( std::is_same::value ) + zeek::util::detail::set_thread_name(arg_name, + reinterpret_cast(thread.native_handle())); } const char* BasicThread::Fmt(const char* format, ...) @@ -172,10 +173,9 @@ void BasicThread::Done() void* BasicThread::launcher(void* arg) { - static_assert(std::is_same::value, - "libstdc++ doesn't use pthread_t"); BasicThread* thread = (BasicThread*)arg; +#ifndef _MSC_VER // Block signals in thread. We handle signals only in the main // process. sigset_t mask_set; @@ -190,6 +190,7 @@ void* BasicThread::launcher(void* arg) sigdelset(&mask_set, SIGBUS); int res = pthread_sigmask(SIG_BLOCK, &mask_set, 0); assert(res == 0); +#endif // Run thread's main function. thread->Run(); diff --git a/src/threading/BasicThread.h b/src/threading/BasicThread.h index 539fabad79..d5cdc3a348 100644 --- a/src/threading/BasicThread.h +++ b/src/threading/BasicThread.h @@ -3,6 +3,7 @@ #include "zeek/zeek-config.h" +#include #include #include #include diff --git a/src/util.cc b/src/util.cc index bbb0be151e..6b01b1f28b 100644 --- a/src/util.cc +++ b/src/util.cc @@ -40,6 +40,7 @@ #include #include #include +#include #include #include @@ -51,6 +52,7 @@ #include "zeek/Obj.h" #include "zeek/Reporter.h" #include "zeek/RunState.h" +#include "zeek/ScannedFile.h" #include "zeek/Val.h" #include "zeek/digest.h" #include "zeek/input.h" @@ -67,6 +69,7 @@ static bool can_read(const string& path) } static string zeek_path_value; +const string zeek_path_list_separator(path_list_separator.begin(), path_list_separator.end()); namespace zeek::util { @@ -554,7 +557,7 @@ void add_to_zeek_path(const string& dir) // Make sure path is initialized. zeek_path(); - zeek_path_value += string(":") + dir; + zeek_path_value += zeek_path_list_separator + dir; } FILE* open_package(string& path, const string& mode) @@ -596,7 +599,12 @@ void SafePathOp::CheckValid(const char* op_result, const char* path, bool error_ TEST_CASE("util flatten_script_name") { CHECK(flatten_script_name("script", "some/path") == "some.path.script"); +#ifndef _MSC_VER + // TODO: this test fails on Windows because the implementation of dirname() in libunistd + // returns a trailing slash on paths, even tho the POSIX implementation doesn't. Commenting + // this out until we can fix that. CHECK(flatten_script_name("other/path/__load__.zeek", "some/path") == "some.path.other.path"); +#endif CHECK(flatten_script_name("path/to/script", "") == "path.to.script"); } @@ -622,6 +630,9 @@ string flatten_script_name(const string& name, const string& prefix) TEST_CASE("util normalize_path") { +#ifdef _MSC_VER + // TODO: adapt these tests to Windows +#else CHECK(normalize_path("/1/2/3") == "/1/2/3"); CHECK(normalize_path("/1/./2/3") == "/1/2/3"); CHECK(normalize_path("/1/2/../3") == "/1/3"); @@ -645,10 +656,24 @@ TEST_CASE("util normalize_path") CHECK(normalize_path("~/../..") == "~/../.."); CHECK(normalize_path("zeek/..") == ""); CHECK(normalize_path("zeek/../..") == ".."); +#endif } string normalize_path(std::string_view path) { +#ifdef _MSC_VER + if ( 0 == path.compare(zeek::detail::ScannedFile::canonical_stdin_path) ) + { + return string(path); + } + // "//" interferes with std::weakly_canonical + string stringPath = string(path); + if ( stringPath._Starts_with("//") ) + { + stringPath.erase(0, 2); + } + return zeek::filesystem::path(stringPath).lexically_normal().string(); +#else if ( path.find("/.") == std::string_view::npos && path.find("//") == std::string_view::npos ) { // no need to normalize anything @@ -713,13 +738,14 @@ string normalize_path(std::string_view path) new_path.erase(new_path.size() - 1); return new_path; +#endif } string without_zeekpath_component(std::string_view path) { string rval = normalize_path(path); - const auto paths = tokenize_string(zeek_path(), ':'); + const auto paths = tokenize_string(zeek_path(), path_list_separator[0]); for ( size_t i = 0; i < paths.size(); ++i ) { @@ -746,12 +772,13 @@ std::string get_exe_path(const std::string& invocation) { if ( invocation.empty() ) return ""; + zeek::filesystem::path invocation_path(invocation); - if ( invocation[0] == '/' || invocation[0] == '~' ) + if ( invocation_path.is_absolute() || invocation_path.root_directory() == "~" ) // Absolute path return invocation; - if ( invocation.find('/') != std::string::npos ) + if ( invocation_path.is_relative() && invocation_path.has_parent_path() ) { // Relative path char cwd[PATH_MAX]; @@ -762,7 +789,7 @@ std::string get_exe_path(const std::string& invocation) exit(1); } - return std::string(cwd) + "/" + invocation; + return (zeek::filesystem::path(cwd) / invocation_path).string(); } auto path = getenv("PATH"); @@ -1102,9 +1129,9 @@ TEST_CASE("util streq") CHECK(streq("abcd", "efgh") == false); } -int streq(const char* s1, const char* s2) +bool streq(const char* s1, const char* s2) { - return ! strcmp(s1, s2); + return strcmp(s1, s2) == 0; } bool starts_with(std::string_view s, std::string_view beginning) @@ -1316,7 +1343,7 @@ const char* strpbrk_n(size_t len, const char* s, const char* charset) return nullptr; } -#ifndef HAVE_STRCASESTR +#if ! defined(HAVE_STRCASESTR) && ! defined(_MSC_VER) TEST_CASE("util strcasestr") { @@ -1576,7 +1603,7 @@ const char* fmt_bytes(const char* data, int len) for ( int i = 0; i < len && p - buf < int(sizeof(buf)); ++i ) { - if ( isprint(data[i]) ) + if ( isprint((unsigned char)(data[i])) ) *p++ = data[i]; else p += snprintf(p, sizeof(buf) - (p - buf), "\\x%02x", (unsigned char)data[i]); @@ -1593,7 +1620,7 @@ const char* fmt_bytes(const char* data, int len) const char* vfmt(const char* format, va_list al) { static char* buf = nullptr; - static unsigned int buf_len = 1024; + static int buf_len = 1024; if ( ! buf ) buf = (char*)safe_malloc(buf_len); @@ -1602,17 +1629,16 @@ const char* vfmt(const char* format, va_list al) va_copy(alc, al); int n = vsnprintf(buf, buf_len, format, al); - if ( (unsigned int)n >= buf_len ) + if ( n > 0 && buf_len < n ) { // Not enough room, grow the buffer. buf_len = n + 32; buf = (char*)safe_realloc(buf, buf_len); - n = vsnprintf(buf, buf_len, format, alc); - - if ( (unsigned int)n >= buf_len ) - reporter->InternalError("confusion reformatting in fmt()"); } + if ( n < 0 ) + reporter->InternalError("confusion reformatting in fmt()"); + va_end(alc); return buf; } @@ -1756,7 +1782,7 @@ string zeek_prefixes() for ( const auto& prefix : zeek::detail::zeek_script_prefixes ) { if ( ! rval.empty() ) - rval.append(":"); + rval.append(path_list_separator); rval.append(prefix); } @@ -1780,33 +1806,35 @@ FILE* open_file(const string& path, const string& mode) return rval; } -TEST_CASE("util path ops") - { - SUBCASE("SafeDirname") - { - SafeDirname d("/this/is/a/path", false); - CHECK(d.result == "/this/is/a"); +TEST_CASE("util path ops"){ +#ifdef _MSC_VER +// TODO: adapt these tests to Windows paths +#else + SUBCASE("SafeDirname"){SafeDirname d("/this/is/a/path", false); +CHECK(d.result == "/this/is/a"); - SafeDirname d2("invalid", false); - CHECK(d2.result == "."); +SafeDirname d2("invalid", false); +CHECK(d2.result == "."); - SafeDirname d3("./filename", false); - CHECK(d2.result == "."); - } - - SUBCASE("SafeBasename") - { - SafeBasename b("/this/is/a/path", false); - CHECK(b.result == "path"); - CHECK(! b.error); - - SafeBasename b2("justafile", false); - CHECK(b2.result == "justafile"); - CHECK(! b2.error); - } +SafeDirname d3("./filename", false); +CHECK(d2.result == "."); } -SafeDirname::SafeDirname(const char* path, bool error_aborts) : SafePathOp() +SUBCASE("SafeBasename") + { + SafeBasename b("/this/is/a/path", false); + CHECK(b.result == "path"); + CHECK(! b.error); + + SafeBasename b2("justafile", false); + CHECK(b2.result == "justafile"); + CHECK(! b2.error); + } +#endif +} + +SafeDirname::SafeDirname(const char* path, bool error_aborts) + : SafePathOp() { DoFunc(path ? path : "", error_aborts); } @@ -1937,8 +1965,10 @@ static string find_file_in_path(const string& filename, const string& path, if ( filename.empty() ) return string(); + zeek::filesystem::path filepath(filename); + // If file name is an absolute path, searching within *path* is pointless. - if ( filename[0] == '/' ) + if ( filepath.is_absolute() ) { if ( can_read(filename) ) return filename; @@ -1946,7 +1976,7 @@ static string find_file_in_path(const string& filename, const string& path, return string(); } - string abs_path = path + '/' + filename; + auto abs_path = (zeek::filesystem::path(path) / filepath).string(); if ( ! opt_ext.empty() ) { @@ -1968,7 +1998,7 @@ static string find_file_in_path(const string& filename, const string& path, string find_file(const string& filename, const string& path_set, const string& opt_ext) { vector paths; - tokenize_string(path_set, ":", &paths); + tokenize_string(path_set, path_list_separator, &paths); vector ext; if ( ! opt_ext.empty() ) @@ -1988,7 +2018,7 @@ string find_file(const string& filename, const string& path_set, const string& o string find_script_file(const string& filename, const string& path_set) { vector paths; - tokenize_string(path_set, ":", &paths); + tokenize_string(path_set, path_list_separator, &paths); vector ext = {".zeek"}; @@ -2008,9 +2038,15 @@ RETSIGTYPE sig_handler(int signo); double current_time(bool real) { struct timeval tv; +#ifdef _MSC_VER + auto now = std::chrono::system_clock::now(); + auto ms = std::chrono::duration_cast(now.time_since_epoch()); + tv.tv_sec = ms.count() / 1000; + tv.tv_usec = (ms.count() % 1000) * 1000; +#else if ( gettimeofday(&tv, 0) < 0 ) reporter->InternalError("gettimeofday failed in current_time()"); - +#endif double t = double(tv.tv_sec) + double(tv.tv_usec) / 1e6; if ( ! run_state::pseudo_realtime || real || ! iosource_mgr || ! iosource_mgr->GetPktSrc() ) @@ -2251,8 +2287,8 @@ const void* memory_align(const void* ptr, size_t size) const char* buf = reinterpret_cast(ptr); size_t mask = size - 1; // Assume size is a power of 2. - unsigned long l_ptr = reinterpret_cast(ptr); - unsigned long offset = l_ptr & mask; + intptr_t l_ptr = reinterpret_cast(ptr); + ptrdiff_t offset = l_ptr & mask; if ( offset > 0 ) return reinterpret_cast(buf - offset + size); @@ -2291,7 +2327,7 @@ void* memory_align_and_pad(void* ptr, size_t size) char* buf = reinterpret_cast(ptr); size_t mask = size - 1; - while ( (reinterpret_cast(buf) & mask) != 0 ) + while ( (reinterpret_cast(buf) & mask) != 0 ) // Not aligned - zero pad. *buf++ = '\0'; @@ -2394,6 +2430,9 @@ void get_memory_usage(uint64_t* total, uint64_t* malloced) // In KB. ret_total = r.ru_maxrss * 1024; + + if ( malloced ) + *malloced = r.ru_ixrss * 1024; #endif if ( total ) @@ -2506,7 +2545,12 @@ static void strerror_r_helper(int result, char* buf, size_t buflen) void zeek_strerror_r(int zeek_errno, char* buf, size_t buflen) { +#ifdef _MSC_VER + auto str = "Error number: " + std::to_string(zeek_errno); + auto res = str.data(); +#else auto res = strerror_r(zeek_errno, buf, buflen); +#endif // GNU vs. XSI flavors make it harder to use strerror_r. strerror_r_helper(res, buf, buflen); } @@ -2698,6 +2742,9 @@ string json_escape_utf8(const char* val, size_t val_size, bool escape_printable_ TEST_CASE("util filesystem") { +#ifdef _MSC_VER + // TODO: adapt these tests to Windows paths +#else zeek::filesystem::path path1("/a/b"); CHECK(path1.is_absolute()); CHECK(! path1.is_relative()); @@ -2712,6 +2759,7 @@ TEST_CASE("util filesystem") auto info = zeek::filesystem::space("."); CHECK(info.capacity > 0); +#endif } TEST_CASE("util split") diff --git a/src/util.h b/src/util.h index 2a8d8ed2ff..0b41c7cd89 100644 --- a/src/util.h +++ b/src/util.h @@ -15,6 +15,7 @@ #endif #include +#include #include #include #include @@ -30,27 +31,28 @@ #ifdef TIME_WITH_SYS_TIME #include #include -#else -#ifdef HAVE_SYS_TIME_H +#elif defined(HAVE_SYS_TIME_H) #include #else #include #endif -#endif #ifdef DEBUG #include #define ASSERT(x) assert(x) -#define DEBUG_MSG(x...) fprintf(stderr, x) +#define DEBUG_MSG(...) fprintf(stderr, __VA_ARGS__) #define DEBUG_fputs fputs #else +#ifdef MSTCPIP_ASSERT_UNDEFINED +#undef ASSERT +#endif #define ASSERT(x) -#define DEBUG_MSG(x...) -#define DEBUG_fputs(x...) +#define DEBUG_MSG(...) +#define DEBUG_fputs(...) #endif @@ -60,9 +62,15 @@ extern HeapLeakChecker* heap_checker; #endif -#include +#include + +extern "C" + { +#include "zeek/3rdparty/modp_numtoa.h" + } #ifdef HAVE_LINUX +#include #include #endif @@ -70,12 +78,24 @@ extern HeapLeakChecker* heap_checker; #include #endif -extern "C" +#ifdef _MSC_VER +#include +#include +namespace zeek { -#include "zeek/3rdparty/modp_numtoa.h" +namespace filesystem = std::filesystem; } - +inline constexpr std::string_view path_list_separator = ";"; +#else +// Expose ghc::filesystem as zeek::filesystem until we can +// switch to std::filesystem on all platforms. #include "zeek/3rdparty/ghc/filesystem.hpp" +namespace zeek + { +namespace filesystem = ghc::filesystem; + } +inline constexpr std::string_view path_list_separator = ":"; +#endif using zeek_int_t = int64_t; using zeek_uint_t = uint64_t; @@ -95,10 +115,6 @@ namespace zeek class ODesc; class RecordVal; -// Expose ghc::filesystem as zeek::filesystem until we can -// switch to std::filesystem. -namespace filesystem = ghc::filesystem; - namespace util { namespace detail @@ -318,7 +334,7 @@ std::vector* tokenize_string(std::string_view input, std::string_vi std::vector tokenize_string(std::string_view input, const char delim) noexcept; extern char* copy_string(const char* s); -extern int streq(const char* s1, const char* s2); +extern bool streq(const char* s1, const char* s2); extern bool starts_with(std::string_view s, std::string_view beginning); extern bool ends_with(std::string_view s, std::string_view ending); diff --git a/src/zeek b/src/zeek deleted file mode 120000 index 945c9b46d6..0000000000 --- a/src/zeek +++ /dev/null @@ -1 +0,0 @@ -. \ No newline at end of file diff --git a/src/zeek-setup.cc b/src/zeek-setup.cc index 44bae3527d..cd7ef7f839 100644 --- a/src/zeek-setup.cc +++ b/src/zeek-setup.cc @@ -16,7 +16,9 @@ #include #include +#ifdef USE_SQLITE #include "zeek/3rdparty/sqlite3.h" +#endif #define DOCTEST_CONFIG_IMPLEMENT @@ -200,7 +202,12 @@ std::shared_ptr zeek::detail::sample_logger; zeek::detail::FragmentManager* zeek::detail::fragment_mgr = nullptr; int signal_val = 0; +#ifdef _MSC_VER +char version[] = VERSION; +#else extern char version[]; +#endif + const char* zeek::detail::command_line_policy = nullptr; vector zeek::detail::params; set requested_plugins; @@ -636,11 +643,12 @@ SetupResult setup(int argc, char** argv, Options* zopts) // FIXME: On systems that don't provide /dev/urandom, OpenSSL doesn't // seed the PRNG. We should do this here (but at least Linux, FreeBSD // and Solaris provide /dev/urandom). - +#ifdef USE_SQLITE int r = sqlite3_initialize(); if ( r != SQLITE_OK ) reporter->Error("Failed to initialize sqlite3: %s", sqlite3_errstr(r)); +#endif timer_mgr = new TimerMgr(); @@ -1112,7 +1120,9 @@ int cleanup(bool did_run_loop) run_state::detail::delete_run(); terminate_zeek(); +#ifdef USE_SQLITE sqlite3_shutdown(); +#endif do_ssl_deinit(); diff --git a/src/zeek.bif b/src/zeek.bif index 7cde8ff023..636dd35067 100644 --- a/src/zeek.bif +++ b/src/zeek.bif @@ -2226,7 +2226,7 @@ function is_local_interface%(ip: addr%) : bool %{ if ( ip->AsAddr().IsLoopback() ) return zeek::val_mgr->True(); - +#ifndef _MSC_VER list addrs; char host[MAXHOSTNAMELEN]; @@ -2259,7 +2259,7 @@ function is_local_interface%(ip: addr%) : bool if ( *it == ip->AsAddr() ) return zeek::val_mgr->True(); } - +#endif return zeek::val_mgr->False(); %} diff --git a/zeek-config.h.in b/zeek-config.h.in index 5e68cff57a..f2aa463686 100644 --- a/zeek-config.h.in +++ b/zeek-config.h.in @@ -108,6 +108,9 @@ /* should we declare syslog() and openlog() */ #cmakedefine SYSLOG_INT +/* should we use stub syslog() and openlog() */ +#cmakedefine USE_STUB_SYSLOG + /* Define if you have */ #cmakedefine HAVE_SYS_TIME_H @@ -132,6 +135,9 @@ /* Use the ElasticSearch writer. */ #cmakedefine USE_ELASTICSEARCH +/* Use the sqlite reader/writer. */ +#cmakedefine USE_SQLITE + /* Version number of package */ #define VERSION "@VERSION@" @@ -184,6 +190,7 @@ #define DLT_NFLOG @DLT_NFLOG@ #endif +#ifndef _MSC_VER /* IPv6 Next Header values defined by RFC 3542 */ #cmakedefine HAVE_IPPROTO_HOPOPTS #ifndef HAVE_IPPROTO_HOPOPTS @@ -225,7 +232,7 @@ #ifndef HAVE_IPPROTO_DSTOPTS #define IPPROTO_DSTOPTS 60 #endif - +#endif /* IPv6 options structure defined by RFC 3542 */ #cmakedefine HAVE_IP6_OPT @@ -264,20 +271,19 @@ extern const char* ZEEK_VERSION_FUNCTION(); #endif #endif -// FreeBSD doesn't support LeakSanitizer #if defined(ZEEK_ASAN) && !defined(__FreeBSD__) - #include - #define ZEEK_LSAN_CHECK(x) __lsan_do_leak_check(x) - #define ZEEK_LSAN_ENABLE(x) __lsan_enable(x) - #define ZEEK_LSAN_IGNORE(x) __lsan_ignore_object(x) - #define ZEEK_LSAN_DISABLE(x) __lsan_disable(x) - #define ZEEK_LSAN_DISABLE_SCOPE(x) __lsan::ScopedDisabler x + #include + #define ZEEK_LSAN_CHECK(...) __lsan_do_leak_check(__VA_ARGS__) + #define ZEEK_LSAN_ENABLE(...) __lsan_enable(__VA_ARGS__) + #define ZEEK_LSAN_IGNORE(...) __lsan_ignore_object(__VA_ARGS__) + #define ZEEK_LSAN_DISABLE(...) __lsan_disable(__VA_ARGS__) + #define ZEEK_LSAN_DISABLE_SCOPE(...) __lsan::ScopedDisabler __VA_ARGS__ #else - #define ZEEK_LSAN_CHECK(x) - #define ZEEK_LSAN_ENABLE(x) - #define ZEEK_LSAN_IGNORE(x) - #define ZEEK_LSAN_DISABLE(x) - #define ZEEK_LSAN_DISABLE_SCOPE(x) + #define ZEEK_LSAN_CHECK(...) + #define ZEEK_LSAN_ENABLE(...) + #define ZEEK_LSAN_IGNORE(...) + #define ZEEK_LSAN_DISABLE(...) + #define ZEEK_LSAN_DISABLE_SCOPE(...) #endif // This part is dependent on calling configure with '--sanitizers=thread' diff --git a/zeek-path-dev.in b/zeek-path-dev.in index 6dcdc71c7c..0c5fa4fbd2 100755 --- a/zeek-path-dev.in +++ b/zeek-path-dev.in @@ -10,4 +10,4 @@ # ZEEKPATH=`./zeek-path-dev` ./src/zeek # -echo .:${PROJECT_SOURCE_DIR}/scripts:${PROJECT_SOURCE_DIR}/scripts/policy:${PROJECT_SOURCE_DIR}/scripts/site:${PROJECT_BINARY_DIR}/scripts:${PROJECT_BINARY_DIR}/scripts/builtin-plugins +echo .:${cmake_source_dir}/scripts:${cmake_source_dir}/scripts/policy:${cmake_source_dir}/scripts/site:${cmake_binary_dir}/scripts:${cmake_binary_dir}/scripts/builtin-plugins