mirror of
https://github.com/catchorg/Catch2.git
synced 2025-09-11 16:05:40 +02:00
Compare commits
16 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
d2d8455b57 | ||
![]() |
ab30621138 | ||
![]() |
1ca8f43b01 | ||
![]() |
dfb83f20e9 | ||
![]() |
319bddd5b8 | ||
![]() |
931441251e | ||
![]() |
ea1f326261 | ||
![]() |
3641706923 | ||
![]() |
3b801c4fda | ||
![]() |
e11508b48a | ||
![]() |
886d799b79 | ||
![]() |
8b78087412 | ||
![]() |
6c99b04c87 | ||
![]() |
0a34cc201e | ||
![]() |
11c89a5f7d | ||
![]() |
dc3e7f9cf7 |
23
.travis.yml
23
.travis.yml
@@ -232,27 +232,24 @@ before_script:
|
||||
# Regenerate single header file, so it is tested in the examples...
|
||||
- python scripts/generateSingleHeader.py
|
||||
|
||||
- |
|
||||
# Use Debug builds for running Valgrind and building examples
|
||||
cmake -H. -BBuild-Debug -DCMAKE_BUILD_TYPE=Debug -Wdev -DUSE_CPP14=${CPP14} -DCATCH_USE_VALGRIND=${VALGRIND} -DCATCH_BUILD_EXAMPLES=${EXAMPLES} -DCATCH_ENABLE_COVERAGE=${COVERAGE}
|
||||
- cmake -H. -BBuild-Debug -DCMAKE_BUILD_TYPE=Debug -Wdev -DUSE_CPP14=${CPP14} -DCATCH_USE_VALGRIND=${VALGRIND} -DCATCH_BUILD_EXAMPLES=${EXAMPLES} -DCATCH_ENABLE_COVERAGE=${COVERAGE}
|
||||
# Don't bother with release build for coverage build
|
||||
cmake -H. -BBuild-Release -DCMAKE_BUILD_TYPE=Release -Wdev -DUSE_CPP14=${CPP14}
|
||||
- cmake -H. -BBuild-Release -DCMAKE_BUILD_TYPE=Release -Wdev -DUSE_CPP14=${CPP14}
|
||||
|
||||
|
||||
script:
|
||||
- |
|
||||
cd Build-Debug
|
||||
make -j 2
|
||||
CTEST_OUTPUT_ON_FAILURE=1 ctest -j 2
|
||||
- cd Build-Debug
|
||||
- make -j 2
|
||||
- CTEST_OUTPUT_ON_FAILURE=1 ctest -j 2
|
||||
# Coverage collection does not work for OS X atm
|
||||
echo "${TRAVIS_OS_NAME}";
|
||||
echo "${COVERAGE}";
|
||||
- |
|
||||
if [[ "${TRAVIS_OS_NAME}" == "linux" ]] && [[ "${COVERAGE}" == "1" ]]; then
|
||||
make gcov
|
||||
make lcov
|
||||
bash <(curl -s https://codecov.io/bash) -X gcov || echo "Codecov did not collect coverage reports"
|
||||
fi
|
||||
# Go to release build
|
||||
cd ../Build-Release
|
||||
make -j 2
|
||||
CTEST_OUTPUT_ON_FAILURE=1 ctest -j 2
|
||||
- # Go to release build
|
||||
- cd ../Build-Release
|
||||
- make -j 2
|
||||
- CTEST_OUTPUT_ON_FAILURE=1 ctest -j 2
|
||||
|
@@ -6,7 +6,7 @@ if(NOT DEFINED PROJECT_NAME)
|
||||
set(NOT_SUBPROJECT ON)
|
||||
endif()
|
||||
|
||||
project(Catch2 LANGUAGES CXX VERSION 2.2.0)
|
||||
project(Catch2 LANGUAGES CXX VERSION 2.2.2)
|
||||
|
||||
include(GNUInstallDirs)
|
||||
|
||||
@@ -152,6 +152,7 @@ set(INTERNAL_HEADERS
|
||||
${HEADER_DIR}/internal/catch_list.h
|
||||
${HEADER_DIR}/internal/catch_matchers.h
|
||||
${HEADER_DIR}/internal/catch_matchers_floating.h
|
||||
${HEADER_DIR}/internal/catch_matchers_generic.hpp
|
||||
${HEADER_DIR}/internal/catch_matchers_string.h
|
||||
${HEADER_DIR}/internal/catch_matchers_vector.h
|
||||
${HEADER_DIR}/internal/catch_message.h
|
||||
@@ -221,6 +222,7 @@ set(IMPL_SOURCES
|
||||
${HEADER_DIR}/internal/catch_leak_detector.cpp
|
||||
${HEADER_DIR}/internal/catch_matchers.cpp
|
||||
${HEADER_DIR}/internal/catch_matchers_floating.cpp
|
||||
${HEADER_DIR}/internal/catch_matchers_generic.cpp
|
||||
${HEADER_DIR}/internal/catch_matchers_string.cpp
|
||||
${HEADER_DIR}/internal/catch_message.cpp
|
||||
${HEADER_DIR}/internal/catch_registry_hub.cpp
|
||||
|
@@ -5,9 +5,9 @@
|
||||
[](https://travis-ci.org/catchorg/Catch2)
|
||||
[](https://ci.appveyor.com/project/catchorg/catch2)
|
||||
[](https://codecov.io/gh/catchorg/Catch2)
|
||||
[](https://wandbox.org/permlink/vOtfjd7LKmcj4JqD)
|
||||
[](https://wandbox.org/permlink/fRDMfYjUnrbOFwLn)
|
||||
|
||||
<a href="https://github.com/catchorg/Catch2/releases/download/v2.2.0/catch.hpp">The latest version of the single header can be downloaded directly using this link</a>
|
||||
<a href="https://github.com/catchorg/Catch2/releases/download/v2.2.2/catch.hpp">The latest version of the single header can be downloaded directly using this link</a>
|
||||
|
||||
## Catch2 is released!
|
||||
|
||||
|
@@ -33,6 +33,8 @@ environment:
|
||||
|
||||
|
||||
matrix:
|
||||
allow_failures:
|
||||
- os: Visual Studio 2017
|
||||
exclude:
|
||||
- os: Visual Studio 2015
|
||||
additional_flags: "/permissive- /std:c++latest"
|
||||
@@ -62,7 +64,7 @@ matrix:
|
||||
|
||||
|
||||
install:
|
||||
- ps: if (($env:CONFIGURATION) -eq "Debug" -And ($env:coverage) -eq "1" ) { python -m pip install codecov }
|
||||
- ps: if (($env:CONFIGURATION) -eq "Debug" -And ($env:coverage) -eq "1" ) { python -m pip --disable-pip-version-check install codecov }
|
||||
- ps: if (($env:CONFIGURATION) -eq "Debug" -And ($env:coverage) -eq "1" ) { .\misc\installOpenCppCoverage.ps1 }
|
||||
|
||||
# Win32 and x64 are CMake-compatible solution platform names.
|
||||
|
@@ -3,4 +3,4 @@ includedir=@CMAKE_INSTALL_FULL_INCLUDEDIR@
|
||||
Name: Catch
|
||||
Description: Testing library for C++
|
||||
Version: @Catch2_VERSION@
|
||||
Cflags: -I${includedir}
|
||||
Cflags: -I${includedir} -I${includedir}/catch
|
||||
|
@@ -4,7 +4,7 @@ from conans import ConanFile
|
||||
|
||||
class CatchConan(ConanFile):
|
||||
name = "Catch"
|
||||
version = "2.2.0"
|
||||
version = "2.2.2"
|
||||
description = "A modern, C++-native, header-only, framework for unit-tests, TDD and BDD"
|
||||
author = "philsquared"
|
||||
generators = "cmake"
|
||||
|
@@ -53,6 +53,25 @@ The floating point matchers are `WithinULP` and `WithinAbs`. `WithinAbs` accepts
|
||||
Do note that ULP-based checks only make sense when both compared numbers are of the same type and `WithinULP` will use type of its argument as the target type. This means that `WithinULP(1.f, 1)` will expect to compare `float`s, but `WithinULP(1., 1)` will expect to compare `double`s.
|
||||
|
||||
|
||||
### Generic matchers
|
||||
Catch also aims to provide a set of generic matchers. Currently this set
|
||||
contains only a matcher that takes arbitrary callable predicate and applies
|
||||
it onto the provided object.
|
||||
|
||||
Because of type inference limitations, the argument type of the predicate
|
||||
has to be provided explicitly. Example:
|
||||
```cpp
|
||||
REQUIRE_THAT("Hello olleH",
|
||||
Predicate<std::string>(
|
||||
[] (std::string const& str) -> bool { return str.front() == str.back(); },
|
||||
"First and last character should be equal")
|
||||
);
|
||||
```
|
||||
|
||||
The second argument is an optional description of the predicate, and is
|
||||
used only during reporting of the result.
|
||||
|
||||
|
||||
## Custom matchers
|
||||
It's easy to provide your own matchers to extend Catch or just to work with your own types.
|
||||
|
||||
|
@@ -1,5 +1,39 @@
|
||||
<a id="top"></a>
|
||||
|
||||
# 2.2.2
|
||||
|
||||
## Fixes
|
||||
* Fixed bug in `WithinAbs::match()` failing spuriously (#1228)
|
||||
* Fixed clang-tidy diagnostic about virtual call in destructor (#1226)
|
||||
* Reduced the number of GCC warnings suppression leaking out of the header (#1090, #1091)
|
||||
* Only `-Wparentheses` should be leaking now
|
||||
* Added upper bound on the time benchmark timer calibration is allowed to take (#1237)
|
||||
* On platforms where `std::chrono::high_resolution_clock`'s resolution is low, the calibration would appear stuck
|
||||
* Fixed compilation error when stringifying static arrays of `unsigned char`s (#1238)
|
||||
|
||||
## Improvements
|
||||
* XML encoder now hex-encodes invalid UTF-8 sequences (#1207)
|
||||
* This affects xml and junit reporters
|
||||
* Some invalid UTF-8 parts are left as is, e.g. surrogate pairs. This is because certain extensions of UTF-8 allow them, such as WTF-8.
|
||||
* CLR objects (`T^`) can now be stringified (#1216)
|
||||
* This affects code compiled as C++/CLI
|
||||
* Added `PredicateMatcher`, a matcher that takes an arbitrary predicate function (#1236)
|
||||
* See [documentation for details](https://github.com/catchorg/Catch2/blob/master/docs/matchers.md)
|
||||
|
||||
## Others
|
||||
* Modified CMake-installed pkg-config to allow `#include <catch.hpp>`(#1239)
|
||||
* The plans to standardize on `#include <catch2/catch.hpp>` are still in effect
|
||||
|
||||
|
||||
# 2.2.1
|
||||
|
||||
## Fixes
|
||||
* Fixed compilation error when compiling Catch2 with `std=c++17` against libc++ (#1214)
|
||||
* Clara (Catch2's CLI parsing library) used `std::optional` without including it explicitly
|
||||
* Fixed Catch2 return code always being 0 (#1215)
|
||||
* In the words of STL, "We feel superbad about letting this in"
|
||||
|
||||
|
||||
# 2.2.0
|
||||
|
||||
## Fixes
|
||||
|
@@ -11,7 +11,7 @@
|
||||
|
||||
#define CATCH_VERSION_MAJOR 2
|
||||
#define CATCH_VERSION_MINOR 2
|
||||
#define CATCH_VERSION_PATCH 0
|
||||
#define CATCH_VERSION_PATCH 2
|
||||
|
||||
#ifdef __clang__
|
||||
# pragma clang system_header
|
||||
|
7
include/external/clara.hpp
vendored
7
include/external/clara.hpp
vendored
@@ -5,7 +5,7 @@
|
||||
//
|
||||
// See https://github.com/philsquared/Clara for more details
|
||||
|
||||
// Clara v1.1.3
|
||||
// Clara v1.1.4
|
||||
|
||||
#ifndef CATCH_CLARA_HPP_INCLUDED
|
||||
#define CATCH_CLARA_HPP_INCLUDED
|
||||
@@ -21,6 +21,7 @@
|
||||
#ifndef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
#ifdef __has_include
|
||||
#if __has_include(<optional>) && __cplusplus >= 201703L
|
||||
#include <optional>
|
||||
#define CLARA_CONFIG_OPTIONAL_TYPE std::optional
|
||||
#endif
|
||||
#endif
|
||||
@@ -665,11 +666,11 @@ namespace detail {
|
||||
}
|
||||
#ifdef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
template<typename T>
|
||||
inline auto convertInto( std::string const &source, std::optional<T>& target ) -> ParserResult {
|
||||
inline auto convertInto( std::string const &source, CLARA_CONFIG_OPTIONAL_TYPE<T>& target ) -> ParserResult {
|
||||
T temp;
|
||||
auto result = convertInto( source, temp );
|
||||
if( result )
|
||||
target = temp;
|
||||
target = std::move(temp);
|
||||
return result;
|
||||
}
|
||||
#endif // CLARA_CONFIG_OPTIONAL_TYPE
|
||||
|
@@ -11,6 +11,7 @@
|
||||
#include "catch_capture.hpp"
|
||||
#include "catch_matchers.h"
|
||||
#include "catch_matchers_floating.h"
|
||||
#include "catch_matchers_generic.hpp"
|
||||
#include "catch_matchers_string.h"
|
||||
#include "catch_matchers_vector.h"
|
||||
|
||||
|
@@ -88,7 +88,7 @@ namespace Floating {
|
||||
// Performs equivalent check of std::fabs(lhs - rhs) <= margin
|
||||
// But without the subtraction to allow for INFINITY in comparison
|
||||
bool WithinAbsMatcher::match(double const& matchee) const {
|
||||
return (matchee + m_margin >= m_target) && (m_target + m_margin >= m_margin);
|
||||
return (matchee + m_margin >= m_target) && (m_target + m_margin >= matchee);
|
||||
}
|
||||
|
||||
std::string WithinAbsMatcher::describe() const {
|
||||
|
9
include/internal/catch_matchers_generic.cpp
Normal file
9
include/internal/catch_matchers_generic.cpp
Normal file
@@ -0,0 +1,9 @@
|
||||
#include "catch_matchers_generic.hpp"
|
||||
|
||||
std::string Catch::Matchers::Generic::Detail::finalizeDescription(const std::string& desc) {
|
||||
if (desc.empty()) {
|
||||
return "matches undescribed predicate";
|
||||
} else {
|
||||
return "matches predicate: \"" + desc + '"';
|
||||
}
|
||||
}
|
58
include/internal/catch_matchers_generic.hpp
Normal file
58
include/internal/catch_matchers_generic.hpp
Normal file
@@ -0,0 +1,58 @@
|
||||
/*
|
||||
* Created by Martin Hořeňovský on 03/04/2017.
|
||||
*
|
||||
* 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_MATCHERS_GENERIC_HPP_INCLUDED
|
||||
#define TWOBLUECUBES_CATCH_MATCHERS_GENERIC_HPP_INCLUDED
|
||||
|
||||
#include "catch_common.h"
|
||||
#include "catch_matchers.h"
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
|
||||
namespace Catch {
|
||||
namespace Matchers {
|
||||
namespace Generic {
|
||||
|
||||
namespace Detail {
|
||||
std::string finalizeDescription(const std::string& desc);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
class PredicateMatcher : public MatcherBase<T> {
|
||||
std::function<bool(T const&)> m_predicate;
|
||||
std::string m_description;
|
||||
public:
|
||||
|
||||
PredicateMatcher(std::function<bool(T const&)> const& elem, std::string const& descr)
|
||||
:m_predicate(std::move(elem)),
|
||||
m_description(Detail::finalizeDescription(descr))
|
||||
{}
|
||||
|
||||
bool match( T const& item ) const override {
|
||||
return m_predicate(item);
|
||||
}
|
||||
|
||||
std::string describe() const override {
|
||||
return m_description;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace Generic
|
||||
|
||||
// The following functions create the actual matcher objects.
|
||||
// The user has to explicitly specify type to the function, because
|
||||
// infering std::function<bool(T const&)> is hard (but possible) and
|
||||
// requires a lot of TMP.
|
||||
template<typename T>
|
||||
Generic::PredicateMatcher<T> Predicate(std::function<bool(T const&)> const& predicate, std::string const& description = "") {
|
||||
return Generic::PredicateMatcher<T>(predicate, description);
|
||||
}
|
||||
|
||||
} // namespace Matchers
|
||||
} // namespace Catch
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_MATCHERS_GENERIC_HPP_INCLUDED
|
@@ -99,7 +99,7 @@ namespace Catch {
|
||||
|
||||
public:
|
||||
// !TBD We need to do this another way!
|
||||
bool aborting() const override;
|
||||
bool aborting() const final;
|
||||
|
||||
private:
|
||||
|
||||
|
@@ -277,7 +277,7 @@ namespace Catch {
|
||||
// Note that on unices only the lower 8 bits are usually used, clamping
|
||||
// the return value to 255 prevents false negative when some multiple
|
||||
// of 256 tests has failed
|
||||
return (std::min)( { MaxExitCode, totals.error, static_cast<int>( totals.assertions.failed ) } );
|
||||
return (std::min) (MaxExitCode, (std::max) (totals.error, static_cast<int>(totals.assertions.failed)));
|
||||
}
|
||||
catch( std::exception& ex ) {
|
||||
Catch::cerr() << ex.what() << std::endl;
|
||||
|
@@ -17,8 +17,8 @@
|
||||
# pragma clang diagnostic ignored "-Wcovered-switch-default"
|
||||
# endif
|
||||
#elif defined __GNUC__
|
||||
# pragma GCC diagnostic ignored "-Wunused-variable"
|
||||
# pragma GCC diagnostic ignored "-Wparentheses"
|
||||
# pragma GCC diagnostic push
|
||||
# pragma GCC diagnostic ignored "-Wunused-variable"
|
||||
# pragma GCC diagnostic ignored "-Wpadded"
|
||||
#endif
|
||||
|
@@ -10,6 +10,8 @@
|
||||
|
||||
#include <chrono>
|
||||
|
||||
static const uint64_t nanosecondsInSecond = 1000000000;
|
||||
|
||||
namespace Catch {
|
||||
|
||||
auto getCurrentNanosecondsSinceEpoch() -> uint64_t {
|
||||
@@ -20,17 +22,25 @@ namespace Catch {
|
||||
uint64_t sum = 0;
|
||||
static const uint64_t iterations = 1000000;
|
||||
|
||||
auto startTime = getCurrentNanosecondsSinceEpoch();
|
||||
|
||||
for( std::size_t i = 0; i < iterations; ++i ) {
|
||||
|
||||
uint64_t ticks;
|
||||
uint64_t baseTicks = getCurrentNanosecondsSinceEpoch();
|
||||
do {
|
||||
ticks = getCurrentNanosecondsSinceEpoch();
|
||||
}
|
||||
while( ticks == baseTicks );
|
||||
} while( ticks == baseTicks );
|
||||
|
||||
auto delta = ticks - baseTicks;
|
||||
sum += delta;
|
||||
|
||||
// If we have been calibrating for over 3 seconds -- the clock
|
||||
// is terrible and we should move on.
|
||||
// TBD: How to signal that the measured resolution is probably wrong?
|
||||
if (ticks > startTime + 3 * nanosecondsInSecond) {
|
||||
return sum / i;
|
||||
}
|
||||
}
|
||||
|
||||
// We're just taking the mean, here. To do better we could take the std. dev and exclude outliers
|
||||
|
@@ -75,6 +75,19 @@ namespace Catch {
|
||||
return convertUnknownEnumToString( value );
|
||||
}
|
||||
|
||||
|
||||
#if defined(_MANAGED)
|
||||
//! Convert a CLR string to a utf8 std::string
|
||||
template<typename T>
|
||||
std::string clrReferenceToString( T^ ref ) {
|
||||
if (ref == nullptr)
|
||||
return std::string("null");
|
||||
auto bytes = System::Text::Encoding::UTF8->GetBytes(ref->ToString());
|
||||
cli::pin_ptr<System::Byte> p = &bytes[0];
|
||||
return std::string(reinterpret_cast<char const *>(p), bytes->Length);
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace Detail
|
||||
|
||||
|
||||
@@ -112,6 +125,13 @@ namespace Catch {
|
||||
return ::Catch::Detail::stringify(static_cast<typename std::underlying_type<E>::type>(e));
|
||||
}
|
||||
|
||||
#if defined(_MANAGED)
|
||||
template <typename T>
|
||||
std::string stringify( T^ e ) {
|
||||
return ::Catch::StringMaker<T^>::convert(e);
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace Detail
|
||||
|
||||
// Some predefined specializations
|
||||
@@ -135,6 +155,7 @@ namespace Catch {
|
||||
struct StringMaker<char *> {
|
||||
static std::string convert(char * str);
|
||||
};
|
||||
|
||||
#ifdef CATCH_CONFIG_WCHAR
|
||||
template<>
|
||||
struct StringMaker<wchar_t const *> {
|
||||
@@ -146,22 +167,24 @@ namespace Catch {
|
||||
};
|
||||
#endif
|
||||
|
||||
// TBD: Should we use `strnlen` to ensure that we don't go out of the buffer,
|
||||
// while keeping string semantics?
|
||||
template<int SZ>
|
||||
struct StringMaker<char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
static std::string convert(char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
}
|
||||
};
|
||||
template<int SZ>
|
||||
struct StringMaker<signed char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
static std::string convert(signed char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ reinterpret_cast<char const *>(str) });
|
||||
}
|
||||
};
|
||||
template<int SZ>
|
||||
struct StringMaker<unsigned char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
static std::string convert(unsigned char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ reinterpret_cast<char const *>(str) });
|
||||
}
|
||||
};
|
||||
|
||||
@@ -245,6 +268,15 @@ namespace Catch {
|
||||
}
|
||||
};
|
||||
|
||||
#if defined(_MANAGED)
|
||||
template <typename T>
|
||||
struct StringMaker<T^> {
|
||||
static std::string convert( T^ ref ) {
|
||||
return ::Catch::Detail::clrReferenceToString(ref);
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
namespace Detail {
|
||||
template<typename InputIterator>
|
||||
std::string rangeToString(InputIterator first, InputIterator last) {
|
||||
@@ -374,6 +406,13 @@ namespace Catch {
|
||||
!std::is_same<decltype(end(std::declval<T>())), not_this_one>::value;
|
||||
};
|
||||
|
||||
#if defined(_MANAGED) // Managed types are never ranges
|
||||
template <typename T>
|
||||
struct is_range<T^> {
|
||||
static const bool value = false;
|
||||
};
|
||||
#endif
|
||||
|
||||
template<typename Range>
|
||||
std::string rangeToString( Range const& range ) {
|
||||
return ::Catch::Detail::rangeToString( begin( range ), end( range ) );
|
||||
|
@@ -37,7 +37,7 @@ namespace Catch {
|
||||
}
|
||||
|
||||
Version const& libraryVersion() {
|
||||
static Version version( 2, 2, 0, "", 0 );
|
||||
static Version version( 2, 2, 2, "", 0 );
|
||||
return version;
|
||||
}
|
||||
|
||||
|
@@ -7,51 +7,145 @@
|
||||
|
||||
#include "catch_xmlwriter.h"
|
||||
|
||||
#include "catch_enforce.h"
|
||||
|
||||
#include <iomanip>
|
||||
|
||||
using uchar = unsigned char;
|
||||
|
||||
namespace Catch {
|
||||
|
||||
namespace {
|
||||
|
||||
size_t trailingBytes(unsigned char c) {
|
||||
if ((c & 0xE0) == 0xC0) {
|
||||
return 2;
|
||||
}
|
||||
if ((c & 0xF0) == 0xE0) {
|
||||
return 3;
|
||||
}
|
||||
if ((c & 0xF8) == 0xF0) {
|
||||
return 4;
|
||||
}
|
||||
CATCH_INTERNAL_ERROR("Invalid multibyte utf-8 start byte encountered");
|
||||
}
|
||||
|
||||
uint32_t headerValue(unsigned char c) {
|
||||
if ((c & 0xE0) == 0xC0) {
|
||||
return c & 0x1F;
|
||||
}
|
||||
if ((c & 0xF0) == 0xE0) {
|
||||
return c & 0x0F;
|
||||
}
|
||||
if ((c & 0xF8) == 0xF0) {
|
||||
return c & 0x07;
|
||||
}
|
||||
CATCH_INTERNAL_ERROR("Invalid multibyte utf-8 start byte encountered");
|
||||
}
|
||||
|
||||
void hexEscapeChar(std::ostream& os, unsigned char c) {
|
||||
os << "\\x"
|
||||
<< std::uppercase << std::hex << std::setfill('0') << std::setw(2)
|
||||
<< static_cast<int>(c);
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
XmlEncode::XmlEncode( std::string const& str, ForWhat forWhat )
|
||||
: m_str( str ),
|
||||
m_forWhat( forWhat )
|
||||
{}
|
||||
|
||||
void XmlEncode::encodeTo( std::ostream& os ) const {
|
||||
|
||||
// Apostrophe escaping not necessary if we always use " to write attributes
|
||||
// (see: http://www.w3.org/TR/xml/#syntax)
|
||||
|
||||
for( std::size_t i = 0; i < m_str.size(); ++ i ) {
|
||||
char c = m_str[i];
|
||||
switch( c ) {
|
||||
case '<': os << "<"; break;
|
||||
case '&': os << "&"; break;
|
||||
for( std::size_t idx = 0; idx < m_str.size(); ++ idx ) {
|
||||
uchar c = m_str[idx];
|
||||
switch (c) {
|
||||
case '<': os << "<"; break;
|
||||
case '&': os << "&"; break;
|
||||
|
||||
case '>':
|
||||
// See: http://www.w3.org/TR/xml/#syntax
|
||||
if( i > 2 && m_str[i-1] == ']' && m_str[i-2] == ']' )
|
||||
os << ">";
|
||||
else
|
||||
os << c;
|
||||
case '>':
|
||||
// See: http://www.w3.org/TR/xml/#syntax
|
||||
if (idx > 2 && m_str[idx - 1] == ']' && m_str[idx - 2] == ']')
|
||||
os << ">";
|
||||
else
|
||||
os << c;
|
||||
break;
|
||||
|
||||
case '\"':
|
||||
if (m_forWhat == ForAttributes)
|
||||
os << """;
|
||||
else
|
||||
os << c;
|
||||
break;
|
||||
|
||||
default:
|
||||
// Check for control characters and invalid utf-8
|
||||
|
||||
// Escape control characters in standard ascii
|
||||
// see http://stackoverflow.com/questions/404107/why-are-control-characters-illegal-in-xml-1-0
|
||||
if (c < 0x09 || (c > 0x0D && c < 0x20) || c == 0x7F) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
case '\"':
|
||||
if( m_forWhat == ForAttributes )
|
||||
os << """;
|
||||
else
|
||||
os << c;
|
||||
// Plain ASCII: Write it to stream
|
||||
if (c < 0x7F) {
|
||||
os << c;
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
// Escape control chars - based on contribution by @espenalb in PR #465 and
|
||||
// by @mrpi PR #588
|
||||
if ( ( c >= 0 && c < '\x09' ) || ( c > '\x0D' && c < '\x20') || c=='\x7F' ) {
|
||||
// see http://stackoverflow.com/questions/404107/why-are-control-characters-illegal-in-xml-1-0
|
||||
os << "\\x" << std::uppercase << std::hex << std::setfill('0') << std::setw(2)
|
||||
<< static_cast<int>( c );
|
||||
}
|
||||
else
|
||||
os << c;
|
||||
// UTF-8 territory
|
||||
// Check if the encoding is valid and if it is not, hex escape bytes.
|
||||
// Important: We do not check the exact decoded values for validity, only the encoding format
|
||||
// First check that this bytes is a valid lead byte:
|
||||
// This means that it is not encoded as 1111 1XXX
|
||||
// Or as 10XX XXXX
|
||||
if (c < 0xC0 ||
|
||||
c >= 0xF8) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
auto encBytes = trailingBytes(c);
|
||||
// Are there enough bytes left to avoid accessing out-of-bounds memory?
|
||||
if (idx + encBytes - 1 >= m_str.size()) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
// The header is valid, check data
|
||||
// The next encBytes bytes must together be a valid utf-8
|
||||
// This means: bitpattern 10XX XXXX and the extracted value is sane (ish)
|
||||
bool valid = true;
|
||||
uint32_t value = headerValue(c);
|
||||
for (std::size_t n = 1; n < encBytes; ++n) {
|
||||
uchar nc = m_str[idx + n];
|
||||
valid &= ((nc & 0xC0) == 0x80);
|
||||
value = (value << 6) | (nc & 0x3F);
|
||||
}
|
||||
|
||||
if (
|
||||
// Wrong bit pattern of following bytes
|
||||
(!valid) ||
|
||||
// Overlong encodings
|
||||
(value < 0x80) ||
|
||||
(0x80 <= value && value < 0x800 && encBytes > 2) ||
|
||||
(0x800 < value && value < 0x10000 && encBytes > 3) ||
|
||||
// Encoded value out of range
|
||||
(value >= 0x110000)
|
||||
) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
// If we got here, this is in fact a valid(ish) utf-8 sequence
|
||||
for (std::size_t n = 0; n < encBytes; ++n) {
|
||||
os << m_str[idx + n];
|
||||
}
|
||||
idx += encBytes - 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -56,7 +56,7 @@ namespace Catch {
|
||||
|
||||
XmlWriter( std::ostream& os = Catch::cout() );
|
||||
~XmlWriter();
|
||||
|
||||
|
||||
XmlWriter( XmlWriter const& ) = delete;
|
||||
XmlWriter& operator=( XmlWriter const& ) = delete;
|
||||
|
||||
|
@@ -10,6 +10,8 @@ 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: {?} >= {?}
|
||||
Misc.tests.cpp:<line number>: passed:
|
||||
Compilation.tests.cpp:<line number>: passed: std::memcmp(uarr, "123", sizeof(uarr)) == 0 for: 0 == 0 with 2 messages: 'uarr := "123"' and 'sarr := "456"'
|
||||
Compilation.tests.cpp:<line number>: passed: std::memcmp(sarr, "456", sizeof(sarr)) == 0 for: 0 == 0 with 2 messages: 'uarr := "123"' and 'sarr := "456"'
|
||||
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'
|
||||
@@ -97,6 +99,10 @@ Approx.tests.cpp:<line number>: passed: 0 == Approx( dZero) for: 0 == Approx( 0.
|
||||
Approx.tests.cpp:<line number>: passed: 0 == Approx( dSmall ).margin( 0.001 ) for: 0 == Approx( 0.00001 )
|
||||
Approx.tests.cpp:<line number>: passed: 1.234f == Approx( dMedium ) for: 1.234f == Approx( 1.234 )
|
||||
Approx.tests.cpp:<line number>: passed: dMedium == Approx( 1.234f ) for: 1.234 == Approx( 1.2339999676 )
|
||||
Matchers.tests.cpp:<line number>: passed: 1, Predicate<int>(alwaysTrue, "always true") for: 1 matches predicate: "always true"
|
||||
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
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
Tricky.tests.cpp:<line number>: passed: true
|
||||
@@ -235,6 +241,10 @@ Matchers.tests.cpp:<line number>: passed: 0., WithinAbs(1., 1) for: 0.0 is withi
|
||||
Matchers.tests.cpp:<line number>: passed: 0., !WithinAbs(1., 0.99) for: 0.0 not is within 0.99 of 1.0
|
||||
Matchers.tests.cpp:<line number>: passed: 0., !WithinAbs(1., 0.99) for: 0.0 not is within 0.99 of 1.0
|
||||
Matchers.tests.cpp:<line number>: passed: NAN, !WithinAbs(NAN, 0) for: nanf not is within 0.0 of nan
|
||||
Matchers.tests.cpp:<line number>: passed: 11., !WithinAbs(10., 0.5) for: 11.0 not is within 0.5 of 10.0
|
||||
Matchers.tests.cpp:<line number>: passed: 10., !WithinAbs(11., 0.5) for: 10.0 not is within 0.5 of 11.0
|
||||
Matchers.tests.cpp:<line number>: passed: -10., WithinAbs(-10., 0.5) for: -10.0 is within 0.5 of -10.0
|
||||
Matchers.tests.cpp:<line number>: passed: -10., WithinAbs(-9.6, 0.5) for: -10.0 is within 0.5 of -9.6
|
||||
Matchers.tests.cpp:<line number>: passed: 1., WithinULP(1., 0) for: 1.0 is within 0 ULPs of 1.0
|
||||
Matchers.tests.cpp:<line number>: passed: nextafter(1., 2.), WithinULP(1., 1) for: 1.0 is within 1 ULPs of 1.0
|
||||
Matchers.tests.cpp:<line number>: passed: nextafter(1., 0.), WithinULP(1., 1) for: 1.0 is within 1 ULPs of 1.0
|
||||
@@ -255,6 +265,10 @@ Matchers.tests.cpp:<line number>: passed: 0.f, !WithinAbs(1.f, 0.99f) for: 0.0f
|
||||
Matchers.tests.cpp:<line number>: passed: 0.f, !WithinAbs(1.f, 0.99f) for: 0.0f not is within 0.9900000095 of 1.0
|
||||
Matchers.tests.cpp:<line number>: passed: 0.f, WithinAbs(-0.f, 0) for: 0.0f is within 0.0 of -0.0
|
||||
Matchers.tests.cpp:<line number>: passed: NAN, !WithinAbs(NAN, 0) for: nanf not is within 0.0 of nan
|
||||
Matchers.tests.cpp:<line number>: passed: 11.f, !WithinAbs(10.f, 0.5f) for: 11.0f not is within 0.5 of 10.0
|
||||
Matchers.tests.cpp:<line number>: passed: 10.f, !WithinAbs(11.f, 0.5f) for: 10.0f not is within 0.5 of 11.0
|
||||
Matchers.tests.cpp:<line number>: passed: -10.f, WithinAbs(-10.f, 0.5f) for: -10.0f is within 0.5 of -10.0
|
||||
Matchers.tests.cpp:<line number>: passed: -10.f, WithinAbs(-9.6f, 0.5f) for: -10.0f is within 0.5 of -9.6000003815
|
||||
Matchers.tests.cpp:<line number>: passed: 1.f, WithinULP(1.f, 0) for: 1.0f is within 0 ULPs of 1.0f
|
||||
Matchers.tests.cpp:<line number>: passed: nextafter(1.f, 2.f), WithinULP(1.f, 1) for: 1.0f is within 1 ULPs of 1.0f
|
||||
Matchers.tests.cpp:<line number>: passed: nextafter(1.f, 0.f), WithinULP(1.f, 1) for: 1.0f is within 1 ULPs of 1.0f
|
||||
@@ -897,6 +911,48 @@ Xml.tests.cpp:<line number>: passed: encode( stringWithQuotes, Catch::XmlEncode:
|
||||
"don't "quote" me on that"
|
||||
Xml.tests.cpp:<line number>: passed: encode( "[/x01]" ) == "[//x01]" for: "[/x01]" == "[/x01]"
|
||||
Xml.tests.cpp:<line number>: passed: encode( "[/x7F]" ) == "[//x7F]" for: "[/x7F]" == "[/x7F]"
|
||||
Xml.tests.cpp:<line number>: passed: encode(u8"Here be 👾") == u8"Here be 👾" for: "Here be 👾" == "Here be 👾"
|
||||
Xml.tests.cpp:<line number>: passed: encode(u8"šš") == u8"šš" for: "šš" == "šš"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xDF/xBF") == "/xDF/xBF" for: "߿" == "߿"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE0/xA0/x80") == "/xE0/xA0/x80" for: "ࠀ" == "ࠀ"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xED/x9F/xBF") == "/xED/x9F/xBF" for: "" == ""
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xEE/x80/x80") == "/xEE/x80/x80" for: "" == ""
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xEF/xBF/xBF") == "/xEF/xBF/xBF" for: "" == ""
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0/x90/x80/x80") == "/xF0/x90/x80/x80" for: "𐀀" == "𐀀"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF4/x8F/xBF/xBF") == "/xF4/x8F/xBF/xBF" for: "" == ""
|
||||
Xml.tests.cpp:<line number>: passed: encode("Here /xFF be 👾") == u8"Here //xFF be 👾" for: "Here /xFF be 👾" == "Here /xFF be 👾"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xFF") == "//xFF" for: "/xFF" == "/xFF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xC5/xC5/xA0") == u8"//xC5Š" for: "/xC5Š" == "/xC5Š"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF4/x90/x80/x80") == u8"//xF4//x90//x80//x80" for: "/xF4/x90/x80/x80" == "/xF4/x90/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xC0/x80") == u8"//xC0//x80" for: "/xC0/x80" == "/xC0/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0/x80/x80/x80") == u8"//xF0//x80//x80//x80" for: "/xF0/x80/x80/x80" == "/xF0/x80/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xC1/xBF") == u8"//xC1//xBF" for: "/xC1/xBF" == "/xC1/xBF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE0/x9F/xBF") == u8"//xE0//x9F//xBF" for: "/xE0/x9F/xBF" == "/xE0/x9F/xBF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0/x8F/xBF/xBF") == u8"//xF0//x8F//xBF//xBF" for: "/xF0/x8F/xBF/xBF" == "/xF0/x8F/xBF/xBF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xED/xA0/x80") == "/xED/xA0/x80" for: "<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xED/xAF/xBF") == "/xED/xAF/xBF" for: "<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xED/xB0/x80") == "/xED/xB0/x80" for: "<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xED/xBF/xBF") == "/xED/xBF/xBF" for: "<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/x80") == u8"//x80" for: "/x80" == "/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/x81") == u8"//x81" for: "/x81" == "/x81"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xBC") == u8"//xBC" for: "/xBC" == "/xBC"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xBF") == u8"//xBF" for: "/xBF" == "/xBF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF5/x80/x80/x80") == u8"//xF5//x80//x80//x80" for: "/xF5/x80/x80/x80" == "/xF5/x80/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF6/x80/x80/x80") == u8"//xF6//x80//x80//x80" for: "/xF6/x80/x80/x80" == "/xF6/x80/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF7/x80/x80/x80") == u8"//xF7//x80//x80//x80" for: "/xF7/x80/x80/x80" == "/xF7/x80/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xDE") == u8"//xDE" for: "/xDE" == "/xDE"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xDF") == u8"//xDF" for: "/xDF" == "/xDF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE0") == u8"//xE0" for: "/xE0" == "/xE0"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xEF") == u8"//xEF" for: "/xEF" == "/xEF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0") == u8"//xF0" for: "/xF0" == "/xF0"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF4") == u8"//xF4" for: "/xF4" == "/xF4"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE0/x80") == u8"//xE0//x80" for: "/xE0/x80" == "/xE0/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE0/xBF") == u8"//xE0//xBF" for: "/xE0/xBF" == "/xE0/xBF"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xE1/x80") == u8"//xE1//x80" for: "/xE1/x80" == "/xE1/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0/x80") == u8"//xF0//x80" for: "/xF0/x80" == "/xF0/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF4/x80") == u8"//xF4//x80" for: "/xF4/x80" == "/xF4/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF0/x80/x80") == u8"//xF0//x80//x80" for: "/xF0/x80/x80" == "/xF0/x80/x80"
|
||||
Xml.tests.cpp:<line number>: passed: encode("/xF4/x80/x80") == u8"//xF4//x80//x80" for: "/xF4/x80/x80" == "/xF4/x80/x80"
|
||||
ToStringVector.tests.cpp:<line number>: passed: Catch::Detail::stringify( empty ) == "{ }" for: "{ }" == "{ }"
|
||||
ToStringVector.tests.cpp:<line number>: passed: Catch::Detail::stringify( oneValue ) == "{ 42 }" for: "{ 42 }" == "{ 42 }"
|
||||
ToStringVector.tests.cpp:<line number>: passed: Catch::Detail::stringify( twoValues ) == "{ 42, 250 }" for: "{ 42, 250 }" == "{ 42, 250 }"
|
||||
|
@@ -1084,6 +1084,6 @@ due to unexpected exception with message:
|
||||
Why would you throw a std::string?
|
||||
|
||||
===============================================================================
|
||||
test cases: 202 | 149 passed | 49 failed | 4 failed as expected
|
||||
assertions: 1007 | 879 passed | 107 failed | 21 failed as expected
|
||||
test cases: 205 | 152 passed | 49 failed | 4 failed as expected
|
||||
assertions: 1063 | 935 passed | 107 failed | 21 failed as expected
|
||||
|
||||
|
@@ -102,6 +102,30 @@ Misc.tests.cpp:<line number>
|
||||
Misc.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1238
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE( std::memcmp(uarr, "123", sizeof(uarr)) == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
with messages:
|
||||
uarr := "123"
|
||||
sarr := "456"
|
||||
|
||||
Compilation.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE( std::memcmp(sarr, "456", sizeof(sarr)) == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
with messages:
|
||||
uarr := "123"
|
||||
sarr := "456"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#748 - captures with unexpected exceptions
|
||||
outside assertions
|
||||
@@ -814,6 +838,44 @@ PASSED:
|
||||
with expansion:
|
||||
1.234 == Approx( 1.2339999676 )
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Arbitrary predicate matcher
|
||||
Function pointer
|
||||
-------------------------------------------------------------------------------
|
||||
Matchers.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 1, Predicate<int>(alwaysTrue, "always true") )
|
||||
with expansion:
|
||||
1 matches predicate: "always true"
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 1, !Predicate<int>(alwaysFalse, "always false") )
|
||||
with expansion:
|
||||
1 not matches predicate: "always false"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Arbitrary predicate matcher
|
||||
Lambdas + different type
|
||||
-------------------------------------------------------------------------------
|
||||
Matchers.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( "Hello olleH", Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); }, "First and last character should be equal") )
|
||||
with expansion:
|
||||
"Hello olleH" matches predicate: "First and last character should be equal"
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( "This wouldn't pass", !Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); } ) )
|
||||
with expansion:
|
||||
"This wouldn't pass" not matches undescribed predicate
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Assertions then sections
|
||||
-------------------------------------------------------------------------------
|
||||
@@ -1858,6 +1920,30 @@ PASSED:
|
||||
with expansion:
|
||||
nanf not is within 0.0 of nan
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 11., !WithinAbs(10., 0.5) )
|
||||
with expansion:
|
||||
11.0 not is within 0.5 of 10.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 10., !WithinAbs(11., 0.5) )
|
||||
with expansion:
|
||||
10.0 not is within 0.5 of 11.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( -10., WithinAbs(-10., 0.5) )
|
||||
with expansion:
|
||||
-10.0 is within 0.5 of -10.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( -10., WithinAbs(-9.6, 0.5) )
|
||||
with expansion:
|
||||
-10.0 is within 0.5 of -9.6
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Floating point matchers: double
|
||||
ULPs
|
||||
@@ -1998,6 +2084,30 @@ PASSED:
|
||||
with expansion:
|
||||
nanf not is within 0.0 of nan
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 11.f, !WithinAbs(10.f, 0.5f) )
|
||||
with expansion:
|
||||
11.0f not is within 0.5 of 10.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( 10.f, !WithinAbs(11.f, 0.5f) )
|
||||
with expansion:
|
||||
10.0f not is within 0.5 of 11.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( -10.f, WithinAbs(-10.f, 0.5f) )
|
||||
with expansion:
|
||||
-10.0f is within 0.5 of -10.0
|
||||
|
||||
Matchers.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE_THAT( -10.f, WithinAbs(-9.6f, 0.5f) )
|
||||
with expansion:
|
||||
-10.0f is within 0.5 of -9.6000003815
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Floating point matchers: float
|
||||
ULPs
|
||||
@@ -7064,6 +7174,305 @@ PASSED:
|
||||
with expansion:
|
||||
"[\x7F]" == "[\x7F]"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Valid utf-8 strings
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode(u8"Here be 👾") == u8"Here be 👾" )
|
||||
with expansion:
|
||||
"Here be 👾" == "Here be 👾"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode(u8"šš") == u8"šš" )
|
||||
with expansion:
|
||||
"šš" == "šš"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xDF\xBF") == "\xDF\xBF" )
|
||||
with expansion:
|
||||
"߿" == "߿"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE0\xA0\x80") == "\xE0\xA0\x80" )
|
||||
with expansion:
|
||||
"ࠀ" == "ࠀ"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xED\x9F\xBF") == "\xED\x9F\xBF" )
|
||||
with expansion:
|
||||
"" == ""
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xEE\x80\x80") == "\xEE\x80\x80" )
|
||||
with expansion:
|
||||
"" == ""
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xEF\xBF\xBF") == "\xEF\xBF\xBF" )
|
||||
with expansion:
|
||||
"" == ""
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0\x90\x80\x80") == "\xF0\x90\x80\x80" )
|
||||
with expansion:
|
||||
"𐀀" == "𐀀"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF4\x8F\xBF\xBF") == "\xF4\x8F\xBF\xBF" )
|
||||
with expansion:
|
||||
"" == ""
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Invalid utf-8 strings
|
||||
Various broken strings
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("Here \xFF be 👾") == u8"Here \\xFF be 👾" )
|
||||
with expansion:
|
||||
"Here \xFF be 👾" == "Here \xFF be 👾"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xFF") == "\\xFF" )
|
||||
with expansion:
|
||||
"\xFF" == "\xFF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xC5\xC5\xA0") == u8"\\xC5Š" )
|
||||
with expansion:
|
||||
"\xC5Š" == "\xC5Š"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF4\x90\x80\x80") == u8"\\xF4\\x90\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF4\x90\x80\x80" == "\xF4\x90\x80\x80"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Invalid utf-8 strings
|
||||
Overlong encodings
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xC0\x80") == u8"\\xC0\\x80" )
|
||||
with expansion:
|
||||
"\xC0\x80" == "\xC0\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0\x80\x80\x80") == u8"\\xF0\\x80\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF0\x80\x80\x80" == "\xF0\x80\x80\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xC1\xBF") == u8"\\xC1\\xBF" )
|
||||
with expansion:
|
||||
"\xC1\xBF" == "\xC1\xBF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE0\x9F\xBF") == u8"\\xE0\\x9F\\xBF" )
|
||||
with expansion:
|
||||
"\xE0\x9F\xBF" == "\xE0\x9F\xBF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0\x8F\xBF\xBF") == u8"\\xF0\\x8F\\xBF\\xBF" )
|
||||
with expansion:
|
||||
"\xF0\x8F\xBF\xBF" == "\xF0\x8F\xBF\xBF"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Invalid utf-8 strings
|
||||
Surrogate pairs
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xED\xA0\x80") == "\xED\xA0\x80" )
|
||||
with expansion:
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xED\xAF\xBF") == "\xED\xAF\xBF" )
|
||||
with expansion:
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xED\xB0\x80") == "\xED\xB0\x80" )
|
||||
with expansion:
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xED\xBF\xBF") == "\xED\xBF\xBF" )
|
||||
with expansion:
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Invalid utf-8 strings
|
||||
Invalid start byte
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\x80") == u8"\\x80" )
|
||||
with expansion:
|
||||
"\x80" == "\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\x81") == u8"\\x81" )
|
||||
with expansion:
|
||||
"\x81" == "\x81"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xBC") == u8"\\xBC" )
|
||||
with expansion:
|
||||
"\xBC" == "\xBC"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xBF") == u8"\\xBF" )
|
||||
with expansion:
|
||||
"\xBF" == "\xBF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF5\x80\x80\x80") == u8"\\xF5\\x80\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF5\x80\x80\x80" == "\xF5\x80\x80\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF6\x80\x80\x80") == u8"\\xF6\\x80\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF6\x80\x80\x80" == "\xF6\x80\x80\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF7\x80\x80\x80") == u8"\\xF7\\x80\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF7\x80\x80\x80" == "\xF7\x80\x80\x80"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
XmlEncode: UTF-8
|
||||
Invalid utf-8 strings
|
||||
Missing continuation byte(s)
|
||||
-------------------------------------------------------------------------------
|
||||
Xml.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xDE") == u8"\\xDE" )
|
||||
with expansion:
|
||||
"\xDE" == "\xDE"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xDF") == u8"\\xDF" )
|
||||
with expansion:
|
||||
"\xDF" == "\xDF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE0") == u8"\\xE0" )
|
||||
with expansion:
|
||||
"\xE0" == "\xE0"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xEF") == u8"\\xEF" )
|
||||
with expansion:
|
||||
"\xEF" == "\xEF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0") == u8"\\xF0" )
|
||||
with expansion:
|
||||
"\xF0" == "\xF0"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF4") == u8"\\xF4" )
|
||||
with expansion:
|
||||
"\xF4" == "\xF4"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE0\x80") == u8"\\xE0\\x80" )
|
||||
with expansion:
|
||||
"\xE0\x80" == "\xE0\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE0\xBF") == u8"\\xE0\\xBF" )
|
||||
with expansion:
|
||||
"\xE0\xBF" == "\xE0\xBF"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xE1\x80") == u8"\\xE1\\x80" )
|
||||
with expansion:
|
||||
"\xE1\x80" == "\xE1\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0\x80") == u8"\\xF0\\x80" )
|
||||
with expansion:
|
||||
"\xF0\x80" == "\xF0\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF4\x80") == u8"\\xF4\\x80" )
|
||||
with expansion:
|
||||
"\xF4\x80" == "\xF4\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF0\x80\x80") == u8"\\xF0\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF0\x80\x80" == "\xF0\x80\x80"
|
||||
|
||||
Xml.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
CHECK( encode("\xF4\x80\x80") == u8"\\xF4\\x80\\x80" )
|
||||
with expansion:
|
||||
"\xF4\x80\x80" == "\xF4\x80\x80"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
array<int, N> -> toString
|
||||
-------------------------------------------------------------------------------
|
||||
@@ -8550,6 +8959,6 @@ Misc.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
|
||||
===============================================================================
|
||||
test cases: 202 | 136 passed | 62 failed | 4 failed as expected
|
||||
assertions: 1021 | 879 passed | 121 failed | 21 failed as expected
|
||||
test cases: 205 | 139 passed | 62 failed | 4 failed as expected
|
||||
assertions: 1077 | 935 passed | 121 failed | 21 failed as expected
|
||||
|
||||
|
@@ -102,6 +102,30 @@ Misc.tests.cpp:<line number>
|
||||
Misc.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#1238
|
||||
-------------------------------------------------------------------------------
|
||||
Compilation.tests.cpp:<line number>
|
||||
...............................................................................
|
||||
|
||||
Compilation.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE( std::memcmp(uarr, "123", sizeof(uarr)) == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
with messages:
|
||||
uarr := "123"
|
||||
sarr := "456"
|
||||
|
||||
Compilation.tests.cpp:<line number>:
|
||||
PASSED:
|
||||
REQUIRE( std::memcmp(sarr, "456", sizeof(sarr)) == 0 )
|
||||
with expansion:
|
||||
0 == 0
|
||||
with messages:
|
||||
uarr := "123"
|
||||
sarr := "456"
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
#748 - captures with unexpected exceptions
|
||||
outside assertions
|
||||
@@ -308,6 +332,6 @@ with expansion:
|
||||
!true
|
||||
|
||||
===============================================================================
|
||||
test cases: 12 | 9 passed | 1 failed | 2 failed as expected
|
||||
assertions: 35 | 28 passed | 4 failed | 3 failed as expected
|
||||
test cases: 13 | 10 passed | 1 failed | 2 failed as expected
|
||||
assertions: 37 | 30 passed | 4 failed | 3 failed as expected
|
||||
|
||||
|
@@ -1,12 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<testsuitesloose text artifact
|
||||
>
|
||||
<testsuite name="<exe-name>" errors="17" failures="105" tests="1022" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
|
||||
<testsuite name="<exe-name>" errors="17" failures="105" tests="1078" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
|
||||
<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="#1147" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1175 - Hidden Test" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#1238" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="#748 - captures with unexpected exceptions/outside assertions" time="{duration}">
|
||||
<error type="TEST_CASE">
|
||||
expected exception
|
||||
@@ -110,6 +111,8 @@ Exception.tests.cpp:<line number>
|
||||
<testcase classname="<exe-name>.global" name="Approximate comparisons with floats" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="Approximate comparisons with ints" time="{duration}"/>
|
||||
<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="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}"/>
|
||||
@@ -706,6 +709,12 @@ Exception.tests.cpp:<line number>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode/string with quotes" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode/string with control char (1)" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode/string with control char (x7F)" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Valid utf-8 strings" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Invalid utf-8 strings/Various broken strings" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Invalid utf-8 strings/Overlong encodings" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Invalid utf-8 strings/Surrogate pairs" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Invalid utf-8 strings/Invalid start byte" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="XmlEncode: UTF-8/Invalid utf-8 strings/Missing continuation byte(s)" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="array<int, N> -> toString" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="atomic if" time="{duration}"/>
|
||||
<testcase classname="<exe-name>.global" name="boolean member" time="{duration}"/>
|
||||
|
@@ -96,6 +96,37 @@
|
||||
<TestCase name="#1175 - Hidden Test" tags="[.]" filename="projects/<exe-name>/UsageTests/Misc.tests.cpp" >
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#1238" filename="projects/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Info>
|
||||
uarr := "123"
|
||||
</Info>
|
||||
<Info>
|
||||
sarr := "456"
|
||||
</Info>
|
||||
<Expression success="true" type="REQUIRE" filename="projects/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
std::memcmp(uarr, "123", sizeof(uarr)) == 0
|
||||
</Original>
|
||||
<Expanded>
|
||||
0 == 0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Info>
|
||||
uarr := "123"
|
||||
</Info>
|
||||
<Info>
|
||||
sarr := "456"
|
||||
</Info>
|
||||
<Expression success="true" type="REQUIRE" filename="projects/<exe-name>/UsageTests/Compilation.tests.cpp" >
|
||||
<Original>
|
||||
std::memcmp(sarr, "456", sizeof(sarr)) == 0
|
||||
</Original>
|
||||
<Expanded>
|
||||
0 == 0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="#748 - captures with unexpected exceptions" tags="[!shouldfail][!throws][.][failing]" filename="projects/<exe-name>/UsageTests/Exception.tests.cpp" >
|
||||
<Section name="outside assertions" filename="projects/<exe-name>/UsageTests/Exception.tests.cpp" >
|
||||
<Info>
|
||||
@@ -870,6 +901,47 @@
|
||||
</Expression>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Arbitrary predicate matcher" tags="[generic][matchers]" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Section name="Function pointer" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
1, Predicate<int>(alwaysTrue, "always true")
|
||||
</Original>
|
||||
<Expanded>
|
||||
1 matches predicate: "always true"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
1, !Predicate<int>(alwaysFalse, "always false")
|
||||
</Original>
|
||||
<Expanded>
|
||||
1 not matches predicate: "always false"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="2" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Lambdas + different type" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
"Hello olleH", Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); }, "First and last character should be equal")
|
||||
</Original>
|
||||
<Expanded>
|
||||
"Hello olleH" matches predicate: "First and last character should be equal"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
"This wouldn't pass", !Predicate<std::string>( [] (std::string const& str) -> bool { return str.front() == str.back(); } )
|
||||
</Original>
|
||||
<Expanded>
|
||||
"This wouldn't pass" not matches undescribed predicate
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="2" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="Assertions then sections" tags="[Tricky]" filename="projects/<exe-name>/UsageTests/Tricky.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="projects/<exe-name>/UsageTests/Tricky.tests.cpp" >
|
||||
<Original>
|
||||
@@ -2108,7 +2180,39 @@
|
||||
nanf not is within 0.0 of nan
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="5" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
11., !WithinAbs(10., 0.5)
|
||||
</Original>
|
||||
<Expanded>
|
||||
11.0 not is within 0.5 of 10.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
10., !WithinAbs(11., 0.5)
|
||||
</Original>
|
||||
<Expanded>
|
||||
10.0 not is within 0.5 of 11.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
-10., WithinAbs(-10., 0.5)
|
||||
</Original>
|
||||
<Expanded>
|
||||
-10.0 is within 0.5 of -10.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
-10., WithinAbs(-9.6, 0.5)
|
||||
</Original>
|
||||
<Expanded>
|
||||
-10.0 is within 0.5 of -9.6
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="9" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="ULPs" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@@ -2283,7 +2387,39 @@
|
||||
nanf not is within 0.0 of nan
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="6" failures="0" expectedFailures="0"/>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
11.f, !WithinAbs(10.f, 0.5f)
|
||||
</Original>
|
||||
<Expanded>
|
||||
11.0f not is within 0.5 of 10.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
10.f, !WithinAbs(11.f, 0.5f)
|
||||
</Original>
|
||||
<Expanded>
|
||||
10.0f not is within 0.5 of 11.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
-10.f, WithinAbs(-10.f, 0.5f)
|
||||
</Original>
|
||||
<Expanded>
|
||||
-10.0f is within 0.5 of -10.0
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Original>
|
||||
-10.f, WithinAbs(-9.6f, 0.5f)
|
||||
</Original>
|
||||
<Expanded>
|
||||
-10.0f is within 0.5 of -9.6000003815
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="10" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="ULPs" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE_THAT" filename="projects/<exe-name>/UsageTests/Matchers.tests.cpp" >
|
||||
@@ -7817,7 +7953,7 @@ Message from section two
|
||||
<TestCase name="X/level/1/b" tags="[Tricky]" filename="projects/<exe-name>/UsageTests/Tricky.tests.cpp" >
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="XmlEncode" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<TestCase name="XmlEncode" tags="[XML]" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="normal string" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
@@ -7930,6 +8066,378 @@ Message from section two
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="XmlEncode: UTF-8" tags="[UTF-8][XML]" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Valid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode(u8"Here be 👾") == u8"Here be 👾"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"Here be 👾" == "Here be 👾"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode(u8"šš") == u8"šš"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"šš" == "šš"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xDF\xBF") == "\xDF\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"߿" == "߿"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE0\xA0\x80") == "\xE0\xA0\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"ࠀ" == "ࠀ"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xED\x9F\xBF") == "\xED\x9F\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"" == ""
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xEE\x80\x80") == "\xEE\x80\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"" == ""
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xEF\xBF\xBF") == "\xEF\xBF\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"" == ""
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0\x90\x80\x80") == "\xF0\x90\x80\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"𐀀" == "𐀀"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF4\x8F\xBF\xBF") == "\xF4\x8F\xBF\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"" == ""
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="9" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Invalid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Various broken strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("Here \xFF be 👾") == u8"Here \\xFF be 👾"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"Here \xFF be 👾" == "Here \xFF be 👾"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xFF") == "\\xFF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xFF" == "\xFF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xC5\xC5\xA0") == u8"\\xC5Š"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xC5Š" == "\xC5Š"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF4\x90\x80\x80") == u8"\\xF4\\x90\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF4\x90\x80\x80" == "\xF4\x90\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Invalid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Overlong encodings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xC0\x80") == u8"\\xC0\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xC0\x80" == "\xC0\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0\x80\x80\x80") == u8"\\xF0\\x80\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF0\x80\x80\x80" == "\xF0\x80\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xC1\xBF") == u8"\\xC1\\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xC1\xBF" == "\xC1\xBF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE0\x9F\xBF") == u8"\\xE0\\x9F\\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xE0\x9F\xBF" == "\xE0\x9F\xBF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0\x8F\xBF\xBF") == u8"\\xF0\\x8F\\xBF\\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF0\x8F\xBF\xBF" == "\xF0\x8F\xBF\xBF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="5" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="5" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Invalid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Surrogate pairs" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xED\xA0\x80") == "\xED\xA0\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xED\xAF\xBF") == "\xED\xAF\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xED\xB0\x80") == "\xED\xB0\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xED\xBF\xBF") == "\xED\xBF\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"<22><><EFBFBD>" == "<22><><EFBFBD>"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="4" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Invalid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Invalid start byte" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\x80") == u8"\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\x80" == "\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\x81") == u8"\\x81"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\x81" == "\x81"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xBC") == u8"\\xBC"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xBC" == "\xBC"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xBF") == u8"\\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xBF" == "\xBF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF5\x80\x80\x80") == u8"\\xF5\\x80\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF5\x80\x80\x80" == "\xF5\x80\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF6\x80\x80\x80") == u8"\\xF6\\x80\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF6\x80\x80\x80" == "\xF6\x80\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF7\x80\x80\x80") == u8"\\xF7\\x80\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF7\x80\x80\x80" == "\xF7\x80\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="7" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="7" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<Section name="Invalid utf-8 strings" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Section name="Missing continuation byte(s)" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xDE") == u8"\\xDE"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xDE" == "\xDE"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xDF") == u8"\\xDF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xDF" == "\xDF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE0") == u8"\\xE0"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xE0" == "\xE0"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xEF") == u8"\\xEF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xEF" == "\xEF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0") == u8"\\xF0"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF0" == "\xF0"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF4") == u8"\\xF4"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF4" == "\xF4"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE0\x80") == u8"\\xE0\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xE0\x80" == "\xE0\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE0\xBF") == u8"\\xE0\\xBF"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xE0\xBF" == "\xE0\xBF"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xE1\x80") == u8"\\xE1\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xE1\x80" == "\xE1\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0\x80") == u8"\\xF0\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF0\x80" == "\xF0\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF4\x80") == u8"\\xF4\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF4\x80" == "\xF4\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF0\x80\x80") == u8"\\xF0\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF0\x80\x80" == "\xF0\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<Expression success="true" type="CHECK" filename="projects/<exe-name>/IntrospectiveTests/Xml.tests.cpp" >
|
||||
<Original>
|
||||
encode("\xF4\x80\x80") == u8"\\xF4\\x80\\x80"
|
||||
</Original>
|
||||
<Expanded>
|
||||
"\xF4\x80\x80" == "\xF4\x80\x80"
|
||||
</Expanded>
|
||||
</Expression>
|
||||
<OverallResults successes="13" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResults successes="13" failures="0" expectedFailures="0"/>
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<TestCase name="array<int, N> -> toString" tags="[array][containers][toString]" filename="projects/<exe-name>/UsageTests/ToStringVector.tests.cpp" >
|
||||
<Expression success="true" type="REQUIRE" filename="projects/<exe-name>/UsageTests/ToStringVector.tests.cpp" >
|
||||
<Original>
|
||||
@@ -9405,7 +9913,7 @@ loose text artifact
|
||||
</Section>
|
||||
<OverallResult success="true"/>
|
||||
</TestCase>
|
||||
<OverallResults successes="879" failures="122" expectedFailures="21"/>
|
||||
<OverallResults successes="935" failures="122" expectedFailures="21"/>
|
||||
</Group>
|
||||
<OverallResults successes="879" failures="121" expectedFailures="21"/>
|
||||
<OverallResults successes="935" failures="121" expectedFailures="21"/>
|
||||
</Catch>
|
||||
|
@@ -1,5 +1,4 @@
|
||||
#include "catch.hpp"
|
||||
|
||||
#include "internal/catch_xmlwriter.h"
|
||||
|
||||
#include <sstream>
|
||||
@@ -10,7 +9,7 @@ inline std::string encode( std::string const& str, Catch::XmlEncode::ForWhat for
|
||||
return oss.str();
|
||||
}
|
||||
|
||||
TEST_CASE( "XmlEncode" ) {
|
||||
TEST_CASE( "XmlEncode", "[XML]" ) {
|
||||
SECTION( "normal string" ) {
|
||||
REQUIRE( encode( "normal string" ) == "normal string" );
|
||||
}
|
||||
@@ -38,4 +37,76 @@ TEST_CASE( "XmlEncode" ) {
|
||||
SECTION( "string with control char (x7F)" ) {
|
||||
REQUIRE( encode( "[\x7F]" ) == "[\\x7F]" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Thanks to Peter Bindels (dascandy) for some of the tests
|
||||
TEST_CASE("XmlEncode: UTF-8", "[XML][UTF-8]") {
|
||||
SECTION("Valid utf-8 strings") {
|
||||
CHECK(encode(u8"Here be 👾") == u8"Here be 👾");
|
||||
CHECK(encode(u8"šš") == u8"šš");
|
||||
|
||||
CHECK(encode("\xDF\xBF") == "\xDF\xBF"); // 0x7FF
|
||||
CHECK(encode("\xE0\xA0\x80") == "\xE0\xA0\x80"); // 0x800
|
||||
CHECK(encode("\xED\x9F\xBF") == "\xED\x9F\xBF"); // 0xD7FF
|
||||
CHECK(encode("\xEE\x80\x80") == "\xEE\x80\x80"); // 0xE000
|
||||
CHECK(encode("\xEF\xBF\xBF") == "\xEF\xBF\xBF"); // 0xFFFF
|
||||
CHECK(encode("\xF0\x90\x80\x80") == "\xF0\x90\x80\x80"); // 0x10000
|
||||
CHECK(encode("\xF4\x8F\xBF\xBF") == "\xF4\x8F\xBF\xBF"); // 0x10FFFF
|
||||
}
|
||||
SECTION("Invalid utf-8 strings") {
|
||||
SECTION("Various broken strings") {
|
||||
CHECK(encode("Here \xFF be 👾") == u8"Here \\xFF be 👾");
|
||||
CHECK(encode("\xFF") == "\\xFF");
|
||||
CHECK(encode("\xC5\xC5\xA0") == u8"\\xC5Š");
|
||||
CHECK(encode("\xF4\x90\x80\x80") == u8"\\xF4\\x90\\x80\\x80"); // 0x110000 -- out of unicode range
|
||||
}
|
||||
|
||||
SECTION("Overlong encodings") {
|
||||
CHECK(encode("\xC0\x80") == u8"\\xC0\\x80"); // \0
|
||||
CHECK(encode("\xF0\x80\x80\x80") == u8"\\xF0\\x80\\x80\\x80"); // Super-over-long \0
|
||||
CHECK(encode("\xC1\xBF") == u8"\\xC1\\xBF"); // ASCII char as UTF-8 (0x7F)
|
||||
CHECK(encode("\xE0\x9F\xBF") == u8"\\xE0\\x9F\\xBF"); // 0x7FF
|
||||
CHECK(encode("\xF0\x8F\xBF\xBF") == u8"\\xF0\\x8F\\xBF\\xBF"); // 0xFFFF
|
||||
}
|
||||
|
||||
// Note that we actually don't modify surrogate pairs, as we do not do strict checking
|
||||
SECTION("Surrogate pairs") {
|
||||
CHECK(encode("\xED\xA0\x80") == "\xED\xA0\x80"); // Invalid surrogate half 0xD800
|
||||
CHECK(encode("\xED\xAF\xBF") == "\xED\xAF\xBF"); // Invalid surrogate half 0xDBFF
|
||||
CHECK(encode("\xED\xB0\x80") == "\xED\xB0\x80"); // Invalid surrogate half 0xDC00
|
||||
CHECK(encode("\xED\xBF\xBF") == "\xED\xBF\xBF"); // Invalid surrogate half 0xDFFF
|
||||
}
|
||||
|
||||
SECTION("Invalid start byte") {
|
||||
CHECK(encode("\x80") == u8"\\x80");
|
||||
CHECK(encode("\x81") == u8"\\x81");
|
||||
CHECK(encode("\xBC") == u8"\\xBC");
|
||||
CHECK(encode("\xBF") == u8"\\xBF");
|
||||
// Out of range
|
||||
CHECK(encode("\xF5\x80\x80\x80") == u8"\\xF5\\x80\\x80\\x80");
|
||||
CHECK(encode("\xF6\x80\x80\x80") == u8"\\xF6\\x80\\x80\\x80");
|
||||
CHECK(encode("\xF7\x80\x80\x80") == u8"\\xF7\\x80\\x80\\x80");
|
||||
}
|
||||
|
||||
SECTION("Missing continuation byte(s)") {
|
||||
// Missing first continuation byte
|
||||
CHECK(encode("\xDE") == u8"\\xDE");
|
||||
CHECK(encode("\xDF") == u8"\\xDF");
|
||||
CHECK(encode("\xE0") == u8"\\xE0");
|
||||
CHECK(encode("\xEF") == u8"\\xEF");
|
||||
CHECK(encode("\xF0") == u8"\\xF0");
|
||||
CHECK(encode("\xF4") == u8"\\xF4");
|
||||
|
||||
// Missing second continuation byte
|
||||
CHECK(encode("\xE0\x80") == u8"\\xE0\\x80");
|
||||
CHECK(encode("\xE0\xBF") == u8"\\xE0\\xBF");
|
||||
CHECK(encode("\xE1\x80") == u8"\\xE1\\x80");
|
||||
CHECK(encode("\xF0\x80") == u8"\\xF0\\x80");
|
||||
CHECK(encode("\xF4\x80") == u8"\\xF4\\x80");
|
||||
|
||||
// Missing third continuation byte
|
||||
CHECK(encode("\xF0\x80\x80") == u8"\\xF0\\x80\\x80");
|
||||
CHECK(encode("\xF4\x80\x80") == u8"\\xF4\\x80\\x80");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -7,6 +7,8 @@
|
||||
|
||||
#include "catch.hpp"
|
||||
|
||||
#include <cstring>
|
||||
|
||||
namespace { namespace CompilationTests {
|
||||
|
||||
#ifndef COMPILATION_TEST_HELPERS_INCLUDED // Don't compile this more than once per TU
|
||||
@@ -134,4 +136,15 @@ namespace { namespace CompilationTests {
|
||||
REQUIRE(t1 >= t2);
|
||||
}
|
||||
|
||||
// unsigned array
|
||||
TEST_CASE("#1238") {
|
||||
unsigned char uarr[] = "123";
|
||||
CAPTURE(uarr);
|
||||
signed char sarr[] = "456";
|
||||
CAPTURE(sarr);
|
||||
|
||||
REQUIRE(std::memcmp(uarr, "123", sizeof(uarr)) == 0);
|
||||
REQUIRE(std::memcmp(sarr, "456", sizeof(sarr)) == 0);
|
||||
}
|
||||
|
||||
}} // namespace CompilationTests
|
||||
|
@@ -32,6 +32,9 @@ namespace { namespace MatchersTests {
|
||||
return "some completely different text that contains one common word";
|
||||
}
|
||||
|
||||
inline bool alwaysTrue(int) { return true; }
|
||||
inline bool alwaysFalse(int) { return false; }
|
||||
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(disable:4702) // Unreachable code -- MSVC 19 (VS 2015) sees right through the indirection
|
||||
@@ -321,6 +324,11 @@ namespace { namespace MatchersTests {
|
||||
|
||||
REQUIRE_THAT(0.f, WithinAbs(-0.f, 0));
|
||||
REQUIRE_THAT(NAN, !WithinAbs(NAN, 0));
|
||||
|
||||
REQUIRE_THAT(11.f, !WithinAbs(10.f, 0.5f));
|
||||
REQUIRE_THAT(10.f, !WithinAbs(11.f, 0.5f));
|
||||
REQUIRE_THAT(-10.f, WithinAbs(-10.f, 0.5f));
|
||||
REQUIRE_THAT(-10.f, WithinAbs(-9.6f, 0.5f));
|
||||
}
|
||||
SECTION("ULPs") {
|
||||
REQUIRE_THAT(1.f, WithinULP(1.f, 0));
|
||||
@@ -358,6 +366,11 @@ namespace { namespace MatchersTests {
|
||||
REQUIRE_THAT(0., !WithinAbs(1., 0.99));
|
||||
|
||||
REQUIRE_THAT(NAN, !WithinAbs(NAN, 0));
|
||||
|
||||
REQUIRE_THAT(11., !WithinAbs(10., 0.5));
|
||||
REQUIRE_THAT(10., !WithinAbs(11., 0.5));
|
||||
REQUIRE_THAT(-10., WithinAbs(-10., 0.5));
|
||||
REQUIRE_THAT(-10., WithinAbs(-9.6, 0.5));
|
||||
}
|
||||
SECTION("ULPs") {
|
||||
REQUIRE_THAT(1., WithinULP(1., 0));
|
||||
@@ -386,6 +399,26 @@ namespace { namespace MatchersTests {
|
||||
}
|
||||
}
|
||||
|
||||
TEST_CASE("Arbitrary predicate matcher", "[matchers][generic]") {
|
||||
SECTION("Function pointer") {
|
||||
REQUIRE_THAT(1, Predicate<int>(alwaysTrue, "always true"));
|
||||
REQUIRE_THAT(1, !Predicate<int>(alwaysFalse, "always false"));
|
||||
}
|
||||
SECTION("Lambdas + different type") {
|
||||
REQUIRE_THAT("Hello olleH",
|
||||
Predicate<std::string>(
|
||||
[] (std::string const& str) -> bool { return str.front() == str.back(); },
|
||||
"First and last character should be equal")
|
||||
);
|
||||
|
||||
REQUIRE_THAT("This wouldn't pass",
|
||||
!Predicate<std::string>(
|
||||
[] (std::string const& str) -> bool { return str.front() == str.back(); }
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
} } // namespace MatchersTests
|
||||
|
||||
#endif // CATCH_CONFIG_DISABLE_MATCHERS
|
||||
|
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Catch v2.2.0
|
||||
* Generated: 2018-03-07 10:56:32.217228
|
||||
* Catch v2.2.2
|
||||
* Generated: 2018-04-06 12:05:03.186665
|
||||
* ----------------------------------------------------------
|
||||
* This file has been merged from multiple headers. Please don't edit it directly
|
||||
* Copyright (c) 2018 Two Blue Cubes Ltd. All rights reserved.
|
||||
@@ -15,7 +15,7 @@
|
||||
|
||||
#define CATCH_VERSION_MAJOR 2
|
||||
#define CATCH_VERSION_MINOR 2
|
||||
#define CATCH_VERSION_PATCH 0
|
||||
#define CATCH_VERSION_PATCH 2
|
||||
|
||||
#ifdef __clang__
|
||||
# pragma clang system_header
|
||||
@@ -37,9 +37,9 @@
|
||||
# pragma clang diagnostic ignored "-Wcovered-switch-default"
|
||||
# endif
|
||||
#elif defined __GNUC__
|
||||
# pragma GCC diagnostic ignored "-Wunused-variable"
|
||||
# pragma GCC diagnostic ignored "-Wparentheses"
|
||||
# pragma GCC diagnostic push
|
||||
# pragma GCC diagnostic ignored "-Wunused-variable"
|
||||
# pragma GCC diagnostic ignored "-Wpadded"
|
||||
#endif
|
||||
// end catch_suppress_warnings.h
|
||||
@@ -783,6 +783,18 @@ namespace Catch {
|
||||
return convertUnknownEnumToString( value );
|
||||
}
|
||||
|
||||
#if defined(_MANAGED)
|
||||
//! Convert a CLR string to a utf8 std::string
|
||||
template<typename T>
|
||||
std::string clrReferenceToString( T^ ref ) {
|
||||
if (ref == nullptr)
|
||||
return std::string("null");
|
||||
auto bytes = System::Text::Encoding::UTF8->GetBytes(ref->ToString());
|
||||
cli::pin_ptr<System::Byte> p = &bytes[0];
|
||||
return std::string(reinterpret_cast<char const *>(p), bytes->Length);
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace Detail
|
||||
|
||||
// If we decide for C++14, change these to enable_if_ts
|
||||
@@ -819,6 +831,13 @@ namespace Catch {
|
||||
return ::Catch::Detail::stringify(static_cast<typename std::underlying_type<E>::type>(e));
|
||||
}
|
||||
|
||||
#if defined(_MANAGED)
|
||||
template <typename T>
|
||||
std::string stringify( T^ e ) {
|
||||
return ::Catch::StringMaker<T^>::convert(e);
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace Detail
|
||||
|
||||
// Some predefined specializations
|
||||
@@ -842,6 +861,7 @@ namespace Catch {
|
||||
struct StringMaker<char *> {
|
||||
static std::string convert(char * str);
|
||||
};
|
||||
|
||||
#ifdef CATCH_CONFIG_WCHAR
|
||||
template<>
|
||||
struct StringMaker<wchar_t const *> {
|
||||
@@ -853,22 +873,24 @@ namespace Catch {
|
||||
};
|
||||
#endif
|
||||
|
||||
// TBD: Should we use `strnlen` to ensure that we don't go out of the buffer,
|
||||
// while keeping string semantics?
|
||||
template<int SZ>
|
||||
struct StringMaker<char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
static std::string convert(char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
}
|
||||
};
|
||||
template<int SZ>
|
||||
struct StringMaker<signed char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
static std::string convert(signed char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ reinterpret_cast<char const *>(str) });
|
||||
}
|
||||
};
|
||||
template<int SZ>
|
||||
struct StringMaker<unsigned char[SZ]> {
|
||||
static std::string convert(const char* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ str });
|
||||
static std::string convert(unsigned char const* str) {
|
||||
return ::Catch::Detail::stringify(std::string{ reinterpret_cast<char const *>(str) });
|
||||
}
|
||||
};
|
||||
|
||||
@@ -952,6 +974,15 @@ namespace Catch {
|
||||
}
|
||||
};
|
||||
|
||||
#if defined(_MANAGED)
|
||||
template <typename T>
|
||||
struct StringMaker<T^> {
|
||||
static std::string convert( T^ ref ) {
|
||||
return ::Catch::Detail::clrReferenceToString(ref);
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
namespace Detail {
|
||||
template<typename InputIterator>
|
||||
std::string rangeToString(InputIterator first, InputIterator last) {
|
||||
@@ -1080,6 +1111,13 @@ namespace Catch {
|
||||
!std::is_same<decltype(end(std::declval<T>())), not_this_one>::value;
|
||||
};
|
||||
|
||||
#if defined(_MANAGED) // Managed types are never ranges
|
||||
template <typename T>
|
||||
struct is_range<T^> {
|
||||
static const bool value = false;
|
||||
};
|
||||
#endif
|
||||
|
||||
template<typename Range>
|
||||
std::string rangeToString( Range const& range ) {
|
||||
return ::Catch::Detail::rangeToString( begin( range ), end( range ) );
|
||||
@@ -2357,6 +2395,54 @@ namespace Matchers {
|
||||
} // namespace Catch
|
||||
|
||||
// end catch_matchers_floating.h
|
||||
// start catch_matchers_generic.hpp
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
|
||||
namespace Catch {
|
||||
namespace Matchers {
|
||||
namespace Generic {
|
||||
|
||||
namespace Detail {
|
||||
std::string finalizeDescription(const std::string& desc);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
class PredicateMatcher : public MatcherBase<T> {
|
||||
std::function<bool(T const&)> m_predicate;
|
||||
std::string m_description;
|
||||
public:
|
||||
|
||||
PredicateMatcher(std::function<bool(T const&)> const& elem, std::string const& descr)
|
||||
:m_predicate(std::move(elem)),
|
||||
m_description(Detail::finalizeDescription(descr))
|
||||
{}
|
||||
|
||||
bool match( T const& item ) const override {
|
||||
return m_predicate(item);
|
||||
}
|
||||
|
||||
std::string describe() const override {
|
||||
return m_description;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace Generic
|
||||
|
||||
// The following functions create the actual matcher objects.
|
||||
// The user has to explicitly specify type to the function, because
|
||||
// infering std::function<bool(T const&)> is hard (but possible) and
|
||||
// requires a lot of TMP.
|
||||
template<typename T>
|
||||
Generic::PredicateMatcher<T> Predicate(std::function<bool(T const&)> const& predicate, std::string const& description = "") {
|
||||
return Generic::PredicateMatcher<T>(predicate, description);
|
||||
}
|
||||
|
||||
} // namespace Matchers
|
||||
} // namespace Catch
|
||||
|
||||
// end catch_matchers_generic.hpp
|
||||
// start catch_matchers_string.h
|
||||
|
||||
#include <string>
|
||||
@@ -4830,7 +4916,7 @@ namespace Catch {
|
||||
|
||||
public:
|
||||
// !TBD We need to do this another way!
|
||||
bool aborting() const override;
|
||||
bool aborting() const final;
|
||||
|
||||
private:
|
||||
|
||||
@@ -5134,7 +5220,7 @@ namespace Catch {
|
||||
//
|
||||
// See https://github.com/philsquared/Clara for more details
|
||||
|
||||
// Clara v1.1.3
|
||||
// Clara v1.1.4
|
||||
|
||||
|
||||
#ifndef CATCH_CLARA_CONFIG_CONSOLE_WIDTH
|
||||
@@ -5148,6 +5234,7 @@ namespace Catch {
|
||||
#ifndef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
#ifdef __has_include
|
||||
#if __has_include(<optional>) && __cplusplus >= 201703L
|
||||
#include <optional>
|
||||
#define CLARA_CONFIG_OPTIONAL_TYPE std::optional
|
||||
#endif
|
||||
#endif
|
||||
@@ -5784,11 +5871,11 @@ namespace detail {
|
||||
}
|
||||
#ifdef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
template<typename T>
|
||||
inline auto convertInto( std::string const &source, std::optional<T>& target ) -> ParserResult {
|
||||
inline auto convertInto( std::string const &source, CLARA_CONFIG_OPTIONAL_TYPE<T>& target ) -> ParserResult {
|
||||
T temp;
|
||||
auto result = convertInto( source, temp );
|
||||
if( result )
|
||||
target = temp;
|
||||
target = std::move(temp);
|
||||
return result;
|
||||
}
|
||||
#endif // CLARA_CONFIG_OPTIONAL_TYPE
|
||||
@@ -7879,7 +7966,7 @@ namespace Floating {
|
||||
// Performs equivalent check of std::fabs(lhs - rhs) <= margin
|
||||
// But without the subtraction to allow for INFINITY in comparison
|
||||
bool WithinAbsMatcher::match(double const& matchee) const {
|
||||
return (matchee + m_margin >= m_target) && (m_target + m_margin >= m_margin);
|
||||
return (matchee + m_margin >= m_target) && (m_target + m_margin >= matchee);
|
||||
}
|
||||
|
||||
std::string WithinAbsMatcher::describe() const {
|
||||
@@ -7926,6 +8013,16 @@ Floating::WithinAbsMatcher WithinAbs(double target, double margin) {
|
||||
} // namespace Catch
|
||||
|
||||
// end catch_matchers_floating.cpp
|
||||
// start catch_matchers_generic.cpp
|
||||
|
||||
std::string Catch::Matchers::Generic::Detail::finalizeDescription(const std::string& desc) {
|
||||
if (desc.empty()) {
|
||||
return "matches undescribed predicate";
|
||||
} else {
|
||||
return "matches predicate: \"" + desc + '"';
|
||||
}
|
||||
}
|
||||
// end catch_matchers_generic.cpp
|
||||
// start catch_matchers_string.cpp
|
||||
|
||||
#include <regex>
|
||||
@@ -9237,7 +9334,7 @@ namespace Catch {
|
||||
// Note that on unices only the lower 8 bits are usually used, clamping
|
||||
// the return value to 255 prevents false negative when some multiple
|
||||
// of 256 tests has failed
|
||||
return (std::min)( { MaxExitCode, totals.error, static_cast<int>( totals.assertions.failed ) } );
|
||||
return (std::min) (MaxExitCode, (std::max) (totals.error, static_cast<int>(totals.assertions.failed)));
|
||||
}
|
||||
catch( std::exception& ex ) {
|
||||
Catch::cerr() << ex.what() << std::endl;
|
||||
@@ -10424,6 +10521,8 @@ namespace Catch {
|
||||
|
||||
#include <chrono>
|
||||
|
||||
static const uint64_t nanosecondsInSecond = 1000000000;
|
||||
|
||||
namespace Catch {
|
||||
|
||||
auto getCurrentNanosecondsSinceEpoch() -> uint64_t {
|
||||
@@ -10434,17 +10533,25 @@ namespace Catch {
|
||||
uint64_t sum = 0;
|
||||
static const uint64_t iterations = 1000000;
|
||||
|
||||
auto startTime = getCurrentNanosecondsSinceEpoch();
|
||||
|
||||
for( std::size_t i = 0; i < iterations; ++i ) {
|
||||
|
||||
uint64_t ticks;
|
||||
uint64_t baseTicks = getCurrentNanosecondsSinceEpoch();
|
||||
do {
|
||||
ticks = getCurrentNanosecondsSinceEpoch();
|
||||
}
|
||||
while( ticks == baseTicks );
|
||||
} while( ticks == baseTicks );
|
||||
|
||||
auto delta = ticks - baseTicks;
|
||||
sum += delta;
|
||||
|
||||
// If we have been calibrating for over 3 seconds -- the clock
|
||||
// is terrible and we should move on.
|
||||
// TBD: How to signal that the measured resolution is probably wrong?
|
||||
if (ticks > startTime + 3 * nanosecondsInSecond) {
|
||||
return sum / i;
|
||||
}
|
||||
}
|
||||
|
||||
// We're just taking the mean, here. To do better we could take the std. dev and exclude outliers
|
||||
@@ -10806,7 +10913,7 @@ namespace Catch {
|
||||
}
|
||||
|
||||
Version const& libraryVersion() {
|
||||
static Version version( 2, 2, 0, "", 0 );
|
||||
static Version version( 2, 2, 2, "", 0 );
|
||||
return version;
|
||||
}
|
||||
|
||||
@@ -10857,49 +10964,141 @@ namespace Catch {
|
||||
|
||||
#include <iomanip>
|
||||
|
||||
using uchar = unsigned char;
|
||||
|
||||
namespace Catch {
|
||||
|
||||
namespace {
|
||||
|
||||
size_t trailingBytes(unsigned char c) {
|
||||
if ((c & 0xE0) == 0xC0) {
|
||||
return 2;
|
||||
}
|
||||
if ((c & 0xF0) == 0xE0) {
|
||||
return 3;
|
||||
}
|
||||
if ((c & 0xF8) == 0xF0) {
|
||||
return 4;
|
||||
}
|
||||
CATCH_INTERNAL_ERROR("Invalid multibyte utf-8 start byte encountered");
|
||||
}
|
||||
|
||||
uint32_t headerValue(unsigned char c) {
|
||||
if ((c & 0xE0) == 0xC0) {
|
||||
return c & 0x1F;
|
||||
}
|
||||
if ((c & 0xF0) == 0xE0) {
|
||||
return c & 0x0F;
|
||||
}
|
||||
if ((c & 0xF8) == 0xF0) {
|
||||
return c & 0x07;
|
||||
}
|
||||
CATCH_INTERNAL_ERROR("Invalid multibyte utf-8 start byte encountered");
|
||||
}
|
||||
|
||||
void hexEscapeChar(std::ostream& os, unsigned char c) {
|
||||
os << "\\x"
|
||||
<< std::uppercase << std::hex << std::setfill('0') << std::setw(2)
|
||||
<< static_cast<int>(c);
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
XmlEncode::XmlEncode( std::string const& str, ForWhat forWhat )
|
||||
: m_str( str ),
|
||||
m_forWhat( forWhat )
|
||||
{}
|
||||
|
||||
void XmlEncode::encodeTo( std::ostream& os ) const {
|
||||
|
||||
// Apostrophe escaping not necessary if we always use " to write attributes
|
||||
// (see: http://www.w3.org/TR/xml/#syntax)
|
||||
|
||||
for( std::size_t i = 0; i < m_str.size(); ++ i ) {
|
||||
char c = m_str[i];
|
||||
switch( c ) {
|
||||
case '<': os << "<"; break;
|
||||
case '&': os << "&"; break;
|
||||
for( std::size_t idx = 0; idx < m_str.size(); ++ idx ) {
|
||||
uchar c = m_str[idx];
|
||||
switch (c) {
|
||||
case '<': os << "<"; break;
|
||||
case '&': os << "&"; break;
|
||||
|
||||
case '>':
|
||||
// See: http://www.w3.org/TR/xml/#syntax
|
||||
if( i > 2 && m_str[i-1] == ']' && m_str[i-2] == ']' )
|
||||
os << ">";
|
||||
else
|
||||
os << c;
|
||||
case '>':
|
||||
// See: http://www.w3.org/TR/xml/#syntax
|
||||
if (idx > 2 && m_str[idx - 1] == ']' && m_str[idx - 2] == ']')
|
||||
os << ">";
|
||||
else
|
||||
os << c;
|
||||
break;
|
||||
|
||||
case '\"':
|
||||
if (m_forWhat == ForAttributes)
|
||||
os << """;
|
||||
else
|
||||
os << c;
|
||||
break;
|
||||
|
||||
default:
|
||||
// Check for control characters and invalid utf-8
|
||||
|
||||
// Escape control characters in standard ascii
|
||||
// see http://stackoverflow.com/questions/404107/why-are-control-characters-illegal-in-xml-1-0
|
||||
if (c < 0x09 || (c > 0x0D && c < 0x20) || c == 0x7F) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
case '\"':
|
||||
if( m_forWhat == ForAttributes )
|
||||
os << """;
|
||||
else
|
||||
os << c;
|
||||
// Plain ASCII: Write it to stream
|
||||
if (c < 0x7F) {
|
||||
os << c;
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
// Escape control chars - based on contribution by @espenalb in PR #465 and
|
||||
// by @mrpi PR #588
|
||||
if ( ( c >= 0 && c < '\x09' ) || ( c > '\x0D' && c < '\x20') || c=='\x7F' ) {
|
||||
// see http://stackoverflow.com/questions/404107/why-are-control-characters-illegal-in-xml-1-0
|
||||
os << "\\x" << std::uppercase << std::hex << std::setfill('0') << std::setw(2)
|
||||
<< static_cast<int>( c );
|
||||
}
|
||||
else
|
||||
os << c;
|
||||
// UTF-8 territory
|
||||
// Check if the encoding is valid and if it is not, hex escape bytes.
|
||||
// Important: We do not check the exact decoded values for validity, only the encoding format
|
||||
// First check that this bytes is a valid lead byte:
|
||||
// This means that it is not encoded as 1111 1XXX
|
||||
// Or as 10XX XXXX
|
||||
if (c < 0xC0 ||
|
||||
c >= 0xF8) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
auto encBytes = trailingBytes(c);
|
||||
// Are there enough bytes left to avoid accessing out-of-bounds memory?
|
||||
if (idx + encBytes - 1 >= m_str.size()) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
// The header is valid, check data
|
||||
// The next encBytes bytes must together be a valid utf-8
|
||||
// This means: bitpattern 10XX XXXX and the extracted value is sane (ish)
|
||||
bool valid = true;
|
||||
uint32_t value = headerValue(c);
|
||||
for (std::size_t n = 1; n < encBytes; ++n) {
|
||||
uchar nc = m_str[idx + n];
|
||||
valid &= ((nc & 0xC0) == 0x80);
|
||||
value = (value << 6) | (nc & 0x3F);
|
||||
}
|
||||
|
||||
if (
|
||||
// Wrong bit pattern of following bytes
|
||||
(!valid) ||
|
||||
// Overlong encodings
|
||||
(value < 0x80) ||
|
||||
(0x80 <= value && value < 0x800 && encBytes > 2) ||
|
||||
(0x800 < value && value < 0x10000 && encBytes > 3) ||
|
||||
// Encoded value out of range
|
||||
(value >= 0x110000)
|
||||
) {
|
||||
hexEscapeChar(os, c);
|
||||
break;
|
||||
}
|
||||
|
||||
// If we got here, this is in fact a valid(ish) utf-8 sequence
|
||||
for (std::size_t n = 0; n < encBytes; ++n) {
|
||||
os << m_str[idx + n];
|
||||
}
|
||||
idx += encBytes - 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -10,7 +10,7 @@ class CatchConanTest(ConanFile):
|
||||
settings = "os", "compiler", "arch", "build_type"
|
||||
username = getenv("CONAN_USERNAME", "philsquared")
|
||||
channel = getenv("CONAN_CHANNEL", "testing")
|
||||
requires = "Catch/2.2.0@%s/%s" % (username, channel)
|
||||
requires = "Catch/2.2.2@%s/%s" % (username, channel)
|
||||
|
||||
def build(self):
|
||||
cmake = CMake(self)
|
||||
|
7
third_party/clara.hpp
vendored
7
third_party/clara.hpp
vendored
@@ -5,7 +5,7 @@
|
||||
//
|
||||
// See https://github.com/philsquared/Clara for more details
|
||||
|
||||
// Clara v1.1.3
|
||||
// Clara v1.1.4
|
||||
|
||||
#ifndef CLARA_HPP_INCLUDED
|
||||
#define CLARA_HPP_INCLUDED
|
||||
@@ -21,6 +21,7 @@
|
||||
#ifndef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
#ifdef __has_include
|
||||
#if __has_include(<optional>) && __cplusplus >= 201703L
|
||||
#include <optional>
|
||||
#define CLARA_CONFIG_OPTIONAL_TYPE std::optional
|
||||
#endif
|
||||
#endif
|
||||
@@ -665,11 +666,11 @@ namespace detail {
|
||||
}
|
||||
#ifdef CLARA_CONFIG_OPTIONAL_TYPE
|
||||
template<typename T>
|
||||
inline auto convertInto( std::string const &source, std::optional<T>& target ) -> ParserResult {
|
||||
inline auto convertInto( std::string const &source, CLARA_CONFIG_OPTIONAL_TYPE<T>& target ) -> ParserResult {
|
||||
T temp;
|
||||
auto result = convertInto( source, temp );
|
||||
if( result )
|
||||
target = temp;
|
||||
target = std::move(temp);
|
||||
return result;
|
||||
}
|
||||
#endif // CLARA_CONFIG_OPTIONAL_TYPE
|
||||
|
Reference in New Issue
Block a user