From 2d359fee545d0fdeae5b5bb6c0f98872fa467f69 Mon Sep 17 00:00:00 2001 From: proller Date: Fri, 23 Jun 2017 17:41:07 +0300 Subject: [PATCH] Make libunwind optional. Allow use custom libcctz (#920) * Make libunwind optional. Allow use custom libcctz * fix * Fix * fix * Update BaseDaemon.cpp * Update CMakeLists.txt --- CMakeLists.txt | 8 +++++ contrib/CMakeLists.txt | 9 ++++-- contrib/libcctz/CMakeLists.txt | 2 +- libs/libcommon/CMakeLists.txt | 5 +-- libs/libcommon/cmake/find_cctz.cmake | 17 +++++++++++ libs/libdaemon/CMakeLists.txt | 8 +++-- libs/libdaemon/cmake/find_unwind.cmake | 42 ++++++++++++++++++++++++++ libs/libdaemon/src/BaseDaemon.cpp | 27 ++++++++++++++--- 8 files changed, 107 insertions(+), 11 deletions(-) create mode 100644 libs/libcommon/cmake/find_cctz.cmake create mode 100644 libs/libdaemon/cmake/find_unwind.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 8c21c1112ff..c074fcb3c87 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -149,6 +149,10 @@ if (UNBUNDLED) else () set(NOT_UNBUNDLED 1) endif () +# Using system libs can cause lot of warnings in includes. +if (UNBUNDLED OR NOT (CMAKE_SYSTEM MATCHES "Linux" OR APPLE)) + option (NO_WERROR "Disable -Werror compiler option" ON) +endif () message (STATUS "Building for: ${CMAKE_SYSTEM} ${CMAKE_SYSTEM_PROCESSOR} ${CMAKE_LIBRARY_ARCHITECTURE} ; USE_STATIC_LIBRARIES=${USE_STATIC_LIBRARIES} MAKE_STATIC_LIBRARIES=${MAKE_STATIC_LIBRARIES} UNBUNDLED=${UNBUNDLED}") @@ -173,9 +177,13 @@ include (cmake/find_readline_edit.cmake) include (cmake/find_zookeeper.cmake) include (cmake/find_double-conversion.cmake) include (cmake/find_re2.cmake) +# Need to process before "contrib" dir: include (libs/libcommon/cmake/find_gperftools.cmake) include (libs/libcommon/cmake/find_jemalloc.cmake) +include (libs/libcommon/cmake/find_cctz.cmake) include (libs/libmysqlxx/cmake/find_mysqlclient.cmake) +include (libs/libdaemon/cmake/find_unwind.cmake) + set (FULL_C_FLAGS "${CMAKE_C_FLAGS} ${CMAKE_C_FLAGS_${CMAKE_BUILD_TYPE}}") set (FULL_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${CMAKE_CXX_FLAGS_${CMAKE_BUILD_TYPE}}") diff --git a/contrib/CMakeLists.txt b/contrib/CMakeLists.txt index 855751ea336..1467bd02891 100644 --- a/contrib/CMakeLists.txt +++ b/contrib/CMakeLists.txt @@ -32,13 +32,18 @@ add_subdirectory (libcityhash) add_subdirectory (libfarmhash) add_subdirectory (libmetrohash) add_subdirectory (libbtrie) -add_subdirectory (libunwind) + +if (USE_INTERNAL_UNWIND_LIBRARY) + add_subdirectory (libunwind) +endif () if (USE_INTERNAL_ZLIB_LIBRARY) add_subdirectory (libzlib-ng) endif () -add_subdirectory (libcctz) +if (USE_INTERNAL_CCTZ_LIBRARY) + add_subdirectory (libcctz) +endif () if (ENABLE_LIBTCMALLOC AND USE_INTERNAL_GPERFTOOLS_LIBRARY) add_subdirectory (libtcmalloc) diff --git a/contrib/libcctz/CMakeLists.txt b/contrib/libcctz/CMakeLists.txt index e7d70f57b8d..14767e6c7f7 100644 --- a/contrib/libcctz/CMakeLists.txt +++ b/contrib/libcctz/CMakeLists.txt @@ -1,7 +1,7 @@ include_directories (include) if (CMAKE_SYSTEM MATCHES "FreeBSD") - #yes, need linux, bacause bsd check inside linux in time_zone_libc.cc:24 + # yes, need linux, because bsd check inside linux in time_zone_libc.cc:24 add_definitions (-D__USE_BSD -Dlinux -D_XOPEN_SOURCE=600) endif () diff --git a/libs/libcommon/CMakeLists.txt b/libs/libcommon/CMakeLists.txt index 5d86ac068c8..6cec22e2d7d 100644 --- a/libs/libcommon/CMakeLists.txt +++ b/libs/libcommon/CMakeLists.txt @@ -1,5 +1,4 @@ include_directories (include) -include_directories (BEFORE ${ClickHouse_SOURCE_DIR}/contrib/libcctz/include) include(${ClickHouse_SOURCE_DIR}/cmake/dbms_include.cmake) @@ -79,10 +78,12 @@ endif () find_package (Threads) +target_include_directories (common PRIVATE ${CCTZ_INCLUDE_DIR}) + target_link_libraries ( common pocoext - cctz + ${CCTZ_LIBRARY} ${Boost_SYSTEM_LIBRARY} ${Boost_FILESYSTEM_LIBRARY} ${MALLOC_LIBRARIES} diff --git a/libs/libcommon/cmake/find_cctz.cmake b/libs/libcommon/cmake/find_cctz.cmake new file mode 100644 index 00000000000..807cb9eb56c --- /dev/null +++ b/libs/libcommon/cmake/find_cctz.cmake @@ -0,0 +1,17 @@ +option (USE_INTERNAL_CCTZ_LIBRARY "Set to FALSE to use system cctz library instead of bundled" ${NOT_UNBUNDLED}) + +if (NOT USE_INTERNAL_CCTZ_LIBRARY) + find_library (CCTZ_LIBRARY cctz) + find_path (CCTZ_INCLUDE_DIR NAMES civil_time.h PATHS ${CCTZ_INCLUDE_PATHS}) +endif () + +if (CCTZ_LIBRARY AND CCTZ_INCLUDE_DIR) + #include_directories (${CCTZ_INCLUDE_DIR}) +else () + set (USE_INTERNAL_CCTZ_LIBRARY 1) + set (CCTZ_INCLUDE_DIR "${ClickHouse_SOURCE_DIR}/contrib/libcctz/include") + #include_directories (BEFORE ${CCTZ_INCLUDE_DIR}) + set (CCTZ_LIBRARY cctz) +endif () + +message (STATUS "Using cctz: ${CCTZ_INCLUDE_DIR} : ${CCTZ_LIBRARY}") diff --git a/libs/libdaemon/CMakeLists.txt b/libs/libdaemon/CMakeLists.txt index 8c857a3a855..7f296a8a264 100644 --- a/libs/libdaemon/CMakeLists.txt +++ b/libs/libdaemon/CMakeLists.txt @@ -1,5 +1,4 @@ include_directories (include) -include_directories (${ClickHouse_SOURCE_DIR}/contrib/libunwind/include) include(${ClickHouse_SOURCE_DIR}/cmake/dbms_include.cmake) add_library (daemon @@ -12,4 +11,9 @@ add_library (daemon include/daemon/OwnPatternFormatter.h ) -target_link_libraries (daemon dbms unwind) +if (USE_UNWIND) + target_include_directories (daemon BEFORE PRIVATE ${UNWIND_INCLUDE_DIR}) + add_definitions(-DUSE_UNWIND=1) + target_link_libraries (daemon ${UNWIND_LIBRARY}) +endif () +target_link_libraries (daemon dbms) diff --git a/libs/libdaemon/cmake/find_unwind.cmake b/libs/libdaemon/cmake/find_unwind.cmake new file mode 100644 index 00000000000..3b81462bd5b --- /dev/null +++ b/libs/libdaemon/cmake/find_unwind.cmake @@ -0,0 +1,42 @@ +if (CMAKE_SYSTEM MATCHES "Linux") + option (USE_INTERNAL_UNWIND_LIBRARY "Set to FALSE to use system unwind library instead of bundled" ${NOT_UNBUNDLED}) +else () + option (USE_INTERNAL_UNWIND_LIBRARY "Set to FALSE to use system unwind library instead of bundled" OFF) +endif () + +if (NOT USE_INTERNAL_UNWIND_LIBRARY) + find_library (UNWIND_LIBRARY unwind) + find_path (UNWIND_INCLUDE_DIR NAMES unwind.h PATHS ${UNWIND_INCLUDE_PATHS}) + + include (CheckCXXSourceCompiles) + set(CMAKE_REQUIRED_INCLUDES ${UNWIND_INCLUDE_DIR}) + set(CMAKE_REQUIRED_LIBRARIES ${UNWIND_LIBRARY}) + check_cxx_source_compiles(" + #include + #include + int main () { + ucontext_t context; + unw_cursor_t cursor; + unw_init_local_signal(&cursor, &context); + return 0; + } + " HAVE_UNWIND_INIT_LOCAL_SIGNAL) + if (NOT HAVE_UNWIND_INIT_LOCAL_SIGNAL) + set(UNWIND_LIBRARY "") + set(UNWIND_INCLUDE_DIR "") + endif () + +endif () + +if (UNWIND_LIBRARY AND UNWIND_INCLUDE_DIR) + #include_directories (${UNWIND_INCLUDE_DIR}) + set (USE_UNWIND 1) +elseif (CMAKE_SYSTEM MATCHES "Linux") + set (USE_INTERNAL_UNWIND_LIBRARY 1) + set (UNWIND_INCLUDE_DIR "${ClickHouse_SOURCE_DIR}/contrib/libunwind/include") + #include_directories (BEFORE ${UNWIND_INCLUDE_DIR}) + set (UNWIND_LIBRARY unwind) + set (USE_UNWIND 1) +endif () + +message (STATUS "Using unwind=${USE_UNWIND}: ${UNWIND_INCLUDE_DIR} : ${UNWIND_LIBRARY}") diff --git a/libs/libdaemon/src/BaseDaemon.cpp b/libs/libdaemon/src/BaseDaemon.cpp index 51bc500881a..2f033d1c282 100644 --- a/libs/libdaemon/src/BaseDaemon.cpp +++ b/libs/libdaemon/src/BaseDaemon.cpp @@ -12,8 +12,10 @@ #include #include -#define UNW_LOCAL_ONLY -#include +#if USE_UNWIND + #define UNW_LOCAL_ONLY + #include +#endif #ifdef __APPLE__ // ucontext is not available without _XOPEN_SOURCE @@ -179,7 +181,7 @@ static void faultSignalHandler(int sig, siginfo_t * info, void * context) static bool already_printed_stack_trace = false; - +#if USE_UNWIND size_t backtraceLibUnwind(void ** out_frames, size_t max_frames, ucontext_t & context) { if (already_printed_stack_trace) @@ -202,7 +204,7 @@ size_t backtraceLibUnwind(void ** out_frames, size_t max_frames, ucontext_t & co return i; } - +#endif /** Получает информацию через pipe. * При получении сигнала HUP / USR1 закрывает лог-файлы. @@ -322,10 +324,27 @@ private: static const int max_frames = 50; void * frames[max_frames]; + + + + + + +#if USE_UNWIND int frames_size = backtraceLibUnwind(frames, max_frames, context); if (frames_size) { +#else + int frames_size = backtrace(frames, max_frames); + + if (frames_size >= 2) + { + /// Overwrite sigaction with caller's address + if (caller_address && (frames_size < 3 || caller_address != frames[2])) + frames[1] = caller_address; +#endif + char ** symbols = backtrace_symbols(frames, frames_size); if (!symbols)