From: Gereon Kremer Date: Thu, 21 Oct 2021 12:31:59 +0000 (-0700) Subject: Working on windows builds (#7381) X-Git-Tag: cvc5-1.0.0~1021 X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=0291f941d4a2bae49a80c3db4afe626b55636fdf;p=cvc5.git Working on windows builds (#7381) This makes a push to fix our windows nightly builds. It does a couple of things: - remove `CVC5_WINDOWS_BUILD` and check `CMAKE_SYSTEM_NAME` instead - use `CMAKE_SHARED_LIBRARY_SUFFIX` instead of `so` - properly set `IMPORTED_IMPLIB` on imported shared libraries - fix the GMP build, where the header is different for shared and static builds - fix the find&sed patching for libpoly - add `CVC5_EXPORT` to nested types in the API - remove `CVC5_EXPORT` from enums - add `-Dcvc5_obj_EXPORTS` to actually enable exports - Fix how template function `safe_print` is exported. --- diff --git a/cmake/ConfigureCvc5.cmake b/cmake/ConfigureCvc5.cmake index 009e9969b..7de13f046 100644 --- a/cmake/ConfigureCvc5.cmake +++ b/cmake/ConfigureCvc5.cmake @@ -59,7 +59,7 @@ check_include_file_cxx(ext/stdio_filebuf.h HAVE_EXT_STDIO_FILEBUF_H) # For Windows builds check if clock_gettime is available via -lpthread # (pthread_time.h). -if(CVC5_WINDOWS_BUILD) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") set(CMAKE_REQUIRED_FLAGS -pthread) check_symbol_exists(clock_gettime "time.h" HAVE_CLOCK_GETTIME) unset(CMAKE_REQUIRED_FLAGS) diff --git a/cmake/FindANTLR3.cmake b/cmake/FindANTLR3.cmake index 60622ab92..772f5f43e 100644 --- a/cmake/FindANTLR3.cmake +++ b/cmake/FindANTLR3.cmake @@ -128,7 +128,7 @@ if(NOT ANTLR3_FOUND_SYSTEM) ${64bit} --host=${TOOLCHAIN_PREFIX} BUILD_BYPRODUCTS /${CMAKE_INSTALL_LIBDIR}/libantlr3c.a - /${CMAKE_INSTALL_LIBDIR}/libantlr3c.so + /${CMAKE_INSTALL_LIBDIR}/libantlr3c${CMAKE_SHARED_LIBRARY_SUFFIX} ) set(ANTLR3_JAR "${DEPS_BASE}/share/java/antlr-3.4-complete.jar") @@ -151,6 +151,9 @@ set_target_properties(ANTLR3_SHARED PROPERTIES IMPORTED_LOCATION "${ANTLR3_LIBRARIES}" INTERFACE_INCLUDE_DIRECTORIES "${ANTLR3_INCLUDE_DIR}" ) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set_target_properties(ANTLR3_SHARED PROPERTIES IMPORTED_IMPLIB "${ANTLR3_LIBRARIES}") +endif() if(ENABLE_STATIC_LIBRARY) add_library(ANTLR3_STATIC STATIC IMPORTED GLOBAL) diff --git a/cmake/FindCryptoMiniSat.cmake b/cmake/FindCryptoMiniSat.cmake index 5b543aedc..b88eaa33e 100644 --- a/cmake/FindCryptoMiniSat.cmake +++ b/cmake/FindCryptoMiniSat.cmake @@ -44,6 +44,12 @@ if(NOT CryptoMiniSat_FOUND_SYSTEM) include(ExternalProject) + if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set(LIBFILENAME "libcryptominisat5win") + else() + set(LIBFILENAME "libcryptominisat5") + endif() + ExternalProject_Add( CryptoMiniSat-EP ${COMMON_EP_CONFIG} @@ -77,7 +83,7 @@ if(NOT CryptoMiniSat_FOUND_SYSTEM) ) set(CryptoMiniSat_INCLUDE_DIR "${DEPS_BASE}/include/") - set(CryptoMiniSat_LIBRARIES "${DEPS_BASE}/${CMAKE_INSTALL_LIBDIR}/libcryptominisat5.a") + set(CryptoMiniSat_LIBRARIES "${DEPS_BASE}/${CMAKE_INSTALL_LIBDIR}/${LIBFILENAME}.a") add_library(CryptoMiniSat STATIC IMPORTED GLOBAL) set_target_properties( diff --git a/cmake/FindGMP.cmake b/cmake/FindGMP.cmake index bd51e8686..6dad15954 100644 --- a/cmake/FindGMP.cmake +++ b/cmake/FindGMP.cmake @@ -48,6 +48,7 @@ if(ENABLE_STATIC_LIBRARY AND GMP_FOUND_SYSTEM) if(NOT GMP_STATIC_LIBRARIES) set(GMP_FOUND_SYSTEM FALSE) endif() + set(GMP_STATIC_INCLUDE_DIR "${GMP_INCLUDE_DIR}") reset_force_static_library() endif() @@ -61,21 +62,63 @@ if(NOT GMP_FOUND_SYSTEM) set(GMP_VERSION "6.2.1") - ExternalProject_Add( - GMP-EP - ${COMMON_EP_CONFIG} - URL https://gmplib.org/download/gmp/gmp-${GMP_VERSION}.tar.bz2 - URL_HASH SHA1=2dcf34d4a432dbe6cce1475a835d20fe44f75822 - CONFIGURE_COMMAND - /configure --prefix= --enable-cxx --with-pic - --enable-shared --enable-static --host=${TOOLCHAIN_PREFIX} - BUILD_BYPRODUCTS /lib/libgmp.a - /lib/libgmp${CMAKE_SHARED_LIBRARY_SUFFIX} - ) + if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + # on windows, the gmp.h is different for shared and static builds. + # we thus need two separate builds. as the configure script taints the + # source folder, we even need two source folders. + ExternalProject_Add( + GMP-EP-shared + ${COMMON_EP_CONFIG} + URL https://gmplib.org/download/gmp/gmp-${GMP_VERSION}.tar.bz2 + URL_HASH SHA1=2dcf34d4a432dbe6cce1475a835d20fe44f75822 + DOWNLOAD_NAME gmp-${GMP_VERSION}-shared.tar.bz2 + CONFIGURE_COMMAND + /configure --enable-shared --disable-static + --prefix=/gmp-shared + --enable-cxx --with-pic --host=${TOOLCHAIN_PREFIX} + BUILD_BYPRODUCTS /lib/libgmp${CMAKE_SHARED_LIBRARY_SUFFIX} + ) + ExternalProject_Add( + GMP-EP-static + ${COMMON_EP_CONFIG} + URL https://gmplib.org/download/gmp/gmp-${GMP_VERSION}.tar.bz2 + URL_HASH SHA1=2dcf34d4a432dbe6cce1475a835d20fe44f75822 + DOWNLOAD_NAME gmp-${GMP_VERSION}-static.tar.bz2 + CONFIGURE_COMMAND + /configure --disable-shared --enable-static + --prefix=/gmp-static + --enable-cxx --with-pic --host=${TOOLCHAIN_PREFIX} + BUILD_BYPRODUCTS /lib/libgmp.a + ) - set(GMP_INCLUDE_DIR "${DEPS_BASE}/include/") - set(GMP_LIBRARIES "${DEPS_BASE}/lib/libgmp${CMAKE_SHARED_LIBRARY_SUFFIX}") - set(GMP_STATIC_LIBRARIES "${DEPS_BASE}/lib/libgmp.a") + add_custom_target(GMP-EP DEPENDS GMP-EP-shared GMP-EP-static) + + set(GMP_INCLUDE_DIR "${DEPS_BASE}/gmp-shared/include/") + set(GMP_STATIC_INCLUDE_DIR "${DEPS_BASE}/gmp-static/include/") + set(GMP_LIBRARIES "${DEPS_BASE}/gmp-shared/bin/libgmp-10${CMAKE_SHARED_LIBRARY_SUFFIX}") + set(GMP_STATIC_LIBRARIES "${DEPS_BASE}/gmp-static/lib/libgmp.a") + + file(MAKE_DIRECTORY "${GMP_INCLUDE_DIR}") + file(MAKE_DIRECTORY "${GMP_STATIC_INCLUDE_DIR}") + else() + ExternalProject_Add( + GMP-EP + ${COMMON_EP_CONFIG} + URL https://gmplib.org/download/gmp/gmp-${GMP_VERSION}.tar.bz2 + URL_HASH SHA1=2dcf34d4a432dbe6cce1475a835d20fe44f75822 + CONFIGURE_COMMAND + /configure --enable-shared --enable-static + --prefix= + --enable-cxx --with-pic --host=${TOOLCHAIN_PREFIX} + BUILD_BYPRODUCTS /lib/libgmp.a + /lib/libgmp${CMAKE_SHARED_LIBRARY_SUFFIX} + ) + + set(GMP_INCLUDE_DIR "${DEPS_BASE}/include/") + set(GMP_STATIC_INCLUDE_DIR "${DEPS_BASE}/include/") + set(GMP_LIBRARIES "${DEPS_BASE}/lib/libgmp${CMAKE_SHARED_LIBRARY_SUFFIX}") + set(GMP_STATIC_LIBRARIES "${DEPS_BASE}/lib/libgmp.a") + endif() endif() set(GMP_FOUND TRUE) @@ -85,12 +128,15 @@ set_target_properties(GMP_SHARED PROPERTIES IMPORTED_LOCATION "${GMP_LIBRARIES}" INTERFACE_INCLUDE_DIRECTORIES "${GMP_INCLUDE_DIR}" ) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set_target_properties(GMP_SHARED PROPERTIES IMPORTED_IMPLIB "${GMP_LIBRARIES}") +endif() if(ENABLE_STATIC_LIBRARY) add_library(GMP_STATIC STATIC IMPORTED GLOBAL) set_target_properties(GMP_STATIC PROPERTIES IMPORTED_LOCATION "${GMP_STATIC_LIBRARIES}" - INTERFACE_INCLUDE_DIRECTORIES "${GMP_INCLUDE_DIR}" + INTERFACE_INCLUDE_DIRECTORIES "${GMP_STATIC_INCLUDE_DIR}" ) endif() diff --git a/cmake/FindPoly.cmake b/cmake/FindPoly.cmake index ae236c6d9..edba3663e 100644 --- a/cmake/FindPoly.cmake +++ b/cmake/FindPoly.cmake @@ -62,15 +62,18 @@ if(NOT Poly_FOUND_SYSTEM) # Roughly following https://stackoverflow.com/a/44383330/2375725 set(patchcmd # Avoid %z and %llu format specifiers - COMMAND find / -type f -exec - sed -i.orig "s/%z[diu]/%\" PRIu64 \"/g" {} + - COMMAND find / -type f -exec - sed -i.orig "s/%ll[du]/%\" PRIu64 \"/g" {} + + COMMAND find / -type f ! -name "*.orig" -exec + sed -i.orig "s/%z[diu]/%\\\" PRIu64 \\\"/g" {} + + COMMAND find / -type f ! -name "*.orig" -exec + sed -i.orig "s/%ll[du]/%\\\" PRIu64 \\\"/g" {} + # Make sure the new macros are available - COMMAND find / -type f -exec - sed -i.orig "s/#include /#include \\n#include /" {} + - COMMAND find / -type f -exec - sed -i.orig "s/#include /#include \\n#include /" {} + + COMMAND find / -type f ! -name "*.orig" -exec + sed -i.orig "s/#include /#include \\\\n#include /" {} + + COMMAND find / -type f ! -name "*.orig" -exec + sed -i.orig "s/#include /#include \\\\n#include /" {} + + # Help with finding GMP + COMMAND sed -i.orig "s/find_library(GMP_LIBRARY gmp)/find_library(GMP_LIBRARY gmp gmp-10)/" + /CMakeLists.txt ) else() unset(patchcmd) @@ -80,6 +83,28 @@ if(NOT Poly_FOUND_SYSTEM) get_target_property(GMP_LIBRARY GMP_SHARED IMPORTED_LOCATION) get_filename_component(GMP_LIB_PATH "${GMP_LIBRARY}" DIRECTORY) + set(POLY_BYPRODUCTS + /lib/libpicpoly.a + /lib/libpicpolyxx.a + /lib/libpoly${CMAKE_SHARED_LIBRARY_SUFFIX} + /lib/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX} + ) + if(CMAKE_SYSTEM_NAME STREQUAL "Darwin") + list(APPEND POLY_BYPRODUCTS + /lib/libpoly.0${CMAKE_SHARED_LIBRARY_SUFFIX} + /lib/libpoly.0.1.9${CMAKE_SHARED_LIBRARY_SUFFIX} + /lib/libpolyxx.0${CMAKE_SHARED_LIBRARY_SUFFIX} + /lib/libpolyxx.0.1.9${CMAKE_SHARED_LIBRARY_SUFFIX} + ) + elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux") + list(APPEND POLY_BYPRODUCTS + /lib/libpoly${CMAKE_SHARED_LIBRARY_SUFFIX}.0 + /lib/libpoly${CMAKE_SHARED_LIBRARY_SUFFIX}.0.1.9 + /lib/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX}.0 + /lib/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX}.0.1.9 + ) + endif() + ExternalProject_Add( Poly-EP ${COMMON_EP_CONFIG} @@ -103,10 +128,7 @@ if(NOT Poly_FOUND_SYSTEM) /lib/libpicpoly.a COMMAND ${CMAKE_COMMAND} -E copy src/libpicpolyxx.a /lib/libpicpolyxx.a - BUILD_BYPRODUCTS /lib/libpicpoly.a - /lib/libpicpolyxx.a - /lib/libpoly${CMAKE_SHARED_LIBRARY_SUFFIX} - /lib/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX} + BUILD_BYPRODUCTS ${POLY_BYPRODUCTS} ) ExternalProject_Add_Step( Poly-EP cleanup @@ -120,6 +142,11 @@ if(NOT Poly_FOUND_SYSTEM) set(PolyXX_LIBRARIES "${DEPS_BASE}/lib/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX}") set(Poly_STATIC_LIBRARIES "${DEPS_BASE}/lib/libpicpoly.a") set(PolyXX_STATIC_LIBRARIES "${DEPS_BASE}/lib/libpicpolyxx.a") + + if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set(Poly_LIBRARIES "${DEPS_BASE}/bin/libpoly${CMAKE_SHARED_LIBRARY_SUFFIX}") + set(PolyXX_LIBRARIES "${DEPS_BASE}/bin/libpolyxx${CMAKE_SHARED_LIBRARY_SUFFIX}") + endif() endif() set(Poly_FOUND TRUE) @@ -129,6 +156,9 @@ set_target_properties(Poly_SHARED PROPERTIES IMPORTED_LOCATION "${Poly_LIBRARIES}" INTERFACE_INCLUDE_DIRECTORIES "${Poly_INCLUDE_DIR}" ) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set_target_properties(Poly_SHARED PROPERTIES IMPORTED_IMPLIB "${Poly_LIBRARIES}") +endif() target_link_libraries(Poly_SHARED INTERFACE GMP_SHARED) add_library(Polyxx_SHARED SHARED IMPORTED GLOBAL) @@ -137,6 +167,9 @@ set_target_properties(Polyxx_SHARED PROPERTIES INTERFACE_INCLUDE_DIRECTORIES "${Poly_INCLUDE_DIR}" INTERFACE_LINK_LIBRARIES Poly_SHARED ) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set_target_properties(Polyxx_SHARED PROPERTIES IMPORTED_IMPLIB "${PolyXX_LIBRARIES}") +endif() if(ENABLE_STATIC_LIBRARY) add_library(Poly_STATIC STATIC IMPORTED GLOBAL) @@ -167,8 +200,10 @@ else() add_dependencies(Poly_SHARED Poly-EP) add_dependencies(Polyxx_SHARED Poly-EP) + ExternalProject_Get_Property(Poly-EP BUILD_BYPRODUCTS INSTALL_DIR) + string(REPLACE "" "${INSTALL_DIR}" BUILD_BYPRODUCTS "${BUILD_BYPRODUCTS}") install(FILES - $ $ + ${BUILD_BYPRODUCTS} DESTINATION ${CMAKE_INSTALL_LIBDIR} ) diff --git a/cmake/Toolchain-mingw64.cmake b/cmake/Toolchain-mingw64.cmake index 5196b7c34..f207875af 100644 --- a/cmake/Toolchain-mingw64.cmake +++ b/cmake/Toolchain-mingw64.cmake @@ -33,4 +33,3 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH) -set(CVC5_WINDOWS_BUILD TRUE) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index a2b5966e1..5bde94a5d 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1308,7 +1308,7 @@ set_source_files_properties(${LIBCVC5_GEN_SRCS} PROPERTIES GENERATED TRUE) # First build the object library add_library(cvc5-obj OBJECT ${LIBCVC5_SRCS} ${LIBCVC5_GEN_SRCS}) -target_compile_definitions(cvc5-obj PRIVATE -D__BUILDING_CVC5LIB) +target_compile_definitions(cvc5-obj PRIVATE -D__BUILDING_CVC5LIB -Dcvc5_obj_EXPORTS) set_target_properties(cvc5-obj PROPERTIES POSITION_INDEPENDENT_CODE ON) # add_dependencies() is necessary for cmake versions before 3.21 add_dependencies(cvc5-obj cvc5base cvc5context) diff --git a/src/api/cpp/cvc5.h b/src/api/cpp/cvc5.h index c46b00d0e..3e8a57d3d 100644 --- a/src/api/cpp/cvc5.h +++ b/src/api/cpp/cvc5.h @@ -1167,7 +1167,7 @@ class CVC5_EXPORT Term * for example, the term f(x, y) will have Kind APPLY_UF and three * children: f, x, and y */ - class const_iterator + class CVC5_EXPORT const_iterator { friend class Term; @@ -2612,7 +2612,7 @@ std::ostream& operator<<(std::ostream& out, const Grammar& g) CVC5_EXPORT; * Standard 754. * \endverbatim */ -enum CVC5_EXPORT RoundingMode +enum RoundingMode { /** * Round to the nearest even number. @@ -2887,7 +2887,7 @@ class CVC5_EXPORT Statistics using BaseType = std::map; /** Custom iterator to hide certain statistics from regular iteration */ - class iterator + class CVC5_EXPORT iterator { public: friend class Statistics; diff --git a/src/api/cpp/cvc5_kind.h b/src/api/cpp/cvc5_kind.h index fe87df934..706dea944 100644 --- a/src/api/cpp/cvc5_kind.h +++ b/src/api/cpp/cvc5_kind.h @@ -43,7 +43,7 @@ namespace api { * depends on the size of `cvc5::Kind` (`NodeValue::NBITS_KIND`, currently 10 * bits, see expr/node_value.h). */ -enum CVC5_EXPORT Kind : int32_t +enum Kind : int32_t { /** * Internal kind. diff --git a/src/api/parsekinds.py b/src/api/parsekinds.py index 0c39bca6f..0dcc7be68 100644 --- a/src/api/parsekinds.py +++ b/src/api/parsekinds.py @@ -34,7 +34,7 @@ US = '_' NL = '\n' # Expected C++ Enum Declarations -ENUM_START = 'enum CVC5_EXPORT Kind' +ENUM_START = 'enum Kind' ENUM_END = CCB + SC # Comments and Macro Tokens diff --git a/src/base/CMakeLists.txt b/src/base/CMakeLists.txt index 8c1c2a714..d2c763159 100644 --- a/src/base/CMakeLists.txt +++ b/src/base/CMakeLists.txt @@ -76,5 +76,5 @@ set_source_files_properties( add_library(cvc5base OBJECT ${LIBBASE_SOURCES}) set_target_properties(cvc5base PROPERTIES POSITION_INDEPENDENT_CODE ON) -target_compile_definitions(cvc5base PRIVATE -D__BUILDING_CVC5LIB) +target_compile_definitions(cvc5base PRIVATE -D__BUILDING_CVC5LIB -Dcvc5_obj_EXPORTS) add_dependencies(cvc5base gen-versioninfo gen-tags) diff --git a/src/context/CMakeLists.txt b/src/context/CMakeLists.txt index 00b4d91ee..482dc6acc 100644 --- a/src/context/CMakeLists.txt +++ b/src/context/CMakeLists.txt @@ -35,4 +35,4 @@ set(LIBCONTEXT_SOURCES add_library(cvc5context OBJECT ${LIBCONTEXT_SOURCES}) set_target_properties(cvc5context PROPERTIES POSITION_INDEPENDENT_CODE ON) -target_compile_definitions(cvc5context PRIVATE -D__BUILDING_CVC5LIB) +target_compile_definitions(cvc5context PRIVATE -D__BUILDING_CVC5LIB -Dcvc5_obj_EXPORTS) diff --git a/src/options/language.h b/src/options/language.h index 05756f98f..2bf596124 100644 --- a/src/options/language.h +++ b/src/options/language.h @@ -25,7 +25,7 @@ namespace cvc5 { -enum class CVC5_EXPORT Language +enum class Language { // SPECIAL "NON-LANGUAGE" LANGUAGES HAVE ENUM VALUE < 0 diff --git a/src/parser/CMakeLists.txt b/src/parser/CMakeLists.txt index eed5b53c9..eeae442a4 100644 --- a/src/parser/CMakeLists.txt +++ b/src/parser/CMakeLists.txt @@ -100,7 +100,7 @@ endforeach() add_library(cvc5parser-objs OBJECT ${libcvc5parser_src_files}) set_target_properties(cvc5parser-objs PROPERTIES POSITION_INDEPENDENT_CODE ON) -target_compile_definitions(cvc5parser-objs PUBLIC -D__BUILDING_CVC5PARSERLIB) +target_compile_definitions(cvc5parser-objs PUBLIC -D__BUILDING_CVC5PARSERLIB -Dcvc5_obj_EXPORTS) add_dependencies(cvc5parser-objs ANTLR3_SHARED) target_include_directories(cvc5parser-objs PRIVATE ${ANTLR3_INCLUDE_DIR}) @@ -109,7 +109,11 @@ add_library(cvc5parser-shared SHARED $) set_target_properties(cvc5parser-shared PROPERTIES SOVERSION ${CVC5_SOVERSION}) set_target_properties(cvc5parser-shared PROPERTIES OUTPUT_NAME cvc5parser) target_link_libraries(cvc5parser-shared PRIVATE cvc5-shared) -target_link_libraries(cvc5parser-shared PRIVATE ANTLR3_SHARED) +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + target_link_libraries(cvc5parser-shared PRIVATE ANTLR3_STATIC) +else() + target_link_libraries(cvc5parser-shared PRIVATE ANTLR3_SHARED) +endif() install(TARGETS cvc5parser-shared EXPORT cvc5-targets @@ -131,7 +135,7 @@ endif() # unresolved symbols when linking against libcvc5parser. # -Wl,--export-all-symbols makes sure that all symbols are exported when # building a DLL. -if(CVC5_WINDOWS_BUILD) - set_target_properties(cvc5parser +if(CMAKE_SYSTEM_NAME STREQUAL "Windows") + set_target_properties(cvc5parser-objs PROPERTIES LINK_FLAGS "-Wl,--export-all-symbols") endif() diff --git a/src/util/safe_print.h b/src/util/safe_print.h index e3280bb55..0bc2b0599 100644 --- a/src/util/safe_print.h +++ b/src/util/safe_print.h @@ -47,12 +47,17 @@ namespace cvc5 { +template +void CVC5_EXPORT safe_print(int fd, const char (&msg)[N]); +template +void CVC5_EXPORT safe_print(int fd, const T& obj); + /** * Prints arrays of chars (e.g. string literals) of length N. Safe to use in a * signal handler. */ template -void CVC5_EXPORT safe_print(int fd, const char (&msg)[N]) +void safe_print(int fd, const char (&msg)[N]) { ssize_t nb = N - 1; if (write(fd, msg, nb) != nb) { @@ -96,7 +101,7 @@ auto toStringImpl(const T& obj, int) -> decltype(toString(obj)) * @param obj The object to print */ template -void CVC5_EXPORT safe_print(int fd, const T& obj) +void safe_print(int fd, const T& obj) { const char* s = toStringImpl(obj, /* prefer the method that uses `toString()` */ 0);