Compare commits

...

15 Commits

Author SHA1 Message Date
Benoit Blanchon
908c370f24 Fix error: ISO C++ forbids in-class initialization of non-const static member 'm_started' 2023-01-18 11:10:26 +01:00
Golubchikov Mihail
6c6cfe126a Backport fix for SIGSTKSZ 2022-07-15 16:13:12 +02:00
Martin Hořeňovský
72df457bab Merge pull request #2151 from fxcoudert/patch-1
Update catch_debugger.h for Apple Silicon
2021-01-13 18:16:54 +01:00
FX Coudert
bb6d08323f Update catch_debugger.h 2021-01-11 12:22:22 +01:00
Vadim Zeitlin
64a533551d Enable variadic macros support for MSVS 2005 as it has them
Fix the test for MSVC version: variadic macros support is available
since MSVS 2005, a.k.a. MSVC 8, using _MSC_VER=1400.
2019-09-06 11:45:32 +02:00
Mapping Suite
c32f275a00 Fix link to catch.hpp in tutorial.md 2018-12-18 18:19:29 +01:00
Martin Hořeňovský
6860c8def0 v1.12.2 2018-05-14 15:15:28 +02:00
Martin Hořeňovský
3255ee6312 Add missing <cassert> includes
Until recently we were probably getting it from some transitive
include, but it broke. Because all files should include what
they use anyway, adding `#include <cassert>` to all files that
use `assert()` without including it is the best solution.

