diff options
author | Thiago de Arruda <tpadilha84@gmail.com> | 2014-03-13 12:11:03 -0300 |
---|---|---|
committer | Thiago de Arruda <tpadilha84@gmail.com> | 2014-03-13 15:26:28 -0300 |
commit | f6ace9962d95eb12236083871154c1501f02c556 (patch) | |
tree | f9a1d5b6ca8eaa68114c98dcd92c6161bc15454d | |
parent | 3cac32e49c7fae9cf5963d35f3fd3052c061b2fa (diff) | |
download | rneovim-f6ace9962d95eb12236083871154c1501f02c556.tar.gz rneovim-f6ace9962d95eb12236083871154c1501f02c556.tar.bz2 rneovim-f6ace9962d95eb12236083871154c1501f02c556.zip |
Refactor travis build to use clang's sanitizers
- Valgrind configuration removed
- Fix errors reported by the undefined behavior sanitizer
- Travis will now run two build steps:
- A normal build of a shared library for unit testing(in parallel with gcc)
- A clang build with some sanitizers enabled for integration testing.
After these changes travis will run much faster, while providing valgrind-like
error detection.
-rw-r--r-- | .gitignore | 2 | ||||
-rw-r--r-- | .travis.yml | 7 | ||||
-rw-r--r-- | .valgrind.supp | 7 | ||||
-rw-r--r-- | CMakeLists.txt | 12 | ||||
-rwxr-xr-x | scripts/travis-setup.sh | 19 | ||||
-rwxr-xr-x | scripts/travis.sh | 62 | ||||
-rw-r--r-- | src/CMakeLists.txt | 58 | ||||
-rw-r--r-- | src/eval.c | 2 | ||||
-rw-r--r-- | src/ex_cmds.c | 4 |
9 files changed, 122 insertions, 51 deletions
diff --git a/.gitignore b/.gitignore index 03ced918a5..e33b0ba01e 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,8 @@ # Build/deps dir /build/ +/dist/ /.deps/ +/tmp/ *.rej *.orig diff --git a/.travis.yml b/.travis.yml index 2346f865e1..99de0aeaf4 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,7 +1,8 @@ language: c -script: ./scripts/travis.sh -before_install: - - sudo apt-get install valgrind compiler: - clang - gcc +before_install: + - sudo ./scripts/travis-setup.sh +script: + - ./scripts/travis.sh diff --git a/.valgrind.supp b/.valgrind.supp deleted file mode 100644 index a0a96518ba..0000000000 --- a/.valgrind.supp +++ /dev/null @@ -1,7 +0,0 @@ -{ - nss_parse_service_list - Memcheck:Leak - fun:malloc - fun:nss_parse_service_list - fun:__nss_database_lookup -} diff --git a/CMakeLists.txt b/CMakeLists.txt index c2a2b71915..c5b59ce403 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -10,12 +10,7 @@ set(NEOVIM_VERSION_PATCH 0) set(CMAKE_EXPORT_COMPILE_COMMANDS ON) -# If the C compiler is some GNU-alike, use the gnu99 standard and enable all warnings. -if(CMAKE_COMPILER_IS_GNUCC) - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Werror -Wall -Wextra -pedantic -Wno-unused-parameter -std=gnu99") -elseif(CMAKE_C_COMPILER_ID MATCHES "Clang") - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Werror -Wall -Wextra -pedantic -Wno-unused-parameter -std=gnu99") -endif(CMAKE_COMPILER_IS_GNUCC) +add_definitions(-Werror -Wall -Wextra -pedantic -Wno-unused-parameter -std=gnu99) add_definitions(-DHAVE_CONFIG_H) if(CMAKE_BUILD_TYPE MATCHES Debug) @@ -25,11 +20,6 @@ else() set(DEBUG 0) endif() -if(DEFINED ENV{VALGRIND_CHECK}) - message(STATUS "Defining EXITFREE for valgrind checks") - add_definitions(-DEXITFREE) -endif() - # Modules used by platform auto-detection include(CheckLibraryExists) diff --git a/scripts/travis-setup.sh b/scripts/travis-setup.sh new file mode 100755 index 0000000000..437659dd77 --- /dev/null +++ b/scripts/travis-setup.sh @@ -0,0 +1,19 @@ +#!/bin/sh -e + +# [ "$CC" != "clang" ] && exit + +add-apt-repository -y ppa:ubuntu-toolchain-r/ppa +wget -O - http://llvm.org/apt/llvm-snapshot.gpg.key | apt-key add - + +cat > /etc/apt/sources.list.d/clang.list << "EOF" +deb http://llvm.org/apt/precise/ llvm-toolchain-precise main +deb-src http://llvm.org/apt/precise/ llvm-toolchain-precise main +# 3.4 +deb http://llvm.org/apt/precise/ llvm-toolchain-precise-3.4 main +deb-src http://llvm.org/apt/precise/ llvm-toolchain-precise-3.4 main +# Common +deb http://ppa.launchpad.net/ubuntu-toolchain-r/test/ubuntu precise main +EOF + +apt-get -qq update +apt-get -qq -y --no-install-recommends install clang-3.4 lldb-3.4 diff --git a/scripts/travis.sh b/scripts/travis.sh index 7292953710..fb5a770863 100755 --- a/scripts/travis.sh +++ b/scripts/travis.sh @@ -1,21 +1,49 @@ #!/bin/sh -e -export VALGRIND_CHECK=1 -export BUSTED_OUTPUT_TYPE="TAP" -make cmake CMAKE_EXTRA_FLAGS="-DCMAKE_INSTALL_PREFIX=$PWD/dist" -make -make unittest -echo "Running tests with valgrind..." -if ! make test; then - if ls src/testdir/valgrind.* > /dev/null 2>&1; then - echo "Memory leak detected" >&2 - cat src/testdir/valgrind.* - else - echo "Failed tests:" >&2 - for t in src/testdir/*.failed; do - echo ${t%%.*} - done +check_and_report() { + reset + ( + cd $tmpdir + if [ -f asan.* ] || [ -f tsan.* ] || [ -f ubsan.* ]; then + cat $tmpdir/asan.* 2> /dev/null || true + cat $tmpdir/tsan.* 2> /dev/null || true + cat $tmpdir/ubsan.* 2> /dev/null || true + exit 1 fi - exit 1 + ) +} + +if [ "$CC" = "clang" ]; then + # force using the version installed by 'travis-setup.sh' + export CC=/usr/bin/clang + + install_dir="$(pwd)/dist" + # temporary directory for writing sanitizer logs + tmpdir="$(pwd)/tmp" + rm -rf "$tmpdir" + mkdir -p "$tmpdir" + + # need the symbolizer path for stack traces with source information + symbolizer=/usr/bin/llvm-symbolizer-3.4 + + export SKIP_UNITTEST=1 + export SANITIZE=1 + export ASAN_SYMBOLIZER_PATH=$symbolizer + export ASAN_OPTIONS="detect_leaks=1:log_path=$tmpdir/asan" + export TSAN_OPTIONS="external_symbolizer_path=$symbolizer:log_path=$tmpdir/tsan" + export UBSAN_OPTIONS="log_path=$tmpdir/ubsan" # not sure if this works + + make cmake CMAKE_EXTRA_FLAGS="-DCMAKE_INSTALL_PREFIX=$install_dir" + make + if ! make test; then + check_and_report + fi + check_and_report + make install +else + export BUSTED_OUTPUT_TYPE="TAP" + export SKIP_EXEC=1 + make cmake + make unittest fi -make install + diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 359a9f5180..fecfea8cdf 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -12,8 +12,25 @@ list(APPEND NEOVIM_SOURCES "${PROJECT_BINARY_DIR}/config/auto/pathdef.c") file( GLOB OS_SOURCES os/*.c ) -add_executable (nvim ${NEOVIM_SOURCES} ${OS_SOURCES}) -add_library (nvim-test MODULE ${NEOVIM_SOURCES} ${OS_SOURCES}) +if(CMAKE_C_COMPILER_ID MATCHES "Clang") + if(DEFINED ENV{SANITIZE}) + message(STATUS "Enabling the sanitizers") + add_definitions(-DEXITFREE) # is this necessary for LeakSanitizer? + add_definitions(-fno-sanitize-recover -fno-omit-frame-pointer + -fno-optimize-sibling-calls -fsanitize=address -fsanitize=undefined) + set(CMAKE_EXE_LINKER_FLAGS + "-fsanitize=address -fsanitize=undefined ${CMAKE_EXE_LINKER_FLAGS}") + set(CMAKE_SHARED_LINKER_FLAGS + "-fsanitize=address -fsanitize=undefined ${CMAKE_SHARED_LINKER_FLAGS}") + endif() +endif() + +if(NOT DEFINED ENV{SKIP_EXEC}) + add_executable (nvim ${NEOVIM_SOURCES} ${OS_SOURCES}) +endif() +if(NOT DEFINED ENV{SKIP_UNITTEST}) + add_library (nvim-test MODULE ${NEOVIM_SOURCES} ${OS_SOURCES}) +endif() # The libraries we link against for nvim set(NVIM_LINK_LIBRARIES m ${LibUV_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT}) @@ -28,27 +45,46 @@ if (LibIntl_FOUND) list(APPEND NVIM_LINK_LIBRARIES ${LibIntl_LIBRARY}) endif() -target_link_libraries (nvim ${NVIM_LINK_LIBRARIES}) -target_link_libraries (nvim-test ${NVIM_LINK_LIBRARIES}) +if(NOT DEFINED ENV{SKIP_EXEC}) + target_link_libraries (nvim ${NVIM_LINK_LIBRARIES}) +endif() +if(NOT DEFINED ENV{SKIP_UNITTEST}) + target_link_libraries (nvim-test ${NVIM_LINK_LIBRARIES}) +endif() include(CheckLibraryExists) check_library_exists(termcap tgetent "" HAVE_LIBTERMCAP) if (HAVE_LIBTERMCAP) - target_link_libraries(nvim termcap) - target_link_libraries(nvim-test termcap) + + if(NOT DEFINED ENV{SKIP_EXEC}) + target_link_libraries(nvim termcap) + endif() + if(NOT DEFINED ENV{SKIP_UNITTEST}) + target_link_libraries(nvim-test termcap) + endif() else() check_library_exists(curses tgetent "" HAVE_LIBCURSES) if (HAVE_LIBCURSES) - target_link_libraries(nvim curses) - target_link_libraries(nvim-test curses) + if(NOT DEFINED ENV{SKIP_EXEC}) + target_link_libraries(nvim curses) + endif() + if(NOT DEFINED ENV{SKIP_UNITTEST}) + target_link_libraries(nvim-test curses) + endif() else() find_package(Curses REQUIRED) - target_link_libraries(nvim ${CURSES_LIBRARIES}) - target_link_libraries(nvim-test ${CURSES_LIBRARIES}) + if(NOT DEFINED ENV{SKIP_EXEC}) + target_link_libraries(nvim ${CURSES_LIBRARIES}) + endif() + if(DEFINED ENV{SKIP_UNITTEST}) + target_link_libraries(nvim-test ${CURSES_LIBRARIES}) + endif() endif() endif() include_directories ("${PROJECT_SOURCE_DIR}/src/proto") -install(TARGETS nvim RUNTIME DESTINATION bin) +if(NOT DEFINED ENV{SKIP_EXEC}) + install(TARGETS nvim RUNTIME DESTINATION bin) +endif() diff --git a/src/eval.c b/src/eval.c index b164912c1c..d5ed1b1e04 100644 --- a/src/eval.c +++ b/src/eval.c @@ -4275,7 +4275,7 @@ eval6 ( else if (op == '/') { /* We rely on the floating point library to handle divide * by zero to result in "inf" and not a crash. */ - f1 = f1 / f2; + f1 = f2 != 0 ? f1 / f2 : INFINITY; } else { EMSG(_("E804: Cannot use '%' with Float")); return FAIL; diff --git a/src/ex_cmds.c b/src/ex_cmds.c index 68b5727786..c4da8d65e7 100644 --- a/src/ex_cmds.c +++ b/src/ex_cmds.c @@ -2834,8 +2834,10 @@ do_ecmd ( * <VN> We could instead free the synblock * and re-attach to buffer, perhaps. */ - if (curwin->w_s == &(curwin->w_buffer->b_s)) + if (curwin->w_buffer != NULL && + curwin->w_s == &(curwin->w_buffer->b_s)) curwin->w_s = &(buf->b_s); + curwin->w_buffer = buf; curbuf = buf; ++curbuf->b_nwindows; |