diff --git a/test/unit-test/catch_assert.h b/test/unit-test/catch_assert.h index acfc6b420..99b11697c 100644 --- a/test/unit-test/catch_assert.h +++ b/test/unit-test/catch_assert.h @@ -37,41 +37,47 @@ #include #include -#ifndef CATCH_JMPBUF - #define CATCH_JMPBUF waypoint_ -#endif - -static jmp_buf CATCH_JMPBUF; +/* Global state apology: Sigaction offers no context. */ +static sigjmp_buf catch_waypoint; #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wunused-function" -static void catchHandler_( int signal ) +static void catch_rollBack( int signal ) +{ + siglongjmp( catch_waypoint, signal ); +} +static void catch_setSigabrtHandler( void ) +{ + struct sigaction sa = { 0 }; + + sa.sa_handler = catch_rollBack; + sigaction( SIGABRT, &sa, NULL ); +} +static int catch_saveStderr() +{ + int savedStderr = dup( 2 ); + + close( 2 ); + return savedStderr; +} +static void catch_restoreStderr( int savedStderr ) { - longjmp( CATCH_JMPBUF, signal ); + dup2( savedStderr, 2 ); + close( savedStderr ); } #pragma GCC diagnostic pop -#define catch_assert( x ) \ - do { \ - int ltry = 0, lcatch = 0; \ - int saveFd = dup( 2 ); \ - struct sigaction sa = { 0 }, saveSa; \ - sa.sa_handler = catchHandler_; \ - sigaction( SIGABRT, &sa, &saveSa ); \ - close( 2 ); \ - if( setjmp( CATCH_JMPBUF ) == 0 ) \ - { \ - ltry++; \ - x; \ - } \ - else \ - { \ - lcatch++; \ - } \ - sigaction( SIGABRT, &saveSa, NULL ); \ - dup2( saveFd, 2 ); \ - close( saveFd ); \ - TEST_ASSERT_EQUAL( ltry, lcatch ); \ +#define catch_assert( x ) \ + do { \ + int catch_stderr = catch_saveStderr(); \ + int catch_signal = sigsetjmp( catch_waypoint, 1 ); \ + if( catch_signal == 0 ) \ + { \ + catch_setSigabrtHandler(); \ + x; \ + } \ + catch_restoreStderr( catch_stderr ); \ + TEST_ASSERT_EQUAL( SIGABRT, catch_signal ); \ } while( 0 ) #endif /* ifndef CATCH_ASSERT_H_ */