Fixes #1249
2018-04-22 20:36:41 +02:00
Martin Hořeňovský
74effafca7 v1.12.1 2018-03-02 21:22:10 +01:00
Martin Hořeňovský
7d0cfd27ce Fix deprecation warning in ~ScopedMessage 2018-02-25 21:29:01 +01:00
Martin Hořeňovský
3fe4d394a5 Wrap all uses in min and max in extra parentheses
This prevents `min` and `max` macros from windows headers (!@#$)
from breaking compilation.

Related to #1191
2018-02-23 13:06:52 +01:00
Martin Hořeňovský
b97e9a2f8b Update path for catch-classic vcpkg's portfile 2018-01-12 11:06:09 +01:00
Martin Hořeňovský
34f7cfe046 v1.12.0 2018-01-12 09:59:21 +01:00
Martin Hořeňovský
07b9bda1d2 Revert backport of new evaluate layer to fix C++98 compilation
The backport fixed some bugs (ie #981), but caused strict C++98
(and MSVC 9) compilers to fail. This means that we will
reintroduce some issues but get back compatibility with obsolete
compilers. People using newer ones can keep using Catch2.

This reverts commit b6e7c9bd7a.
This reverts commit b7bd52cc98.

Should fix #1103
2017-12-07 20:02:47 +01:00
Phil Nash
84e8b696b1 Include Info messages in xml reporter even without -s 2017-12-06 16:11:12 +00:00
20 changed files with 536 additions and 219 deletions

View File

@@ -3,9 +3,9 @@
[![Github Releases](https://img.shields.io/github/release/philsquared/catch.svg)](https://github.com/philsquared/catch/releases) [![Github Releases](https://img.shields.io/github/release/philsquared/catch.svg)](https://github.com/philsquared/catch/releases)
[![Build Status](https://travis-ci.org/philsquared/Catch.svg?branch=master)](https://travis-ci.org/philsquared/Catch) [![Build Status](https://travis-ci.org/philsquared/Catch.svg?branch=master)](https://travis-ci.org/philsquared/Catch)
[![Build status](https://ci.appveyor.com/api/projects/status/hrtk60hv6tw6fght/branch/master?svg=true)](https://ci.appveyor.com/project/philsquared/catch/branch/master) [![Build status](https://ci.appveyor.com/api/projects/status/hrtk60hv6tw6fght/branch/master?svg=true)](https://ci.appveyor.com/project/philsquared/catch/branch/master)
[![Try online](https://img.shields.io/badge/try-online-blue.svg)](https://wandbox.org/permlink/EyEbEIfp8CnnjguW) [![Try online](https://img.shields.io/badge/try-online-blue.svg)](https://wandbox.org/permlink/jG7wnHX9VAcxpSHy)
<a href="https://github.com/philsquared/Catch/releases/download/v1.11.0/catch.hpp">The latest, single header, version can be downloaded directly using this link</a> <a href="https://github.com/philsquared/Catch/releases/download/v1.12.2/catch.hpp">The latest, single header, version can be downloaded directly using this link</a>
## What's the Catch? ## What's the Catch?

View File

@@ -4,7 +4,7 @@ from conans import ConanFile
class CatchConan(ConanFile): class CatchConan(ConanFile):
name = "Catch" name = "Catch"
version = "1.11.0" version = "1.12.2"
description = "A modern, C++-native, header-only, framework for unit-tests, TDD and BDD" description = "A modern, C++-native, header-only, framework for unit-tests, TDD and BDD"
author = "philsquared" author = "philsquared"
generators = "cmake" generators = "cmake"

View File

@@ -1,3 +1,24 @@
# 1.12.2
### Fixes
* Fixed missing <cassert> include
# 1.12.1
### Fixes
* Fixed deprecation warning in `ScopedMessage::~ScopedMessage`
* All uses of `min` or `max` identifiers are now wrapped in parentheses
* This avoids problems when Windows headers define `min` and `max` macros
# 1.12.0
### Fixes
* Fixed compilation for strict C++98 mode (ie not gnu++98) and older compilers (#1103)
* `INFO` messages are included in the `xml` reporter output even without `-s` specified.
# 1.11.0 # 1.11.0
### Fixes ### Fixes

View File

@@ -1,6 +1,6 @@
# Getting Catch # Getting Catch
The simplest way to get Catch is to download the latest [single header version](https://raw.githubusercontent.com/philsquared/Catch/master/single_include/catch.hpp). The single header is generated by merging a set of individual headers but it is still just normal source code in a header file. The simplest way to get Catch is to download the latest [single header version](https://github.com/philsquared/Catch/releases/download/v1.12.2/catch.hpp). The single header is generated by merging a set of individual headers but it is still just normal source code in a header file.
The full source for Catch, including test projects, documentation, and other things, is hosted on GitHub. [http://catch-lib.net](http://catch-lib.net) will redirect you there. The full source for Catch, including test projects, documentation, and other things, is hosted on GitHub. [http://catch-lib.net](http://catch-lib.net) will redirect you there.

View File

@@ -163,7 +163,7 @@
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// Use variadic macros if the compiler supports them // Use variadic macros if the compiler supports them
#if ( defined _MSC_VER && _MSC_VER > 1400 && !defined __EDGE__) || \ #if ( defined _MSC_VER && _MSC_VER >= 1400 && !defined __EDGE__) || \
( defined __WAVE__ && __WAVE_HAS_VARIADICS ) || \ ( defined __WAVE__ && __WAVE_HAS_VARIADICS ) || \
( defined __GNUC__ && __GNUC__ >= 3 ) || \ ( defined __GNUC__ && __GNUC__ >= 3 ) || \
( !defined __cplusplus && __STDC_VERSION__ >= 199901L || __cplusplus >= 201103L ) ( !defined __cplusplus && __STDC_VERSION__ >= 199901L || __cplusplus >= 201103L )

View File

@@ -27,6 +27,9 @@ namespace Catch{
#define CATCH_TRAP() \ #define CATCH_TRAP() \
__asm__("li r0, 20\nsc\nnop\nli r0, 37\nli r4, 2\nsc\nnop\n" \ __asm__("li r0, 20\nsc\nnop\nli r0, 37\nli r4, 2\nsc\nnop\n" \
: : : "memory","r0","r3","r4" ) /* NOLINT */ : : : "memory","r0","r3","r4" ) /* NOLINT */
#elif defined(__aarch64__)
// Backport of https://github.com/catchorg/Catch2/commit/a25c1a24af8bffd35727a888a307ff0280cf9387
#define CATCH_TRAP() __asm__(".inst 0xd4200000")
#else #else
#define CATCH_TRAP() __asm__("int $3\n" : : /* NOLINT */ ) #define CATCH_TRAP() __asm__("int $3\n" : : /* NOLINT */ )
#endif #endif

View File

@@ -38,10 +38,12 @@ namespace Internal {
template<> struct OperatorTraits<IsGreaterThanOrEqualTo>{ static const char* getName(){ return ">="; } }; template<> struct OperatorTraits<IsGreaterThanOrEqualTo>{ static const char* getName(){ return ">="; } };
template<typename T> template<typename T>
T& removeConst(T const &t) { return const_cast<T&>(t); } T& opCast(T const& t) { return const_cast<T&>(t); }
// nullptr_t support based on pull request #154 from Konstantin Baumann
#ifdef CATCH_CONFIG_CPP11_NULLPTR #ifdef CATCH_CONFIG_CPP11_NULLPTR
inline std::nullptr_t removeConst(std::nullptr_t) { return nullptr; } inline std::nullptr_t opCast(std::nullptr_t) { return nullptr; }
#endif #endif // CATCH_CONFIG_CPP11_NULLPTR
// So the compare overloads can be operator agnostic we convey the operator as a template // So the compare overloads can be operator agnostic we convey the operator as a template
@@ -52,90 +54,161 @@ namespace Internal {
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsEqualTo> { struct Evaluator<T1, T2, IsEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs) { static bool evaluate( T1 const& lhs, T2 const& rhs) {
return bool(removeConst(lhs) == removeConst(rhs) ); return bool( opCast( lhs ) == opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsNotEqualTo> { struct Evaluator<T1, T2, IsNotEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) != removeConst(rhs) ); return bool( opCast( lhs ) != opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsLessThan> { struct Evaluator<T1, T2, IsLessThan> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) < removeConst(rhs) ); return bool( opCast( lhs ) < opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsGreaterThan> { struct Evaluator<T1, T2, IsGreaterThan> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) > removeConst(rhs) ); return bool( opCast( lhs ) > opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsGreaterThanOrEqualTo> { struct Evaluator<T1, T2, IsGreaterThanOrEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) >= removeConst(rhs) ); return bool( opCast( lhs ) >= opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsLessThanOrEqualTo> { struct Evaluator<T1, T2, IsLessThanOrEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) <= removeConst(rhs) ); return bool( opCast( lhs ) <= opCast( rhs ) );
} }
}; };
// Special case for comparing a pointer to an int (deduced for p==0) template<Operator Op, typename T1, typename T2>
template<typename T> bool applyEvaluator( T1 const& lhs, T2 const& rhs ) {
struct Evaluator<int const&, T* const&, IsEqualTo> { return Evaluator<T1, T2, Op>::evaluate( lhs, rhs );
static bool evaluate( int lhs, T* rhs) { }
return reinterpret_cast<void const*>( lhs ) == rhs;
}
};
template<typename T>
struct Evaluator<T* const&, int const&, IsEqualTo> {
static bool evaluate( T* lhs, int rhs) {
return lhs == reinterpret_cast<void const*>( rhs );
}
};
template<typename T>
struct Evaluator<int const&, T* const&, IsNotEqualTo> {
static bool evaluate( int lhs, T* rhs) {
return reinterpret_cast<void const*>( lhs ) != rhs;
}
};
template<typename T>
struct Evaluator<T* const&, int const&, IsNotEqualTo> {
static bool evaluate( T* lhs, int rhs) {
return lhs != reinterpret_cast<void const*>( rhs );
}
};
template<typename T> // This level of indirection allows us to specialise for integer types
struct Evaluator<long const&, T* const&, IsEqualTo> { // to avoid signed/ unsigned warnings
static bool evaluate( long lhs, T* rhs) {
return reinterpret_cast<void const*>( lhs ) == rhs; // "base" overload
} template<Operator Op, typename T1, typename T2>
}; bool compare( T1 const& lhs, T2 const& rhs ) {
template<typename T> return Evaluator<T1, T2, Op>::evaluate( lhs, rhs );
struct Evaluator<T* const&, long const&, IsEqualTo> { }
static bool evaluate( T* lhs, long rhs) {
return lhs == reinterpret_cast<void const*>( rhs ); // unsigned X to int
} template<Operator Op> bool compare( unsigned int lhs, int rhs ) {
}; return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
template<typename T> }
struct Evaluator<long const&, T* const&, IsNotEqualTo> { template<Operator Op> bool compare( unsigned long lhs, int rhs ) {
static bool evaluate( long lhs, T* rhs) { return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
return reinterpret_cast<void const*>( lhs ) != rhs; }
} template<Operator Op> bool compare( unsigned char lhs, int rhs ) {
}; return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
template<typename T> }
struct Evaluator<T* const&, long const&, IsNotEqualTo> {
static bool evaluate( T* lhs, long rhs) { // unsigned X to long
return lhs != reinterpret_cast<void const*>( rhs ); template<Operator Op> bool compare( unsigned int lhs, long rhs ) {
} return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}; }
template<Operator Op> bool compare( unsigned long lhs, long rhs ) {
return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}
template<Operator Op> bool compare( unsigned char lhs, long rhs ) {
return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}
// int to unsigned X
template<Operator Op> bool compare( int lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
template<Operator Op> bool compare( int lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
template<Operator Op> bool compare( int lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
// long to unsigned X
template<Operator Op> bool compare( long lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
// pointer to long (when comparing against NULL)
template<Operator Op, typename T> bool compare( long lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, long rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
// pointer to int (when comparing against NULL)
template<Operator Op, typename T> bool compare( int lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, int rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
#ifdef CATCH_CONFIG_CPP11_LONG_LONG
// long long to unsigned X
template<Operator Op> bool compare( long long lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned long long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
// unsigned long long to X
template<Operator Op> bool compare( unsigned long long lhs, int rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, long rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, long long rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, char rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
// pointer to long long (when comparing against NULL)
template<Operator Op, typename T> bool compare( long long lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, long long rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
#endif // CATCH_CONFIG_CPP11_LONG_LONG
#ifdef CATCH_CONFIG_CPP11_NULLPTR
// pointer to nullptr_t (when comparing against nullptr)
template<Operator Op, typename T> bool compare( std::nullptr_t, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( nullptr, rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, std::nullptr_t ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, nullptr );
}
#endif // CATCH_CONFIG_CPP11_NULLPTR
} // end of namespace Internal } // end of namespace Internal
} // end of namespace Catch } // end of namespace Catch

View File

@@ -111,7 +111,7 @@ public:
void endExpression() const { void endExpression() const {
m_rb m_rb
.setResultType( Internal::Evaluator<LhsT, RhsT, Op>::evaluate( m_lhs, m_rhs ) ) .setResultType( Internal::compare<Op>( m_lhs, m_rhs ) )
.endExpression( *this ); .endExpression( *this );
} }

View File

@@ -9,10 +9,12 @@
#ifndef TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED #ifndef TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED
#define TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED #define TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED
#include <cassert>
#include <stdexcept>
namespace Catch { namespace Catch {
// Report the error condition //! Signals fatal error message to the run context
inline void reportFatal( std::string const& message ) { inline void reportFatal( std::string const& message ) {
IContext& context = Catch::getCurrentContext(); IContext& context = Catch::getCurrentContext();
IResultCapture* resultCapture = context.getResultCapture(); IResultCapture* resultCapture = context.getResultCapture();
@@ -27,8 +29,31 @@ namespace Catch {
# if !defined ( CATCH_CONFIG_WINDOWS_SEH ) # if !defined ( CATCH_CONFIG_WINDOWS_SEH )
namespace Catch { namespace Catch {
struct FatalConditionHandler { class FatalConditionHandler {
void reset() {} bool m_started;
// Install/disengage implementation for specific platform.
// Should be if-defed to work on current platform, can assume
// engage-disengage 1:1 pairing.
void engage_platform() {}
void disengage_platform() {}
public:
// Should also have platform-specific implementations as needed
FatalConditionHandler() : m_started(false) {}
~FatalConditionHandler() {}
void engage() {
assert(!m_started && "Handler cannot be installed twice.");
m_started = true;
engage_platform();
}
void disengage() {
assert(m_started && "Handler cannot be uninstalled without being installed first");
m_started = false;
disengage_platform();
}
}; };
} }
@@ -48,53 +73,72 @@ namespace Catch {
{ EXCEPTION_INT_DIVIDE_BY_ZERO, "Divide by zero error" }, { EXCEPTION_INT_DIVIDE_BY_ZERO, "Divide by zero error" },
}; };
struct FatalConditionHandler { static LONG CALLBACK handleVectoredException(PEXCEPTION_POINTERS ExceptionInfo) {
for (int i = 0; i < sizeof(signalDefs) / sizeof(SignalDefs); ++i) {
static LONG CALLBACK handleVectoredException(PEXCEPTION_POINTERS ExceptionInfo) { if (ExceptionInfo->ExceptionRecord->ExceptionCode == signalDefs[i].id) {
for (int i = 0; i < sizeof(signalDefs) / sizeof(SignalDefs); ++i) { reportFatal(signalDefs[i].name);
if (ExceptionInfo->ExceptionRecord->ExceptionCode == signalDefs[i].id) {
reportFatal(signalDefs[i].name);
}
} }
// If its not an exception we care about, pass it along.
// This stops us from eating debugger breaks etc.
return EXCEPTION_CONTINUE_SEARCH;
} }
// If its not an exception we care about, pass it along.
// This stops us from eating debugger breaks etc.
return EXCEPTION_CONTINUE_SEARCH;
}
FatalConditionHandler() { // Since we do not support multiple instantiations, we put these
isSet = true; // into global variables and rely on cleaning them up in outlined
// 32k seems enough for Catch to handle stack overflow, // constructors/destructors
// but the value was found experimentally, so there is no strong guarantee static PVOID exceptionHandlerHandle = CATCH_NULL;
guaranteeSize = 32 * 1024;
exceptionHandlerHandle = CATCH_NULL; class FatalConditionHandler {
bool m_started;
// Install/disengage implementation for specific platform.
// Should be if-defed to work on current platform, can assume
// engage-disengage 1:1 pairing.
void engage_platform() {
// Register as first handler in current chain // Register as first handler in current chain
exceptionHandlerHandle = AddVectoredExceptionHandler(1, handleVectoredException); exceptionHandlerHandle = AddVectoredExceptionHandler(1, handleVectoredException);
// Pass in guarantee size to be filled if (!exceptionHandlerHandle) {
SetThreadStackGuarantee(&guaranteeSize); throw std::runtime_error("Could not register vectored exception handler");
}
static void reset() {
if (isSet) {
// Unregister handler and restore the old guarantee
RemoveVectoredExceptionHandler(exceptionHandlerHandle);
SetThreadStackGuarantee(&guaranteeSize);
exceptionHandlerHandle = CATCH_NULL;
isSet = false;
} }
} }
~FatalConditionHandler() { void disengage_platform() {
reset(); if (!RemoveVectoredExceptionHandler(exceptionHandlerHandle)) {
throw std::runtime_error("Could not unregister vectored exception handler");
}
exceptionHandlerHandle = CATCH_NULL;
} }
private:
static bool isSet;
static ULONG guaranteeSize;
static PVOID exceptionHandlerHandle;
};
bool FatalConditionHandler::isSet = false; public:
ULONG FatalConditionHandler::guaranteeSize = 0; FatalConditionHandler() : m_started(false) {
PVOID FatalConditionHandler::exceptionHandlerHandle = CATCH_NULL; ULONG guaranteeSize = static_cast<ULONG>(32 * 1024);
if (!SetThreadStackGuarantee(&guaranteeSize)) {
// We do not want to fully error out, because needing
// the stack reserve should be rare enough anyway.
Catch::cerr()
<< "Failed to reserve piece of stack."
<< " Stack overflows will not be reported successfully.";
}
}
// We do not attempt to unset the stack guarantee, because
// Windows does not support lowering the stack size guarantee.
~FatalConditionHandler() {}
void engage() {
assert(!m_started && "Handler cannot be installed twice.");
m_started = true;
engage_platform();
}
void disengage() {
assert(m_started && "Handler cannot be uninstalled without being installed first");
m_started = false;
disengage_platform();
}
};
} // namespace Catch } // namespace Catch
@@ -105,8 +149,31 @@ namespace Catch {
# if !defined(CATCH_CONFIG_POSIX_SIGNALS) # if !defined(CATCH_CONFIG_POSIX_SIGNALS)
namespace Catch { namespace Catch {
struct FatalConditionHandler { class FatalConditionHandler {
void reset() {} bool m_started;
// Install/disengage implementation for specific platform.
// Should be if-defed to work on current platform, can assume
// engage-disengage 1:1 pairing.
void engage_platform() {}
void disengage_platform() {}
public:
// Should also have platform-specific implementations as needed
FatalConditionHandler() : m_started(false) {}
~FatalConditionHandler() {}
void engage() {
assert(!m_started && "Handler cannot be installed twice.");
m_started = true;
engage_platform();
}
void disengage() {
assert(m_started && "Handler cannot be uninstalled without being installed first");
m_started = false;
disengage_platform();
}
}; };
} }
@@ -131,29 +198,56 @@ namespace Catch {
{ SIGABRT, "SIGABRT - Abort (abnormal termination) signal" } { SIGABRT, "SIGABRT - Abort (abnormal termination) signal" }
}; };
struct FatalConditionHandler { // Older GCCs trigger -Wmissing-field-initializers for T foo = {}
// which is zero initialization, but not explicit. We want to avoid
// that.
#if defined(__GNUC__)
# pragma GCC diagnostic push
# pragma GCC diagnostic ignored "-Wmissing-field-initializers"
#endif
static bool isSet; static char* altStackMem = CATCH_NULL;
static struct sigaction oldSigActions [sizeof(signalDefs)/sizeof(SignalDefs)]; static std::size_t altStackSize = 0;
static stack_t oldSigStack; static stack_t oldSigStack;
static char altStackMem[SIGSTKSZ]; static struct sigaction oldSigActions[sizeof(signalDefs) / sizeof(SignalDefs)];
static void handleSignal( int sig ) { static void restorePreviousSignalHandlers() {
std::string name = "<unknown signal>"; // We set signal handlers back to the previous ones. Hopefully
for (std::size_t i = 0; i < sizeof(signalDefs) / sizeof(SignalDefs); ++i) { // nobody overwrote them in the meantime, and doesn't expect
SignalDefs &def = signalDefs[i]; // their signal handlers to live past ours given that they
if (sig == def.id) { // installed them after ours..
name = def.name; for (std::size_t i = 0; i < sizeof(signalDefs) / sizeof(SignalDefs); ++i) {
break; sigaction(signalDefs[i].id, &oldSigActions[i], CATCH_NULL);
}
}
reset();
reportFatal(name);
raise( sig );
} }
// Return the old stack
sigaltstack(&oldSigStack, CATCH_NULL);
}
FatalConditionHandler() { static void handleSignal( int sig ) {
isSet = true; char const * name = "<unknown signal>";
for (std::size_t i = 0; i < sizeof(signalDefs) / sizeof(SignalDefs); ++i) {
SignalDefs &def = signalDefs[i];
if (sig == def.id) {
name = def.name;
break;
}
}
// We need to restore previous signal handlers and let them do
// their thing, so that the users can have the debugger break
// when a signal is raised, and so on.
restorePreviousSignalHandlers();
reportFatal( name );
raise( sig );
}
class FatalConditionHandler {
bool m_started;
// Install/disengage implementation for specific platform.
// Should be if-defed to work on current platform, can assume
// engage-disengage 1:1 pairing.
void engage_platform() {
stack_t sigStack; stack_t sigStack;
sigStack.ss_sp = altStackMem; sigStack.ss_sp = altStackMem;
sigStack.ss_size = SIGSTKSZ; sigStack.ss_size = SIGSTKSZ;
@@ -168,28 +262,42 @@ namespace Catch {
} }
} }
void disengage_platform() {
restorePreviousSignalHandlers();
}
public:
FatalConditionHandler() : m_started(false) {
assert(!altStackMem && "Cannot initialize POSIX signal handler when one already exists");
if (altStackSize == 0) {
altStackSize = SIGSTKSZ;
}
altStackMem = new char[altStackSize]();
}
~FatalConditionHandler() { ~FatalConditionHandler() {
reset(); delete[] altStackMem;
// We signal that another instance can be constructed by zeroing
// out the pointer.
altStackMem = CATCH_NULL;
} }
static void reset() {
if( isSet ) { void engage() {
// Set signals back to previous values -- hopefully nobody overwrote them in the meantime assert(!m_started && "Handler cannot be installed twice.");
for( std::size_t i = 0; i < sizeof(signalDefs)/sizeof(SignalDefs); ++i ) { m_started = true;
sigaction(signalDefs[i].id, &oldSigActions[i], CATCH_NULL); engage_platform();
} }
// Return the old stack
sigaltstack(&oldSigStack, CATCH_NULL); void disengage() {
isSet = false; assert(m_started && "Handler cannot be uninstalled without being installed first");
} m_started = false;
disengage_platform();
} }
}; };
bool FatalConditionHandler::isSet = false; #if defined(__GNUC__)
struct sigaction FatalConditionHandler::oldSigActions[sizeof(signalDefs)/sizeof(SignalDefs)] = {}; # pragma GCC diagnostic pop
stack_t FatalConditionHandler::oldSigStack = {}; #endif
char FatalConditionHandler::altStackMem[SIGSTKSZ] = {};
} // namespace Catch } // namespace Catch
@@ -197,4 +305,21 @@ namespace Catch {
#endif // not Windows #endif // not Windows
namespace Catch {
//! Simple RAII guard for (dis)engaging the FatalConditionHandler
class FatalConditionHandlerGuard {
FatalConditionHandler* m_handler;
public:
FatalConditionHandlerGuard(FatalConditionHandler* handler):
m_handler(handler) {
m_handler->engage();
}
~FatalConditionHandlerGuard() {
m_handler->disengage();
}
};
} // end namespace Catch
#endif // TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED #endif // TWOBLUECUBES_CATCH_FATAL_CONDITION_H_INCLUDED

View File

@@ -37,11 +37,18 @@ namespace Catch {
: m_info( other.m_info ) : m_info( other.m_info )
{} {}
#if defined(_MSC_VER)
#pragma warning(push)
#pragma warning(disable:4996) // std::uncaught_exception is deprecated in C++17
#endif
ScopedMessage::~ScopedMessage() { ScopedMessage::~ScopedMessage() {
if ( !std::uncaught_exception() ){ if ( !std::uncaught_exception() ){
getResultCapture().popScopedMessage(m_info); getResultCapture().popScopedMessage(m_info);
} }
} }
#if defined(_MSC_VER)
#pragma warning(pop)
#endif
} // end namespace Catch } // end namespace Catch

View File

@@ -16,6 +16,8 @@
#include "catch_interfaces_registry_hub.h" #include "catch_interfaces_registry_hub.h"
#include "catch_wildcard_pattern.hpp" #include "catch_wildcard_pattern.hpp"
#include <cassert>
namespace Catch { namespace Catch {
ResultBuilder::ResultBuilder( char const* macroName, ResultBuilder::ResultBuilder( char const* macroName,

View File

@@ -22,7 +22,7 @@
#include "catch_result_builder.h" #include "catch_result_builder.h"
#include "catch_fatal_condition.hpp" #include "catch_fatal_condition.hpp"
#include <cassert>
#include <set> #include <set>
#include <string> #include <string>
@@ -363,9 +363,8 @@ namespace Catch {
} }
void invokeActiveTestCase() { void invokeActiveTestCase() {
FatalConditionHandler fatalConditionHandler; // Handle signals FatalConditionHandlerGuard _(&m_fatalConditionhandler);
m_activeTestCase->invoke(); m_activeTestCase->invoke();
fatalConditionHandler.reset();
} }
private: private:
@@ -403,6 +402,7 @@ namespace Catch {
std::vector<SectionEndInfo> m_unfinishedSections; std::vector<SectionEndInfo> m_unfinishedSections;
std::vector<ITracker*> m_activeSections; std::vector<ITracker*> m_activeSections;
TrackerContext m_trackerContext; TrackerContext m_trackerContext;
FatalConditionHandler m_fatalConditionhandler;
size_t m_prevPassed; size_t m_prevPassed;
bool m_shouldReportUnexpected; bool m_shouldReportUnexpected;
}; };

View File

@@ -27,9 +27,9 @@ namespace Catch {
result_type operator()( result_type n ) const { return std::rand() % n; } result_type operator()( result_type n ) const { return std::rand() % n; }
#ifdef CATCH_CONFIG_CPP11_SHUFFLE #ifdef CATCH_CONFIG_CPP11_SHUFFLE
static constexpr result_type min() { return 0; } static constexpr result_type (min)() { return 0; }
static constexpr result_type max() { return 1000000; } static constexpr result_type (max)() { return 1000000; }
result_type operator()() const { return std::rand() % max(); } result_type operator()() const { return std::rand() % (max)(); }
#endif #endif
template<typename V> template<typename V>
static void shuffle( V& vector ) { static void shuffle( V& vector ) {

View File

@@ -38,7 +38,7 @@ namespace Catch {
} }
inline Version libraryVersion() { inline Version libraryVersion() {
static Version version( 1, 11, 0, "", 0 ); static Version version( 1, 12, 2, "", 0 );
return version; return version;
} }

View File

@@ -13,6 +13,7 @@
#include "../internal/catch_reporter_registrars.hpp" #include "../internal/catch_reporter_registrars.hpp"
#include "../internal/catch_console_colour.hpp" #include "../internal/catch_console_colour.hpp"
#include <cassert>
#include <cfloat> #include <cfloat>
#include <cstdio> #include <cstdio>

View File

@@ -14,6 +14,7 @@
// file can be distributed as a single header that works with the main // file can be distributed as a single header that works with the main
// Catch single header. // Catch single header.
#include <cassert>
#include <cstring> #include <cstring>
#ifdef __clang__ #ifdef __clang__

View File

@@ -97,12 +97,12 @@ namespace Catch {
bool includeResults = m_config->includeSuccessfulResults() || !result.isOk(); bool includeResults = m_config->includeSuccessfulResults() || !result.isOk();
if( includeResults ) { if( includeResults || result.getResultType() == ResultWas::Warning ) {
// Print any info messages in <Info> tags. // Print any info messages in <Info> tags.
for( std::vector<MessageInfo>::const_iterator it = assertionStats.infoMessages.begin(), itEnd = assertionStats.infoMessages.end(); for( std::vector<MessageInfo>::const_iterator it = assertionStats.infoMessages.begin(), itEnd = assertionStats.infoMessages.end();
it != itEnd; it != itEnd;
++it ) { ++it ) {
if( it->type == ResultWas::Info ) { if( it->type == ResultWas::Info && includeResults ) {
m_xml.scopedElement( "Info" ) m_xml.scopedElement( "Info" )
.writeText( it->message ); .writeText( it->message );
} else if ( it->type == ResultWas::Warning ) { } else if ( it->type == ResultWas::Warning ) {

View File

@@ -8,7 +8,7 @@ from releaseCommon import Version
print(catchPath) print(catchPath)
default_path = '../vcpkg/ports/catch/' default_path = '../vcpkg/ports/catch-classic/'
def adjusted_path(path): def adjusted_path(path):
return os.path.join(catchPath, path) return os.path.join(catchPath, path)

View File

@@ -1,6 +1,6 @@
/* /*
* Catch v1.11.0 * Catch v1.12.2
* Generated: 2017-10-31 13:42:42.914833 * Generated: 2018-05-14 15:10:01.112442
* ---------------------------------------------------------- * ----------------------------------------------------------
* This file has been merged from multiple headers. Please don't edit it directly * This file has been merged from multiple headers. Please don't edit it directly
* Copyright (c) 2012 Two Blue Cubes Ltd. All rights reserved. * Copyright (c) 2012 Two Blue Cubes Ltd. All rights reserved.
@@ -1320,10 +1320,12 @@ namespace Internal {
template<> struct OperatorTraits<IsGreaterThanOrEqualTo>{ static const char* getName(){ return ">="; } }; template<> struct OperatorTraits<IsGreaterThanOrEqualTo>{ static const char* getName(){ return ">="; } };
template<typename T> template<typename T>
T& removeConst(T const &t) { return const_cast<T&>(t); } T& opCast(T const& t) { return const_cast<T&>(t); }
// nullptr_t support based on pull request #154 from Konstantin Baumann
#ifdef CATCH_CONFIG_CPP11_NULLPTR #ifdef CATCH_CONFIG_CPP11_NULLPTR
inline std::nullptr_t removeConst(std::nullptr_t) { return nullptr; } inline std::nullptr_t opCast(std::nullptr_t) { return nullptr; }
#endif #endif // CATCH_CONFIG_CPP11_NULLPTR
// So the compare overloads can be operator agnostic we convey the operator as a template // So the compare overloads can be operator agnostic we convey the operator as a template
// enum, which is used to specialise an Evaluator for doing the comparison. // enum, which is used to specialise an Evaluator for doing the comparison.
@@ -1333,90 +1335,161 @@ namespace Internal {
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsEqualTo> { struct Evaluator<T1, T2, IsEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs) { static bool evaluate( T1 const& lhs, T2 const& rhs) {
return bool(removeConst(lhs) == removeConst(rhs) ); return bool( opCast( lhs ) == opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsNotEqualTo> { struct Evaluator<T1, T2, IsNotEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) != removeConst(rhs) ); return bool( opCast( lhs ) != opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsLessThan> { struct Evaluator<T1, T2, IsLessThan> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) < removeConst(rhs) ); return bool( opCast( lhs ) < opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsGreaterThan> { struct Evaluator<T1, T2, IsGreaterThan> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) > removeConst(rhs) ); return bool( opCast( lhs ) > opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsGreaterThanOrEqualTo> { struct Evaluator<T1, T2, IsGreaterThanOrEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) >= removeConst(rhs) ); return bool( opCast( lhs ) >= opCast( rhs ) );
} }
}; };
template<typename T1, typename T2> template<typename T1, typename T2>
struct Evaluator<T1, T2, IsLessThanOrEqualTo> { struct Evaluator<T1, T2, IsLessThanOrEqualTo> {
static bool evaluate( T1 const& lhs, T2 const& rhs ) { static bool evaluate( T1 const& lhs, T2 const& rhs ) {
return bool(removeConst(lhs) <= removeConst(rhs) ); return bool( opCast( lhs ) <= opCast( rhs ) );
} }
}; };
// Special case for comparing a pointer to an int (deduced for p==0) template<Operator Op, typename T1, typename T2>
template<typename T> bool applyEvaluator( T1 const& lhs, T2 const& rhs ) {
struct Evaluator<int const&, T* const&, IsEqualTo> { return Evaluator<T1, T2, Op>::evaluate( lhs, rhs );
static bool evaluate( int lhs, T* rhs) { }
return reinterpret_cast<void const*>( lhs ) == rhs;
}
};
template<typename T>
struct Evaluator<T* const&, int const&, IsEqualTo> {
static bool evaluate( T* lhs, int rhs) {
return lhs == reinterpret_cast<void const*>( rhs );
}
};
template<typename T>
struct Evaluator<int const&, T* const&, IsNotEqualTo> {
static bool evaluate( int lhs, T* rhs) {
return reinterpret_cast<void const*>( lhs ) != rhs;
}
};
template<typename T>
struct Evaluator<T* const&, int const&, IsNotEqualTo> {
static bool evaluate( T* lhs, int rhs) {
return lhs != reinterpret_cast<void const*>( rhs );
}
};
template<typename T> // This level of indirection allows us to specialise for integer types
struct Evaluator<long const&, T* const&, IsEqualTo> { // to avoid signed/ unsigned warnings
static bool evaluate( long lhs, T* rhs) {
return reinterpret_cast<void const*>( lhs ) == rhs; // "base" overload
} template<Operator Op, typename T1, typename T2>
}; bool compare( T1 const& lhs, T2 const& rhs ) {
template<typename T> return Evaluator<T1, T2, Op>::evaluate( lhs, rhs );
struct Evaluator<T* const&, long const&, IsEqualTo> { }
static bool evaluate( T* lhs, long rhs) {
return lhs == reinterpret_cast<void const*>( rhs ); // unsigned X to int
} template<Operator Op> bool compare( unsigned int lhs, int rhs ) {
}; return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
template<typename T> }
struct Evaluator<long const&, T* const&, IsNotEqualTo> { template<Operator Op> bool compare( unsigned long lhs, int rhs ) {
static bool evaluate( long lhs, T* rhs) { return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
return reinterpret_cast<void const*>( lhs ) != rhs; }
} template<Operator Op> bool compare( unsigned char lhs, int rhs ) {
}; return applyEvaluator<Op>( lhs, static_cast<unsigned int>( rhs ) );
template<typename T> }
struct Evaluator<T* const&, long const&, IsNotEqualTo> {
static bool evaluate( T* lhs, long rhs) { // unsigned X to long
return lhs != reinterpret_cast<void const*>( rhs ); template<Operator Op> bool compare( unsigned int lhs, long rhs ) {
} return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}; }
template<Operator Op> bool compare( unsigned long lhs, long rhs ) {
return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}
template<Operator Op> bool compare( unsigned char lhs, long rhs ) {
return applyEvaluator<Op>( lhs, static_cast<unsigned long>( rhs ) );
}
// int to unsigned X
template<Operator Op> bool compare( int lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
template<Operator Op> bool compare( int lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
template<Operator Op> bool compare( int lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned int>( lhs ), rhs );
}
// long to unsigned X
template<Operator Op> bool compare( long lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
// pointer to long (when comparing against NULL)
template<Operator Op, typename T> bool compare( long lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, long rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
// pointer to int (when comparing against NULL)
template<Operator Op, typename T> bool compare( int lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, int rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
#ifdef CATCH_CONFIG_CPP11_LONG_LONG
// long long to unsigned X
template<Operator Op> bool compare( long long lhs, unsigned int rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned long long rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
template<Operator Op> bool compare( long long lhs, unsigned char rhs ) {
return applyEvaluator<Op>( static_cast<unsigned long>( lhs ), rhs );
}
// unsigned long long to X
template<Operator Op> bool compare( unsigned long long lhs, int rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, long rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, long long rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
template<Operator Op> bool compare( unsigned long long lhs, char rhs ) {
return applyEvaluator<Op>( static_cast<long>( lhs ), rhs );
}
// pointer to long long (when comparing against NULL)
template<Operator Op, typename T> bool compare( long long lhs, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( reinterpret_cast<T*>( lhs ), rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, long long rhs ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, reinterpret_cast<T*>( rhs ) );
}
#endif // CATCH_CONFIG_CPP11_LONG_LONG
#ifdef CATCH_CONFIG_CPP11_NULLPTR
// pointer to nullptr_t (when comparing against nullptr)
template<Operator Op, typename T> bool compare( std::nullptr_t, T* rhs ) {
return Evaluator<T*, T*, Op>::evaluate( nullptr, rhs );
}
template<Operator Op, typename T> bool compare( T* lhs, std::nullptr_t ) {
return Evaluator<T*, T*, Op>::evaluate( lhs, nullptr );
}
#endif // CATCH_CONFIG_CPP11_NULLPTR
} // end of namespace Internal } // end of namespace Internal
} // end of namespace Catch } // end of namespace Catch
@@ -1837,7 +1910,7 @@ public:
void endExpression() const { void endExpression() const {
m_rb m_rb
.setResultType( Internal::Evaluator<LhsT, RhsT, Op>::evaluate( m_lhs, m_rhs ) ) .setResultType( Internal::compare<Op>( m_lhs, m_rhs ) )
.endExpression( *this ); .endExpression( *this );
} }
@@ -6526,6 +6599,7 @@ namespace Catch {
#endif // not Windows #endif // not Windows
#include <cassert>
#include <set> #include <set>
#include <string> #include <string>
@@ -7219,9 +7293,9 @@ namespace Catch {
result_type operator()( result_type n ) const { return std::rand() % n; } result_type operator()( result_type n ) const { return std::rand() % n; }
#ifdef CATCH_CONFIG_CPP11_SHUFFLE #ifdef CATCH_CONFIG_CPP11_SHUFFLE
static constexpr result_type min() { return 0; } static constexpr result_type (min)() { return 0; }
static constexpr result_type max() { return 1000000; } static constexpr result_type (max)() { return 1000000; }
result_type operator()() const { return std::rand() % max(); } result_type operator()() const { return std::rand() % (max)(); }
#endif #endif
template<typename V> template<typename V>
static void shuffle( V& vector ) { static void shuffle( V& vector ) {
@@ -8393,7 +8467,7 @@ namespace Catch {
} }
inline Version libraryVersion() { inline Version libraryVersion() {
static Version version( 1, 11, 0, "", 0 ); static Version version( 1, 12, 2, "", 0 );
return version; return version;
} }
@@ -8428,11 +8502,18 @@ namespace Catch {
: m_info( other.m_info ) : m_info( other.m_info )
{} {}
#if defined(_MSC_VER)
#pragma warning(push)
#pragma warning(disable:4996) // std::uncaught_exception is deprecated in C++17
#endif
ScopedMessage::~ScopedMessage() { ScopedMessage::~ScopedMessage() {
if ( !std::uncaught_exception() ){ if ( !std::uncaught_exception() ){
getResultCapture().popScopedMessage(m_info); getResultCapture().popScopedMessage(m_info);
} }
} }
#if defined(_MSC_VER)
#pragma warning(pop)
#endif
} // end namespace Catch } // end namespace Catch
@@ -9091,6 +9172,8 @@ std::string toString( std::nullptr_t ) {
// #included from: catch_result_builder.hpp // #included from: catch_result_builder.hpp
#define TWOBLUECUBES_CATCH_RESULT_BUILDER_HPP_INCLUDED #define TWOBLUECUBES_CATCH_RESULT_BUILDER_HPP_INCLUDED
#include <cassert>
namespace Catch { namespace Catch {
ResultBuilder::ResultBuilder( char const* macroName, ResultBuilder::ResultBuilder( char const* macroName,
@@ -10207,12 +10290,12 @@ namespace Catch {
bool includeResults = m_config->includeSuccessfulResults() || !result.isOk(); bool includeResults = m_config->includeSuccessfulResults() || !result.isOk();
if( includeResults ) { if( includeResults || result.getResultType() == ResultWas::Warning ) {
// Print any info messages in <Info> tags. // Print any info messages in <Info> tags.
for( std::vector<MessageInfo>::const_iterator it = assertionStats.infoMessages.begin(), itEnd = assertionStats.infoMessages.end(); for( std::vector<MessageInfo>::const_iterator it = assertionStats.infoMessages.begin(), itEnd = assertionStats.infoMessages.end();
it != itEnd; it != itEnd;
++it ) { ++it ) {
if( it->type == ResultWas::Info ) { if( it->type == ResultWas::Info && includeResults ) {
m_xml.scopedElement( "Info" ) m_xml.scopedElement( "Info" )
.writeText( it->message ); .writeText( it->message );
} else if ( it->type == ResultWas::Warning ) { } else if ( it->type == ResultWas::Warning ) {
@@ -10584,6 +10667,7 @@ namespace Catch {
// #included from: ../reporters/catch_reporter_console.hpp // #included from: ../reporters/catch_reporter_console.hpp
#define TWOBLUECUBES_CATCH_REPORTER_CONSOLE_HPP_INCLUDED #define TWOBLUECUBES_CATCH_REPORTER_CONSOLE_HPP_INCLUDED
#include <cassert>
#include <cfloat> #include <cfloat>
#include <cstdio> #include <cstdio>

View File

@@ -10,7 +10,7 @@ class CatchConanTest(ConanFile):
settings = "os", "compiler", "arch", "build_type" settings = "os", "compiler", "arch", "build_type"
username = getenv("CONAN_USERNAME", "philsquared") username = getenv("CONAN_USERNAME", "philsquared")
channel = getenv("CONAN_CHANNEL", "testing") channel = getenv("CONAN_CHANNEL", "testing")
requires = "Catch/1.11.0@%s/%s" % (username, channel) requires = "Catch/1.12.2@%s/%s" % (username, channel)
def build(self): def build(self):
cmake = CMake(self) cmake = CMake(self)