mirror of
https://github.com/catchorg/Catch2.git
synced 2025-01-16 07:08:01 +00:00
Compare commits
38 Commits
0fdeb10c65
...
33c58dad41
Author | SHA1 | Date | |
---|---|---|---|
|
33c58dad41 | ||
|
68061bbed4 | ||
|
e83c9fb674 | ||
|
b8221c8350 | ||
|
31ff89709f | ||
|
5b8cccaf6a | ||
|
4aefbbcd02 | ||
|
53434a2f32 | ||
|
2a93a65bc2 | ||
|
dd35430a2b | ||
|
bbbc7a0d7f | ||
|
89fab65382 | ||
|
1bd7cac09f | ||
|
9b5fc9eaea | ||
|
630ba26278 | ||
|
26b2c3e7e2 | ||
|
87a8b61d5a | ||
|
ca27b0dcc5 | ||
|
87c8055176 | ||
|
46cc551b7a | ||
|
f34aacfe5f | ||
|
0d3e933d71 | ||
|
02a998598c | ||
|
8ea45bf50c | ||
|
beb8c3a99d | ||
|
656b15d37b | ||
|
5198fd3c9a | ||
|
08f8a81b2c | ||
|
0d8eeec557 | ||
|
d3c0b36487 | ||
|
95a2e54702 | ||
|
6badd7d9ed | ||
|
60cfaa38fb | ||
|
38a0dfca6d | ||
|
b014d988fe | ||
|
7a0f8ff4b8 | ||
|
efbfaa1704 | ||
|
c4e5b05cfc |
@ -5,12 +5,11 @@
|
||||
[![Build Status](https://travis-ci.org/catchorg/Catch2.svg?branch=master)](https://travis-ci.org/catchorg/Catch2)
|
||||
[![Build status](https://ci.appveyor.com/api/projects/status/github/catchorg/Catch2?svg=true)](https://ci.appveyor.com/project/catchorg/catch2)
|
||||
[![codecov](https://codecov.io/gh/catchorg/Catch2/branch/master/graph/badge.svg)](https://codecov.io/gh/catchorg/Catch2)
|
||||
[![Try online](https://img.shields.io/badge/try-online-blue.svg)](https://wandbox.org/permlink/LzYWgcPrcy9yQmed)
|
||||
<!-- We can eventually bring this back, but the upload script will have to be more complex -->
|
||||
<!-- [![Try online](https://img.shields.io/badge/try-online-blue.svg)](https://wandbox.org/permlink/LzYWgcPrcy9yQmed) -->
|
||||
[![Join the chat in Discord: https://discord.gg/4CWS9zD](https://img.shields.io/badge/Discord-Chat!-brightgreen.svg)](https://discord.gg/4CWS9zD)
|
||||
|
||||
|
||||
<a href="https://github.com/catchorg/Catch2/releases/download/v2.10.2/catch.hpp">The latest version of the single header can be downloaded directly using this link</a>
|
||||
|
||||
## Catch2 is released!
|
||||
|
||||
If you've been using an earlier version of Catch, please see the
|
||||
|
@ -6,6 +6,7 @@
|
||||
[Automatic test registration](#automatic-test-registration)<br>
|
||||
[CMake project options](#cmake-project-options)<br>
|
||||
[Installing Catch2 from git repository](#installing-catch2-from-git-repository)<br>
|
||||
[Installing Catch2 from vcpkg](#installing-catch2-from-vcpkg)<br>
|
||||
|
||||
Because we use CMake to build Catch2, we also provide a couple of
|
||||
integration points for our users.
|
||||
@ -220,6 +221,19 @@ when configuring the build, and then modify your calls to
|
||||
[find_package](https://cmake.org/cmake/help/latest/command/find_package.html)
|
||||
accordingly.
|
||||
|
||||
## Installing Catch2 from vcpkg
|
||||
|
||||
Alternatively, you can build and install Catch2 using [vcpkg](https://github.com/microsoft/vcpkg/) dependency manager:
|
||||
```
|
||||
git clone https://github.com/Microsoft/vcpkg.git
|
||||
cd vcpkg
|
||||
./bootstrap-vcpkg.sh
|
||||
./vcpkg integrate install
|
||||
./vcpkg install catch2
|
||||
```
|
||||
|
||||
The catch2 port in vcpkg is kept up to date by microsoft team members and community contributors.
|
||||
If the version is out of date, please [create an issue or pull request](https://github.com/Microsoft/vcpkg) on the vcpkg repository.
|
||||
|
||||
---
|
||||
|
||||
|
@ -243,15 +243,25 @@ This option lists all available tests in a non-indented form, one on each line.
|
||||
|
||||
Test cases are ordered one of three ways:
|
||||
|
||||
|
||||
### decl
|
||||
Declaration order (this is the default order if no --order argument is provided). The order the tests were originally declared in. Note that ordering between files is not guaranteed and is implementation dependent.
|
||||
Declaration order (this is the default order if no --order argument is provided).
|
||||
Tests in the same TU are sorted using their declaration orders, different
|
||||
TUs are in an implementation (linking) dependent order.
|
||||
|
||||
|
||||
### lex
|
||||
Lexicographically sorted. Tests are sorted, alpha-numerically, by name.
|
||||
Lexicographic order. Tests are sorted by their name, their tags are ignored.
|
||||
|
||||
|
||||
### rand
|
||||
Randomly sorted. Test names are sorted using ```std::random_shuffle()```. By default the random number generator is seeded with 0 - and so the order is repeatable. To control the random seed see <a href="#rng-seed">rng-seed</a>.
|
||||
|
||||
Randomly sorted. The order is dependent on Catch2's random seed (see
|
||||
[`--rng-seed`](#rng-seed)), and is subset invariant. What this means
|
||||
is that as long as the random seed is fixed, running only some tests
|
||||
(e.g. via tag) does not change their relative order.
|
||||
|
||||
> The subset stability was introduced in Catch2 v2.12.0
|
||||
|
||||
|
||||
<a id="rng-seed"></a>
|
||||
## Specify a seed for the Random Number Generator
|
||||
@ -323,7 +333,7 @@ Instead the user code is only measured and the plain mean from the samples is re
|
||||
## Specify the amount of time in milliseconds spent on warming up each test
|
||||
<pre>--benchmark-warmup-time</pre>
|
||||
|
||||
> [Introduced](https://github.com/catchorg/Catch2/pull/1844) in Catch X.Y.Z.
|
||||
> [Introduced](https://github.com/catchorg/Catch2/pull/1844) in Catch 2.11.2.
|
||||
|
||||
Configure the amount of time spent warming up each test.
|
||||
|
||||
|
@ -18,3 +18,5 @@ fact then please let us know - either directly, via a PR or
|
||||
- [Inscopix Inc.](https://www.inscopix.com/)
|
||||
- [Makimo](https://makimo.pl/)
|
||||
- [UX3D](https://ux3d.io)
|
||||
- [King](https://king.com)
|
||||
|
||||
|
@ -127,8 +127,8 @@ Catch's selection, by defining either `CATCH_CONFIG_CPP11_TO_STRING` or
|
||||
|
||||
## C++17 toggles
|
||||
|
||||
CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS // Use std::uncaught_exceptions instead of std::uncaught_exception
|
||||
CATCH_CONFIG_CPP17_STRING_VIEW // Override std::string_view support detection(Catch provides a StringMaker specialization by default)
|
||||
CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS // Override std::uncaught_exceptions (instead of std::uncaught_exception) support detection
|
||||
CATCH_CONFIG_CPP17_STRING_VIEW // Override std::string_view support detection (Catch provides a StringMaker specialization by default)
|
||||
CATCH_CONFIG_CPP17_VARIANT // Override std::variant support detection (checked by CATCH_CONFIG_ENABLE_VARIANT_STRINGMAKER)
|
||||
CATCH_CONFIG_CPP17_OPTIONAL // Override std::optional support detection (checked by CATCH_CONFIG_ENABLE_OPTIONAL_STRINGMAKER)
|
||||
CATCH_CONFIG_CPP17_BYTE // Override std::byte support detection (Catch provides a StringMaker specialization by default)
|
||||
@ -252,7 +252,7 @@ namespace Catch {
|
||||
|
||||
## Overriding Catch's debug break (`-b`)
|
||||
|
||||
> [Introduced](https://github.com/catchorg/Catch2/pull/1846) in Catch X.Y.Z.
|
||||
> [Introduced](https://github.com/catchorg/Catch2/pull/1846) in Catch 2.11.2.
|
||||
|
||||
You can override Catch2's break-into-debugger code by defining the
|
||||
`CATCH_BREAK_INTO_DEBUGGER()` macro. This can be used if e.g. Catch2 does
|
||||
|
@ -20,18 +20,21 @@ Listing a project here does not imply endorsement and the plan is to keep these
|
||||
### [ApprovalTests.cpp](https://github.com/approvals/ApprovalTests.cpp)
|
||||
C++11 implementation of Approval Tests, for quick, convenient testing of legacy code.
|
||||
|
||||
### [args](https://github.com/Taywee/args)
|
||||
A simple header-only C++ argument parser library.
|
||||
|
||||
### [Azmq](https://github.com/zeromq/azmq)
|
||||
Boost Asio style bindings for ZeroMQ.
|
||||
|
||||
### [Cataclysm: Dark Days Ahead](https://github.com/CleverRaven/Cataclysm-DDA)
|
||||
Post-apocalyptic survival RPG.
|
||||
|
||||
### [ChakraCore](https://github.com/Microsoft/ChakraCore)
|
||||
The core part of the Chakra JavaScript engine that powers Microsoft Edge.
|
||||
|
||||
### [ChaiScript](https://github.com/ChaiScript/ChaiScript)
|
||||
A, header-only, embedded scripting language designed from the ground up to directly target C++ and take advantage of modern C++ development techniques.
|
||||
|
||||
### [ChakraCore](https://github.com/Microsoft/ChakraCore)
|
||||
The core part of the Chakra JavaScript engine that powers Microsoft Edge.
|
||||
|
||||
### [Clara](https://github.com/philsquared/Clara)
|
||||
A, single-header-only, type-safe, command line parser - which also prints formatted usage strings.
|
||||
|
||||
@ -65,9 +68,6 @@ A small C++ library wrapper for the native C ODBC API.
|
||||
### [Nonius](https://github.com/libnonius/nonius)
|
||||
A header-only framework for benchmarking small snippets of C++ code.
|
||||
|
||||
### [SOCI](https://github.com/SOCI/soci)
|
||||
The C++ Database Access Library.
|
||||
|
||||
### [polymorphic_value](https://github.com/jbcoe/polymorphic_value)
|
||||
A polymorphic value-type for C++.
|
||||
|
||||
@ -77,18 +77,21 @@ A C++ client library for Consul. Consul is a distributed tool for discovering an
|
||||
### [Reactive-Extensions/ RxCpp](https://github.com/Reactive-Extensions/RxCpp)
|
||||
A library of algorithms for values-distributed-in-time.
|
||||
|
||||
### [thor](https://github.com/xorz57/thor)
|
||||
Wrapper Library for CUDA.
|
||||
### [SOCI](https://github.com/SOCI/soci)
|
||||
The C++ Database Access Library.
|
||||
|
||||
### [TextFlowCpp](https://github.com/philsquared/textflowcpp)
|
||||
A small, single-header-only, library for wrapping and composing columns of text.
|
||||
|
||||
### [thor](https://github.com/xorz57/thor)
|
||||
Wrapper Library for CUDA.
|
||||
|
||||
### [toml++](https://github.com/marzer/tomlplusplus)
|
||||
A header-only TOML parser and serializer for modern C++.
|
||||
|
||||
### [Trompeloeil](https://github.com/rollbear/trompeloeil)
|
||||
A thread-safe header-only mocking framework for C++14.
|
||||
|
||||
### [args](https://github.com/Taywee/args)
|
||||
A simple header-only C++ argument parser library.
|
||||
|
||||
## Applications & Tools
|
||||
|
||||
### [ArangoDB](https://github.com/arangodb/arangodb)
|
||||
@ -103,6 +106,9 @@ MAME originally stood for Multiple Arcade Machine Emulator.
|
||||
### [Newsbeuter](https://github.com/akrennmair/newsbeuter)
|
||||
Newsbeuter is an open-source RSS/Atom feed reader for text terminals.
|
||||
|
||||
### [PopHead](https://github.com/SPC-Some-Polish-Coders/PopHead)
|
||||
A 2D, Zombie, RPG game which is being made on our own engine.
|
||||
|
||||
### [raspigcd](https://github.com/pantadeusz/raspigcd)
|
||||
Low level CLI app and library for execution of GCODE on Raspberry Pi without any additional microcontrolers (just RPi + Stepsticks).
|
||||
|
||||
@ -112,9 +118,6 @@ SpECTRE is a code for multi-scale, multi-physics problems in astrophysics and gr
|
||||
### [Standardese](https://github.com/foonathan/standardese)
|
||||
Standardese aims to be a nextgen Doxygen.
|
||||
|
||||
### [PopHead](https://github.com/SPC-Some-Polish-Coders/PopHead)
|
||||
A 2D, Zombie, RPG game which is being made on our own engine.
|
||||
|
||||
---
|
||||
|
||||
[Home](Readme.md#top)
|
||||
|
@ -2,6 +2,10 @@
|
||||
|
||||
# Release notes
|
||||
**Contents**<br>
|
||||
[2.12.1](#2121)<br>
|
||||
[2.12.0](#2120)<br>
|
||||
[2.11.3](#2113)<br>
|
||||
[2.11.2](#2112)<br>
|
||||
[2.11.1](#2111)<br>
|
||||
[2.11.0](#2110)<br>
|
||||
[2.10.2](#2102)<br>
|
||||
@ -32,6 +36,43 @@
|
||||
[Older versions](#older-versions)<br>
|
||||
[Even Older versions](#even-older-versions)<br>
|
||||
|
||||
## 2.12.1
|
||||
|
||||
### Fixes
|
||||
* Vector matchers now support initializer list literals better
|
||||
|
||||
### Improvements
|
||||
* Added support for `^` (bitwise xor) to `CHECK` and `REQUIRE`
|
||||
|
||||
|
||||
## 2.12.0
|
||||
|
||||
### Improvements
|
||||
* Running tests in random order (`--order rand`) has been reworked significantly (#1908)
|
||||
* Given same seed, all platforms now produce the same order
|
||||
* Given same seed, the relative order of tests does not change if you select only a subset of them
|
||||
* Vector matchers support custom allocators (#1909)
|
||||
* `|` and `&` (bitwise or and bitwise and) are now supported in `CHECK` and `REQUIRE`
|
||||
* The resulting type must be convertible to `bool`
|
||||
|
||||
### Fixes
|
||||
* Fixed computation of benchmarking column widths in ConsoleReporter (#1885, #1886)
|
||||
* Suppressed clang-tidy's `cppcoreguidelines-pro-type-vararg` in assertions (#1901)
|
||||
* It was a false positive trigered by the new warning support workaround
|
||||
* Fixed bug in test specification parser handling of OR'd patterns using escaping (#1905)
|
||||
|
||||
### Miscellaneous
|
||||
* Worked around IBM XL's codegen bug (#1907)
|
||||
* It would emit code for _destructors_ of temporaries in an unevaluated context
|
||||
* Improved detection of stdlib's support for `std::uncaught_exceptions` (#1911)
|
||||
|
||||
|
||||
## 2.11.3
|
||||
|
||||
### Fixes
|
||||
* Fixed compilation error caused by lambdas in assertions under MSVC
|
||||
|
||||
|
||||
## 3.0.0 (in progress)
|
||||
|
||||
### (Potentially) Breaking changes
|
||||
@ -86,6 +127,32 @@
|
||||
|
||||
|
||||
|
||||
## 2.11.2
|
||||
|
||||
### Improvements
|
||||
* GCC and Clang now issue warnings for suspicious code in assertions (#1880)
|
||||
* E.g. `REQUIRE( int != unsigned int )` will now issue mixed signedness comparison warning
|
||||
* This has always worked on MSVC, but it now also works for GCC and current Clang versions
|
||||
* Colorization of "Test filters" output should be more robust now
|
||||
* `--wait-for-keypress` now also accepts `never` as an option (#1866)
|
||||
* Reporters no longer round-off nanoseconds when reporting benchmarking results (#1876)
|
||||
* Catch2's debug break now supports iOS while using Thumb instruction set (#1862)
|
||||
* It is now possible to customize benchmark's warm-up time when running the test binary (#1844)
|
||||
* `--benchmark-warmup-time {ms}`
|
||||
* User can now specify how Catch2 should break into debugger (#1846)
|
||||
|
||||
### Fixes
|
||||
* Fixes missing `<random>` include in benchmarking (#1831)
|
||||
* Fixed missing `<iterator>` include in benchmarking (#1874)
|
||||
* Hidden test cases are now also tagged with `[!hide]` as per documentation (#1847)
|
||||
* Detection of whether libc provides `std::nextafter` has been improved (#1854)
|
||||
* Detection of `wmain` no longer incorrectly looks for `WIN32` macro (#1849)
|
||||
* Now it just detects Windows platform
|
||||
* Composing already-composed matchers no longer modifies the partially-composed matcher expression
|
||||
* This bug has been present for the last ~2 years and nobody reported it
|
||||
|
||||
|
||||
|
||||
## 2.11.1
|
||||
|
||||
### Improvements
|
||||
|
@ -22,7 +22,7 @@ But functions and methods can also be written inline in header files. The downsi
|
||||
|
||||
Because Catch is implemented *entirely* in headers you might think that the whole of Catch must be compiled into every translation unit that uses it! Actually it's not quite as bad as that. Catch mitigates this situation by effectively maintaining the traditional separation between the implementation code and declarations. Internally the implementation code is protected by ```#ifdef```s and is conditionally compiled into only one translation unit. This translation unit is that one that ```#define```s ```CATCH_CONFIG_MAIN``` or ```CATCH_CONFIG_RUNNER```. Let's call this the main source file.
|
||||
|
||||
As a result the main source file *does* compile the whole of Catch every time! So it makes sense to dedicate this file to *only* ```#define```-ing the identifier and ```#include```-ing Catch (and implementing the runner code, if you're doing that). Keep all your test cases in other files. This way you won't pay the recompilation cost for the whole of Catch
|
||||
As a result the main source file *does* compile the whole of Catch every time! So it makes sense to dedicate this file to *only* ```#define```-ing the identifier and ```#include```-ing Catch (and implementing the runner code, if you're doing that). Keep all your test cases in other files. This way you won't pay the recompilation cost for the whole of Catch.
|
||||
|
||||
## Practical example
|
||||
Assume you have the `Factorial` function from the [tutorial](tutorial.md#top) in `factorial.cpp` (with forward declaration in `factorial.h`) and want to test it and keep the compile times down when adding new tests. Then you should have 2 files, `tests-main.cpp` and `tests-factorial.cpp`:
|
||||
|
@ -106,7 +106,7 @@ Of course there are still more issues to deal with. For example we'll hit proble
|
||||
Although this was a simple test it's been enough to demonstrate a few things about how Catch is used. Let's take a moment to consider those before we move on.
|
||||
|
||||
1. All we did was ```#define``` one identifier and ```#include``` one header and we got everything - even an implementation of ```main()``` that will [respond to command line arguments](command-line.md#top). You can only use that ```#define``` in one implementation file, for (hopefully) obvious reasons. Once you have more than one file with unit tests in you'll just ```#include "catch.hpp"``` and go. Usually it's a good idea to have a dedicated implementation file that just has ```#define CATCH_CONFIG_MAIN``` and ```#include "catch.hpp"```. You can also provide your own implementation of main and drive Catch yourself (see [Supplying-your-own-main()](own-main.md#top)).
|
||||
2. We introduce test cases with the ```TEST_CASE``` macro. This macro takes one or two arguments - a free form test name and, optionally, one or more tags (for more see <a href="#test-cases-and-sections">Test cases and Sections</a>, ). The test name must be unique. You can run sets of tests by specifying a wildcarded test name or a tag expression. See the [command line docs](command-line.md#top) for more information on running tests.
|
||||
2. We introduce test cases with the ```TEST_CASE``` macro. This macro takes one or two arguments - a free form test name and, optionally, one or more tags (for more see <a href="#test-cases-and-sections">Test cases and Sections</a>). The test name must be unique. You can run sets of tests by specifying a wildcarded test name or a tag expression. See the [command line docs](command-line.md#top) for more information on running tests.
|
||||
3. The name and tags arguments are just strings. We haven't had to declare a function or method - or explicitly register the test case anywhere. Behind the scenes a function with a generated name is defined for you, and automatically registered using static registry classes. By abstracting the function name away we can name our tests without the constraints of identifier names.
|
||||
4. We write our individual test assertions using the ```REQUIRE``` macro. Rather than a separate macro for each type of condition we express the condition naturally using C/C++ syntax. Behind the scenes a simple set of expression templates captures the left-hand-side and right-hand-side of the expression so we can display the values in our test report. As we'll see later there _are_ other assertion macros - but because of this technique the number of them is drastically reduced.
|
||||
|
||||
|
@ -144,7 +144,7 @@ function(ParseAndAddCatchTests_ParseFile SourceFile TestTarget)
|
||||
if("${TestType}" STREQUAL "SCENARIO")
|
||||
set(Name "Scenario: ${Name}")
|
||||
endif()
|
||||
if(PARSE_CATCH_TESTS_ADD_FIXTURE_IN_TEST_NAME AND TestFixture)
|
||||
if(PARSE_CATCH_TESTS_ADD_FIXTURE_IN_TEST_NAME AND "${TestType}" MATCHES "(CATCH_)?TEST_CASE_METHOD" AND TestFixture )
|
||||
set(CTestName "${TestFixture}:${Name}")
|
||||
else()
|
||||
set(CTestName "${Name}")
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,62 +0,0 @@
|
||||
/*
|
||||
* Created by Justin R. Wilson on 2/19/2017.
|
||||
* Copyright 2017 Justin R. Wilson. All rights reserved.
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
#ifndef TWOBLUECUBES_CATCH_REPORTER_AUTOMAKE_HPP_INCLUDED
|
||||
#define TWOBLUECUBES_CATCH_REPORTER_AUTOMAKE_HPP_INCLUDED
|
||||
|
||||
// Don't #include any Catch headers here - we can assume they are already
|
||||
// included before this header.
|
||||
// This is not good practice in general but is necessary in this case so this
|
||||
// file can be distributed as a single header that works with the main
|
||||
// Catch single header.
|
||||
|
||||
namespace Catch {
|
||||
|
||||
struct AutomakeReporter : StreamingReporterBase<AutomakeReporter> {
|
||||
AutomakeReporter( ReporterConfig const& _config )
|
||||
: StreamingReporterBase( _config )
|
||||
{}
|
||||
|
||||
~AutomakeReporter() override;
|
||||
|
||||
static std::string getDescription() {
|
||||
return "Reports test results in the format of Automake .trs files";
|
||||
}
|
||||
|
||||
void assertionStarting( AssertionInfo const& ) override {}
|
||||
|
||||
bool assertionEnded( AssertionStats const& /*_assertionStats*/ ) override { return true; }
|
||||
|
||||
void testCaseEnded( TestCaseStats const& _testCaseStats ) override {
|
||||
// Possible values to emit are PASS, XFAIL, SKIP, FAIL, XPASS and ERROR.
|
||||
stream << ":test-result: ";
|
||||
if (_testCaseStats.totals.assertions.allPassed()) {
|
||||
stream << "PASS";
|
||||
} else if (_testCaseStats.totals.assertions.allOk()) {
|
||||
stream << "XFAIL";
|
||||
} else {
|
||||
stream << "FAIL";
|
||||
}
|
||||
stream << ' ' << _testCaseStats.testInfo.name << '\n';
|
||||
StreamingReporterBase::testCaseEnded( _testCaseStats );
|
||||
}
|
||||
|
||||
void skipTest( TestCaseInfo const& testInfo ) override {
|
||||
stream << ":test-result: SKIP " << testInfo.name << '\n';
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#ifdef CATCH_IMPL
|
||||
AutomakeReporter::~AutomakeReporter() {}
|
||||
#endif
|
||||
|
||||
CATCH_REGISTER_REPORTER( "automake", AutomakeReporter)
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_REPORTER_AUTOMAKE_HPP_INCLUDED
|
@ -1,253 +0,0 @@
|
||||
/*
|
||||
* Created by Colton Wolkins on 2015-08-15.
|
||||
* Copyright 2015 Martin Moene. All rights reserved.
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
#ifndef TWOBLUECUBES_CATCH_REPORTER_TAP_HPP_INCLUDED
|
||||
#define TWOBLUECUBES_CATCH_REPORTER_TAP_HPP_INCLUDED
|
||||
|
||||
|
||||
// Don't #include any Catch headers here - we can assume they are already
|
||||
// included before this header.
|
||||
// This is not good practice in general but is necessary in this case so this
|
||||
// file can be distributed as a single header that works with the main
|
||||
// Catch single header.
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
namespace Catch {
|
||||
|
||||
struct TAPReporter : StreamingReporterBase<TAPReporter> {
|
||||
|
||||
using StreamingReporterBase::StreamingReporterBase;
|
||||
|
||||
~TAPReporter() override;
|
||||
|
||||
static std::string getDescription() {
|
||||
return "Reports test results in TAP format, suitable for test harnesses";
|
||||
}
|
||||
|
||||
ReporterPreferences getPreferences() const override {
|
||||
return m_reporterPrefs;
|
||||
}
|
||||
|
||||
void noMatchingTestCases( std::string const& spec ) override {
|
||||
stream << "# No test cases matched '" << spec << "'" << std::endl;
|
||||
}
|
||||
|
||||
void assertionStarting( AssertionInfo const& ) override {}
|
||||
|
||||
bool assertionEnded( AssertionStats const& _assertionStats ) override {
|
||||
++counter;
|
||||
|
||||
stream << "# " << currentTestCaseInfo->name << std::endl;
|
||||
AssertionPrinter printer( stream, _assertionStats, counter );
|
||||
printer.print();
|
||||
|
||||
stream << std::endl;
|
||||
return true;
|
||||
}
|
||||
|
||||
void testRunEnded( TestRunStats const& _testRunStats ) override {
|
||||
printTotals( _testRunStats.totals );
|
||||
stream << "\n" << std::endl;
|
||||
StreamingReporterBase::testRunEnded( _testRunStats );
|
||||
}
|
||||
|
||||
private:
|
||||
std::size_t counter = 0;
|
||||
class AssertionPrinter {
|
||||
public:
|
||||
AssertionPrinter& operator= ( AssertionPrinter const& ) = delete;
|
||||
AssertionPrinter( AssertionPrinter const& ) = delete;
|
||||
AssertionPrinter( std::ostream& _stream, AssertionStats const& _stats, std::size_t _counter )
|
||||
: stream( _stream )
|
||||
, result( _stats.assertionResult )
|
||||
, messages( _stats.infoMessages )
|
||||
, itMessage( _stats.infoMessages.begin() )
|
||||
, printInfoMessages( true )
|
||||
, counter(_counter)
|
||||
{}
|
||||
|
||||
void print() {
|
||||
itMessage = messages.begin();
|
||||
|
||||
switch( result.getResultType() ) {
|
||||
case ResultWas::Ok:
|
||||
printResultType( passedString() );
|
||||
printOriginalExpression();
|
||||
printReconstructedExpression();
|
||||
if ( ! result.hasExpression() )
|
||||
printRemainingMessages( Colour::None );
|
||||
else
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::ExpressionFailed:
|
||||
if (result.isOk()) {
|
||||
printResultType(passedString());
|
||||
} else {
|
||||
printResultType(failedString());
|
||||
}
|
||||
printOriginalExpression();
|
||||
printReconstructedExpression();
|
||||
if (result.isOk()) {
|
||||
printIssue(" # TODO");
|
||||
}
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::ThrewException:
|
||||
printResultType( failedString() );
|
||||
printIssue( "unexpected exception with message:" );
|
||||
printMessage();
|
||||
printExpressionWas();
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::FatalErrorCondition:
|
||||
printResultType( failedString() );
|
||||
printIssue( "fatal error condition with message:" );
|
||||
printMessage();
|
||||
printExpressionWas();
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::DidntThrowException:
|
||||
printResultType( failedString() );
|
||||
printIssue( "expected exception, got none" );
|
||||
printExpressionWas();
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::Info:
|
||||
printResultType( "info" );
|
||||
printMessage();
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::Warning:
|
||||
printResultType( "warning" );
|
||||
printMessage();
|
||||
printRemainingMessages();
|
||||
break;
|
||||
case ResultWas::ExplicitFailure:
|
||||
printResultType( failedString() );
|
||||
printIssue( "explicitly" );
|
||||
printRemainingMessages( Colour::None );
|
||||
break;
|
||||
// These cases are here to prevent compiler warnings
|
||||
case ResultWas::Unknown:
|
||||
case ResultWas::FailureBit:
|
||||
case ResultWas::Exception:
|
||||
printResultType( "** internal error **" );
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
static Colour::Code dimColour() { return Colour::FileName; }
|
||||
|
||||
static const char* failedString() { return "not ok"; }
|
||||
static const char* passedString() { return "ok"; }
|
||||
|
||||
void printSourceInfo() const {
|
||||
Colour colourGuard( dimColour() );
|
||||
stream << result.getSourceInfo() << ":";
|
||||
}
|
||||
|
||||
void printResultType( std::string const& passOrFail ) const {
|
||||
if( !passOrFail.empty() ) {
|
||||
stream << passOrFail << ' ' << counter << " -";
|
||||
}
|
||||
}
|
||||
|
||||
void printIssue( std::string const& issue ) const {
|
||||
stream << " " << issue;
|
||||
}
|
||||
|
||||
void printExpressionWas() {
|
||||
if( result.hasExpression() ) {
|
||||
stream << ";";
|
||||
{
|
||||
Colour colour( dimColour() );
|
||||
stream << " expression was:";
|
||||
}
|
||||
printOriginalExpression();
|
||||
}
|
||||
}
|
||||
|
||||
void printOriginalExpression() const {
|
||||
if( result.hasExpression() ) {
|
||||
stream << " " << result.getExpression();
|
||||
}
|
||||
}
|
||||
|
||||
void printReconstructedExpression() const {
|
||||
if( result.hasExpandedExpression() ) {
|
||||
{
|
||||
Colour colour( dimColour() );
|
||||
stream << " for: ";
|
||||
}
|
||||
std::string expr = result.getExpandedExpression();
|
||||
std::replace( expr.begin(), expr.end(), '\n', ' ');
|
||||
stream << expr;
|
||||
}
|
||||
}
|
||||
|
||||
void printMessage() {
|
||||
if ( itMessage != messages.end() ) {
|
||||
stream << " '" << itMessage->message << "'";
|
||||
++itMessage;
|
||||
}
|
||||
}
|
||||
|
||||
void printRemainingMessages( Colour::Code colour = dimColour() ) {
|
||||
if (itMessage == messages.end()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// using messages.end() directly (or auto) yields compilation error:
|
||||
std::vector<MessageInfo>::const_iterator itEnd = messages.end();
|
||||
const std::size_t N = static_cast<std::size_t>( std::distance( itMessage, itEnd ) );
|
||||
|
||||
{
|
||||
Colour colourGuard( colour );
|
||||
stream << " with " << pluralise( N, "message" ) << ":";
|
||||
}
|
||||
|
||||
for(; itMessage != itEnd; ) {
|
||||
// If this assertion is a warning ignore any INFO messages
|
||||
if( printInfoMessages || itMessage->type != ResultWas::Info ) {
|
||||
stream << " '" << itMessage->message << "'";
|
||||
if ( ++itMessage != itEnd ) {
|
||||
Colour colourGuard( dimColour() );
|
||||
stream << " and";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
std::ostream& stream;
|
||||
AssertionResult const& result;
|
||||
std::vector<MessageInfo> messages;
|
||||
std::vector<MessageInfo>::const_iterator itMessage;
|
||||
bool printInfoMessages;
|
||||
std::size_t counter;
|
||||
};
|
||||
|
||||
void printTotals( const Totals& totals ) const {
|
||||
if( totals.testCases.total() == 0 ) {
|
||||
stream << "1..0 # Skipped: No tests ran.";
|
||||
} else {
|
||||
stream << "1.." << counter;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
#ifdef CATCH_IMPL
|
||||
TAPReporter::~TAPReporter() {}
|
||||
#endif
|
||||
|
||||
CATCH_REGISTER_REPORTER( "tap", TAPReporter )
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_REPORTER_TAP_HPP_INCLUDED
|
@ -1,219 +0,0 @@
|
||||
/*
|
||||
* Created by Phil Nash on 19th December 2014
|
||||
* Copyright 2014 Two Blue Cubes Ltd. All rights reserved.
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
#ifndef TWOBLUECUBES_CATCH_REPORTER_TEAMCITY_HPP_INCLUDED
|
||||
#define TWOBLUECUBES_CATCH_REPORTER_TEAMCITY_HPP_INCLUDED
|
||||
|
||||
// Don't #include any Catch headers here - we can assume they are already
|
||||
// included before this header.
|
||||
// This is not good practice in general but is necessary in this case so this
|
||||
// file can be distributed as a single header that works with the main
|
||||
// Catch single header.
|
||||
|
||||
#include <cstring>
|
||||
|
||||
#ifdef __clang__
|
||||
# pragma clang diagnostic push
|
||||
# pragma clang diagnostic ignored "-Wpadded"
|
||||
#endif
|
||||
|
||||
namespace Catch {
|
||||
|
||||
struct TeamCityReporter : StreamingReporterBase<TeamCityReporter> {
|
||||
TeamCityReporter( ReporterConfig const& _config )
|
||||
: StreamingReporterBase( _config )
|
||||
{
|
||||
m_reporterPrefs.shouldRedirectStdOut = true;
|
||||
}
|
||||
|
||||
static std::string escape( std::string const& str ) {
|
||||
std::string escaped = str;
|
||||
replaceInPlace( escaped, "|", "||" );
|
||||
replaceInPlace( escaped, "'", "|'" );
|
||||
replaceInPlace( escaped, "\n", "|n" );
|
||||
replaceInPlace( escaped, "\r", "|r" );
|
||||
replaceInPlace( escaped, "[", "|[" );
|
||||
replaceInPlace( escaped, "]", "|]" );
|
||||
return escaped;
|
||||
}
|
||||
~TeamCityReporter() override;
|
||||
|
||||
static std::string getDescription() {
|
||||
return "Reports test results as TeamCity service messages";
|
||||
}
|
||||
|
||||
void skipTest( TestCaseInfo const& /* testInfo */ ) override {
|
||||
}
|
||||
|
||||
void noMatchingTestCases( std::string const& /* spec */ ) override {}
|
||||
|
||||
void testGroupStarting( GroupInfo const& groupInfo ) override {
|
||||
StreamingReporterBase::testGroupStarting( groupInfo );
|
||||
stream << "##teamcity[testSuiteStarted name='"
|
||||
<< escape( groupInfo.name ) << "']\n";
|
||||
}
|
||||
void testGroupEnded( TestGroupStats const& testGroupStats ) override {
|
||||
StreamingReporterBase::testGroupEnded( testGroupStats );
|
||||
stream << "##teamcity[testSuiteFinished name='"
|
||||
<< escape( testGroupStats.groupInfo.name ) << "']\n";
|
||||
}
|
||||
|
||||
|
||||
void assertionStarting( AssertionInfo const& ) override {}
|
||||
|
||||
bool assertionEnded( AssertionStats const& assertionStats ) override {
|
||||
AssertionResult const& result = assertionStats.assertionResult;
|
||||
if( !result.isOk() ) {
|
||||
|
||||
ReusableStringStream msg;
|
||||
if( !m_headerPrintedForThisSection )
|
||||
printSectionHeader( msg.get() );
|
||||
m_headerPrintedForThisSection = true;
|
||||
|
||||
msg << result.getSourceInfo() << "\n";
|
||||
|
||||
switch( result.getResultType() ) {
|
||||
case ResultWas::ExpressionFailed:
|
||||
msg << "expression failed";
|
||||
break;
|
||||
case ResultWas::ThrewException:
|
||||
msg << "unexpected exception";
|
||||
break;
|
||||
case ResultWas::FatalErrorCondition:
|
||||
msg << "fatal error condition";
|
||||
break;
|
||||
case ResultWas::DidntThrowException:
|
||||
msg << "no exception was thrown where one was expected";
|
||||
break;
|
||||
case ResultWas::ExplicitFailure:
|
||||
msg << "explicit failure";
|
||||
break;
|
||||
|
||||
// We shouldn't get here because of the isOk() test
|
||||
case ResultWas::Ok:
|
||||
case ResultWas::Info:
|
||||
case ResultWas::Warning:
|
||||
CATCH_ERROR( "Internal error in TeamCity reporter" );
|
||||
// These cases are here to prevent compiler warnings
|
||||
case ResultWas::Unknown:
|
||||
case ResultWas::FailureBit:
|
||||
case ResultWas::Exception:
|
||||
CATCH_ERROR( "Not implemented" );
|
||||
}
|
||||
if( assertionStats.infoMessages.size() == 1 )
|
||||
msg << " with message:";
|
||||
if( assertionStats.infoMessages.size() > 1 )
|
||||
msg << " with messages:";
|
||||
for( auto const& messageInfo : assertionStats.infoMessages )
|
||||
msg << "\n \"" << messageInfo.message << "\"";
|
||||
|
||||
|
||||
if( result.hasExpression() ) {
|
||||
msg <<
|
||||
"\n " << result.getExpressionInMacro() << "\n"
|
||||
"with expansion:\n" <<
|
||||
" " << result.getExpandedExpression() << "\n";
|
||||
}
|
||||
|
||||
if( currentTestCaseInfo->okToFail() ) {
|
||||
msg << "- failure ignore as test marked as 'ok to fail'\n";
|
||||
stream << "##teamcity[testIgnored"
|
||||
<< " name='" << escape( currentTestCaseInfo->name )<< "'"
|
||||
<< " message='" << escape( msg.str() ) << "'"
|
||||
<< "]\n";
|
||||
}
|
||||
else {
|
||||
stream << "##teamcity[testFailed"
|
||||
<< " name='" << escape( currentTestCaseInfo->name )<< "'"
|
||||
<< " message='" << escape( msg.str() ) << "'"
|
||||
<< "]\n";
|
||||
}
|
||||
}
|
||||
stream.flush();
|
||||
return true;
|
||||
}
|
||||
|
||||
void sectionStarting( SectionInfo const& sectionInfo ) override {
|
||||
m_headerPrintedForThisSection = false;
|
||||
StreamingReporterBase::sectionStarting( sectionInfo );
|
||||
}
|
||||
|
||||
void testCaseStarting( TestCaseInfo const& testInfo ) override {
|
||||
m_testTimer.start();
|
||||
StreamingReporterBase::testCaseStarting( testInfo );
|
||||
stream << "##teamcity[testStarted name='"
|
||||
<< escape( testInfo.name ) << "']\n";
|
||||
stream.flush();
|
||||
}
|
||||
|
||||
void testCaseEnded( TestCaseStats const& testCaseStats ) override {
|
||||
StreamingReporterBase::testCaseEnded( testCaseStats );
|
||||
if( !testCaseStats.stdOut.empty() )
|
||||
stream << "##teamcity[testStdOut name='"
|
||||
<< escape( testCaseStats.testInfo.name )
|
||||
<< "' out='" << escape( testCaseStats.stdOut ) << "']\n";
|
||||
if( !testCaseStats.stdErr.empty() )
|
||||
stream << "##teamcity[testStdErr name='"
|
||||
<< escape( testCaseStats.testInfo.name )
|
||||
<< "' out='" << escape( testCaseStats.stdErr ) << "']\n";
|
||||
stream << "##teamcity[testFinished name='"
|
||||
<< escape( testCaseStats.testInfo.name ) << "' duration='"
|
||||
<< m_testTimer.getElapsedMilliseconds() << "']\n";
|
||||
stream.flush();
|
||||
}
|
||||
|
||||
private:
|
||||
void printSectionHeader( std::ostream& os ) {
|
||||
assert( !m_sectionStack.empty() );
|
||||
|
||||
if( m_sectionStack.size() > 1 ) {
|
||||
os << getLineOfChars<'-'>() << "\n";
|
||||
|
||||
std::vector<SectionInfo>::const_iterator
|
||||
it = m_sectionStack.begin()+1, // Skip first section (test case)
|
||||
itEnd = m_sectionStack.end();
|
||||
for( ; it != itEnd; ++it )
|
||||
printHeaderString( os, it->name );
|
||||
os << getLineOfChars<'-'>() << "\n";
|
||||
}
|
||||
|
||||
SourceLineInfo lineInfo = m_sectionStack.front().lineInfo;
|
||||
|
||||
os << lineInfo << "\n";
|
||||
os << getLineOfChars<'.'>() << "\n\n";
|
||||
}
|
||||
|
||||
// if string has a : in first line will set indent to follow it on
|
||||
// subsequent lines
|
||||
static void printHeaderString( std::ostream& os, std::string const& _string, std::size_t indent = 0 ) {
|
||||
std::size_t i = _string.find( ": " );
|
||||
if( i != std::string::npos )
|
||||
i+=2;
|
||||
else
|
||||
i = 0;
|
||||
os << Column( _string )
|
||||
.indent( indent+i)
|
||||
.initialIndent( indent ) << "\n";
|
||||
}
|
||||
private:
|
||||
bool m_headerPrintedForThisSection = false;
|
||||
Timer m_testTimer;
|
||||
};
|
||||
|
||||
#ifdef CATCH_IMPL
|
||||
TeamCityReporter::~TeamCityReporter() {}
|
||||
#endif
|
||||
|
||||
CATCH_REGISTER_REPORTER( "teamcity", TeamCityReporter )
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
#ifdef __clang__
|
||||
# pragma clang diagnostic pop
|
||||
#endif
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_REPORTER_TEAMCITY_HPP_INCLUDED
|
@ -18,6 +18,7 @@
|
||||
#include <algorithm>
|
||||
#include <functional>
|
||||
#include <vector>
|
||||
#include <iterator>
|
||||
#include <numeric>
|
||||
#include <tuple>
|
||||
#include <cmath>
|
||||
|
@ -39,10 +39,6 @@
|
||||
|
||||
#endif
|
||||
|
||||
#if defined(CATCH_CPP17_OR_GREATER)
|
||||
# define CATCH_INTERNAL_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS
|
||||
#endif
|
||||
|
||||
// We have to avoid both ICC and Clang, because they try to mask themselves
|
||||
// as gcc, and we want only GCC in this block
|
||||
#if defined(__GNUC__) && !defined(__clang__) && !defined(__ICC)
|
||||
@ -56,6 +52,9 @@
|
||||
|
||||
# define CATCH_INTERNAL_SUPPRESS_UNUSED_VARIABLE_WARNINGS \
|
||||
_Pragma( "GCC diagnostic ignored \"-Wunused-variable\"" )
|
||||
|
||||
# define CATCH_INTERNAL_IGNORE_BUT_WARN(...) (void)__builtin_constant_p(__VA_ARGS__)
|
||||
|
||||
#endif
|
||||
|
||||
#if defined(__clang__)
|
||||
@ -63,6 +62,22 @@
|
||||
# define CATCH_INTERNAL_START_WARNINGS_SUPPRESSION _Pragma( "clang diagnostic push" )
|
||||
# define CATCH_INTERNAL_STOP_WARNINGS_SUPPRESSION _Pragma( "clang diagnostic pop" )
|
||||
|
||||
// As of this writing, IBM XL's implementation of __builtin_constant_p has a bug
|
||||
// which results in calls to destructors being emitted for each temporary,
|
||||
// without a matching initialization. In practice, this can result in something
|
||||
// like `std::string::~string` being called on an uninitialized value.
|
||||
//
|
||||
// For example, this code will likely segfault under IBM XL:
|
||||
// ```
|
||||
// REQUIRE(std::string("12") + "34" == "1234")
|
||||
// ```
|
||||
//
|
||||
// Therefore, `CATCH_INTERNAL_IGNORE_BUT_WARN` is not implemented.
|
||||
# if !defined(__ibmxl__)
|
||||
# define CATCH_INTERNAL_IGNORE_BUT_WARN(...) (void)__builtin_constant_p(__VA_ARGS__) /* NOLINT(cppcoreguidelines-pro-type-vararg) */
|
||||
# endif
|
||||
|
||||
|
||||
# define CATCH_INTERNAL_SUPPRESS_GLOBALS_WARNINGS \
|
||||
_Pragma( "clang diagnostic ignored \"-Wexit-time-destructors\"" ) \
|
||||
_Pragma( "clang diagnostic ignored \"-Wglobal-constructors\"")
|
||||
@ -142,10 +157,6 @@
|
||||
# define CATCH_INTERNAL_START_WARNINGS_SUPPRESSION __pragma( warning(push) )
|
||||
# define CATCH_INTERNAL_STOP_WARNINGS_SUPPRESSION __pragma( warning(pop) )
|
||||
|
||||
# if _MSC_VER >= 1900 // Visual Studio 2015 or newer
|
||||
# define CATCH_INTERNAL_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS
|
||||
# endif
|
||||
|
||||
// Universal Windows platform does not support SEH
|
||||
// Or console colours (or console at all...)
|
||||
# if defined(WINAPI_FAMILY) && (WINAPI_FAMILY == WINAPI_FAMILY_APP)
|
||||
@ -273,10 +284,6 @@
|
||||
# define CATCH_CONFIG_CPP17_OPTIONAL
|
||||
#endif
|
||||
|
||||
#if defined(CATCH_INTERNAL_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS) && !defined(CATCH_CONFIG_NO_CPP17_UNCAUGHT_EXCEPTIONS) && !defined(CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS)
|
||||
# define CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS
|
||||
#endif
|
||||
|
||||
#if defined(CATCH_INTERNAL_CONFIG_CPP17_STRING_VIEW) && !defined(CATCH_CONFIG_NO_CPP17_STRING_VIEW) && !defined(CATCH_CONFIG_CPP17_STRING_VIEW)
|
||||
# define CATCH_CONFIG_CPP17_STRING_VIEW
|
||||
#endif
|
||||
@ -340,6 +347,11 @@
|
||||
# define CATCH_INTERNAL_SUPPRESS_ZERO_VARIADIC_WARNINGS
|
||||
#endif
|
||||
|
||||
// The goal of this macro is to avoid evaluation of the arguments, but
|
||||
// still have the compiler warn on problems inside...
|
||||
#if !defined(CATCH_INTERNAL_IGNORE_BUT_WARN)
|
||||
# define CATCH_INTERNAL_IGNORE_BUT_WARN(...)
|
||||
#endif
|
||||
|
||||
#if defined(__APPLE__) && defined(__apple_build_version__) && (__clang_major__ < 10)
|
||||
# undef CATCH_INTERNAL_SUPPRESS_UNUSED_TEMPLATE_WARNINGS
|
||||
|
@ -14,8 +14,7 @@
|
||||
|
||||
#if defined(CATCH_PLATFORM_MAC) || defined(CATCH_PLATFORM_IPHONE)
|
||||
|
||||
# include <assert.h>
|
||||
# include <stdbool.h>
|
||||
# include <cassert>
|
||||
# include <sys/types.h>
|
||||
# include <unistd.h>
|
||||
# include <cstddef>
|
||||
|
@ -208,6 +208,18 @@ namespace Catch {
|
||||
auto operator <= ( RhsT const& rhs ) -> BinaryExpr<LhsT, RhsT const&> const {
|
||||
return { static_cast<bool>(m_lhs <= rhs), m_lhs, "<=", rhs };
|
||||
}
|
||||
template <typename RhsT>
|
||||
auto operator | (RhsT const& rhs) -> BinaryExpr<LhsT, RhsT const&> const {
|
||||
return { static_cast<bool>(m_lhs | rhs), m_lhs, "|", rhs };
|
||||
}
|
||||
template <typename RhsT>
|
||||
auto operator & (RhsT const& rhs) -> BinaryExpr<LhsT, RhsT const&> const {
|
||||
return { static_cast<bool>(m_lhs & rhs), m_lhs, "&", rhs };
|
||||
}
|
||||
template <typename RhsT>
|
||||
auto operator ^ (RhsT const& rhs) -> BinaryExpr<LhsT, RhsT const&> const {
|
||||
return { static_cast<bool>(m_lhs ^ rhs), m_lhs, "^", rhs };
|
||||
}
|
||||
|
||||
template<typename RhsT>
|
||||
auto operator && ( RhsT const& ) -> BinaryExpr<LhsT, RhsT const&> const {
|
||||
|
@ -16,27 +16,70 @@
|
||||
#include <catch2/catch_test_case_info.hpp>
|
||||
#include <catch2/catch_test_spec.hpp>
|
||||
|
||||
#include <algorithm>
|
||||
#include <iterator>
|
||||
#include <random>
|
||||
#include <sstream>
|
||||
|
||||
namespace Catch {
|
||||
|
||||
std::vector<TestCaseHandle> sortTests( IConfig const& config, std::vector<TestCaseHandle> const& unsortedTestCases ) {
|
||||
|
||||
std::vector<TestCaseHandle> sorted = unsortedTestCases;
|
||||
|
||||
switch( config.runOrder() ) {
|
||||
case RunTests::InLexicographicalOrder:
|
||||
std::sort( sorted.begin(), sorted.end() );
|
||||
break;
|
||||
case RunTests::InRandomOrder:
|
||||
seedRng( config );
|
||||
std::shuffle( sorted.begin(), sorted.end(), rng() );
|
||||
break;
|
||||
case RunTests::InDeclarationOrder:
|
||||
// already in declaration order
|
||||
break;
|
||||
namespace {
|
||||
struct HashTest {
|
||||
explicit HashTest(SimplePcg32& rng) {
|
||||
basis = rng();
|
||||
basis <<= 32;
|
||||
basis |= rng();
|
||||
}
|
||||
return sorted;
|
||||
|
||||
uint64_t basis;
|
||||
|
||||
uint64_t operator()(TestCaseInfo const& t) const {
|
||||
// Modified FNV-1a hash
|
||||
static constexpr uint64_t prime = 1099511628211;
|
||||
uint64_t hash = basis;
|
||||
for (const char c : t.name) {
|
||||
hash ^= c;
|
||||
hash *= prime;
|
||||
}
|
||||
return hash;
|
||||
}
|
||||
};
|
||||
} // end anonymous namespace
|
||||
|
||||
std::vector<TestCaseHandle> sortTests( IConfig const& config, std::vector<TestCaseHandle> const& unsortedTestCases ) {
|
||||
switch (config.runOrder()) {
|
||||
case RunTests::InDeclarationOrder:
|
||||
return unsortedTestCases;
|
||||
|
||||
case RunTests::InLexicographicalOrder: {
|
||||
std::vector<TestCaseHandle> sorted = unsortedTestCases;
|
||||
std::sort(sorted.begin(), sorted.end());
|
||||
return sorted;
|
||||
}
|
||||
case RunTests::InRandomOrder: {
|
||||
seedRng(config);
|
||||
HashTest h(rng());
|
||||
std::vector<std::pair<uint64_t, TestCaseHandle>> indexed_tests;
|
||||
indexed_tests.reserve(unsortedTestCases.size());
|
||||
|
||||
for (auto const& handle : unsortedTestCases) {
|
||||
indexed_tests.emplace_back(h(handle.getTestCaseInfo()), handle);
|
||||
}
|
||||
|
||||
std::sort(indexed_tests.begin(), indexed_tests.end());
|
||||
|
||||
std::vector<TestCaseHandle> randomized;
|
||||
randomized.reserve(indexed_tests.size());
|
||||
|
||||
for (auto const& indexed : indexed_tests) {
|
||||
randomized.push_back(indexed.second);
|
||||
}
|
||||
|
||||
return randomized;
|
||||
}
|
||||
}
|
||||
|
||||
CATCH_INTERNAL_ERROR("Unknown test order value!");
|
||||
}
|
||||
|
||||
bool isThrowSafe( TestCaseHandle const& testCase, IConfig const& config ) {
|
||||
|
@ -46,6 +46,8 @@
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_TEST( macroName, resultDisposition, ... ) \
|
||||
do { \
|
||||
/* The expression should not be evaluated, but warnings should hopefully be checked */ \
|
||||
CATCH_INTERNAL_IGNORE_BUT_WARN(__VA_ARGS__); \
|
||||
Catch::AssertionHandler catchAssertionHandler( macroName##_catch_sr, CATCH_INTERNAL_LINEINFO, CATCH_INTERNAL_STRINGIFY(__VA_ARGS__), resultDisposition ); \
|
||||
INTERNAL_CATCH_TRY { \
|
||||
CATCH_INTERNAL_START_WARNINGS_SUPPRESSION \
|
||||
@ -54,8 +56,7 @@
|
||||
CATCH_INTERNAL_STOP_WARNINGS_SUPPRESSION \
|
||||
} INTERNAL_CATCH_CATCH( catchAssertionHandler ) \
|
||||
INTERNAL_CATCH_REACT( catchAssertionHandler ) \
|
||||
} while( (void)0, (false) && static_cast<bool>( !!(__VA_ARGS__) ) ) // the expression here is never evaluated at runtime but it forces the compiler to give it a look
|
||||
// The double negation silences MSVC's C4800 warning, the static_cast forces short-circuit evaluation if the type has overloaded &&.
|
||||
} while( (void)0, (false) && static_cast<bool>( !!(__VA_ARGS__) ) )
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_IF( macroName, resultDisposition, ... ) \
|
||||
|
@ -170,6 +170,7 @@ namespace Catch {
|
||||
m_pos = m_arg.size();
|
||||
m_substring.clear();
|
||||
m_patternName.clear();
|
||||
m_realPatternPos = 0;
|
||||
return false;
|
||||
}
|
||||
endMode();
|
||||
@ -188,6 +189,7 @@ namespace Catch {
|
||||
}
|
||||
|
||||
m_patternName.clear();
|
||||
m_realPatternPos = 0;
|
||||
|
||||
return token;
|
||||
}
|
||||
|
@ -12,7 +12,7 @@
|
||||
|
||||
namespace Catch {
|
||||
bool uncaught_exceptions() {
|
||||
#if defined(CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS)
|
||||
#if defined(CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS) || (defined(__cpp_lib_uncaught_exceptions) && !defined(CATCH_CONFIG_NO_CPP17_UNCAUGHT_EXCEPTIONS))
|
||||
return std::uncaught_exceptions() > 0;
|
||||
#else
|
||||
return std::uncaught_exception();
|
||||
|
@ -16,14 +16,14 @@
|
||||
namespace Catch {
|
||||
namespace Matchers {
|
||||
|
||||
template<typename T>
|
||||
struct ContainsElementMatcher final : MatcherBase<std::vector<T>> {
|
||||
template<typename T, typename Alloc>
|
||||
struct ContainsElementMatcher final : MatcherBase<std::vector<T, Alloc>> {
|
||||
|
||||
ContainsElementMatcher(T const& comparator):
|
||||
m_comparator(comparator)
|
||||
{}
|
||||
|
||||
bool match(std::vector<T> const& v) const override {
|
||||
bool match(std::vector<T, Alloc> const& v) const override {
|
||||
for (auto const& el : v) {
|
||||
if (el == m_comparator) {
|
||||
return true;
|
||||
@ -39,14 +39,14 @@ namespace Matchers {
|
||||
T const& m_comparator;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct ContainsMatcher final : MatcherBase<std::vector<T>> {
|
||||
template<typename T, typename AllocComp, typename AllocMatch>
|
||||
struct ContainsMatcher final : MatcherBase<std::vector<T, AllocMatch>> {
|
||||
|
||||
ContainsMatcher(std::vector<T> const& comparator):
|
||||
m_comparator(comparator)
|
||||
ContainsMatcher(std::vector<T, AllocComp> const& comparator):
|
||||
m_comparator( comparator )
|
||||
{}
|
||||
|
||||
bool match(std::vector<T> const& v) const override {
|
||||
bool match(std::vector<T, AllocMatch> const& v) const override {
|
||||
// !TBD: see note in EqualsMatcher
|
||||
if (m_comparator.size() > v.size())
|
||||
return false;
|
||||
@ -68,15 +68,17 @@ namespace Matchers {
|
||||
return "Contains: " + ::Catch::Detail::stringify( m_comparator );
|
||||
}
|
||||
|
||||
std::vector<T> const& m_comparator;
|
||||
std::vector<T, AllocComp> const& m_comparator;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct EqualsMatcher final : MatcherBase<std::vector<T>> {
|
||||
template<typename T, typename AllocComp, typename AllocMatch>
|
||||
struct EqualsMatcher final : MatcherBase<std::vector<T, AllocMatch>> {
|
||||
|
||||
EqualsMatcher(std::vector<T> const &comparator) : m_comparator( comparator ) {}
|
||||
EqualsMatcher(std::vector<T, AllocComp> const& comparator):
|
||||
m_comparator( comparator )
|
||||
{}
|
||||
|
||||
bool match(std::vector<T> const &v) const override {
|
||||
bool match(std::vector<T, AllocMatch> const& v) const override {
|
||||
// !TBD: This currently works if all elements can be compared using !=
|
||||
// - a more general approach would be via a compare template that defaults
|
||||
// to using !=. but could be specialised for, e.g. std::vector<T> etc
|
||||
@ -91,15 +93,17 @@ namespace Matchers {
|
||||
std::string describe() const override {
|
||||
return "Equals: " + ::Catch::Detail::stringify( m_comparator );
|
||||
}
|
||||
std::vector<T> const& m_comparator;
|
||||
std::vector<T, AllocComp> const& m_comparator;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct ApproxMatcher final : MatcherBase<std::vector<T>> {
|
||||
template<typename T, typename AllocComp, typename AllocMatch>
|
||||
struct ApproxMatcher final : MatcherBase<std::vector<T, AllocMatch>> {
|
||||
|
||||
ApproxMatcher(std::vector<T> const& comparator) : m_comparator( comparator ) {}
|
||||
ApproxMatcher(std::vector<T, AllocComp> const& comparator):
|
||||
m_comparator( comparator )
|
||||
{}
|
||||
|
||||
bool match(std::vector<T> const &v) const override {
|
||||
bool match(std::vector<T, AllocMatch> const& v) const override {
|
||||
if (m_comparator.size() != v.size())
|
||||
return false;
|
||||
for (std::size_t i = 0; i < v.size(); ++i)
|
||||
@ -126,14 +130,16 @@ namespace Matchers {
|
||||
return *this;
|
||||
}
|
||||
|
||||
std::vector<T> const& m_comparator;
|
||||
std::vector<T, AllocComp> const& m_comparator;
|
||||
mutable Catch::Approx approx = Catch::Approx::custom();
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct UnorderedEqualsMatcher final : MatcherBase<std::vector<T>> {
|
||||
UnorderedEqualsMatcher(std::vector<T> const& target) : m_target(target) {}
|
||||
bool match(std::vector<T> const& vec) const override {
|
||||
template<typename T, typename AllocComp, typename AllocMatch>
|
||||
struct UnorderedEqualsMatcher final : MatcherBase<std::vector<T, AllocMatch>> {
|
||||
UnorderedEqualsMatcher(std::vector<T, AllocComp> const& target):
|
||||
m_target(target)
|
||||
{}
|
||||
bool match(std::vector<T, AllocMatch> const& vec) const override {
|
||||
// Note: This is a reimplementation of std::is_permutation,
|
||||
// because I don't want to include <algorithm> inside the common path
|
||||
if (m_target.size() != vec.size()) {
|
||||
@ -146,7 +152,7 @@ namespace Matchers {
|
||||
return "UnorderedEquals: " + ::Catch::Detail::stringify(m_target);
|
||||
}
|
||||
private:
|
||||
std::vector<T> const& m_target;
|
||||
std::vector<T, AllocComp> const& m_target;
|
||||
};
|
||||
|
||||
|
||||
@ -155,33 +161,33 @@ namespace Matchers {
|
||||
|
||||
|
||||
//! Creates a matcher that matches vectors that contain all elements in `comparator`
|
||||
template<typename T>
|
||||
ContainsMatcher<T> Contains( std::vector<T> const& comparator ) {
|
||||
return ContainsMatcher<T>( comparator );
|
||||
template<typename T, typename AllocComp = std::allocator<T>, typename AllocMatch = AllocComp>
|
||||
ContainsMatcher<T, AllocComp, AllocMatch> Contains( std::vector<T, AllocComp> const& comparator ) {
|
||||
return ContainsMatcher<T, AllocComp, AllocMatch>(comparator);
|
||||
}
|
||||
|
||||
//! Creates a matcher that matches vectors that contain `comparator` as an element
|
||||
template<typename T>
|
||||
ContainsElementMatcher<T> VectorContains( T const& comparator ) {
|
||||
return ContainsElementMatcher<T>( comparator );
|
||||
template<typename T, typename Alloc = std::allocator<T>>
|
||||
ContainsElementMatcher<T, Alloc> VectorContains( T const& comparator ) {
|
||||
return ContainsElementMatcher<T, Alloc>(comparator);
|
||||
}
|
||||
|
||||
//! Creates a matcher that matches vectors that are exactly equal to `comparator`
|
||||
template<typename T>
|
||||
EqualsMatcher<T> Equals( std::vector<T> const& comparator ) {
|
||||
return EqualsMatcher<T>( comparator );
|
||||
template<typename T, typename AllocComp = std::allocator<T>, typename AllocMatch = AllocComp>
|
||||
EqualsMatcher<T, AllocComp, AllocMatch> Equals( std::vector<T, AllocComp> const& comparator ) {
|
||||
return EqualsMatcher<T, AllocComp, AllocMatch>(comparator);
|
||||
}
|
||||
|
||||
//! Creates a matcher that matches vectors that `comparator` as an element
|
||||
template<typename T>
|
||||
ApproxMatcher<T> Approx( std::vector<T> const& comparator ) {
|
||||
return ApproxMatcher<T>( comparator );
|
||||
template<typename T, typename AllocComp = std::allocator<T>, typename AllocMatch = AllocComp>
|
||||
ApproxMatcher<T, AllocComp, AllocMatch> Approx( std::vector<T, AllocComp> const& comparator ) {
|
||||
return ApproxMatcher<T, AllocComp, AllocMatch>(comparator);
|
||||
}
|
||||
|
||||
//! Creates a matcher that matches vectors that is equal to `target` modulo permutation
|
||||
template<typename T>
|
||||
UnorderedEqualsMatcher<T> UnorderedEquals(std::vector<T> const& target) {
|
||||
return UnorderedEqualsMatcher<T>(target);
|
||||
template<typename T, typename AllocComp = std::allocator<T>, typename AllocMatch = AllocComp>
|
||||
UnorderedEqualsMatcher<T, AllocComp, AllocMatch> UnorderedEquals(std::vector<T, AllocComp> const& target) {
|
||||
return UnorderedEqualsMatcher<T, AllocComp, AllocMatch>(target);
|
||||
}
|
||||
|
||||
} // namespace Matchers
|
||||
|
@ -211,15 +211,11 @@ class Duration {
|
||||
static const uint64_t s_nanosecondsInASecond = 1000 * s_nanosecondsInAMillisecond;
|
||||
static const uint64_t s_nanosecondsInAMinute = 60 * s_nanosecondsInASecond;
|
||||
|
||||
uint64_t m_inNanoseconds;
|
||||
double m_inNanoseconds;
|
||||
Unit m_units;
|
||||
|
||||
public:
|
||||
explicit Duration(double inNanoseconds, Unit units = Unit::Auto)
|
||||
: Duration(static_cast<uint64_t>(inNanoseconds), units) {
|
||||
}
|
||||
|
||||
explicit Duration(uint64_t inNanoseconds, Unit units = Unit::Auto)
|
||||
explicit Duration(double inNanoseconds, Unit units = Unit::Auto)
|
||||
: m_inNanoseconds(inNanoseconds),
|
||||
m_units(units) {
|
||||
if (m_units == Unit::Auto) {
|
||||
@ -248,7 +244,7 @@ public:
|
||||
case Unit::Minutes:
|
||||
return m_inNanoseconds / static_cast<double>(s_nanosecondsInAMinute);
|
||||
default:
|
||||
return static_cast<double>(m_inNanoseconds);
|
||||
return m_inNanoseconds;
|
||||
}
|
||||
}
|
||||
StringRef unitsAsString() const {
|
||||
@ -367,7 +363,7 @@ ConsoleReporter::ConsoleReporter(ReporterConfig const& config)
|
||||
else
|
||||
{
|
||||
return{
|
||||
{ "benchmark name", CATCH_CONFIG_CONSOLE_WIDTH - 32, ColumnInfo::Left },
|
||||
{ "benchmark name", CATCH_CONFIG_CONSOLE_WIDTH - 43, ColumnInfo::Left },
|
||||
{ "samples mean std dev", 14, ColumnInfo::Right },
|
||||
{ "iterations low mean low std dev", 14, ColumnInfo::Right },
|
||||
{ "estimated high mean high std dev", 14, ColumnInfo::Right }
|
||||
@ -683,8 +679,10 @@ void ConsoleReporter::printSummaryDivider() {
|
||||
}
|
||||
|
||||
void ConsoleReporter::printTestFilters() {
|
||||
if (m_config->testSpec().hasFilters())
|
||||
stream << Colour(Colour::BrightYellow) << "Filters: " << serializeFilters( m_config->getTestsOrTags() ) << '\n';
|
||||
if (m_config->testSpec().hasFilters()) {
|
||||
Colour guard(Colour::BrightYellow);
|
||||
stream << "Filters: " << serializeFilters(m_config->getTestsOrTags()) << '\n';
|
||||
}
|
||||
}
|
||||
|
||||
} // end namespace Catch
|
||||
@ -695,4 +693,4 @@ void ConsoleReporter::printTestFilters() {
|
||||
|
||||
#if defined(__clang__)
|
||||
# pragma clang diagnostic pop
|
||||
#endif
|
||||
#endif
|
||||
|
@ -229,16 +229,16 @@ namespace Catch {
|
||||
m_xml.writeAttribute("samples", info.samples)
|
||||
.writeAttribute("resamples", info.resamples)
|
||||
.writeAttribute("iterations", info.iterations)
|
||||
.writeAttribute("clockResolution", static_cast<uint64_t>(info.clockResolution))
|
||||
.writeAttribute("estimatedDuration", static_cast<uint64_t>(info.estimatedDuration))
|
||||
.writeAttribute("clockResolution", info.clockResolution)
|
||||
.writeAttribute("estimatedDuration", info.estimatedDuration)
|
||||
.writeComment("All values in nano seconds");
|
||||
}
|
||||
|
||||
void XmlReporter::benchmarkEnded(BenchmarkStats<> const& benchmarkStats) {
|
||||
m_xml.startElement("mean")
|
||||
.writeAttribute("value", static_cast<uint64_t>(benchmarkStats.mean.point.count()))
|
||||
.writeAttribute("lowerBound", static_cast<uint64_t>(benchmarkStats.mean.lower_bound.count()))
|
||||
.writeAttribute("upperBound", static_cast<uint64_t>(benchmarkStats.mean.upper_bound.count()))
|
||||
.writeAttribute("value", benchmarkStats.mean.point.count())
|
||||
.writeAttribute("lowerBound", benchmarkStats.mean.lower_bound.count())
|
||||
.writeAttribute("upperBound", benchmarkStats.mean.upper_bound.count())
|
||||
.writeAttribute("ci", benchmarkStats.mean.confidence_interval);
|
||||
m_xml.endElement();
|
||||
m_xml.startElement("standardDeviation")
|
||||
|
@ -84,7 +84,7 @@ if (CATCH_ENABLE_COVERAGE)
|
||||
endif()
|
||||
|
||||
# configure unit tests via CTest
|
||||
add_test(NAME RunTests COMMAND $<TARGET_FILE:SelfTest>)
|
||||
add_test(NAME RunTests COMMAND $<TARGET_FILE:SelfTest> --order rand --rng-seed time)
|
||||
set_tests_properties(RunTests PROPERTIES
|
||||
FAIL_REGULAR_EXPRESSION "Filters:"
|
||||
COST 60
|
||||
@ -198,6 +198,9 @@ set_tests_properties(TagAlias PROPERTIES
|
||||
FAIL_REGULAR_EXPRESSION "0 matching test cases"
|
||||
)
|
||||
|
||||
add_test(NAME RandomTestOrdering COMMAND ${PYTHON_EXECUTABLE}
|
||||
${CATCH_DIR}/tests/TestScripts/testRandomOrder.py $<TARGET_FILE:SelfTest>)
|
||||
|
||||
if (CATCH_USE_VALGRIND)
|
||||
add_test(NAME ValgrindRunTests COMMAND valgrind --leak-check=full --error-exitcode=1 $<TARGET_FILE:SelfTest>)
|
||||
add_test(NAME ValgrindListTests COMMAND valgrind --leak-check=full --error-exitcode=1 $<TARGET_FILE:SelfTest> --list-tests --verbosity high)
|
||||
|
@ -1,6 +1,5 @@
|
||||
:test-result: PASS # A test name that starts with a #
|
||||
:test-result: PASS #1005: Comparing pointer to int and long (NULL can be either on various systems)
|
||||
:test-result: PASS #1027
|
||||
:test-result: PASS #1027: Bitfields can be captured
|
||||
:test-result: PASS #1147
|
||||
:test-result: PASS #1175 - Hidden Test
|
||||
@ -13,6 +12,8 @@ This would not be caught previously
|
||||
Nor would this
|
||||
:test-result: FAIL #1514: stderr/stdout is not captured in tests aborted by an exception
|
||||
:test-result: PASS #1548
|
||||
:test-result: PASS #1905 -- test spec parser properly clears internal state between compound tests
|
||||
:test-result: PASS #1912 -- test spec parser handles escaping
|
||||
:test-result: XFAIL #748 - captures with unexpected exceptions
|
||||
:test-result: PASS #809
|
||||
:test-result: PASS #833
|
||||
@ -79,6 +80,7 @@ Nor would this
|
||||
:test-result: PASS Approximate comparisons with ints
|
||||
:test-result: PASS Approximate comparisons with mixed numeric types
|
||||
:test-result: PASS Arbitrary predicate matcher
|
||||
:test-result: PASS Assertion macros support bit operators and bool conversions
|
||||
:test-result: PASS Assertions then sections
|
||||
:test-result: PASS Basic use of the Contains range matcher
|
||||
:test-result: PASS Basic use of the Empty range matcher
|
||||
@ -138,6 +140,7 @@ Nor would this
|
||||
:test-result: FAIL INFO is reset for each loop
|
||||
:test-result: XFAIL Inequality checks that should fail
|
||||
:test-result: PASS Inequality checks that should succeed
|
||||
:test-result: PASS Lambdas in assertions
|
||||
:test-result: PASS Less-than inequalities with different epsilons
|
||||
:test-result: PASS ManuallyRegistered
|
||||
:test-result: PASS Matchers can be (AllOf) composed with the && operator
|
||||
|
@ -3,8 +3,6 @@ Decomposition.tests.cpp:<line number>: passed: fptr == 0 for: 0 == 0
|
||||
Decomposition.tests.cpp:<line number>: passed: fptr == 0l for: 0 == 0
|
||||
Compilation.tests.cpp:<line number>: passed: y.v == 0 for: 0 == 0
|
||||
Compilation.tests.cpp:<line number>: passed: 0 == y.v for: 0 == 0
|
||||
Compilation.tests.cpp:<line number>: passed: y.v == 0 for: 0 == 0
|
||||
Compilation.tests.cpp:<line number>: passed: 0 == y.v for: 0 == 0
|
||||
Compilation.tests.cpp:<line number>: passed: t1 == t2 for: {?} == {?}
|
||||
Compilation.tests.cpp:<line number>: passed: t1 != t2 for: {?} != {?}
|
||||
Compilation.tests.cpp:<line number>: passed: t1 < t2 for: {?} < {?}
|
||||
@ -24,6 +22,13 @@ This would not be caught previously
|
||||
Nor would this
|
||||
Tricky.tests.cpp:<line number>: failed: explicitly with 1 message: '1514'
|
||||
Compilation.tests.cpp:<line number>: passed: std::is_same<TypeList<int>, TypeList<int>>::value for: true
|
||||
CmdLine.tests.cpp:<line number>: passed: spec.matches(*fakeTestCase("spec . char")) for: true
|
||||
CmdLine.tests.cpp:<line number>: passed: spec.matches(*fakeTestCase("spec , char")) for: true
|
||||
CmdLine.tests.cpp:<line number>: passed: !(spec.matches(*fakeTestCase(R"(spec \, char)"))) for: !false
|
||||
CmdLine.tests.cpp:<line number>: passed: spec.matches(*fakeTestCase(R"(spec {a} char)")) for: true
|
||||
CmdLine.tests.cpp:<line number>: passed: spec.matches(*fakeTestCase(R"(spec [a] char)")) for: true
|
||||
CmdLine.tests.cpp:<line number>: passed: !(spec.matches(*fakeTestCase("differs but has similar tag", "[a]"))) for: !false
|
||||
CmdLine.tests.cpp:<line number>: passed: spec.matches(*fakeTestCase(R"(spec \ char)")) for: true
|
||||
Exception.tests.cpp:<line number>: failed: unexpected exception with message: 'answer := 42' with 1 message: 'expected exception'
|
||||
Exception.tests.cpp:<line number>: failed: unexpected exception with message: 'answer := 42'; expression was: thisThrows() with 1 message: 'expected exception'
|
||||
Exception.tests.cpp:<line number>: passed: thisThrows() with 1 message: 'answer := 42'
|
||||
@ -238,6 +243,11 @@ Matchers.tests.cpp:<line number>: passed: 1, Predicate<int>(alwaysTrue, "always
|
||||
Matchers.tests.cpp:<line number>: passed: 1, !Predicate<int>(alwaysFalse, "always false") for: 1 not matches predicate: "always false"
|
||||
Matchers.tests.cpp:<line number>: passed: "Hello olleH", Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); }, "First and last character should be equal") for: "Hello olleH" matches predicate: "First and last character should be equal"
|
||||
Matchers.tests.cpp:<line number>: passed: "This wouldn't pass", !Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); } ) for: "This wouldn't pass" not matches undescribed predicate
|
||||
Compilation.tests.cpp:<line number>: passed: lhs | rhs for: Val: 1 | Val: 2
|
||||
Compilation.tests.cpp:<line number>: passed: !(lhs & rhs) for: !(Val: 1 & Val: 2)
|
||||
Compilation.tests.cpp:<line number>: passed: HasBitOperators{ 1 } & HasBitOperators{ 1 } for: Val: 1 & Val: 1
|
||||
Compilation.tests.cpp:<line number>: passed: lhs ^ rhs for: Val: 1 ^ Val: 2
|
||||
Compilation.tests.cpp:<line number>: passed: !(lhs ^ lhs) for: !(Val: 1 ^ Val: 1)
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
@ -818,6 +828,7 @@ Condition.tests.cpp:<line number>: passed: data.str_hello != "goodbye" for: "hel
|
||||
Condition.tests.cpp:<line number>: passed: data.str_hello != "hell" for: "hello" != "hell"
|
||||
Condition.tests.cpp:<line number>: passed: data.str_hello != "hello1" for: "hello" != "hello1"
|
||||
Condition.tests.cpp:<line number>: passed: data.str_hello.size() != 6 for: 5 != 6
|
||||
Compilation.tests.cpp:<line number>: passed: []() { return true; }() for: true
|
||||
Approx.tests.cpp:<line number>: passed: d <= Approx( 1.24 ) for: 1.23 <= Approx( 1.24 )
|
||||
Approx.tests.cpp:<line number>: passed: d <= Approx( 1.23 ) for: 1.23 <= Approx( 1.23 )
|
||||
Approx.tests.cpp:<line number>: passed: !(d <= Approx( 1.22 )) for: !(1.23 <= Approx( 1.22 ))
|
||||
@ -1595,6 +1606,7 @@ Approx.tests.cpp:<line number>: passed: approx( d ) != 1.25 for: Approx( 1.23 )
|
||||
VariadicMacros.tests.cpp:<line number>: passed: with 1 message: 'no assertions'
|
||||
Matchers.tests.cpp:<line number>: passed: empty, Approx(empty) for: { } is approx: { }
|
||||
Matchers.tests.cpp:<line number>: passed: v1, Approx(v1) for: { 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
Matchers.tests.cpp:<line number>: passed: v1, Approx<double>({ 1., 2., 3. }) for: { 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
Matchers.tests.cpp:<line number>: passed: v1, !Approx(temp) for: { 1.0, 2.0, 3.0 } not is approx: { 1.0, 2.0, 3.0, 4.0 }
|
||||
Matchers.tests.cpp:<line number>: passed: v1, !Approx(v2) for: { 1.0, 2.0, 3.0 } not is approx: { 1.5, 2.5, 3.5 }
|
||||
Matchers.tests.cpp:<line number>: passed: v1, Approx(v2).margin(0.5) for: { 1.0, 2.0, 3.0 } is approx: { 1.5, 2.5, 3.5 }
|
||||
@ -1604,18 +1616,29 @@ Matchers.tests.cpp:<line number>: failed: empty, Approx(t1) for: { } is approx:
|
||||
Matchers.tests.cpp:<line number>: failed: v1, Approx(v2) for: { 2.0, 4.0, 6.0 } is approx: { 1.0, 3.0, 5.0 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, VectorContains(1) for: { 1, 2, 3 } Contains: 1
|
||||
Matchers.tests.cpp:<line number>: passed: v, VectorContains(2) for: { 1, 2, 3 } Contains: 2
|
||||
Matchers.tests.cpp:<line number>: passed: v5, (VectorContains<int, CustomAllocator<int>>(2)) for: { 1, 2, 3 } Contains: 2
|
||||
Matchers.tests.cpp:<line number>: passed: v, Contains(v2) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, Contains<int>({ 1, 2 }) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, Contains(v2) for: { 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, Contains(empty) for: { 1, 2, 3 } Contains: { }
|
||||
Matchers.tests.cpp:<line number>: passed: empty, Contains(empty) for: { } Contains: { }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, Contains(v6) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, VectorContains(1) && VectorContains(2) for: { 1, 2, 3 } ( Contains: 1 and Contains: 2 )
|
||||
Matchers.tests.cpp:<line number>: passed: v, Equals(v) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: empty, Equals(empty) for: { } Equals: { }
|
||||
Matchers.tests.cpp:<line number>: passed: v, Equals<int>({ 1, 2, 3 }) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, Equals(v2) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, (Equals<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, Equals(v6) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, UnorderedEquals(v) for: { 1, 2, 3 } UnorderedEquals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v, UnorderedEquals<int>({ 3, 2, 1 }) for: { 1, 2, 3 } UnorderedEquals: { 3, 2, 1 }
|
||||
Matchers.tests.cpp:<line number>: passed: empty, UnorderedEquals(empty) for: { } UnorderedEquals: { }
|
||||
Matchers.tests.cpp:<line number>: passed: permuted, UnorderedEquals(v) for: { 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: permuted, UnorderedEquals(v) for: { 2, 3, 1 } UnorderedEquals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5, (UnorderedEquals<int, std::allocator<int>, CustomAllocator<int>>(permuted)) for: { 1, 2, 3 } UnorderedEquals: { 2, 3, 1 }
|
||||
Matchers.tests.cpp:<line number>: passed: v5_permuted, UnorderedEquals(v5) for: { 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
Matchers.tests.cpp:<line number>: failed: v, VectorContains(-1) for: { 1, 2, 3 } Contains: -1
|
||||
Matchers.tests.cpp:<line number>: failed: empty, VectorContains(1) for: { } Contains: 1
|
||||
Matchers.tests.cpp:<line number>: failed: empty, Contains(v) for: { } Contains: { 1, 2, 3 }
|
||||
|
@ -1380,6 +1380,6 @@ due to unexpected exception with message:
|
||||
Why would you throw a std::string?
|
||||
|
||||
===============================================================================
|
||||
test cases: 331 | 257 passed | 70 failed | 4 failed as expected
|
||||
assertions: 1872 | 1720 passed | 131 failed | 21 failed as expected
|
||||
test cases: 334 | 260 passed | 70 failed | 4 failed as expected
|
||||
assertions: 1895 | 1743 passed | 131 failed | 21 failed as expected
|
||||
|
||||
|
@ -33,22 +33,6 @@ Decomposition.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1027
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( y.v == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( 0 == y.v )
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1027: Bitfields can be captured
|
||||
-------------------------------------------------------------------------------
|
||||
@ -197,6 +181,61 @@ Compilation.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
true
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1905 -- test spec parser properly clears internal state between compound tests
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase("spec . char")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase("spec , char")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( spec.matches(*fakeTestCase(R"(spec \, char)")) )
|
||||
with expansion:
|
||||
!false
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1912 -- test spec parser handles escaping
|
||||
Various parentheses
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec {a} char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec [a] char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( spec.matches(*fakeTestCase("differs but has similar tag", "[a]")) )
|
||||
with expansion:
|
||||
!false
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1912 -- test spec parser handles escaping
|
||||
backslash in test name
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec \ char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#748 - captures with unexpected exceptions
|
||||
outside assertions
|
||||
@ -1888,6 +1927,37 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
"This wouldn't pass" not matches undescribed predicate
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Assertion macros support bit operators and bool conversions
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( lhs | rhs )
|
||||
with expansion:
|
||||
Val: 1 | Val: 2
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( lhs & rhs )
|
||||
with expansion:
|
||||
!(Val: 1 & Val: 2)
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( HasBitOperators{ 1 } & HasBitOperators{ 1 } )
|
||||
with expansion:
|
||||
Val: 1 & Val: 1
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( lhs ^ rhs )
|
||||
with expansion:
|
||||
Val: 1 ^ Val: 2
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( lhs ^ lhs )
|
||||
with expansion:
|
||||
!(Val: 1 ^ Val: 1)
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Assertions then sections
|
||||
-------------------------------------------------------------------------------
|
||||
@ -6116,6 +6186,17 @@ Condition.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
5 != 6
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Lambdas in assertions
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( []() { return true; }() )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Less-than inequalities with different epsilons
|
||||
-------------------------------------------------------------------------------
|
||||
@ -11610,6 +11691,11 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_THAT( v1, Approx<double>({ 1., 2., 3. }) )
|
||||
with expansion:
|
||||
{ 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Vector Approx matcher
|
||||
Vectors with elements
|
||||
@ -11692,6 +11778,11 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: 2
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, (VectorContains<int, CustomAllocator<int>>(2)) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: 2
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Vector matchers
|
||||
Contains (vector)
|
||||
@ -11704,6 +11795,16 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v, Contains<int>({ 1, 2 }) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v, Contains(v2) )
|
||||
with expansion:
|
||||
@ -11719,6 +11820,16 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ } Contains: { }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, Contains(v6) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Vector matchers
|
||||
Contains (element), composed
|
||||
@ -11748,11 +11859,26 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ } Equals: { }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v, Equals<int>({ 1, 2, 3 }) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v, Equals(v2) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, (Equals<int, std::allocator<int>, CustomAllocator<int>>(v2)) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, Equals(v6) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Vector matchers
|
||||
UnorderedEquals
|
||||
@ -11765,6 +11891,11 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ 1, 2, 3 } UnorderedEquals: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v, UnorderedEquals<int>({ 3, 2, 1 }) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } UnorderedEquals: { 3, 2, 1 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( empty, UnorderedEquals(empty) )
|
||||
with expansion:
|
||||
@ -11780,6 +11911,16 @@ Matchers.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
{ 2, 3, 1 } UnorderedEquals: { 1, 2, 3 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5, (UnorderedEquals<int, std::allocator<int>, CustomAllocator<int>>(permuted)) )
|
||||
with expansion:
|
||||
{ 1, 2, 3 } UnorderedEquals: { 2, 3, 1 }
|
||||
|
||||
Matchers.tests.cpp:<line number>: PASSED:
|
||||
CHECK_THAT( v5_permuted, UnorderedEquals(v5) )
|
||||
with expansion:
|
||||
{ 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Vector matchers that fail
|
||||
Contains (element)
|
||||
@ -14647,6 +14788,6 @@ Misc.tests.cpp:<line number>
|
||||
Misc.tests.cpp:<line number>: PASSED:
|
||||
|
||||
===============================================================================
|
||||
test cases: 331 | 241 passed | 86 failed | 4 failed as expected
|
||||
assertions: 1889 | 1720 passed | 148 failed | 21 failed as expected
|
||||
test cases: 334 | 244 passed | 86 failed | 4 failed as expected
|
||||
assertions: 1912 | 1743 passed | 148 failed | 21 failed as expected
|
||||
|
||||
|
@ -33,22 +33,6 @@ Decomposition.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1027
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( y.v == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
Compilation.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( 0 == y.v )
|
||||
with expansion:
|
||||
0 == 0
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1027: Bitfields can be captured
|
||||
-------------------------------------------------------------------------------
|
||||
@ -197,6 +181,61 @@ Compilation.tests.cpp:<line number>: PASSED:
|
||||
with expansion:
|
||||
true
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1905 -- test spec parser properly clears internal state between compound tests
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase("spec . char")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase("spec , char")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( spec.matches(*fakeTestCase(R"(spec \, char)")) )
|
||||
with expansion:
|
||||
!false
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1912 -- test spec parser handles escaping
|
||||
Various parentheses
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec {a} char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec [a] char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE_FALSE( spec.matches(*fakeTestCase("differs but has similar tag", "[a]")) )
|
||||
with expansion:
|
||||
!false
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1912 -- test spec parser handles escaping
|
||||
backslash in test name
|
||||
-------------------------------------------------------------------------------
|
||||
CmdLine.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
CmdLine.tests.cpp:<line number>: PASSED:
|
||||
REQUIRE( spec.matches(*fakeTestCase(R"(spec \ char)")) )
|
||||
with expansion:
|
||||
true
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#748 - captures with unexpected exceptions
|
||||
outside assertions
|
||||
@ -377,6 +416,6 @@ Condition.tests.cpp:<line number>: FAILED:
|
||||
CHECK( true != true )
|
||||
|
||||
===============================================================================
|
||||
test cases: 20 | 15 passed | 3 failed | 2 failed as expected
|
||||
assertions: 43 | 36 passed | 4 failed | 3 failed as expected
|
||||
test cases: 21 | 16 passed | 3 failed | 2 failed as expected
|
||||
assertions: 48 | 41 passed | 4 failed | 3 failed as expected
|
||||
|
||||
|
@ -1,14 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<testsuitesloose text artifact
|
||||
>
|
||||
<testsuite name="<exe-name>" errors="17" failures="132" tests="1890" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
|
||||
<testsuite name="<exe-name>" errors="17" failures="132" tests="1913" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
|
||||
<properties>
|
||||
<property name="filters" value="~[!nonportable]~[!benchmark]~[approvals] *"/>
|
||||
<property name="random-seed" value="1"/>
|
||||
</properties>
|
||||
<testcase classname="<exe-name>.global" name="# A test name that starts with a #" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1005: Comparing pointer to int and long (NULL can be either on various systems)" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1027" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1027: Bitfields can be captured" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1147" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1175 - Hidden Test" time="{duration}"/>
|
||||
@ -31,6 +30,9 @@ Nor would this
|
||||
</system-err>
|
||||
</testcase>
|
||||
<testcase classname="<exe-name>.global" name="#1548" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1905 -- test spec parser properly clears internal state between compound tests" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1912 -- test spec parser handles escaping/Various parentheses" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1912 -- test spec parser handles escaping/backslash in test name" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#748 - captures with unexpected exceptions/outside assertions" time="{duration}">
|
||||
<error type="TEST_CASE">
|
||||
FAILED:
|
||||
@ -338,6 +340,7 @@ Exception.tests.cpp:<line number>
|
||||
<testcase classname="<exe-name>.global" name="Approximate comparisons with mixed numeric types" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Arbitrary predicate matcher/Function pointer" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Arbitrary predicate matcher/Lambdas + different type" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Assertion macros support bit operators and bool conversions" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Assertions then sections" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Assertions then sections/A section" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Assertions then sections/A section/Another section" time="{duration}"/>
|
||||
@ -769,6 +772,7 @@ Condition.tests.cpp:<line number>
|
||||
</failure>
|
||||
</testcase>
|
||||
<testcase classname="<exe-name>.global" name="Inequality checks that should succeed" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Lambdas in assertions" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Less-than inequalities with different epsilons" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="ManuallyRegistered" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Matchers can be (AllOf) composed with the && operator" time="{duration}"/>
|
||||
|
@ -2,6 +2,9 @@
|
||||
<testExecutions version="1"loose text artifact
|
||||
>
|
||||
<file path="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp">
|
||||
<testCase name="#1905 -- test spec parser properly clears internal state between compound tests" duration="{duration}"/>
|
||||
<testCase name="#1912 -- test spec parser handles escaping/Various parentheses" duration="{duration}"/>
|
||||
<testCase name="#1912 -- test spec parser handles escaping/backslash in test name" duration="{duration}"/>
|
||||
<testCase name="Parse test names and tags/Empty test spec should have no filters" duration="{duration}"/>
|
||||
<testCase name="Parse test names and tags/Test spec from empty string should have no filters" duration="{duration}"/>
|
||||
<testCase name="Parse test names and tags/Test spec from just a comma should have no filters" duration="{duration}"/>
|
||||
@ -382,7 +385,6 @@ Class.tests.cpp:<line number>
|
||||
<testCase name="Template test case method with test types specified inside std::tuple - MyTypes - 2" duration="{duration}"/>
|
||||
</file>
|
||||
<file path="tests/<exe-name>/UsageTests/Compilation.tests.cpp">
|
||||
<testCase name="#1027" duration="{duration}"/>
|
||||
<testCase name="#1027: Bitfields can be captured" duration="{duration}"/>
|
||||
<testCase name="#1147" duration="{duration}"/>
|
||||
<testCase name="#1238" duration="{duration}"/>
|
||||
@ -393,6 +395,8 @@ Class.tests.cpp:<line number>
|
||||
<testCase name="#809" duration="{duration}"/>
|
||||
<testCase name="#833" duration="{duration}"/>
|
||||
<testCase name="#872" duration="{duration}"/>
|
||||
<testCase name="Assertion macros support bit operators and bool conversions" duration="{duration}"/>
|
||||
<testCase name="Lambdas in assertions" duration="{duration}"/>
|
||||
<testCase name="Optionally static assertions" duration="{duration}"/>
|
||||
</file>
|
||||
<file path="tests/<exe-name>/UsageTests/Condition.tests.cpp">
|
||||
|
@ -4,10 +4,6 @@ ok {test-number} - with 1 message: 'yay'
|
||||
ok {test-number} - fptr == 0 for: 0 == 0
|
||||
# #1005: Comparing pointer to int and long (NULL can be either on various systems)
|
||||
ok {test-number} - fptr == 0l for: 0 == 0
|
||||
# #1027
|
||||
ok {test-number} - y.v == 0 for: 0 == 0
|
||||
# #1027
|
||||
ok {test-number} - 0 == y.v for: 0 == 0
|
||||
# #1027: Bitfields can be captured
|
||||
ok {test-number} - y.v == 0 for: 0 == 0
|
||||
# #1027: Bitfields can be captured
|
||||
@ -46,6 +42,20 @@ Nor would this
|
||||
not ok {test-number} - explicitly with 1 message: '1514'
|
||||
# #1548
|
||||
ok {test-number} - std::is_same<TypeList<int>, TypeList<int>>::value for: true
|
||||
# #1905 -- test spec parser properly clears internal state between compound tests
|
||||
ok {test-number} - spec.matches(*fakeTestCase("spec . char")) for: true
|
||||
# #1905 -- test spec parser properly clears internal state between compound tests
|
||||
ok {test-number} - spec.matches(*fakeTestCase("spec , char")) for: true
|
||||
# #1905 -- test spec parser properly clears internal state between compound tests
|
||||
ok {test-number} - !(spec.matches(*fakeTestCase(R"(spec \, char)"))) for: !false
|
||||
# #1912 -- test spec parser handles escaping
|
||||
ok {test-number} - spec.matches(*fakeTestCase(R"(spec {a} char)")) for: true
|
||||
# #1912 -- test spec parser handles escaping
|
||||
ok {test-number} - spec.matches(*fakeTestCase(R"(spec [a] char)")) for: true
|
||||
# #1912 -- test spec parser handles escaping
|
||||
ok {test-number} - !(spec.matches(*fakeTestCase("differs but has similar tag", "[a]"))) for: !false
|
||||
# #1912 -- test spec parser handles escaping
|
||||
ok {test-number} - spec.matches(*fakeTestCase(R"(spec \ char)")) for: true
|
||||
# #748 - captures with unexpected exceptions
|
||||
not ok {test-number} - unexpected exception with message: 'answer := 42' with 1 message: 'expected exception'
|
||||
# #748 - captures with unexpected exceptions
|
||||
@ -474,6 +484,16 @@ ok {test-number} - 1, !Predicate<int>(alwaysFalse, "always false") for: 1 not ma
|
||||
ok {test-number} - "Hello olleH", Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); }, "First and last character should be equal") for: "Hello olleH" matches predicate: "First and last character should be equal"
|
||||
# Arbitrary predicate matcher
|
||||
ok {test-number} - "This wouldn't pass", !Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); } ) for: "This wouldn't pass" not matches undescribed predicate
|
||||
# Assertion macros support bit operators and bool conversions
|
||||
ok {test-number} - lhs | rhs for: Val: 1 | Val: 2
|
||||
# Assertion macros support bit operators and bool conversions
|
||||
ok {test-number} - !(lhs & rhs) for: !(Val: 1 & Val: 2)
|
||||
# Assertion macros support bit operators and bool conversions
|
||||
ok {test-number} - HasBitOperators{ 1 } & HasBitOperators{ 1 } for: Val: 1 & Val: 1
|
||||
# Assertion macros support bit operators and bool conversions
|
||||
ok {test-number} - lhs ^ rhs for: Val: 1 ^ Val: 2
|
||||
# Assertion macros support bit operators and bool conversions
|
||||
ok {test-number} - !(lhs ^ lhs) for: !(Val: 1 ^ Val: 1)
|
||||
# Assertions then sections
|
||||
ok {test-number} - true
|
||||
# Assertions then sections
|
||||
@ -1618,6 +1638,8 @@ ok {test-number} - data.str_hello != "hell" for: "hello" != "hell"
|
||||
ok {test-number} - data.str_hello != "hello1" for: "hello" != "hello1"
|
||||
# Inequality checks that should succeed
|
||||
ok {test-number} - data.str_hello.size() != 6 for: 5 != 6
|
||||
# Lambdas in assertions
|
||||
ok {test-number} - []() { return true; }() for: true
|
||||
# Less-than inequalities with different epsilons
|
||||
ok {test-number} - d <= Approx( 1.24 ) for: 1.23 <= Approx( 1.24 )
|
||||
# Less-than inequalities with different epsilons
|
||||
@ -3038,6 +3060,8 @@ ok {test-number} - empty, Approx(empty) for: { } is approx: { }
|
||||
# Vector Approx matcher
|
||||
ok {test-number} - v1, Approx(v1) for: { 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
# Vector Approx matcher
|
||||
ok {test-number} - v1, Approx<double>({ 1., 2., 3. }) for: { 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
# Vector Approx matcher
|
||||
ok {test-number} - v1, !Approx(temp) for: { 1.0, 2.0, 3.0 } not is approx: { 1.0, 2.0, 3.0, 4.0 }
|
||||
# Vector Approx matcher
|
||||
ok {test-number} - v1, !Approx(v2) for: { 1.0, 2.0, 3.0 } not is approx: { 1.5, 2.5, 3.5 }
|
||||
@ -3056,29 +3080,51 @@ ok {test-number} - v, VectorContains(1) for: { 1, 2, 3 } Contains: 1
|
||||
# Vector matchers
|
||||
ok {test-number} - v, VectorContains(2) for: { 1, 2, 3 } Contains: 2
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, (VectorContains<int, CustomAllocator<int>>(2)) for: { 1, 2, 3 } Contains: 2
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Contains(v2) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Contains<int>({ 1, 2 }) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Contains(v2) for: { 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Contains(empty) for: { 1, 2, 3 } Contains: { }
|
||||
# Vector matchers
|
||||
ok {test-number} - empty, Contains(empty) for: { } Contains: { }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, Contains(v6) for: { 1, 2, 3 } Contains: { 1, 2 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, VectorContains(1) && VectorContains(2) for: { 1, 2, 3 } ( Contains: 1 and Contains: 2 )
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Equals(v) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - empty, Equals(empty) for: { } Equals: { }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Equals<int>({ 1, 2, 3 }) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, Equals(v2) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, (Equals<int, std::allocator<int>, CustomAllocator<int>>(v2)) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, Equals(v6) for: { 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, UnorderedEquals(v) for: { 1, 2, 3 } UnorderedEquals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v, UnorderedEquals<int>({ 3, 2, 1 }) for: { 1, 2, 3 } UnorderedEquals: { 3, 2, 1 }
|
||||
# Vector matchers
|
||||
ok {test-number} - empty, UnorderedEquals(empty) for: { } UnorderedEquals: { }
|
||||
# Vector matchers
|
||||
ok {test-number} - permuted, UnorderedEquals(v) for: { 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - permuted, UnorderedEquals(v) for: { 2, 3, 1 } UnorderedEquals: { 1, 2, 3 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5, (UnorderedEquals<int, std::allocator<int>, CustomAllocator<int>>(permuted)) for: { 1, 2, 3 } UnorderedEquals: { 2, 3, 1 }
|
||||
# Vector matchers
|
||||
ok {test-number} - v5_permuted, UnorderedEquals(v5) for: { 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
# Vector matchers that fail
|
||||
not ok {test-number} - v, VectorContains(-1) for: { 1, 2, 3 } Contains: -1
|
||||
# Vector matchers that fail
|
||||
@ -3770,5 +3816,5 @@ ok {test-number} - q3 == 23. for: 23.0 == 23.0
|
||||
ok {test-number} -
|
||||
# xmlentitycheck
|
||||
ok {test-number} -
|
||||
1..1881
|
||||
1..1904
|
||||
|
||||
|
@ -3,8 +3,6 @@
|
||||
##teamcity[testFinished name='# A test name that starts with a #' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1005: Comparing pointer to int and long (NULL can be either on various systems)']
|
||||
##teamcity[testFinished name='#1005: Comparing pointer to int and long (NULL can be either on various systems)' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1027']
|
||||
##teamcity[testFinished name='#1027' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1027: Bitfields can be captured']
|
||||
##teamcity[testFinished name='#1027: Bitfields can be captured' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1147']
|
||||
@ -28,6 +26,10 @@ Tricky.tests.cpp:<line number>|nexplicit failure with message:|n "1514"']
|
||||
##teamcity[testFinished name='#1514: stderr/stdout is not captured in tests aborted by an exception' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1548']
|
||||
##teamcity[testFinished name='#1548' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1905 -- test spec parser properly clears internal state between compound tests']
|
||||
##teamcity[testFinished name='#1905 -- test spec parser properly clears internal state between compound tests' duration="{duration}"]
|
||||
##teamcity[testStarted name='#1912 -- test spec parser handles escaping']
|
||||
##teamcity[testFinished name='#1912 -- test spec parser handles escaping' duration="{duration}"]
|
||||
##teamcity[testStarted name='#748 - captures with unexpected exceptions']
|
||||
Exception.tests.cpp:<line number>|nunexpected exception with messages:|n "answer := 42"|n "expected exception"- failure ignore as test marked as |'ok to fail|'|n']
|
||||
Exception.tests.cpp:<line number>|nunexpected exception with messages:|n "answer := 42"|n "expected exception"|n REQUIRE_NOTHROW( thisThrows() )|nwith expansion:|n thisThrows()|n- failure ignore as test marked as |'ok to fail|'|n']
|
||||
@ -191,6 +193,8 @@ Exception.tests.cpp:<line number>|nunexpected exception with message:|n "unexpe
|
||||
##teamcity[testFinished name='Approximate comparisons with mixed numeric types' duration="{duration}"]
|
||||
##teamcity[testStarted name='Arbitrary predicate matcher']
|
||||
##teamcity[testFinished name='Arbitrary predicate matcher' duration="{duration}"]
|
||||
##teamcity[testStarted name='Assertion macros support bit operators and bool conversions']
|
||||
##teamcity[testFinished name='Assertion macros support bit operators and bool conversions' duration="{duration}"]
|
||||
##teamcity[testStarted name='Assertions then sections']
|
||||
##teamcity[testFinished name='Assertions then sections' duration="{duration}"]
|
||||
##teamcity[testStarted name='Basic use of the Contains range matcher']
|
||||
@ -352,6 +356,8 @@ Condition.tests.cpp:<line number>|nexpression failed|n CHECK( data.str_hello.si
|
||||
##teamcity[testFinished name='Inequality checks that should fail' duration="{duration}"]
|
||||
##teamcity[testStarted name='Inequality checks that should succeed']
|
||||
##teamcity[testFinished name='Inequality checks that should succeed' duration="{duration}"]
|
||||
##teamcity[testStarted name='Lambdas in assertions']
|
||||
##teamcity[testFinished name='Lambdas in assertions' duration="{duration}"]
|
||||
##teamcity[testStarted name='Less-than inequalities with different epsilons']
|
||||
##teamcity[testFinished name='Less-than inequalities with different epsilons' duration="{duration}"]
|
||||
##teamcity[testStarted name='ManuallyRegistered']
|
||||
|
@ -24,25 +24,6 @@
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#1027" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
y.v == 0
|
||||
</Original>
|
||||
<Expanded>
|
||||
0 == 0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
0 == y.v
|
||||
</Original>
|
||||
<Expanded>
|
||||
0 == 0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#1027: Bitfields can be captured" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
@ -202,6 +183,74 @@ Nor would this
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#1905 -- test spec parser properly clears internal state between compound tests" tags="[command-line][test-spec]" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
spec.matches(*fakeTestCase("spec . char"))
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
spec.matches(*fakeTestCase("spec , char"))
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_FALSE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
!(spec.matches(*fakeTestCase(R"(spec \, char)")))
|
||||
</Original>
|
||||
<Expanded>
|
||||
!false
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#1912 -- test spec parser handles escaping" tags="[command-line][test-spec]" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Section name="Various parentheses" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
spec.matches(*fakeTestCase(R"(spec {a} char)"))
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
spec.matches(*fakeTestCase(R"(spec [a] char)"))
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_FALSE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
!(spec.matches(*fakeTestCase("differs but has similar tag", "[a]")))
|
||||
</Original>
|
||||
<Expanded>
|
||||
!false
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="3" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="backslash in test name" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/IntrospectiveTests/CmdLine.tests.cpp" >
|
||||
<Original>
|
||||
spec.matches(*fakeTestCase(R"(spec \ char)"))
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="1" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#748 - captures with unexpected exceptions" tags="[!shouldfail][!throws][.][failing]" filename="tests/<exe-name>/UsageTests/Exception.tests.cpp" >
|
||||
<Section name="outside assertions" filename="tests/<exe-name>/UsageTests/Exception.tests.cpp" >
|
||||
<Info>
|
||||
@ -2115,6 +2164,49 @@ Nor would this
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Assertion macros support bit operators and bool conversions" tags="[bitops][compilation]" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
lhs | rhs
|
||||
</Original>
|
||||
<Expanded>
|
||||
Val: 1 | Val: 2
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_FALSE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
!(lhs & rhs)
|
||||
</Original>
|
||||
<Expanded>
|
||||
!(Val: 1 & Val: 2)
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
HasBitOperators{ 1 } & HasBitOperators{ 1 }
|
||||
</Original>
|
||||
<Expanded>
|
||||
Val: 1 & Val: 1
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
lhs ^ rhs
|
||||
</Original>
|
||||
<Expanded>
|
||||
Val: 1 ^ Val: 2
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_FALSE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
!(lhs ^ lhs)
|
||||
</Original>
|
||||
<Expanded>
|
||||
!(Val: 1 ^ Val: 1)
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Assertions then sections" tags="[Tricky]" filename="tests/<exe-name>/UsageTests/Tricky.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Tricky.tests.cpp" >
|
||||
<Original>
|
||||
@ -7635,6 +7727,17 @@ Nor would this
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Lambdas in assertions" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
[]() { return true; }()
|
||||
</Original>
|
||||
<Expanded>
|
||||
true
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Less-than inequalities with different epsilons" tags="[Approx]" filename="tests/<exe-name>/UsageTests/Approx.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="tests/<exe-name>/UsageTests/Approx.tests.cpp" >
|
||||
<Original>
|
||||
@ -14020,9 +14123,17 @@ There is no extra whitespace here
|
||||
{ 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="1" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v1, Approx<double>({ 1., 2., 3. })
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1.0, 2.0, 3.0 } is approx: { 1.0, 2.0, 3.0 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="2" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="1" failures="0" expectedFailures="0"/>
|
||||
<OverallResults successes="2" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Vectors with elements" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Section name="Different length" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@ -14121,7 +14232,15 @@ There is no extra whitespace here
|
||||
{ 1, 2, 3 } Contains: 2
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="2" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, (VectorContains<int, CustomAllocator<int>>(2))
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Contains: 2
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="3" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Contains (vector)" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@ -14132,6 +14251,22 @@ There is no extra whitespace here
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v, Contains<int>({ 1, 2 })
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2))
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v, Contains(v2)
|
||||
@ -14156,7 +14291,23 @@ There is no extra whitespace here
|
||||
{ } Contains: { }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2))
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Contains: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, Contains(v6)
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Contains: { 1, 2 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="8" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Contains (element), composed" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@ -14186,6 +14337,14 @@ There is no extra whitespace here
|
||||
{ } Equals: { }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v, Equals<int>({ 1, 2, 3 })
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v, Equals(v2)
|
||||
@ -14194,7 +14353,23 @@ There is no extra whitespace here
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="3" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, (Equals<int, std::allocator<int>, CustomAllocator<int>>(v2))
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, Equals(v6)
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } Equals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="6" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="UnorderedEquals" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@ -14205,6 +14380,14 @@ There is no extra whitespace here
|
||||
{ 1, 2, 3 } UnorderedEquals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v, UnorderedEquals<int>({ 3, 2, 1 })
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } UnorderedEquals: { 3, 2, 1 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
empty, UnorderedEquals(empty)
|
||||
@ -14229,7 +14412,23 @@ There is no extra whitespace here
|
||||
{ 2, 3, 1 } UnorderedEquals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5, (UnorderedEquals<int, std::allocator<int>, CustomAllocator<int>>(permuted))
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 2, 3 } UnorderedEquals: { 2, 3, 1 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
v5_permuted, UnorderedEquals(v5)
|
||||
</Original>
|
||||
<Expanded>
|
||||
{ 1, 3, 2 } UnorderedEquals: { 1, 2, 3 }
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="7" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
@ -17557,7 +17756,7 @@ loose text artifact
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<OverallResults successes="1720" failures="149" expectedFailures="21"/>
|
||||
<OverallResults successes="1743" failures="149" expectedFailures="21"/>
|
||||
</Group>
|
||||
<OverallResults successes="1720" failures="148" expectedFailures="21"/>
|
||||
<OverallResults successes="1743" failures="148" expectedFailures="21"/>
|
||||
</Catch>
|
||||
|
@ -296,6 +296,35 @@ TEST_CASE( "Parse test names and tags", "[command-line][test-spec]" ) {
|
||||
}
|
||||
}
|
||||
|
||||
TEST_CASE("#1905 -- test spec parser properly clears internal state between compound tests", "[command-line][test-spec]") {
|
||||
using Catch::parseTestSpec;
|
||||
using Catch::TestSpec;
|
||||
// We ask for one of 2 different tests and the latter one of them has a , in name that needs escaping
|
||||
TestSpec spec = parseTestSpec(R"("spec . char","spec \, char")");
|
||||
|
||||
REQUIRE(spec.matches(*fakeTestCase("spec . char")));
|
||||
REQUIRE(spec.matches(*fakeTestCase("spec , char")));
|
||||
REQUIRE_FALSE(spec.matches(*fakeTestCase(R"(spec \, char)")));
|
||||
}
|
||||
|
||||
TEST_CASE("#1912 -- test spec parser handles escaping", "[command-line][test-spec]") {
|
||||
using Catch::parseTestSpec;
|
||||
using Catch::TestSpec;
|
||||
|
||||
SECTION("Various parentheses") {
|
||||
TestSpec spec = parseTestSpec(R"(spec {a} char,spec \[a] char)");
|
||||
|
||||
REQUIRE(spec.matches(*fakeTestCase(R"(spec {a} char)")));
|
||||
REQUIRE(spec.matches(*fakeTestCase(R"(spec [a] char)")));
|
||||
REQUIRE_FALSE(spec.matches(*fakeTestCase("differs but has similar tag", "[a]")));
|
||||
}
|
||||
SECTION("backslash in test name") {
|
||||
TestSpec spec = parseTestSpec(R"(spec \\ char)");
|
||||
|
||||
REQUIRE(spec.matches(*fakeTestCase(R"(spec \ char)")));
|
||||
}
|
||||
}
|
||||
|
||||
TEST_CASE( "Process can be configured on command line", "[config][command-line]" ) {
|
||||
|
||||
using namespace Catch::Matchers;
|
||||
|
@ -300,7 +300,7 @@ TEST_CASE("analyse", "[approvals][benchmark]") {
|
||||
CHECK(analysis.outliers.low_severe == 0);
|
||||
CHECK(analysis.outliers.high_mild == 0);
|
||||
CHECK(analysis.outliers.high_severe == 0);
|
||||
CHECK(analysis.outliers.samples_seen == samples.size());
|
||||
CHECK(analysis.outliers.samples_seen == static_cast<int>(samples.size()));
|
||||
|
||||
CHECK(analysis.outlier_variance < 0.5);
|
||||
CHECK(analysis.outlier_variance > 0);
|
||||
|
@ -61,10 +61,6 @@ namespace { namespace CompilationTests {
|
||||
return val == f.i;
|
||||
}
|
||||
|
||||
struct Y {
|
||||
uint32_t v : 1;
|
||||
};
|
||||
|
||||
void throws_int(bool b) {
|
||||
if (b) {
|
||||
throw 1;
|
||||
@ -142,9 +138,11 @@ namespace { namespace CompilationTests {
|
||||
REQUIRE (x == 4);
|
||||
}
|
||||
|
||||
|
||||
TEST_CASE("#1027") {
|
||||
Y y{0};
|
||||
TEST_CASE("#1027: Bitfields can be captured") {
|
||||
struct Y {
|
||||
uint32_t v : 1;
|
||||
};
|
||||
Y y{ 0 };
|
||||
REQUIRE(y.v == 0);
|
||||
REQUIRE(0 == y.v);
|
||||
}
|
||||
@ -202,19 +200,19 @@ namespace { namespace CompilationTests {
|
||||
inline static void synchronizing_callback( void * ) { }
|
||||
}
|
||||
|
||||
#if defined (_MSC_VER)
|
||||
#pragma warning(push)
|
||||
// The function pointer comparison below triggers warning because of
|
||||
// calling conventions
|
||||
#pragma warning(disable:4244)
|
||||
#endif
|
||||
TEST_CASE("#925: comparing function pointer to function address failed to compile", "[!nonportable]" ) {
|
||||
TestClass test;
|
||||
REQUIRE(utility::synchronizing_callback != test.testMethod_uponComplete_arg);
|
||||
}
|
||||
|
||||
TEST_CASE( "#1027: Bitfields can be captured" ) {
|
||||
struct Y {
|
||||
uint32_t v : 1;
|
||||
};
|
||||
Y y{ 0 };
|
||||
REQUIRE( y.v == 0 );
|
||||
REQUIRE( 0 == y.v );
|
||||
}
|
||||
#if defined (_MSC_VER)
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
TEST_CASE("#1319: Sections can have description (even if it is not saved", "[compilation]") {
|
||||
SECTION("SectionName", "This is a long form section description") {
|
||||
@ -222,6 +220,42 @@ namespace { namespace CompilationTests {
|
||||
}
|
||||
}
|
||||
|
||||
TEST_CASE("Lambdas in assertions") {
|
||||
REQUIRE([]() { return true; }());
|
||||
}
|
||||
|
||||
}} // namespace CompilationTests
|
||||
|
||||
namespace {
|
||||
struct HasBitOperators {
|
||||
int value;
|
||||
|
||||
friend HasBitOperators operator| (HasBitOperators lhs, HasBitOperators rhs) {
|
||||
return { lhs.value | rhs.value };
|
||||
}
|
||||
friend HasBitOperators operator& (HasBitOperators lhs, HasBitOperators rhs) {
|
||||
return { lhs.value & rhs.value };
|
||||
}
|
||||
friend HasBitOperators operator^ (HasBitOperators lhs, HasBitOperators rhs) {
|
||||
return { lhs.value ^ rhs.value };
|
||||
}
|
||||
explicit operator bool() const {
|
||||
return !!value;
|
||||
}
|
||||
|
||||
friend std::ostream& operator<<(std::ostream& out, HasBitOperators val) {
|
||||
out << "Val: " << val.value;
|
||||
return out;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
TEST_CASE("Assertion macros support bit operators and bool conversions", "[compilation][bitops]") {
|
||||
HasBitOperators lhs{ 1 }, rhs{ 2 };
|
||||
REQUIRE(lhs | rhs);
|
||||
REQUIRE_FALSE(lhs & rhs);
|
||||
REQUIRE(HasBitOperators{ 1 } & HasBitOperators{ 1 });
|
||||
REQUIRE(lhs ^ rhs);
|
||||
REQUIRE_FALSE(lhs ^ lhs);
|
||||
}
|
||||
|
||||
|
@ -217,6 +217,42 @@ namespace { namespace MatchersTests {
|
||||
CHECK_THAT(testStringForMatching(), !Contains("substring"));
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
struct CustomAllocator : private std::allocator<T>
|
||||
{
|
||||
using size_type = size_t;
|
||||
using difference_type = ptrdiff_t;
|
||||
using pointer = T*;
|
||||
using const_pointer = const T*;
|
||||
using reference = T&;
|
||||
using const_reference = const T&;
|
||||
using value_type = T;
|
||||
|
||||
template<typename U>
|
||||
struct rebind
|
||||
{ using other = CustomAllocator<U>; };
|
||||
|
||||
using propagate_on_container_move_assignment = std::true_type;
|
||||
using is_always_equal = std::true_type;
|
||||
|
||||
CustomAllocator() = default;
|
||||
|
||||
CustomAllocator(const CustomAllocator& other)
|
||||
: std::allocator<T>(other) { }
|
||||
|
||||
template<typename U>
|
||||
CustomAllocator(const CustomAllocator<U>&) { }
|
||||
|
||||
~CustomAllocator() = default;
|
||||
|
||||
using std::allocator<T>::address;
|
||||
using std::allocator<T>::allocate;
|
||||
using std::allocator<T>::construct;
|
||||
using std::allocator<T>::deallocate;
|
||||
using std::allocator<T>::max_size;
|
||||
using std::allocator<T>::destroy;
|
||||
};
|
||||
|
||||
TEST_CASE("Vector matchers", "[matchers][vector]") {
|
||||
std::vector<int> v;
|
||||
v.push_back(1);
|
||||
@ -237,19 +273,35 @@ namespace { namespace MatchersTests {
|
||||
v4.push_back(2 + 1e-8);
|
||||
v4.push_back(3 + 1e-8);
|
||||
|
||||
std::vector<int, CustomAllocator<int>> v5;
|
||||
v5.push_back(1);
|
||||
v5.push_back(2);
|
||||
v5.push_back(3);
|
||||
|
||||
std::vector<int, CustomAllocator<int>> v6;
|
||||
v6.push_back(1);
|
||||
v6.push_back(2);
|
||||
|
||||
std::vector<int> empty;
|
||||
|
||||
SECTION("Contains (element)") {
|
||||
CHECK_THAT(v, VectorContains(1));
|
||||
CHECK_THAT(v, VectorContains(2));
|
||||
CHECK_THAT(v5, (VectorContains<int, CustomAllocator<int>>(2)));
|
||||
}
|
||||
SECTION("Contains (vector)") {
|
||||
CHECK_THAT(v, Contains(v2));
|
||||
CHECK_THAT(v, Contains<int>({ 1, 2 }));
|
||||
CHECK_THAT(v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)));
|
||||
|
||||
v2.push_back(3); // now exactly matches
|
||||
CHECK_THAT(v, Contains(v2));
|
||||
|
||||
CHECK_THAT(v, Contains(empty));
|
||||
CHECK_THAT(empty, Contains(empty));
|
||||
|
||||
CHECK_THAT(v5, (Contains<int, std::allocator<int>, CustomAllocator<int>>(v2)));
|
||||
CHECK_THAT(v5, Contains(v6));
|
||||
}
|
||||
SECTION("Contains (element), composed") {
|
||||
CHECK_THAT(v, VectorContains(1) && VectorContains(2));
|
||||
@ -263,11 +315,18 @@ namespace { namespace MatchersTests {
|
||||
CHECK_THAT(empty, Equals(empty));
|
||||
|
||||
// Different vector with same elements
|
||||
CHECK_THAT(v, Equals<int>({ 1, 2, 3 }));
|
||||
v2.push_back(3);
|
||||
CHECK_THAT(v, Equals(v2));
|
||||
|
||||
CHECK_THAT(v5, (Equals<int, std::allocator<int>, CustomAllocator<int>>(v2)));
|
||||
|
||||
v6.push_back(3);
|
||||
CHECK_THAT(v5, Equals(v6));
|
||||
}
|
||||
SECTION("UnorderedEquals") {
|
||||
CHECK_THAT(v, UnorderedEquals(v));
|
||||
CHECK_THAT(v, UnorderedEquals<int>({ 3, 2, 1 }));
|
||||
CHECK_THAT(empty, UnorderedEquals(empty));
|
||||
|
||||
auto permuted = v;
|
||||
@ -276,6 +335,12 @@ namespace { namespace MatchersTests {
|
||||
|
||||
std::reverse(begin(permuted), end(permuted));
|
||||
REQUIRE_THAT(permuted, UnorderedEquals(v));
|
||||
|
||||
CHECK_THAT(v5, (UnorderedEquals<int, std::allocator<int>, CustomAllocator<int>>(permuted)));
|
||||
|
||||
auto v5_permuted = v5;
|
||||
std::next_permutation(begin(v5_permuted), end(v5_permuted));
|
||||
CHECK_THAT(v5_permuted, UnorderedEquals(v5));
|
||||
}
|
||||
}
|
||||
|
||||
@ -521,6 +586,7 @@ namespace { namespace MatchersTests {
|
||||
std::vector<double> v1({1., 2., 3.});
|
||||
SECTION("A vector is approx equal to itself") {
|
||||
REQUIRE_THAT(v1, Approx(v1));
|
||||
REQUIRE_THAT(v1, Approx<double>({ 1., 2., 3. }));
|
||||
}
|
||||
std::vector<double> v2({1.5, 2.5, 3.5});
|
||||
SECTION("Different length") {
|
||||
|
62
tests/TestScripts/testRandomOrder.py
Executable file
62
tests/TestScripts/testRandomOrder.py
Executable file
@ -0,0 +1,62 @@
|
||||
#!/usr/bin/env python3
|
||||
|
||||
"""
|
||||
This test script verifies that the random ordering of tests inside
|
||||
Catch2 is invariant in regards to subsetting. This is done by running
|
||||
the binary 3 times, once with all tests selected, and twice with smaller
|
||||
subsets of tests selected, and verifying that the selected tests are in
|
||||
the same relative order.
|
||||
"""
|
||||
|
||||
import subprocess
|
||||
import sys
|
||||
import random
|
||||
import xml.etree.ElementTree as ET
|
||||
|
||||
def list_tests(self_test_exe, tags, rng_seed):
|
||||
cmd = [self_test_exe, '--reporter', 'xml', '--list-tests', '--order', 'rand',
|
||||
'--rng-seed', str(rng_seed)]
|
||||
tags_arg = ','.join('[{}]'.format(t) for t in tags)
|
||||
if tags_arg:
|
||||
cmd.append(tags_arg + '~[.]')
|
||||
process = subprocess.Popen(
|
||||
cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
|
||||
stdout, stderr = process.communicate()
|
||||
if stderr:
|
||||
raise RuntimeError("Unexpected error output:\n" + process.stderr)
|
||||
|
||||
root = ET.fromstring(stdout)
|
||||
result = [elem.text for elem in root.findall('./TestCase/Name')]
|
||||
|
||||
if len(result) < 2:
|
||||
raise RuntimeError("Unexpectedly few tests listed (got {})".format(
|
||||
len(result)))
|
||||
return result
|
||||
|
||||
def check_is_sublist_of(shorter, longer):
|
||||
assert len(shorter) < len(longer)
|
||||
assert len(set(longer)) == len(longer)
|
||||
|
||||
indexes_in_longer = {s: i for i, s in enumerate(longer)}
|
||||
for s1, s2 in zip(shorter, shorter[1:]):
|
||||
assert indexes_in_longer[s1] < indexes_in_longer[s2], (
|
||||
'{} comes before {} in longer list.\n'
|
||||
'Longer: {}\nShorter: {}'.format(s2, s1, longer, shorter))
|
||||
|
||||
def main():
|
||||
self_test_exe, = sys.argv[1:]
|
||||
|
||||
# We want a random seed for the test, but want to avoid 0,
|
||||
# because it has special meaning
|
||||
seed = random.randint(1, 2 ** 32 - 1)
|
||||
|
||||
list_one_tag = list_tests(self_test_exe, ['generators'], seed)
|
||||
list_two_tags = list_tests(self_test_exe, ['generators', 'matchers'], seed)
|
||||
list_all = list_tests(self_test_exe, [], seed)
|
||||
|
||||
# First, verify that restricting to a subset yields the same order
|
||||
check_is_sublist_of(list_two_tags, list_all)
|
||||
check_is_sublist_of(list_one_tag, list_two_tags)
|
||||
|
||||
if __name__ == '__main__':
|
||||
sys.exit(main())
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import releaseCommon
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
# Execute this script any time you import a new copy of Clara into the third_party area
|
||||
import os
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
#
|
||||
# extractFeaturesFromReleaseNotes.py
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import os
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import releaseCommon
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import releaseCommon
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import releaseCommon
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
#
|
||||
# updateDocumentToC.py
|
||||
|
@ -1,16 +1,22 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
import json
|
||||
import os
|
||||
import urllib2
|
||||
import urllib.request
|
||||
import urllib.parse
|
||||
|
||||
|
||||
from scriptCommon import catchPath
|
||||
|
||||
def upload(options):
|
||||
request = urllib2.Request('http://melpon.org/wandbox/api/compile.json')
|
||||
request.add_header('Content-Type', 'application/json')
|
||||
response = urllib2.urlopen(request, json.dumps(options))
|
||||
return json.loads(response.read())
|
||||
# request_blah = urllib.request.Request('https://
|
||||
|
||||
request = urllib.request.Request('https://melpon.org/wandbox/api/compile.json', method='POST')
|
||||
json_bytes = json.dumps(options).encode('utf-8')
|
||||
request.add_header('Content-Type', 'application/json; charset=utf-8')
|
||||
request.add_header('Content-Length', len(json_bytes))
|
||||
response = urllib.request.urlopen(request, json_bytes)
|
||||
return json.loads(response.read().decode('utf-8'))
|
||||
|
||||
main_file = '''
|
||||
#define CATCH_CONFIG_MAIN // This tells Catch to provide a main() - only do this in one cpp file
|
||||
|
Loading…
Reference in New Issue
Block a user