From ef1bf44531b260c5ae8f316797255e6f90eada0d Mon Sep 17 00:00:00 2001 From: "Joachim Wuttke (h)" <j.wuttke@fz-juelich.de> Date: Wed, 5 Aug 2020 20:22:25 +0200 Subject: [PATCH] tAsserts now works with qFatal --- CMakeLists.txt | 2 +- Core/Basics/Assert.h | 21 ++++---- Core/CMakeLists.txt | 4 ++ GUI/main/CMakeLists.txt | 4 +- GUI/main/MessageHandler.cpp | 62 ++++++++++++++++++++++ GUI/main/MessageHandler.h | 17 ++++++ GUI/main/main.cpp | 5 +- Tests/UnitTests/Core/Basics/TestAssert.cpp | 6 ++- Tests/UnitTests/Core/CMakeLists.txt | 7 ++- 9 files changed, 107 insertions(+), 21 deletions(-) create mode 100644 GUI/main/MessageHandler.cpp create mode 100644 GUI/main/MessageHandler.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 96d6befb381..5ed494eb306 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -67,6 +67,7 @@ if(ZERO_TOLERANCE) set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Werror -Wfatal-errors") endif() if(BORNAGAIN_GUI) + include(SearchQt) set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DQT_MESSAGELOGCONTEXT=ON") endif() include(BornAgainConfiguration) @@ -108,7 +109,6 @@ add_subdirectory(Tests/UnitTests/Numeric) add_subdirectory(Tests/Performance/Core) if(BORNAGAIN_GUI) - include(SearchQt) add_subdirectory(ThirdParty/GUI) add_subdirectory(GUI) add_subdirectory(Tests/UnitTests/GUI) diff --git a/Core/Basics/Assert.h b/Core/Basics/Assert.h index b9a2d457f1d..fd0e15b53c4 100644 --- a/Core/Basics/Assert.h +++ b/Core/Basics/Assert.h @@ -15,22 +15,19 @@ #ifndef BORNAGAIN_CORE_BASICS_ASSERT_H #define BORNAGAIN_CORE_BASICS_ASSERT_H -#ifdef BORNAGAIN_GUI +// ASSERT must be declared as a macro, not a function, in order for the error +// message to correctly report the source line where the assertion failed. + +#ifdef QT_MESSAGELOGCONTEXT #include <QtGlobal> -#define ASSERT(condition) \ - if (!(condition)) \ - qFatal("assertion failed"); +#define ASSERT(condition) if (!(condition)) qFatal("Assertion failed") -#else // The non-GUI case is used by our test suite +#else // QT_MESSAGELOGCONTEXT undefined -#include <iostream> -#define ASSERT(condition) \ - if (!(condition)) { \ - std::cerr << "assertion failed" << std::endl; \ - exit(1); \ - } +#include <cassert> +#define ASSERT(condition) assert(condition) -#endif // BORNAGAIN_GUI +#endif // QT_MESSAGELOGCONTEXT #endif // BORNAGAIN_CORE_BASICS_ASSERT_H diff --git a/Core/CMakeLists.txt b/Core/CMakeLists.txt index 505ae524815..546a2dfae39 100644 --- a/Core/CMakeLists.txt +++ b/Core/CMakeLists.txt @@ -154,6 +154,10 @@ target_include_directories(${library_name} ${CMAKE_SOURCE_DIR}/ThirdParty/Core/cerf_wrapper # TEMPORARY SYSTEM PUBLIC ${EIGEN3_INCLUDE_DIRS} ) +if(BORNAGAIN_GUI) + target_include_directories(${library_name} PUBLIC ${Qt5Core_INCLUDE_DIRS}) +endif() + target_link_libraries(${library_name} ${Boost_LIBRARIES} ${FFTW3_LIBRARIES} ${GSL_LIBRARIES} ${tspectrum_LIBRARY} ${Cerf_LIBRARIES}) diff --git a/GUI/main/CMakeLists.txt b/GUI/main/CMakeLists.txt index 3e2450a18db..2acb75efd7c 100644 --- a/GUI/main/CMakeLists.txt +++ b/GUI/main/CMakeLists.txt @@ -3,8 +3,8 @@ ############################################################################### set(executable_name BornAgain) -set(source_files main.cpp appoptions.cpp) -set(include_files appoptions.h) +set(source_files main.cpp appoptions.cpp MessageHandler.cpp) +set(include_files appoptions.h MessageHandler.h ) # ----------------------------------------------------------------------------- # Qt configuration diff --git a/GUI/main/MessageHandler.cpp b/GUI/main/MessageHandler.cpp new file mode 100644 index 00000000000..db6b72c797c --- /dev/null +++ b/GUI/main/MessageHandler.cpp @@ -0,0 +1,62 @@ +// ************************************************************************** // +// +// BornAgain: simulate and fit scattering at grazing incidence +// +//! @file GUI/main/MessageHandler.cpp +//! @brief Implements function MessageHandler +//! +//! @homepage http://www.bornagainproject.org +//! @license GNU General Public License v3 or higher (see COPYING) +//! @copyright Forschungszentrum Jülich GmbH 2018 +//! @authors Scientific Computing Group at MLZ (see CITATION, AUTHORS) +// +// ************************************************************************** // + +#include "GUI/main/MessageHandler.h" +#include <iostream> +#include <QMessageBox> + +#ifndef QT_NO_DEBUG +#define context(ctx) " [" << ctx.function << "]" +#else +#define context(ctx) "" +#endif + +//! This is set by main to be the message handler of our GUI. +void MessageHandler(QtMsgType type, const QMessageLogContext& ctx, const QString& msg) +{ + switch (type) { + case QtDebugMsg: + if (!msg.size()) // KDE will pass a zero-length msg qstring + break; + std::cerr << "DEBUG: " << msg.toStdString() << std::endl; + break; + case QtInfoMsg: + std::cerr << "INFO: " << msg.toStdString() << context(ctx) << std::endl; + break; + case QtWarningMsg: + default: + if (msg.left(4) == "QXcb") + return; + std::cerr << "WARNING: " << msg.toStdString() << " [" << ctx.function << "]" + << std::endl; + QMessageBox::warning(QApplication::activeWindow(), qAppName(), msg); + break; + case QtFatalMsg: + std::cerr << "FATAL: " << msg.toStdString() << " [" << ctx.function << "]" << std::endl; + qApp->restoreOverrideCursor(); + QMessageBox::critical( + QApplication::activeWindow(), qAppName(), + "Sorry, you encountered a fatal bug.\n" + "The application will terminate.\n" + "Please note the following and inform the maintainers.\n\n" + "Error:\n" + + msg + + "\n" + "Context:\n" + + ctx.function + "\n" + ); + qApp->quit(); + exit(1); + } +} diff --git a/GUI/main/MessageHandler.h b/GUI/main/MessageHandler.h new file mode 100644 index 00000000000..961d4248d01 --- /dev/null +++ b/GUI/main/MessageHandler.h @@ -0,0 +1,17 @@ +// ************************************************************************** // +// +// BornAgain: simulate and fit scattering at grazing incidence +// +//! @file GUI/main/MessageHandler.cpp +//! @brief Declares function MessageHandler +//! +//! @homepage http://www.bornagainproject.org +//! @license GNU General Public License v3 or higher (see COPYING) +//! @copyright Forschungszentrum Jülich GmbH 2018 +//! @authors Scientific Computing Group at MLZ (see CITATION, AUTHORS) +// +// ************************************************************************** // + +#include <QApplication> + +void MessageHandler(QtMsgType type, const QMessageLogContext& ctx, const QString& msg); diff --git a/GUI/main/main.cpp b/GUI/main/main.cpp index 9b6d77f59c3..e997a45ba59 100644 --- a/GUI/main/main.cpp +++ b/GUI/main/main.cpp @@ -17,7 +17,7 @@ #include "GUI/coregui/mainwindow/mainwindow.h" #include "GUI/coregui/utils/hostosinfo.h" #include "GUI/main/appoptions.h" -#include <QApplication> +#include "GUI/main/MessageHandler.h" #include <QLocale> #include <QMetaType> @@ -37,8 +37,7 @@ int main(int argc, char* argv[]) QApplication app(argc, argv); - if (!options.find("with-debug")) - qInstallMessageHandler(messageHandler); + qInstallMessageHandler(MessageHandler); std::unique_ptr<SplashScreen> splash; if (!options.find("no-splash")) { diff --git a/Tests/UnitTests/Core/Basics/TestAssert.cpp b/Tests/UnitTests/Core/Basics/TestAssert.cpp index e52a734c12d..06ef68b29c7 100644 --- a/Tests/UnitTests/Core/Basics/TestAssert.cpp +++ b/Tests/UnitTests/Core/Basics/TestAssert.cpp @@ -8,5 +8,9 @@ class TestAssert : public ::testing::Test TEST_F(TestAssert, Assert) { EXPECT_NO_THROW(ASSERT(1)); - EXPECT_EXIT(ASSERT(0), ::testing::ExitedWithCode(1), "assertion failed"); +#ifdef QT_MESSAGELOGCONTEXT + EXPECT_EXIT(ASSERT(0), ::testing::KilledBySignal(6), "Assertion failed"); +#else + EXPECT_EXIT(ASSERT(0), ::testing::KilledBySignal(6), "Assertion .* failed"); +#endif } diff --git a/Tests/UnitTests/Core/CMakeLists.txt b/Tests/UnitTests/Core/CMakeLists.txt index 294b8fcd3ee..6e312354ee6 100644 --- a/Tests/UnitTests/Core/CMakeLists.txt +++ b/Tests/UnitTests/Core/CMakeLists.txt @@ -2,11 +2,14 @@ include(GoogleTest) # provides gtest_discover_tests set(test UnitTestCore) -include_directories(${CMAKE_SOURCE_DIR}/Tests/UnitTests/utilities) - file(GLOB source_files "*/*.cpp" ${CMAKE_SOURCE_DIR}/Tests/GTestWrapper/TestAll.cpp) add_executable(${test} ${source_files}) +target_include_directories(${test} PUBLIC ${CMAKE_SOURCE_DIR}/Tests/UnitTests/utilities) target_link_libraries(${test} ${BornAgainCore_LIBRARY} gtest) +if(BORNAGAIN_GUI) + target_include_directories(${test} PUBLIC ${Qt5Core_INCLUDE_DIRS}) + target_link_libraries(${test} ${Qt5Core_LIBRARIES}) +endif() gtest_discover_tests(${test} TEST_PREFIX Core.Unit.) -- GitLab