Created
October 23, 2018 00:53
-
-
Save srz-zumix/d81f09474173461bc337ce97cd17ccf4 to your computer and use it in GitHub Desktop.
iutest v1.16.7 iutest.wandbox.min.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#ifndef INCG_IRIS_IUTEST_HPP_ | |
#define INCG_IRIS_IUTEST_HPP_ | |
#define IUTEST_VER 0x1160700u | |
#define IUTEST_MAJORVER 1u | |
#define IUTEST_MINORVER 0x16u | |
#define IUTEST_MICROVER 7u | |
#define IUTEST_REVISION 0u | |
#define IUTEST_BUILD IUTEST_MICROVER | |
#if defined(__FreeBSD__) | |
#define IUTEST_OS_FREEBSD 1 | |
#define IUTEST_PLATFORM "FreeBSD" | |
#elif defined(sun)||defined(__sun) | |
#define IUTEST_OS_SOLARIS 1 | |
#define IUTEST_PLATFORM "Solaris" | |
#elif defined(__linux__) | |
#define IUTEST_OS_LINUX 1 | |
#define IUTEST_PLATFORM "LINUX" | |
#endif | |
#ifndef IUTEST_HAS_CXX2A | |
#if(defined(__cplusplus)&&__cplusplus>201703L) | |
#define IUTEST_HAS_CXX2A 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CXX2A | |
#define IUTEST_HAS_CXX2A 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX17 | |
#if(defined(__cplusplus)&&__cplusplus>=201406L) | |
#define IUTEST_HAS_CXX17 1 | |
#elif defined(_MSVC_LANG)&&_MSVC_LANG>201402 | |
#define IUTEST_HAS_CXX17 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CXX17 | |
#define IUTEST_HAS_CXX17 0 | |
#endif | |
#ifndef IUTEST_HAS_INLINE_VARIABLE | |
#ifdef __clang__ | |
#if(__clang_major__>3 ||(__clang_major__==3 && __clang_minor__>=9))&&IUTEST_HAS_CXX17 | |
#define IUTEST_HAS_INLINE_VARIABLE 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_INLINE_VARIABLE | |
#define IUTEST_HAS_INLINE_VARIABLE 0 | |
#endif | |
#ifndef IUTEST_HAS_CONSTEXPR_IF | |
#if defined(__cpp_if_constexpr)&&__cpp_if_constexpr>=201606 | |
#define IUTEST_HAS_CONSTEXPR_IF 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CONSTEXPR_IF | |
#define IUTEST_HAS_CONSTEXPR_IF 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX11 | |
#if(defined(__cplusplus)&&__cplusplus>=201103L)||defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_CXX11 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CXX11 | |
#define IUTEST_HAS_CXX11 0 | |
#endif | |
#ifndef IUTEST_HAS_NULLPTR | |
#ifdef _NATIVE_NULLPTR_SUPPORTED | |
#define IUTEST_HAS_NULLPTR 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_nullptr) | |
#define IUTEST_HAS_NULLPTR 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=6))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_NULLPTR 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_NULLPTR | |
#define IUTEST_HAS_NULLPTR 0 | |
#endif | |
#ifndef IUTEST_NULLPTR | |
#if IUTEST_HAS_NULLPTR | |
#define IUTEST_NULLPTR nullptr | |
#else | |
#define IUTEST_NULLPTR 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_AUTO | |
#ifdef __clang__ | |
#if __has_feature(cxx_auto_type) | |
#define IUTEST_HAS_AUTO 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_AUTO 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_AUTO | |
#define IUTEST_HAS_AUTO 0 | |
#endif | |
#ifndef IUTEST_HAS_DECLTYPE | |
#if defined(__cpp_decltype)&&__cpp_decltype>=200707 | |
#define IUTEST_HAS_DECLTYPE 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_decltype) | |
#define IUTEST_HAS_DECLTYPE 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=3))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_DECLTYPE 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_DECLTYPE | |
#define IUTEST_HAS_DECLTYPE 0 | |
#endif | |
#ifndef IUTEST_HAS_STATIC_ASSERT | |
#if defined(__cpp_static_assert)&&__cpp_static_assert>=200410 | |
#define IUTEST_HAS_STATIC_ASSERT 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_static_assert) | |
#define IUTEST_HAS_STATIC_ASSERT 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=3))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_STATIC_ASSERT 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_STATIC_ASSERT | |
#define IUTEST_HAS_STATIC_ASSERT 0 | |
#endif | |
#ifndef IUTEST_HAS_CONSTEXPR | |
#if defined(__cpp_constexpr)&&__cpp_constexpr>=200704 | |
#define IUTEST_HAS_CONSTEXPR 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_constexpr) | |
#define IUTEST_HAS_CONSTEXPR 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=6))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_CONSTEXPR 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CONSTEXPR | |
#define IUTEST_HAS_CONSTEXPR 0 | |
#endif | |
#if IUTEST_HAS_CONSTEXPR | |
#define IUTEST_CXX_CONSTEXPR constexpr | |
#else | |
#define IUTEST_CXX_CONSTEXPR | |
#endif | |
#if IUTEST_HAS_CONSTEXPR | |
#define IUTEST_CXX_CONSTEXPR_OR_CONST constexpr | |
#else | |
#define IUTEST_CXX_CONSTEXPR_OR_CONST const | |
#endif | |
#ifndef IUTEST_HAS_RVALUE_REFS | |
#if defined(__cpp_rvalue_references)&&__cpp_rvalue_references>=200610 | |
#define IUTEST_HAS_RVALUE_REFS 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_rvalue_references) | |
#define IUTEST_HAS_RVALUE_REFS 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=3))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_RVALUE_REFS 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_RVALUE_REFS | |
#define IUTEST_HAS_RVALUE_REFS 0 | |
#endif | |
#ifndef IUTEST_HAS_DELETED_FUNCTIONS | |
#ifdef __clang__ | |
#if __has_feature(cxx_deleted_functions) | |
#define IUTEST_HAS_DELETED_FUNCTIONS 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_DELETED_FUNCTIONS 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_DELETED_FUNCTIONS | |
#define IUTEST_HAS_DELETED_FUNCTIONS 0 | |
#endif | |
#if IUTEST_HAS_DELETED_FUNCTIONS | |
#define IUTEST_CXX_DELETED_FUNCTION =delete | |
#else | |
#define IUTEST_CXX_DELETED_FUNCTION | |
#endif | |
#ifndef IUTEST_HAS_DEFAULT_FUNCTIONS | |
#ifdef __clang__ | |
#if __has_feature(cxx_defaulted_functions) | |
#define IUTEST_HAS_DEFAULT_FUNCTIONS 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__==4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_DEFAULT_FUNCTIONS 1 | |
#elif(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=7))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_DEFAULT_FUNCTIONS 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_DEFAULT_FUNCTIONS | |
#define IUTEST_HAS_DEFAULT_FUNCTIONS 0 | |
#endif | |
#if IUTEST_HAS_DEFAULT_FUNCTIONS | |
#define IUTEST_CXX_DEFAULT_FUNCTION =default; | |
#else | |
#define IUTEST_CXX_DEFAULT_FUNCTION {} | |
#endif | |
#ifndef IUTEST_HAS_INITIALIZER_LIST | |
#if defined(__cpp_initializer_lists)&&__cpp_initializer_lists>=200806 | |
#define IUTEST_HAS_INITIALIZER_LIST 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_generalized_initializers) | |
#define IUTEST_HAS_INITIALIZER_LIST 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_INITIALIZER_LIST 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_INITIALIZER_LIST | |
#define IUTEST_HAS_INITIALIZER_LIST 0 | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_TEMPLATES | |
#if defined(__cpp_variadic_templates)&&__cpp_variadic_templates>=200704 | |
#define IUTEST_HAS_VARIADIC_TEMPLATES 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_variadic_templates) | |
#define IUTEST_HAS_VARIADIC_TEMPLATES 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if defined(__VARIADIC_TEMPLATES) ||(((__GNUC__>4)||((__GNUC__==4)&&(__GNUC_MINOR__>=7)))&&defined(__GXX_EXPERIMENTAL_CXX0X__)) | |
#define IUTEST_HAS_VARIADIC_TEMPLATES 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_TEMPLATES | |
#define IUTEST_HAS_VARIADIC_TEMPLATES 0 | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES | |
#ifdef __clang__ | |
#if __has_feature(cxx_variadic_templates) | |
#define IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if defined(__VARIADIC_TEMPLATES)||(((__GNUC__>4) ||((__GNUC__==4)&&(__GNUC_MINOR__>=8)) ||((__GNUC__==4)&&(__GNUC_MINOR__>=7)&&(__GNUC_PATCHLEVEL__>=1))) && defined(__GXX_EXPERIMENTAL_CXX0X__)) | |
#define IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES | |
#define IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES 0 | |
#endif | |
#ifndef IUTEST_HAS_CHAR16_T | |
#if defined(__cpp_unicode_characters)&&__cpp_unicode_characters>=200704&&defined(__cpp_unicode_literals)&&__cpp_unicode_literals>=200710 | |
#define IUTEST_HAS_CHAR16_T 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_unicode_literals) | |
#define IUTEST_HAS_CHAR16_T 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_CHAR16_T 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CHAR16_T | |
#define IUTEST_HAS_CHAR16_T 0 | |
#endif | |
#ifndef IUTEST_HAS_CHAR32_T | |
#if defined(__cpp_unicode_characters)&&__cpp_unicode_characters>=200704&&defined(__cpp_unicode_literals)&&__cpp_unicode_literals>=200710 | |
#define IUTEST_HAS_CHAR32_T 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_unicode_literals) | |
#define IUTEST_HAS_CHAR32_T 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=4))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_CHAR32_T 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CHAR32_T | |
#define IUTEST_HAS_CHAR32_T 0 | |
#endif | |
#ifndef IUTEST_HAS_LAMBDA | |
#if defined(__cpp_lambdas)&&__cpp_lambdas>=200907 | |
#define IUTEST_HAS_LAMBDA 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_lambdas) | |
#define IUTEST_HAS_LAMBDA 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=5))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_LAMBDA 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_LAMBDA | |
#define IUTEST_HAS_LAMBDA 0 | |
#endif | |
#if IUTEST_HAS_LAMBDA | |
#ifdef __GNUC__ | |
#if(__GNUC__<4 ||(__GNUC__==4 && __GNUC_MINOR__<7)) | |
#define IUTEST_NO_LAMBDA_LOCAL_OBJECT_TEMPLATE_PARAMETERS | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_EXPLICIT_CONVERSION | |
#ifdef __clang__ | |
#if __has_feature(cxx_explicit_conversions) | |
#define IUTEST_HAS_EXPLICIT_CONVERSION 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=5))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_EXPLICIT_CONVERSION 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_EXPLICIT_CONVERSION | |
#define IUTEST_HAS_EXPLICIT_CONVERSION 0 | |
#endif | |
#ifndef IUTEST_CXX_EXPLICIT_CONVERSION | |
#if IUTEST_HAS_EXPLICIT_CONVERSION | |
#define IUTEST_CXX_EXPLICIT_CONVERSION explicit | |
#else | |
#define IUTEST_CXX_EXPLICIT_CONVERSION | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_OVERRIDE_AND_FINAL | |
#ifdef __clang__ | |
#if __has_feature(cxx_override_control) | |
#define IUTEST_HAS_OVERRIDE_AND_FINAL 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=7))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_OVERRIDE_AND_FINAL 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_OVERRIDE_AND_FINAL | |
#define IUTEST_HAS_OVERRIDE_AND_FINAL 0 | |
#endif | |
#ifndef IUTEST_CXX_OVERRIDE | |
#if IUTEST_HAS_OVERRIDE_AND_FINAL | |
#define IUTEST_CXX_OVERRIDE override | |
#else | |
#define IUTEST_CXX_OVERRIDE | |
#endif | |
#endif | |
#ifndef IUTEST_CXX_FINAL | |
#if IUTEST_HAS_OVERRIDE_AND_FINAL | |
#define IUTEST_CXX_FINAL final | |
#else | |
#define IUTEST_CXX_FINAL | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_NOEXCEPT | |
#ifdef __clang__ | |
#if __has_feature(cxx_noexcept) | |
#define IUTEST_HAS_NOEXCEPT 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=6))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_NOEXCEPT 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_NOEXCEPT | |
#define IUTEST_HAS_NOEXCEPT 0 | |
#endif | |
#ifndef IUTEST_HAS_NOEXCEPT_FUNCTION_TYPE | |
#if defined(__cpp_noexcept_function_type)&&__cpp_noexcept_function_type>=201510L | |
#define IUTEST_HAS_NOEXCEPT_FUNCTION_TYPE 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_NOEXCEPT_FUNCTION_TYPE | |
#define IUTEST_HAS_NOEXCEPT_FUNCTION_TYPE 0 | |
#endif | |
#ifndef IUTEST_CXX_NOEXCEPT | |
#if IUTEST_HAS_NOEXCEPT | |
#define IUTEST_CXX_NOEXCEPT(expr_) noexcept(expr_) | |
#else | |
#define IUTEST_CXX_NOEXCEPT(expr_) | |
#endif | |
#endif | |
#ifndef IUTEST_CXX_NOEXCEPT_SPEC | |
#if IUTEST_HAS_NOEXCEPT | |
#define IUTEST_CXX_NOEXCEPT_SPEC noexcept | |
#else | |
#define IUTEST_CXX_NOEXCEPT_SPEC | |
#endif | |
#endif | |
#ifndef IUTEST_CXX_NOEXCEPT_AS | |
#if IUTEST_HAS_NOEXCEPT | |
#define IUTEST_CXX_NOEXCEPT_AS(expr_) noexcept(noexcept(expr_)) | |
#else | |
#define IUTEST_CXX_NOEXCEPT_AS(expr_) | |
#endif | |
#endif | |
#ifndef IUTEST_CXX_NOTHROW | |
#if IUTEST_HAS_NOEXCEPT | |
#define IUTEST_CXX_NOTHROW noexcept | |
#elif IUTEST_HAS_CXX2A | |
#define IUTEST_CXX_NOTHROW | |
#else | |
#define IUTEST_CXX_NOTHROW throw() | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_EXTERN_TEMPLATE | |
#if defined(__GNUC__)||defined(__clang__) | |
#define IUTEST_HAS_EXTERN_TEMPLATE 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_EXTERN_TEMPLATE | |
#define IUTEST_HAS_EXTERN_TEMPLATE 0 | |
#endif | |
#ifndef IUTEST_HAS_STRONG_ENUMS | |
#ifdef __clang__ | |
#if __has_feature(cxx_strong_enums) | |
#define IUTEST_HAS_STRONG_ENUMS 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=6))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_STRONG_ENUMS 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_STRONG_ENUMS | |
#define IUTEST_HAS_STRONG_ENUMS 0 | |
#endif | |
#ifndef IUTEST_HAS_EXCEPTIONS | |
#if defined(__clang__) | |
#if __EXCEPTIONS&&__has_feature(cxx_exceptions) | |
#define IUTEST_HAS_EXCEPTIONS 1 | |
#endif | |
#elif defined(__GNUC__) | |
#ifdef __EXCEPTIONS | |
#define IUTEST_HAS_EXCEPTIONS 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_EXCEPTIONS | |
#define IUTEST_HAS_EXCEPTIONS 0 | |
#endif | |
#ifndef IUTEST_HAS_RTTI | |
#ifdef __clang__ | |
#if __has_feature(cxx_rtti) | |
#define IUTEST_HAS_RTTI 1 | |
#endif | |
#elif defined(__GNUC__) | |
#ifdef __RTTI | |
#define IUTEST_HAS_RTTI 1 | |
#endif | |
#ifdef __GXX_RTTI | |
#define IUTEST_HAS_RTTI 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_RTTI | |
#define IUTEST_HAS_RTTI 0 | |
#endif | |
#if IUTEST_HAS_RTTI | |
#include <typeinfo> | |
#endif | |
#ifndef IUTEST_HAS_INT128 | |
#if defined(__SIZEOF_INT128__)&&__SIZEOF_INT128__==16 | |
#define IUTEST_HAS_INT128 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_INT128 | |
#define IUTEST_HAS_INT128 0 | |
#endif | |
#ifndef IUTEST_HAS_COUNTER_MACRO | |
#if defined(__clang__) | |
#define IUTEST_HAS_COUNTER_MACRO 1 | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=3)) | |
#define IUTEST_HAS_COUNTER_MACRO 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_COUNTER_MACRO | |
#define IUTEST_HAS_COUNTER_MACRO 0 | |
#endif | |
#ifndef IUTEST_HAS_FILE_STAT | |
#define IUTEST_HAS_FILE_STAT 1 | |
#endif | |
#ifndef IUTEST_HAS_FILENO | |
#if !defined(__STRICT_ANSI__) | |
#define IUTEST_HAS_FILENO 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_ATTRIBUTE | |
#if defined(__cpp_attributes)&&__cpp_attributes>=200809 | |
#define IUTEST_HAS_ATTRIBUTE 1 | |
#elif defined(__clang__) | |
#if __has_feature(cxx_attributes) | |
#define IUTEST_HAS_ATTRIBUTE 1 | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>=8))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_ATTRIBUTE 1 | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_ATTRIBUTE | |
#define IUTEST_HAS_ATTRIBUTE 0 | |
#endif | |
#ifndef IUTEST_ATTRIBUTE_UNUSED_ | |
#if(defined(__GNUC__)) | |
#define IUTEST_ATTRIBUTE_UNUSED_ __attribute__((unused)) | |
#elif defined(__clang__) | |
#if __has_attribute(unused) | |
#define IUTEST_ATTRIBUTE_UNUSED_ __attribute__((unused)) | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_ATTRIBUTE_UNUSED_ | |
#define IUTEST_ATTRIBUTE_UNUSED_ | |
#endif | |
#ifndef IUTEST_ATTRIBUTE_NORETURN_ | |
#if IUTEST_HAS_ATTRIBUTE | |
#define IUTEST_ATTRIBUTE_NORETURN_ [[noreturn]] | |
#elif defined(__clang__) | |
#if __has_attribute(noreturn) | |
#define IUTEST_ATTRIBUTE_NORETURN_ __attribute__((noreturn)) | |
#endif | |
#elif defined(__GNUC__) | |
#define IUTEST_ATTRIBUTE_NORETURN_ __attribute__((noreturn)) | |
#endif | |
#endif | |
#ifndef IUTEST_ATTRIBUTE_NORETURN_ | |
#define IUTEST_ATTRIBUTE_NORETURN_ | |
#endif | |
#if defined(__GNUC__) | |
#define IUTEST_PRAGMA(x) _Pragma(#x) | |
#elif defined(__clang__) | |
#define IUTEST_PRAGMA(x) _Pragma(#x) | |
#else | |
#define IUTEST_PRAGMA(x) | |
#endif | |
#define IUTEST_PRAGMA_MESSAGE(m) IUTEST_PRAGMA(message(m)) | |
#ifdef __clang__ | |
#define IUTEST_PRAGMA_CLANG_WARN_PUSH() IUTEST_PRAGMA(clang diagnostic push) | |
#define IUTEST_PRAGMA_CLANG_WARN_DISABLE(x) IUTEST_PRAGMA(clang diagnostic ignored x) | |
#define IUTEST_PRAGMA_CLANG_WARN_POP() IUTEST_PRAGMA(clang diagnostic pop) | |
#define IUTEST_PRAGMA_GCC_WARN_PUSH IUTEST_PRAGMA_CLANG_WARN_PUSH | |
#define IUTEST_PRAGMA_GCC_WARN_DISABLE IUTEST_PRAGMA_CLANG_WARN_DISABLE | |
#define IUTEST_PRAGMA_GCC_WARN_POP IUTEST_PRAGMA_CLANG_WARN_POP | |
#endif | |
#ifdef __GNUC__ | |
#if((__GNUC__>4)||(__GNUC__==4 && __GNUC_MINOR__>=6)) | |
#define IUTEST_PRAGMA_GCC_WARN_PUSH() IUTEST_PRAGMA(GCC diagnostic push) | |
#define IUTEST_PRAGMA_GCC_WARN_DISABLE(x) IUTEST_PRAGMA(GCC diagnostic ignored x) | |
#define IUTEST_PRAGMA_GCC_WARN_POP() IUTEST_PRAGMA(GCC diagnostic pop) | |
#define IUTEST_PRAGMA_CLANG_WARN_PUSH IUTEST_PRAGMA_GCC_WARN_PUSH | |
#define IUTEST_PRAGMA_CLANG_WARN_DISABLE IUTEST_PRAGMA_GCC_WARN_DISABLE | |
#define IUTEST_PRAGMA_CLANG_WARN_POP IUTEST_PRAGMA_GCC_WARN_POP | |
#endif | |
#endif | |
#ifndef IUTEST_PRAGMA_CLANG_WARN_PUSH | |
#define IUTEST_PRAGMA_CLANG_WARN_PUSH() | |
#endif | |
#ifndef IUTEST_PRAGMA_CLANG_WARN_DISABLE | |
#define IUTEST_PRAGMA_CLANG_WARN_DISABLE(x) | |
#endif | |
#ifndef IUTEST_PRAGMA_CLANG_WARN_POP | |
#define IUTEST_PRAGMA_CLANG_WARN_POP() | |
#endif | |
#ifndef IUTEST_PRAGMA_GCC_WARN_PUSH | |
#define IUTEST_PRAGMA_GCC_WARN_PUSH() | |
#endif | |
#ifndef IUTEST_PRAGMA_GCC_WARN_DISABLE | |
#define IUTEST_PRAGMA_GCC_WARN_DISABLE(x) | |
#endif | |
#ifndef IUTEST_PRAGMA_GCC_WARN_POP | |
#define IUTEST_PRAGMA_GCC_WARN_POP() | |
#endif | |
#ifdef __clang__ | |
#define IUTEST_PRAGMA_WARN_PUSH() IUTEST_PRAGMA_CLANG_WARN_PUSH() | |
#define IUTEST_PRAGMA_WARN_POP() IUTEST_PRAGMA_CLANG_WARN_PUSH() | |
#define IUTEST_PRAGMA_WARN_DISABLE(x) IUTEST_PRAGMA_CLANG_WARN_DISABLE(x) | |
#elif defined(__GNUC__) | |
#define IUTEST_PRAGMA_WARN_PUSH() IUTEST_PRAGMA_GCC_WARN_PUSH() | |
#define IUTEST_PRAGMA_WARN_POP() IUTEST_PRAGMA_GCC_WARN_POP() | |
#define IUTEST_PRAGMA_WARN_DISABLE(x) IUTEST_PRAGMA_GCC_WARN_DISABLE(x) | |
#else | |
#define IUTEST_PRAGMA_WARN_PUSH() | |
#define IUTEST_PRAGMA_WARN_POP() | |
#define IUTEST_PRAGMA_WARN_DISABLE(x) | |
#endif | |
#if defined(__clang__)||defined(__GNUC__) | |
#define IUTEST_PRAGMA_UNUSED_LOCAL_TYPEDEFS_WARN_DISABLE_BEGIN() IUTEST_PRAGMA_WARN_PUSH() IUTEST_PRAGMA_WARN_DISABLE("-Wunused-local-typedefs") | |
#define IUTEST_PRAGMA_UNUSED_LOCAL_TYPEDEFS_WARN_DISABLE_END() IUTEST_PRAGMA_WARN_POP() | |
#else | |
#define IUTEST_PRAGMA_UNUSED_LOCAL_TYPEDEFS_WARN_DISABLE_BEGIN() | |
#define IUTEST_PRAGMA_UNUSED_LOCAL_TYPEDEFS_WARN_DISABLE_END() | |
#endif | |
#define IUTEST_PRAGMA_UNREACHCODE_WARN_DISABLE_BEGIN() | |
#define IUTEST_PRAGMA_UNREACHCODE_WARN_DISABLE_END() | |
#define IUTEST_PRAGMA_ASSIGNMENT_OPERATOR_COULD_NOT_GENERATE_WARN_DISABLE_BEGIN() | |
#define IUTEST_PRAGMA_ASSIGNMENT_OPERATOR_COULD_NOT_GENERATE_WARN_DISABLE_END() | |
#if defined(__clang__) | |
#define IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE() IUTEST_PRAGMA_CLANG_WARN_DISABLE("-Wsign-compare") | |
#elif defined(__GNUC__) | |
#define IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE() IUTEST_PRAGMA_GCC_WARN_DISABLE("-Wsign-compare") | |
#else | |
#define IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE() | |
#endif | |
#if defined(__clang__) | |
#define IUTEST_PRAGMA_WARN_DISABLE_EMPTY_BODY() IUTEST_PRAGMA_CLANG_WARN_DISABLE("-Wempty-body") | |
#elif defined(__GNUC__) | |
#define IUTEST_PRAGMA_WARN_DISABLE_EMPTY_BODY() IUTEST_PRAGMA_GCC_WARN_DISABLE("-Wempty-body") | |
#else | |
#define IUTEST_PRAGMA_WARN_DISABLE_EMPTY_BODY() | |
#endif | |
#if defined(__clang__) | |
#if(__clang_major__>3 ||(__clang_major__==3 && __clang_minor__>0)) | |
#define IUTEST_PRAGMA_WARN_DISABLE_DANGLING_ELSE() IUTEST_PRAGMA_CLANG_WARN_DISABLE("-Wdangling-else") | |
#endif | |
#elif defined(__GNUC__) | |
#if(__GNUC__>6) | |
#define IUTEST_PRAGMA_WARN_DISABLE_DANGLING_ELSE() IUTEST_PRAGMA_GCC_WARN_DISABLE("-Wdangling-else") | |
#endif | |
#endif | |
#ifndef IUTEST_PRAGMA_WARN_DISABLE_DANGLING_ELSE | |
#define IUTEST_PRAGMA_WARN_DISABLE_DANGLING_ELSE() | |
#endif | |
#ifdef __GNUC__ | |
#if(__GNUC__>6) | |
#define IUTEST_PRAGMA_WARN_DISABLE_NOEXCEPT_TPYE() IUTEST_PRAGMA_GCC_WARN_DISABLE("-Wnoexcept-type") | |
#endif | |
#endif | |
#ifndef IUTEST_PRAGMA_WARN_DISABLE_NOEXCEPT_TPYE | |
#define IUTEST_PRAGMA_WARN_DISABLE_NOEXCEPT_TPYE() | |
#endif | |
#define IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TypeName) TypeName(const TypeName&);TypeName& operator=(const TypeName&) | |
#define IUTEST_PP_DISALLOW_ASSIGN(TypeName) private: TypeName& operator=(const TypeName&) | |
#if defined(IUTEST_HAS_RVALUE_REFS)&&IUTEST_HAS_RVALUE_REFS | |
#define IUTEST_PP_DISALLOW_MOVE_AND_COPY_AND_ASSIGN(TypeName) IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TypeName);TypeName(TypeName&& rhs);TypeName& operator=(TypeName&&) | |
#else | |
#define IUTEST_PP_DISALLOW_MOVE_AND_COPY_AND_ASSIGN(TypeName) IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TypeName) | |
#endif | |
#ifndef IUTEST_PP_TOSTRING | |
#define IUTEST_PP_TOSTRING(z_) IP_TOSTRING_(z_) | |
#endif | |
#define IP_TOSTRING_(z_) #z_ | |
#ifndef IUTEST_PP_CAT | |
#define IUTEST_PP_CAT(a_,b_) IP_CAT_(a_,b_) | |
#endif | |
#define IP_CAT_(a_,b_) a_##b_ | |
#define IUTEST_PP_EXPAND(x) x | |
#define IUTEST_PP_COUNTOF(x) (sizeof(x)/sizeof(x[0])) | |
#if IUTEST_HAS_COUNTER_MACRO | |
#define IUTEST_PP_COUNTER __COUNTER__ | |
#else | |
#define IUTEST_PP_COUNTER __LINE__ | |
#endif | |
#if IUTEST_HAS_COUNTER_MACRO | |
#define IUTEST_PP_UNIQUEID IUTEST_PP_CAT(__LINE__,__COUNTER__) | |
#else | |
#define IUTEST_PP_UNIQUEID __LINE__ | |
#endif | |
#define IUTEST_UNUSED_RETURN(x) (void)(x) | |
#define IUTEST_PP_DEC(n) IP_D_I(n) | |
#define IP_D_I(n) IP_D_##n | |
#define IP_D_0 nil | |
#define IP_D_1 0 | |
#define IP_D_2 1 | |
#define IP_D_3 2 | |
#define IP_D_4 3 | |
#define IP_D_5 4 | |
#define IP_D_6 5 | |
#define IP_D_7 6 | |
#define IP_D_8 7 | |
#define IP_D_9 8 | |
#define IP_D_10 9 | |
#define IP_D_11 10 | |
#define IP_D_12 11 | |
#define IP_D_13 12 | |
#define IP_D_14 13 | |
#define IP_D_15 14 | |
#define IP_D_16 15 | |
#define IP_D_17 16 | |
#define IP_D_18 17 | |
#define IP_D_19 18 | |
#define IP_D_20 19 | |
#define IP_D_21 20 | |
#define IP_D_22 21 | |
#define IP_D_23 22 | |
#define IP_D_24 23 | |
#define IP_D_25 24 | |
#define IP_D_26 25 | |
#define IP_D_27 26 | |
#define IP_D_28 27 | |
#define IP_D_29 28 | |
#define IP_D_30 29 | |
#define IP_D_31 30 | |
#define IP_D_32 31 | |
#define IP_D_33 32 | |
#define IP_D_34 33 | |
#define IP_D_35 34 | |
#define IP_D_36 35 | |
#define IP_D_37 36 | |
#define IP_D_38 37 | |
#define IP_D_39 38 | |
#define IP_D_40 39 | |
#define IP_D_41 40 | |
#define IP_D_42 41 | |
#define IP_D_43 42 | |
#define IP_D_44 43 | |
#define IP_D_45 44 | |
#define IP_D_46 45 | |
#define IP_D_47 46 | |
#define IP_D_48 47 | |
#define IP_D_49 48 | |
#define IP_D_50 49 | |
#define IP_D_51 50 | |
#define IP_D_52 51 | |
#define IP_D_53 52 | |
#define IP_D_54 53 | |
#define IP_D_55 54 | |
#define IP_D_56 55 | |
#define IP_D_57 56 | |
#define IP_D_58 57 | |
#define IP_D_59 58 | |
#define IP_D_60 59 | |
#define IP_D_61 60 | |
#define IP_D_62 61 | |
#define IP_D_63 62 | |
#define IP_D_64 63 | |
#define IP_D_65 64 | |
#define IP_D_66 65 | |
#define IP_D_67 66 | |
#define IP_D_68 67 | |
#define IP_D_69 68 | |
#define IP_D_70 69 | |
#define IP_D_71 70 | |
#define IP_D_72 71 | |
#define IP_D_73 72 | |
#define IP_D_74 73 | |
#define IP_D_75 74 | |
#define IP_D_76 75 | |
#define IP_D_77 76 | |
#define IP_D_78 77 | |
#define IP_D_79 78 | |
#define IP_D_80 79 | |
#define IP_D_81 80 | |
#define IP_D_82 81 | |
#define IP_D_83 82 | |
#define IP_D_84 83 | |
#define IP_D_85 84 | |
#define IP_D_86 85 | |
#define IP_D_87 86 | |
#define IP_D_88 87 | |
#define IP_D_89 88 | |
#define IP_D_90 89 | |
#define IP_D_91 90 | |
#define IP_D_92 91 | |
#define IP_D_93 92 | |
#define IP_D_94 93 | |
#define IP_D_95 94 | |
#define IP_D_96 95 | |
#define IP_D_97 96 | |
#define IP_D_98 97 | |
#define IP_D_99 98 | |
#define IP_D_100 99 | |
#define IUTEST_PP_INC(n) IP_I_I(n) | |
#define IP_I_I(n) IP_I_##n | |
#define IP_I_0 1 | |
#define IP_I_1 2 | |
#define IP_I_2 3 | |
#define IP_I_3 4 | |
#define IP_I_4 5 | |
#define IP_I_5 6 | |
#define IP_I_6 7 | |
#define IP_I_7 8 | |
#define IP_I_8 9 | |
#define IP_I_9 10 | |
#define IP_I_10 11 | |
#define IP_I_11 12 | |
#define IP_I_12 13 | |
#define IP_I_13 14 | |
#define IP_I_14 15 | |
#define IP_I_15 16 | |
#define IP_I_16 17 | |
#define IP_I_17 18 | |
#define IP_I_18 19 | |
#define IP_I_19 20 | |
#define IP_I_20 21 | |
#define IP_I_21 22 | |
#define IP_I_22 23 | |
#define IP_I_23 24 | |
#define IP_I_24 25 | |
#define IP_I_25 26 | |
#define IP_I_26 27 | |
#define IP_I_27 28 | |
#define IP_I_28 29 | |
#define IP_I_29 30 | |
#define IP_I_30 31 | |
#define IP_I_31 32 | |
#define IP_I_32 33 | |
#define IP_I_33 34 | |
#define IP_I_34 35 | |
#define IP_I_35 36 | |
#define IP_I_36 37 | |
#define IP_I_37 38 | |
#define IP_I_38 39 | |
#define IP_I_39 40 | |
#define IP_I_40 41 | |
#define IP_I_41 42 | |
#define IP_I_42 43 | |
#define IP_I_43 44 | |
#define IP_I_44 45 | |
#define IP_I_45 46 | |
#define IP_I_46 47 | |
#define IP_I_47 48 | |
#define IP_I_48 49 | |
#define IP_I_49 50 | |
#define IP_I_50 51 | |
#define IP_I_51 52 | |
#define IP_I_52 53 | |
#define IP_I_53 54 | |
#define IP_I_54 55 | |
#define IP_I_55 56 | |
#define IP_I_56 57 | |
#define IP_I_57 58 | |
#define IP_I_58 59 | |
#define IP_I_59 60 | |
#define IP_I_60 61 | |
#define IP_I_61 62 | |
#define IP_I_62 63 | |
#define IP_I_63 64 | |
#define IP_I_64 65 | |
#define IP_I_65 66 | |
#define IP_I_66 67 | |
#define IP_I_67 68 | |
#define IP_I_68 69 | |
#define IP_I_69 70 | |
#define IP_I_70 71 | |
#define IP_I_71 72 | |
#define IP_I_72 73 | |
#define IP_I_73 74 | |
#define IP_I_74 75 | |
#define IP_I_75 76 | |
#define IP_I_76 77 | |
#define IP_I_77 78 | |
#define IP_I_78 79 | |
#define IP_I_79 80 | |
#define IP_I_80 81 | |
#define IP_I_81 82 | |
#define IP_I_82 83 | |
#define IP_I_83 84 | |
#define IP_I_84 85 | |
#define IP_I_85 86 | |
#define IP_I_86 87 | |
#define IP_I_87 88 | |
#define IP_I_88 89 | |
#define IP_I_89 90 | |
#define IP_I_90 91 | |
#define IP_I_91 92 | |
#define IP_I_92 93 | |
#define IP_I_93 94 | |
#define IP_I_94 95 | |
#define IP_I_95 96 | |
#define IP_I_96 97 | |
#define IP_I_97 98 | |
#define IP_I_98 99 | |
#define IP_I_99 100 | |
#define IP_I_100 nil | |
#define IUTEST_PP_LIMIT_REPEAT 50 | |
#define IP_R_P_M_(i,param) param | |
#define IP_R_P_M_B_(i,param1,param2) param2(i,param1) | |
#define IUTEST_PP_REPEAT_PARAMS(n,param) IUTEST_PP_REPEAT(n,IP_R_P_M_,param) | |
#define IUTEST_PP_REPEAT(n,m,param) IUTEST_PP_REPEAT_BINARY(n,IP_R_P_M_B_,param,m) | |
#define IP_R_B_P_M_(i,param1,param2) param1 param2 | |
#define IUTEST_PP_REPEAT_BINARY_PARAMS(n,param1,param2) IUTEST_PP_REPEAT_BINARY(n,IP_R_B_P_M_,param1,param2) | |
#define IUTEST_PP_REPEAT_BINARY(n,m,param1,param2) IP_R_B_P_I(n,m,param1,param2) | |
#define IP_R_B_P_I(n,m,p1,p2) IUTEST_PP_CAT(IP_R_I_,IUTEST_PP_DEC(n))(0,m,p1,p2) | |
#define IP_R_I_nil(i,m,p1,p2) | |
#define IP_R_I_0(i,m,p1,p2) m(i,p1,p2) | |
#define IP_R_I_1(i,m,p1,p2) m(i,p1,p2) IP_R_I_0(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_2(i,m,p1,p2) m(i,p1,p2) IP_R_I_1(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_3(i,m,p1,p2) m(i,p1,p2) IP_R_I_2(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_4(i,m,p1,p2) m(i,p1,p2) IP_R_I_3(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_5(i,m,p1,p2) m(i,p1,p2) IP_R_I_4(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_6(i,m,p1,p2) m(i,p1,p2) IP_R_I_5(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_7(i,m,p1,p2) m(i,p1,p2) IP_R_I_6(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_8(i,m,p1,p2) m(i,p1,p2) IP_R_I_7(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_9(i,m,p1,p2) m(i,p1,p2) IP_R_I_8(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_10(i,m,p1,p2) m(i,p1,p2) IP_R_I_9(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_11(i,m,p1,p2) m(i,p1,p2) IP_R_I_10(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_12(i,m,p1,p2) m(i,p1,p2) IP_R_I_11(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_13(i,m,p1,p2) m(i,p1,p2) IP_R_I_12(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_14(i,m,p1,p2) m(i,p1,p2) IP_R_I_13(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_15(i,m,p1,p2) m(i,p1,p2) IP_R_I_14(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_16(i,m,p1,p2) m(i,p1,p2) IP_R_I_15(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_17(i,m,p1,p2) m(i,p1,p2) IP_R_I_16(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_18(i,m,p1,p2) m(i,p1,p2) IP_R_I_17(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_19(i,m,p1,p2) m(i,p1,p2) IP_R_I_18(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_20(i,m,p1,p2) m(i,p1,p2) IP_R_I_19(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_21(i,m,p1,p2) m(i,p1,p2) IP_R_I_20(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_22(i,m,p1,p2) m(i,p1,p2) IP_R_I_21(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_23(i,m,p1,p2) m(i,p1,p2) IP_R_I_22(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_24(i,m,p1,p2) m(i,p1,p2) IP_R_I_23(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_25(i,m,p1,p2) m(i,p1,p2) IP_R_I_24(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_26(i,m,p1,p2) m(i,p1,p2) IP_R_I_25(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_27(i,m,p1,p2) m(i,p1,p2) IP_R_I_26(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_28(i,m,p1,p2) m(i,p1,p2) IP_R_I_27(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_29(i,m,p1,p2) m(i,p1,p2) IP_R_I_28(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_30(i,m,p1,p2) m(i,p1,p2) IP_R_I_29(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_31(i,m,p1,p2) m(i,p1,p2) IP_R_I_30(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_32(i,m,p1,p2) m(i,p1,p2) IP_R_I_31(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_33(i,m,p1,p2) m(i,p1,p2) IP_R_I_32(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_34(i,m,p1,p2) m(i,p1,p2) IP_R_I_33(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_35(i,m,p1,p2) m(i,p1,p2) IP_R_I_34(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_36(i,m,p1,p2) m(i,p1,p2) IP_R_I_35(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_37(i,m,p1,p2) m(i,p1,p2) IP_R_I_36(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_38(i,m,p1,p2) m(i,p1,p2) IP_R_I_37(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_39(i,m,p1,p2) m(i,p1,p2) IP_R_I_38(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_40(i,m,p1,p2) m(i,p1,p2) IP_R_I_39(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_41(i,m,p1,p2) m(i,p1,p2) IP_R_I_40(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_42(i,m,p1,p2) m(i,p1,p2) IP_R_I_41(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_43(i,m,p1,p2) m(i,p1,p2) IP_R_I_42(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_44(i,m,p1,p2) m(i,p1,p2) IP_R_I_43(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_45(i,m,p1,p2) m(i,p1,p2) IP_R_I_44(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_46(i,m,p1,p2) m(i,p1,p2) IP_R_I_45(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_47(i,m,p1,p2) m(i,p1,p2) IP_R_I_46(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_48(i,m,p1,p2) m(i,p1,p2) IP_R_I_47(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_49(i,m,p1,p2) m(i,p1,p2) IP_R_I_48(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_R_I_50(i,m,p1,p2) m(i,p1,p2) IP_R_I_49(IUTEST_PP_INC(i),m,p1,p2) | |
#define IUTEST_PP_LIMIT_ENUM 50 | |
#define IP_E_P_M_(i,param) IUTEST_PP_CAT(param,i) | |
#define IP_E_P_M_B_(i,param1,param2) param2(i,param1) | |
#define IUTEST_PP_ENUM_PARAMS(n,param) IUTEST_PP_ENUM(n,IP_E_P_M_,param) | |
#define IUTEST_PP_ENUM(n,m,param) IUTEST_PP_ENUM_BINARY(n,IP_E_P_M_B_,param,m) | |
#define IUTEST_PP_ENUM_SHIFTED_PARAMS(n,param) IUTEST_PP_ENUM_SHIFTED(n,IP_E_P_M_,param) | |
#define IUTEST_PP_ENUM_SHIFTED(n,m,param) IUTEST_PP_ENUM_SHIFTED_BINARY(n,IP_E_P_M_B_,param,m) | |
#define IP_E_B_P_M_(i,param1,param2) IUTEST_PP_CAT(param1,i) IUTEST_PP_CAT(param2,i) | |
#define IUTEST_PP_ENUM_BINARY_PARAMS(n,param1,param2) IUTEST_PP_ENUM_BINARY(n,IP_E_B_P_M_,param1,param2) | |
#define IUTEST_PP_ENUM_BINARY(n,m,param1,param2) IP_E_B_P_I(0,n,m,param1,param2) | |
#define IUTEST_PP_ENUM_SHIFTED_BINARY_PARAMS(n,param1,param2) IUTEST_PP_ENUM_BINARY(n,IP_E_B_P_M_,param1,param2) | |
#define IUTEST_PP_ENUM_SHIFTED_BINARY(n,m,param1,param2) IP_E_B_P_I(1,n,m,param1,param2) | |
#define IP_E_B_P_I(begin,n,m,p1,p2) IUTEST_PP_CAT(IP_E_I_,IUTEST_PP_DEC(n))(begin,m,p1,p2) | |
#define IP_E_I_nil(i,m,p1,p2) | |
#define IP_E_I_0(i,m,p1,p2) m(i,p1,p2) | |
#define IP_E_I_1(i,m,p1,p2) m(i,p1,p2),IP_E_I_0(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_2(i,m,p1,p2) m(i,p1,p2),IP_E_I_1(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_3(i,m,p1,p2) m(i,p1,p2),IP_E_I_2(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_4(i,m,p1,p2) m(i,p1,p2),IP_E_I_3(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_5(i,m,p1,p2) m(i,p1,p2),IP_E_I_4(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_6(i,m,p1,p2) m(i,p1,p2),IP_E_I_5(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_7(i,m,p1,p2) m(i,p1,p2),IP_E_I_6(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_8(i,m,p1,p2) m(i,p1,p2),IP_E_I_7(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_9(i,m,p1,p2) m(i,p1,p2),IP_E_I_8(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_10(i,m,p1,p2) m(i,p1,p2),IP_E_I_9(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_11(i,m,p1,p2) m(i,p1,p2),IP_E_I_10(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_12(i,m,p1,p2) m(i,p1,p2),IP_E_I_11(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_13(i,m,p1,p2) m(i,p1,p2),IP_E_I_12(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_14(i,m,p1,p2) m(i,p1,p2),IP_E_I_13(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_15(i,m,p1,p2) m(i,p1,p2),IP_E_I_14(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_16(i,m,p1,p2) m(i,p1,p2),IP_E_I_15(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_17(i,m,p1,p2) m(i,p1,p2),IP_E_I_16(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_18(i,m,p1,p2) m(i,p1,p2),IP_E_I_17(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_19(i,m,p1,p2) m(i,p1,p2),IP_E_I_18(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_20(i,m,p1,p2) m(i,p1,p2),IP_E_I_19(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_21(i,m,p1,p2) m(i,p1,p2),IP_E_I_20(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_22(i,m,p1,p2) m(i,p1,p2),IP_E_I_21(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_23(i,m,p1,p2) m(i,p1,p2),IP_E_I_22(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_24(i,m,p1,p2) m(i,p1,p2),IP_E_I_23(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_25(i,m,p1,p2) m(i,p1,p2),IP_E_I_24(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_26(i,m,p1,p2) m(i,p1,p2),IP_E_I_25(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_27(i,m,p1,p2) m(i,p1,p2),IP_E_I_26(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_28(i,m,p1,p2) m(i,p1,p2),IP_E_I_27(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_29(i,m,p1,p2) m(i,p1,p2),IP_E_I_28(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_30(i,m,p1,p2) m(i,p1,p2),IP_E_I_29(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_31(i,m,p1,p2) m(i,p1,p2),IP_E_I_30(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_32(i,m,p1,p2) m(i,p1,p2),IP_E_I_31(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_33(i,m,p1,p2) m(i,p1,p2),IP_E_I_32(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_34(i,m,p1,p2) m(i,p1,p2),IP_E_I_33(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_35(i,m,p1,p2) m(i,p1,p2),IP_E_I_34(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_36(i,m,p1,p2) m(i,p1,p2),IP_E_I_35(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_37(i,m,p1,p2) m(i,p1,p2),IP_E_I_36(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_38(i,m,p1,p2) m(i,p1,p2),IP_E_I_37(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_39(i,m,p1,p2) m(i,p1,p2),IP_E_I_38(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_40(i,m,p1,p2) m(i,p1,p2),IP_E_I_39(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_41(i,m,p1,p2) m(i,p1,p2),IP_E_I_40(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_42(i,m,p1,p2) m(i,p1,p2),IP_E_I_41(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_43(i,m,p1,p2) m(i,p1,p2),IP_E_I_42(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_44(i,m,p1,p2) m(i,p1,p2),IP_E_I_43(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_45(i,m,p1,p2) m(i,p1,p2),IP_E_I_44(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_46(i,m,p1,p2) m(i,p1,p2),IP_E_I_45(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_47(i,m,p1,p2) m(i,p1,p2),IP_E_I_46(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_48(i,m,p1,p2) m(i,p1,p2),IP_E_I_47(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_49(i,m,p1,p2) m(i,p1,p2),IP_E_I_48(IUTEST_PP_INC(i),m,p1,p2) | |
#define IP_E_I_50(i,m,p1,p2) m(i,p1,p2),IP_E_I_49(IUTEST_PP_INC(i),m,p1,p2) | |
#define IUTEST_PP_BOOL(n) IP_B_I(n) | |
#define IP_B_I(n) IP_B_##n | |
#define IP_B_0 0 | |
#define IP_B_1 1 | |
#define IP_B_2 1 | |
#define IP_B_3 1 | |
#define IP_B_4 1 | |
#define IP_B_5 1 | |
#define IP_B_6 1 | |
#define IP_B_7 1 | |
#define IP_B_8 1 | |
#define IP_B_9 1 | |
#define IP_B_10 1 | |
#define IP_B_11 1 | |
#define IP_B_12 1 | |
#define IP_B_13 1 | |
#define IP_B_14 1 | |
#define IP_B_15 1 | |
#define IP_B_16 1 | |
#define IP_B_17 1 | |
#define IP_B_18 1 | |
#define IP_B_19 1 | |
#define IP_B_20 1 | |
#define IP_B_21 1 | |
#define IP_B_22 1 | |
#define IP_B_23 1 | |
#define IP_B_24 1 | |
#define IP_B_25 1 | |
#define IP_B_26 1 | |
#define IP_B_27 1 | |
#define IP_B_28 1 | |
#define IP_B_29 1 | |
#define IP_B_30 1 | |
#define IP_B_31 1 | |
#define IP_B_32 1 | |
#define IP_B_33 1 | |
#define IP_B_34 1 | |
#define IP_B_35 1 | |
#define IP_B_36 1 | |
#define IP_B_37 1 | |
#define IP_B_38 1 | |
#define IP_B_39 1 | |
#define IP_B_40 1 | |
#define IP_B_41 1 | |
#define IP_B_42 1 | |
#define IP_B_43 1 | |
#define IP_B_44 1 | |
#define IP_B_45 1 | |
#define IP_B_46 1 | |
#define IP_B_47 1 | |
#define IP_B_48 1 | |
#define IP_B_49 1 | |
#define IP_B_50 1 | |
#define IP_B_51 1 | |
#define IP_B_52 1 | |
#define IP_B_53 1 | |
#define IP_B_54 1 | |
#define IP_B_55 1 | |
#define IP_B_56 1 | |
#define IP_B_57 1 | |
#define IP_B_58 1 | |
#define IP_B_59 1 | |
#define IP_B_60 1 | |
#define IP_B_61 1 | |
#define IP_B_62 1 | |
#define IP_B_63 1 | |
#define IP_B_64 1 | |
#define IP_B_65 1 | |
#define IP_B_66 1 | |
#define IP_B_67 1 | |
#define IP_B_68 1 | |
#define IP_B_69 1 | |
#define IP_B_70 1 | |
#define IP_B_71 1 | |
#define IP_B_72 1 | |
#define IP_B_73 1 | |
#define IP_B_74 1 | |
#define IP_B_75 1 | |
#define IP_B_76 1 | |
#define IP_B_77 1 | |
#define IP_B_78 1 | |
#define IP_B_79 1 | |
#define IP_B_80 1 | |
#define IP_B_81 1 | |
#define IP_B_82 1 | |
#define IP_B_83 1 | |
#define IP_B_84 1 | |
#define IP_B_85 1 | |
#define IP_B_86 1 | |
#define IP_B_87 1 | |
#define IP_B_88 1 | |
#define IP_B_89 1 | |
#define IP_B_90 1 | |
#define IP_B_91 1 | |
#define IP_B_92 1 | |
#define IP_B_93 1 | |
#define IP_B_94 1 | |
#define IP_B_95 1 | |
#define IP_B_96 1 | |
#define IP_B_97 1 | |
#define IP_B_98 1 | |
#define IP_B_99 1 | |
#define IP_B_100 1 | |
#define IP_B_101 1 | |
#define IP_B_102 1 | |
#define IP_B_103 1 | |
#define IP_B_104 1 | |
#define IP_B_105 1 | |
#define IP_B_106 1 | |
#define IP_B_107 1 | |
#define IP_B_108 1 | |
#define IP_B_109 1 | |
#define IP_B_110 1 | |
#define IP_B_111 1 | |
#define IP_B_112 1 | |
#define IP_B_113 1 | |
#define IP_B_114 1 | |
#define IP_B_115 1 | |
#define IP_B_116 1 | |
#define IP_B_117 1 | |
#define IP_B_118 1 | |
#define IP_B_119 1 | |
#define IP_B_120 1 | |
#define IP_B_121 1 | |
#define IP_B_122 1 | |
#define IP_B_123 1 | |
#define IP_B_124 1 | |
#define IP_B_125 1 | |
#define IP_B_126 1 | |
#define IP_B_127 1 | |
#define IP_B_128 1 | |
#define IP_B_129 1 | |
#define IP_B_130 1 | |
#define IP_B_131 1 | |
#define IP_B_132 1 | |
#define IP_B_133 1 | |
#define IP_B_134 1 | |
#define IP_B_135 1 | |
#define IP_B_136 1 | |
#define IP_B_137 1 | |
#define IP_B_138 1 | |
#define IP_B_139 1 | |
#define IP_B_140 1 | |
#define IP_B_141 1 | |
#define IP_B_142 1 | |
#define IP_B_143 1 | |
#define IP_B_144 1 | |
#define IP_B_145 1 | |
#define IP_B_146 1 | |
#define IP_B_147 1 | |
#define IP_B_148 1 | |
#define IP_B_149 1 | |
#define IP_B_150 1 | |
#define IP_B_151 1 | |
#define IP_B_152 1 | |
#define IP_B_153 1 | |
#define IP_B_154 1 | |
#define IP_B_155 1 | |
#define IP_B_156 1 | |
#define IP_B_157 1 | |
#define IP_B_158 1 | |
#define IP_B_159 1 | |
#define IP_B_160 1 | |
#define IP_B_161 1 | |
#define IP_B_162 1 | |
#define IP_B_163 1 | |
#define IP_B_164 1 | |
#define IP_B_165 1 | |
#define IP_B_166 1 | |
#define IP_B_167 1 | |
#define IP_B_168 1 | |
#define IP_B_169 1 | |
#define IP_B_170 1 | |
#define IP_B_171 1 | |
#define IP_B_172 1 | |
#define IP_B_173 1 | |
#define IP_B_174 1 | |
#define IP_B_175 1 | |
#define IP_B_176 1 | |
#define IP_B_177 1 | |
#define IP_B_178 1 | |
#define IP_B_179 1 | |
#define IP_B_180 1 | |
#define IP_B_181 1 | |
#define IP_B_182 1 | |
#define IP_B_183 1 | |
#define IP_B_184 1 | |
#define IP_B_185 1 | |
#define IP_B_186 1 | |
#define IP_B_187 1 | |
#define IP_B_188 1 | |
#define IP_B_189 1 | |
#define IP_B_190 1 | |
#define IP_B_191 1 | |
#define IP_B_192 1 | |
#define IP_B_193 1 | |
#define IP_B_194 1 | |
#define IP_B_195 1 | |
#define IP_B_196 1 | |
#define IP_B_197 1 | |
#define IP_B_198 1 | |
#define IP_B_199 1 | |
#define IP_B_200 1 | |
#define IP_B_201 1 | |
#define IP_B_202 1 | |
#define IP_B_203 1 | |
#define IP_B_204 1 | |
#define IP_B_205 1 | |
#define IP_B_206 1 | |
#define IP_B_207 1 | |
#define IP_B_208 1 | |
#define IP_B_209 1 | |
#define IP_B_210 1 | |
#define IP_B_211 1 | |
#define IP_B_212 1 | |
#define IP_B_213 1 | |
#define IP_B_214 1 | |
#define IP_B_215 1 | |
#define IP_B_216 1 | |
#define IP_B_217 1 | |
#define IP_B_218 1 | |
#define IP_B_219 1 | |
#define IP_B_220 1 | |
#define IP_B_221 1 | |
#define IP_B_222 1 | |
#define IP_B_223 1 | |
#define IP_B_224 1 | |
#define IP_B_225 1 | |
#define IP_B_226 1 | |
#define IP_B_227 1 | |
#define IP_B_228 1 | |
#define IP_B_229 1 | |
#define IP_B_230 1 | |
#define IP_B_231 1 | |
#define IP_B_232 1 | |
#define IP_B_233 1 | |
#define IP_B_234 1 | |
#define IP_B_235 1 | |
#define IP_B_236 1 | |
#define IP_B_237 1 | |
#define IP_B_238 1 | |
#define IP_B_239 1 | |
#define IP_B_240 1 | |
#define IP_B_241 1 | |
#define IP_B_242 1 | |
#define IP_B_243 1 | |
#define IP_B_244 1 | |
#define IP_B_245 1 | |
#define IP_B_246 1 | |
#define IP_B_247 1 | |
#define IP_B_248 1 | |
#define IP_B_249 1 | |
#define IP_B_250 1 | |
#define IP_B_251 1 | |
#define IP_B_252 1 | |
#define IP_B_253 1 | |
#define IP_B_254 1 | |
#define IP_B_255 1 | |
#define IUTEST_PP_IF(cond,t,f) IP_IF_I(IUTEST_PP_BOOL(cond),t,f) | |
#define IP_IF_I(cond,t,f) IUTEST_PP_CAT(IP_IF_,cond)(t,f) | |
#define IP_IF_0(t,f) f | |
#define IP_IF_1(t,f) t | |
#define IUTEST_PP_IS_EMPTY(x) IP_IS_EMP_I(x IP_EMP_T) | |
#define IP_IS_EMP_I(x) IP_IS_EMP_I_(IUTEST_PP_CAT(IP_EMP_T_,x)()) | |
#define IP_IS_EMP_I_(x) IP_IS_EMP_II((x)) | |
#define IP_IS_EMP_II(x) IP_IS_EMP_II_ x | |
#define IP_IS_EMP_II_(a,b) b | |
#define IUTEST_PP_EMPTY() | |
#define IP_EMP_T() ,0 | |
#define IP_EMP_T_IP_EMP_T 1,1 IUTEST_PP_EMPTY | |
#define IUTEST_PP_IDENTITY(x) x IUTEST_PP_EMPTY | |
#ifndef IUTEST_PP_VA_CAT | |
#define IUTEST_PP_VA_CAT(a,...) IP_VA_CAT_I(a,__VA_ARGS__) | |
#define IP_VA_CAT_I(a,...) a ## __VA_ARGS__ | |
#endif | |
#define IP_SPLIT(i,...) IP_VA_CAT_I(IP_SPLIT_,i)(__VA_ARGS__) | |
#define IP_IS_BGN_P_C(...) 1 | |
#define IP_SPLIT_0(a,...) a | |
#define IP_SPLIT_1(a,...) __VA_ARGS__ | |
#define IUTEST_PP_IS_BEGIN_PARENS(...) IP_SPLIT(0,IUTEST_PP_VA_CAT(IP_IS_BGN_P_R_ ,IP_IS_BGN_P_C __VA_ARGS__)) | |
#define IP_IS_BGN_P_R_1 1, | |
#define IP_IS_BGN_P_R_IP_IS_BGN_P_C 0, | |
#include <cstdlib> | |
#if defined(__GLIBCPP__)||defined(__GLIBCXX__) | |
#ifdef __clang__ | |
#if __has_include(<experimental/any>) | |
#define IUTEST_LIBSTDCXX_VERSION 50100 | |
#elif __has_include(<shared_mutex>) | |
#define IUTEST_LIBSTDCXX_VERSION 40900 | |
#elif __has_include(<ext/cmath>) | |
#define IUTEST_LIBSTDCXX_VERSION 40800 | |
#elif __has_include(<scoped_allocator>) | |
#define IUTEST_LIBSTDCXX_VERSION 40700 | |
#elif __has_include(<typeindex>) | |
#define IUTEST_LIBSTDCXX_VERSION 40600 | |
#elif __has_include(<future>) | |
#define IUTEST_LIBSTDCXX_VERSION 40500 | |
#elif __has_include(<ratio>) | |
#define IUTEST_LIBSTDCXX_VERSION 40400 | |
#elif __has_include(<array>) | |
#define IUTEST_LIBSTDCXX_VERSION 40300 | |
#endif | |
#elif defined(__GNUC__) | |
#define IUTEST_LIBSTDCXX_VERSION (__GNUC__*10000+__GNUC_MINOR__*100+__GNUC_PATCHLEVEL__) | |
#endif | |
#if IUTEST_HAS_CXX11 | |
#if IUTEST_LIBSTDCXX_VERSION>=50100 | |
#ifndef IUTEST_HAS_CXX_HDR_CODECVT | |
#define IUTEST_HAS_CXX_HDR_CODECVT 1 | |
#endif | |
#endif | |
#if IUTEST_LIBSTDCXX_VERSION>=40900 | |
#ifndef IUTEST_HAS_CXX_HDR_REGEX | |
#define IUTEST_HAS_CXX_HDR_REGEX 1 | |
#endif | |
#endif | |
#if IUTEST_LIBSTDCXX_VERSION>=40700 | |
#ifndef IUTEST_HAS_STD_EMPLACE | |
#define IUTEST_HAS_STD_EMPLACE 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CHRONO | |
#define IUTEST_HAS_CXX_HDR_CHRONO 1 | |
#endif | |
#endif | |
#if IUTEST_LIBSTDCXX_VERSION>=40600 | |
#ifndef IUTEST_HAS_STD_BEGIN_END | |
#define IUTEST_HAS_STD_BEGIN_END 1 | |
#endif | |
#endif | |
#if IUTEST_LIBSTDCXX_VERSION>=40500 | |
#ifndef IUTEST_HAS_STD_DECLVAL | |
#define IUTEST_HAS_STD_DECLVAL 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_RANDOM | |
#define IUTEST_HAS_CXX_HDR_RANDOM 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CSTDINT | |
#define IUTEST_HAS_CXX_HDR_CSTDINT 1 | |
#endif | |
#endif | |
#if IUTEST_LIBSTDCXX_VERSION>=40300 | |
#ifndef IUTEST_HAS_CXX_HDR_ARRAY | |
#define IUTEST_HAS_CXX_HDR_ARRAY 1 | |
#endif | |
#endif | |
#if defined(_GLIBCXX_HAVE_QUICK_EXIT)&&defined(_GLIBCXX_HAVE_AT_QUICK_EXIT) | |
#ifndef IUTEST_HAS_STD_QUICK_EXIT | |
#define IUTEST_HAS_STD_QUICK_EXIT 1 | |
#endif | |
#endif | |
#ifdef __has_include | |
#if !defined(IUTEST_HAS_CXX_HDR_CUCHAR)&&__has_include(<cuchar>) | |
#if defined(_GLIBCXX_USE_C11_UCHAR_CXX11)&&_GLIBCXX_USE_C11_UCHAR_CXX11 | |
#define IUTEST_HAS_CXX_HDR_CUCHAR 1 | |
#endif | |
#endif | |
#endif | |
#endif | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#ifndef IUTEST_HAS_STD_TUPLE | |
#define IUTEST_HAS_STD_TUPLE 1 | |
#endif | |
#elif((IUTEST_LIBSTDCXX_VERSION>=40000)) | |
#ifndef IUTEST_HAS_TR1_TUPLE | |
#define IUTEST_HAS_TR1_TUPLE 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_HDR_CXXABI | |
#ifdef __has_include | |
#if __has_include(<cxxabi.h>) | |
#define IUTEST_HAS_HDR_CXXABI 1 | |
#endif | |
#else | |
#define IUTEST_HAS_HDR_CXXABI 1 | |
#endif | |
#endif | |
#elif defined(_LIBCPP_VERSION) | |
#if IUTEST_HAS_CXX11 | |
#ifndef IUTEST_HAS_STD_BEGIN_END | |
#define IUTEST_HAS_STD_BEGIN_END 1 | |
#endif | |
#ifndef IUTEST_HAS_STD_DECLVAL | |
#define IUTEST_HAS_STD_DECLVAL 1 | |
#endif | |
#ifndef IUTEST_HAS_STD_EMPLACE | |
#define IUTEST_HAS_STD_EMPLACE 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CHRONO | |
#define IUTEST_HAS_CXX_HDR_CHRONO 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_REGEX | |
#define IUTEST_HAS_CXX_HDR_REGEX 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_RANDOM | |
#define IUTEST_HAS_CXX_HDR_RANDOM 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CODECVT | |
#define IUTEST_HAS_CXX_HDR_CODECVT 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CSTDINT | |
#define IUTEST_HAS_CXX_HDR_CSTDINT 1 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_ARRAY | |
#define IUTEST_HAS_CXX_HDR_ARRAY 1 | |
#endif | |
#if !defined(IUTEST_HAS_STD_QUICK_EXIT)&&defined(_LIBCPP_HAS_QUICK_EXIT) | |
#define IUTEST_HAS_STD_QUICK_EXIT 1 | |
#endif | |
#ifdef __has_include | |
#if !defined(IUTEST_HAS_CXX_HDR_CUCHAR)&&__has_include(<cuchar>) | |
#define IUTEST_HAS_CXX_HDR_CUCHAR 1 | |
#endif | |
#endif | |
#endif | |
#if _LIBCPP_VERSION>=1001 | |
#ifndef IUTEST_HAS_STD_BEGIN_END | |
#define IUTEST_HAS_STD_BEGIN_END 1 | |
#endif | |
#endif | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#ifndef IUTEST_HAS_STD_TUPLE | |
#define IUTEST_HAS_STD_TUPLE 1 | |
#endif | |
#elif defined(__has_include) | |
#if !defined(IUTEST_HAS_TR1_TUPLE)&&__has_include(<tr1/tuple>) | |
#define IUTEST_HAS_TR1_TUPLE 1 | |
#endif | |
#endif | |
#ifdef __has_include | |
#if !defined(IUTEST_HAS_HDR_CXXABI)&&__has_include(<cxxabi.h>) | |
#define IUTEST_HAS_HDR_CXXABI 1 | |
#endif | |
#endif | |
#endif | |
#ifdef __has_include | |
#if defined(IUTEST_HAS_CXX_HDR_CODECVT)&&IUTEST_HAS_CXX_HDR_CODECVT | |
#if !__has_include(<codecvt>) | |
#undef IUTEST_HAS_CXX_HDR_CODECVT | |
#endif | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_STD_BEGIN_END | |
#define IUTEST_HAS_STD_BEGIN_END 0 | |
#endif | |
#ifndef IUTEST_HAS_STD_DECLVAL | |
#define IUTEST_HAS_STD_DECLVAL 0 | |
#endif | |
#ifndef IUTEST_USE_EXTERNAL_TR1_TUPLE | |
#define IUTEST_USE_EXTERNAL_TR1_TUPLE 0 | |
#endif | |
#ifndef IUTEST_USE_EXTERNAL_STD_TUPLE | |
#define IUTEST_USE_EXTERNAL_STD_TUPLE 0 | |
#endif | |
#ifndef IUTEST_HAS_STD_TUPLE | |
#define IUTEST_HAS_STD_TUPLE 0 | |
#endif | |
#ifndef IUTEST_HAS_TR1_TUPLE | |
#define IUTEST_HAS_TR1_TUPLE 0 | |
#endif | |
#if IUTEST_HAS_STD_TUPLE||IUTEST_HAS_TR1_TUPLE||IUTEST_USE_EXTERNAL_TR1_TUPLE||IUTEST_USE_EXTERNAL_STD_TUPLE | |
#ifndef IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_TUPLE 1 | |
#endif | |
#else | |
#ifdef IUTEST_HAS_TUPLE | |
#undef IUTEST_HAS_TUPLE | |
#endif | |
#define IUTEST_HAS_TUPLE 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CHRONO | |
#define IUTEST_HAS_CXX_HDR_CHRONO 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_REGEX | |
#define IUTEST_HAS_CXX_HDR_REGEX 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_RANDOM | |
#define IUTEST_HAS_CXX_HDR_RANDOM 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CODECVT | |
#define IUTEST_HAS_CXX_HDR_CODECVT 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CSTDINT | |
#define IUTEST_HAS_CXX_HDR_CSTDINT 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_ARRAY | |
#define IUTEST_HAS_CXX_HDR_ARRAY 0 | |
#endif | |
#ifndef IUTEST_HAS_STD_EMPLACE | |
#define IUTEST_HAS_STD_EMPLACE 0 | |
#endif | |
#ifndef IUTEST_HAS_STD_QUICK_EXIT | |
#define IUTEST_HAS_STD_QUICK_EXIT 0 | |
#endif | |
#ifndef IUTEST_HAS_HDR_CXXABI | |
#define IUTEST_HAS_HDR_CXXABI 0 | |
#endif | |
#ifndef IUTEST_HAS_CXX_HDR_CUCHAR | |
#define IUTEST_HAS_CXX_HDR_CUCHAR 0 | |
#endif | |
#if IUTEST_HAS_CXX_HDR_CSTDINT | |
#include <cstdint> | |
#endif | |
#include <iterator> | |
#ifndef IUTEST_HAS_STD_STR_TO_VALUE | |
#if IUTEST_HAS_CXX11 | |
#define IUTEST_HAS_STD_STR_TO_VALUE 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_STD_STR_TO_VALUE | |
#define IUTEST_HAS_STD_STR_TO_VALUE 0 | |
#endif | |
#ifndef IUTEST_USING_BEGIN_END | |
#if IUTEST_HAS_STD_BEGIN_END | |
#define IUTEST_USING_BEGIN_END() using ::std::begin;using ::std::end | |
#else | |
#define IUTEST_USING_BEGIN_END() using ::iutest::detail::cxx::begin;using ::iutest::detail::cxx::end | |
#endif | |
#endif | |
namespace iutest{namespace detail{namespace cxx{ | |
#if IUTEST_HAS_STD_BEGIN_END | |
using ::std::begin;using ::std::end; | |
#else | |
template<typename T> typename T::iterator begin(T& x){return x.begin();}template<typename T> typename T::iterator end(T& x){return x.end();}template<typename T> typename T::const_iterator begin(const T& x){return x.begin();}template<typename T> typename T::const_iterator end(const T& x){return x.end();}template<typename T,size_t SIZE> T* begin(T(&x)[SIZE]){return &x[0];}template<typename T,size_t SIZE> T* end(T(&x)[SIZE]){return begin(x)+SIZE;}template<typename T,size_t SIZE> const T* begin(const T(&x)[SIZE]){return &x[0];}template<typename T,size_t SIZE> const T* end(const T(&x)[SIZE]){return begin(x)+SIZE;} | |
#endif | |
}}} | |
#if IUTEST_HAS_TUPLE | |
#if !IUTEST_USE_EXTERNAL_STD_TUPLE&&!IUTEST_USE_EXTERNAL_TR1_TUPLE | |
#if IUTEST_HAS_STD_TUPLE | |
#include <tuple> | |
#elif IUTEST_HAS_TR1_TUPLE | |
#if(defined(__GNUC__)&&(__GNUC__>=4)) | |
#include <tr1/tuple> | |
#else | |
#include <tuple> | |
#endif | |
#endif | |
#endif | |
namespace iutest{namespace tuples{ | |
#if IUTEST_HAS_STD_TUPLE | |
namespace alias=::std; | |
#elif IUTEST_HAS_TR1_TUPLE | |
namespace alias=::std::tr1; | |
#endif | |
using alias::tuple;using alias::tuple_element;using alias::make_tuple;using alias::get;template<typename T>struct tuple_size:public alias::tuple_size<T>{};template<typename T>struct tuple_size<const T>:public alias::tuple_size<T>{};template<typename T>struct tuple_size<volatile T>:public alias::tuple_size<T>{};template<typename T>struct tuple_size<const volatile T>:public alias::tuple_size<T>{};namespace detail{template<typename T,typename F,int Begin>struct tuple_foreach_impl{template<int N,int I>struct impl{static void do_something(T& t,F fn){fn(I,get<I>(t));impl<N,I+1>::do_something(t,fn);}};template<int N>struct impl<N,N>{static void do_something(T&,F){}};static void do_something(T& t,F fn){impl<tuple_size<T>::value,Begin>::do_something(t,fn);}};template<typename T,typename U>struct tuple_cast_copy_impl{template<int N,int I>struct impl{static void copy(T& dst,const U& src){get<I>(dst)=static_cast<typename tuple_element<I,T>::type>(get<I>(src));impl<N,I+1>::copy(dst,src);}};template<int N>struct impl<N,N>{static void copy(T&,const U&){}};static void copy(T& dst,const U& src){impl<tuple_size<T>::value,0>::copy(dst,src);}};}template<int I,typename tuple_t,typename F>void tuple_foreach(tuple_t& t,F& fn){detail::tuple_foreach_impl<tuple_t,F&,I>::do_something(t,fn);}template<typename tuple_t,typename F>void tuple_foreach(tuple_t& t,F& fn){tuple_foreach<0>(t,fn);}template<int I,typename tuple_t,typename F>void tuple_foreach(tuple_t& t,const F& fn){detail::tuple_foreach_impl<tuple_t,const F&,I>::do_something(t,fn);}template<typename tuple_t,typename F>void tuple_foreach(tuple_t& t,const F& fn){tuple_foreach<0>(t,fn);}template<typename T,typename U>void tuple_cast_copy(T& dst,const U& src){detail::tuple_cast_copy_impl<T,U>::copy(dst,src);}}using tuples::tuple;using tuples::tuple_size;using tuples::tuple_element;using tuples::tuple_foreach;using tuples::make_tuple;using tuples::get;} | |
#endif | |
#ifndef IUTEST_HAS_HDR_SYSTIME | |
#define IUTEST_HAS_HDR_SYSTIME 1 | |
#endif | |
namespace iutest{namespace detail{template<int SIZE>struct type_least_t{};template<>struct type_least_t<1>{ | |
#ifdef INT_LEAST8_MIN | |
typedef int_least8_t Int;typedef uint_least8_t UInt; | |
#else | |
typedef char Int;typedef unsigned char UInt; | |
#endif | |
};template<>struct type_least_t<2>{ | |
#ifdef INT_LEAST16_MIN | |
typedef int_least16_t Int;typedef uint_least16_t UInt; | |
#else | |
typedef short Int;typedef unsigned short UInt; | |
#endif | |
};template<>struct type_least_t<4>{ | |
#ifdef INT_LEAST32_MIN | |
typedef int_least32_t Int;typedef uint_least32_t UInt; | |
#else | |
typedef int Int;typedef unsigned int UInt; | |
#endif | |
};template<>struct type_least_t<8>{ | |
#ifdef INT_LEAST64_MIN | |
typedef int_least64_t Int;typedef uint_least64_t UInt; | |
#else | |
typedef long long Int;typedef unsigned long long UInt; | |
#endif | |
};template<int SIZE>struct type_fit_t{};template<>struct type_fit_t<1>{ | |
#ifdef INT8_MIN | |
typedef int8_t Int;typedef uint8_t UInt; | |
#else | |
typedef char Int;typedef unsigned char UInt; | |
#endif | |
};template<>struct type_fit_t<2>{ | |
#ifdef INT16_MIN | |
typedef int16_t Int;typedef uint16_t UInt; | |
#else | |
typedef short Int;typedef unsigned short UInt; | |
#endif | |
};template<>struct type_fit_t<4>{ | |
#ifdef INT32_MIN | |
typedef int32_t Int;typedef uint32_t UInt; | |
#else | |
private: template<typename T,typename F,bool b>struct impl{typedef T type;};template<typename T,typename F>struct impl<T,F,false>{typedef F type;};public: typedef impl<long,int,sizeof(int)!=4&&sizeof(long)==4>::type Int;typedef impl<unsigned long,unsigned int,sizeof(int)!=4&&sizeof(long)==4>::type UInt; | |
#endif | |
};template<>struct type_fit_t<8>{ | |
#ifdef INT64_MIN | |
typedef int64_t Int;typedef uint64_t UInt; | |
#else | |
typedef long long Int;typedef unsigned long long UInt; | |
#endif | |
};template<>struct type_fit_t<16>{ | |
#if IUTEST_HAS_INT128 | |
typedef __int128_t Int;typedef __uint128_t UInt; | |
#endif | |
};inline int iu_mbtowc(wchar_t* dst,const char* src,size_t size){return mbtowc(dst,src,size);}}} | |
#define IUTEST_HAS_LIB 0 | |
#define IUTEST_HAS_TESTNAME_ALIAS_JP 0 | |
#define IUTEST_HAS_IF_EXISTS 0 | |
#define IUTEST_HAS_ANALYSIS_ASSUME 0 | |
#define IUTEST_HAS_IGNORE_TEST 0 | |
#define IUTEST_HAS_MINIDUMP 0 | |
#define IUTEST_HAS_STRSTREAM 0 | |
#define IUTEST_HAS_STRINGSTREAM 1 | |
#define IUTEST_HAS_CLASS_MEMBER_TEMPLATE_SPECIALIZATION 0 | |
#define IUTEST_HAS_GENERIC 0 | |
#define IUTEST_HAS_MEMORY_SANITIZER 0 | |
#define IUTEST_HAS_ADDRESS_SANITIZER 0 | |
#define IUTEST_HAS_THREAD_SANITIZER 0 | |
#define IUTEST_HAS_SEH 0 | |
#ifndef IUTEST_VPRINTF | |
#define IUTEST_VPRINTF(f,a) vprintf(f,a) | |
#endif | |
#ifndef IUTEST_HAS_REPORT_SKIPPED | |
#define IUTEST_HAS_REPORT_SKIPPED 1 | |
#endif | |
#ifndef IUTEST_HAS_PARAM_METHOD_TEST | |
#define IUTEST_HAS_PARAM_METHOD_TEST 1 | |
#endif | |
#ifndef IUTEST_HAS_PARAM_TEST | |
#define IUTEST_HAS_PARAM_TEST 1 | |
#endif | |
#ifndef IUTEST_HAS_TYPED_TEST | |
#define IUTEST_HAS_TYPED_TEST 1 | |
#endif | |
#ifndef IUTEST_HAS_TYPED_TEST_P | |
#if IUTEST_HAS_TYPED_TEST | |
#define IUTEST_HAS_TYPED_TEST_P 1 | |
#else | |
#define IUTEST_HAS_TYPED_TEST_P 0 | |
#endif | |
#endif | |
#ifndef IUTEST_TYPED_TEST_P_STRICT | |
#define IUTEST_TYPED_TEST_P_STRICT 1 | |
#endif | |
#ifndef IUTEST_HAS_MATCHERS | |
#define IUTEST_HAS_MATCHERS 1 | |
#endif | |
#ifndef IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE | |
#define IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE 1 | |
#endif | |
#ifndef IUTEST_HAS_BITWISE_EXPRESSION_DECOMPOSE | |
#if IUTEST_HAS_DECLTYPE | |
#define IUTEST_HAS_BITWISE_EXPRESSION_DECOMPOSE 1 | |
#else | |
#define IUTEST_HAS_BITWISE_EXPRESSION_DECOMPOSE 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VALUESGEN | |
#if IUTEST_HAS_PARAM_TEST | |
#define IUTEST_HAS_VALUESGEN 1 | |
#else | |
#define IUTEST_HAS_VALUESGEN 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_RANDOMVALUES | |
#if IUTEST_HAS_PARAM_TEST&&IUTEST_HAS_VALUESGEN | |
#define IUTEST_HAS_RANDOMVALUES 1 | |
#else | |
#define IUTEST_HAS_RANDOMVALUES 0 | |
#endif | |
#endif | |
#if IUTEST_HAS_RANDOMVALUES | |
#if !IUTEST_HAS_PARAM_TEST||!IUTEST_HAS_VALUESGEN | |
#undef IUTEST_HAS_RANDOMVALUES | |
#define IUTEST_HAS_RANDOMVALUES 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_COMBINE | |
#if IUTEST_HAS_PARAM_TEST&&IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_COMBINE 1 | |
#endif | |
#else | |
#if IUTEST_HAS_COMBINE&&!IUTEST_HAS_TUPLE | |
#undef IUTEST_HAS_COMBINE | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_COMBINE | |
#define IUTEST_HAS_COMBINE 0 | |
#endif | |
#ifndef IUTEST_HAS_PAIRWISE | |
#if IUTEST_HAS_PARAM_TEST&&IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_PAIRWISE 1 | |
#endif | |
#else | |
#if IUTEST_HAS_PAIRWISE&&!IUTEST_HAS_TUPLE | |
#undef IUTEST_HAS_PAIRWISE | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_PAIRWISE | |
#define IUTEST_HAS_PAIRWISE 0 | |
#endif | |
#ifndef IUTEST_HAS_CONCAT | |
#define IUTEST_HAS_CONCAT 1 | |
#endif | |
#ifndef IUTEST_HAS_CSVPARAMS | |
#if IUTEST_HAS_PARAM_TEST&&IUTEST_HAS_STRINGSTREAM | |
#define IUTEST_HAS_CSVPARAMS 1 | |
#else | |
#define IUTEST_HAS_CSVPARAMS 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_VALUES | |
#if IUTEST_HAS_PARAM_TEST&&IUTEST_HAS_VARIADIC_TEMPLATES&&IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_VARIADIC_VALUES 1 | |
#else | |
#define IUTEST_HAS_VARIADIC_VALUES 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_COMBINE | |
#if IUTEST_HAS_COMBINE&&IUTEST_HAS_VARIADIC_TEMPLATES&&IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_VARIADIC_COMBINE 1 | |
#else | |
#define IUTEST_HAS_VARIADIC_COMBINE 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_PAIRWISE | |
#if IUTEST_HAS_PAIRWISE&&IUTEST_HAS_VARIADIC_TEMPLATES&&IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_VARIADIC_PAIRWISE 1 | |
#else | |
#define IUTEST_HAS_VARIADIC_PAIRWISE 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_MATCHER_ELEMENTSARE | |
#if IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_MATCHER_ELEMENTSARE IUTEST_HAS_MATCHERS | |
#else | |
#define IUTEST_HAS_MATCHER_ELEMENTSARE 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_MATCHER_ELEMENTSAREARRAYFORWARD | |
#if IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_MATCHER_ELEMENTSAREARRAYFORWARD IUTEST_HAS_MATCHERS | |
#else | |
#define IUTEST_HAS_MATCHER_ELEMENTSAREARRAYFORWARD 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_REGEX | |
#if IUTEST_HAS_CXX_HDR_REGEX | |
#define IUTEST_HAS_REGEX 1 | |
#else | |
#define IUTEST_HAS_REGEX 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_MATCHER_REGEX | |
#if IUTEST_HAS_CXX_HDR_REGEX&&IUTEST_HAS_REGEX | |
#define IUTEST_HAS_MATCHER_REGEX IUTEST_HAS_MATCHERS | |
#else | |
#define IUTEST_HAS_MATCHER_REGEX 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF | |
#if IUTEST_HAS_TUPLE | |
#define IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF IUTEST_HAS_MATCHERS | |
#else | |
#define IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF 0 | |
#endif | |
#endif | |
#ifndef IUTEST_USE_THROW_ON_ASSERTION_FAILURE | |
#ifdef IUTEST_USE_THROW_ON_ASSERT_FAILURE | |
#define IUTEST_USE_THROW_ON_ASSERTION_FAILURE IUTEST_USE_THROW_ON_ASSERT_FAILURE | |
#else | |
#define IUTEST_USE_THROW_ON_ASSERTION_FAILURE 0 | |
#endif | |
#endif | |
#if !IUTEST_HAS_EXCEPTIONS&&IUTEST_USE_THROW_ON_ASSERTION_FAILURE | |
#undef IUTEST_USE_THROW_ON_ASSERTION_FAILURE | |
#define IUTEST_USE_THROW_ON_ASSERTION_FAILURE 0 | |
#endif | |
#ifndef IUTEST_HAS_LAMBDA_STATEMENTS | |
#if IUTEST_HAS_LAMBDA | |
#define IUTEST_HAS_LAMBDA_STATEMENTS 1 | |
#else | |
#define IUTEST_HAS_LAMBDA_STATEMENTS 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_SPI_LAMBDA_SUPPORT | |
#if IUTEST_HAS_LAMBDA_STATEMENTS | |
#define IUTEST_HAS_SPI_LAMBDA_SUPPORT 1 | |
#else | |
#define IUTEST_HAS_SPI_LAMBDA_SUPPORT 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CATCH_SEH_EXCEPTION_ASSERTION | |
#define IUTEST_HAS_CATCH_SEH_EXCEPTION_ASSERTION 0 | |
#endif | |
#ifndef IUTEST_HAS_GENRAND | |
#define IUTEST_HAS_GENRAND 1 | |
#endif | |
#ifndef IUTEST_HAS_PACKAGE | |
#define IUTEST_HAS_PACKAGE 1 | |
#endif | |
#ifndef IUTEST_HAS_PEEP | |
#define IUTEST_HAS_PEEP 1 | |
#endif | |
#ifndef IUTEST_HAS_PEEP_FUNC | |
#define IUTEST_HAS_PEEP_FUNC IUTEST_HAS_PEEP | |
#endif | |
#ifndef IUTEST_HAS_PEEP_STATIC_FUNC | |
#define IUTEST_HAS_PEEP_STATIC_FUNC IUTEST_HAS_PEEP | |
#endif | |
#ifndef IUTEST_HAS_PEEP_CLASS | |
#define IUTEST_HAS_PEEP_CLASS IUTEST_HAS_PEEP | |
#endif | |
#ifndef IUTEST_HAS_STATIC_ASSERT_TYPEEQ | |
#define IUTEST_HAS_STATIC_ASSERT_TYPEEQ 1 | |
#endif | |
#ifndef IUTEST_HAS_PRINT_TO | |
#define IUTEST_HAS_PRINT_TO 1 | |
#endif | |
#ifndef IUTEST_HAS_VARIADIC_PRED | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#define IUTEST_HAS_VARIADIC_PRED 1 | |
#else | |
#define IUTEST_HAS_VARIADIC_PRED 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_ASSERTION_RETURN | |
#define IUTEST_HAS_ASSERTION_RETURN 1 | |
#endif | |
#ifndef IUTEST_HAS_ASSERTION_NOEQUALTO_OBJECT | |
#define IUTEST_HAS_ASSERTION_NOEQUALTO_OBJECT 1 | |
#endif | |
#ifndef IUTEST_HAS_TESTNAME_ALIAS | |
#define IUTEST_HAS_TESTNAME_ALIAS 1 | |
#endif | |
#ifndef IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE IUTEST_HAS_TESTNAME_ALIAS | |
#endif | |
#ifndef IUTEST_HAS_AUTOFIXTURE_PARAM_TEST | |
#define IUTEST_HAS_AUTOFIXTURE_PARAM_TEST IUTEST_HAS_PARAM_TEST | |
#endif | |
#ifndef IUTEST_HAS_ANY_PARAM_TEST | |
#if IUTEST_HAS_TESTNAME_ALIAS | |
#define IUTEST_HAS_ANY_PARAM_TEST IUTEST_HAS_PARAM_TEST | |
#else | |
#define IUTEST_HAS_ANY_PARAM_TEST 0 | |
#endif | |
#endif | |
#ifndef IUTEST_TYPED_TEST_APPEND_TYPENAME | |
#define IUTEST_TYPED_TEST_APPEND_TYPENAME 0 | |
#endif | |
#ifndef IUTEST_HAS_TYPED_TEST_APPEND_TYPENAME | |
#define IUTEST_HAS_TYPED_TEST_APPEND_TYPENAME IUTEST_TYPED_TEST_APPEND_TYPENAME | |
#endif | |
#ifndef IUTEST_HAS_PARAM_TEST_PARAM_NAME_GENERATOR | |
#define IUTEST_HAS_PARAM_TEST_PARAM_NAME_GENERATOR 1 | |
#endif | |
#ifndef IUTEST_HAS_LONG_DOUBLE | |
#if IUTEST_HAS_INT128 | |
#define IUTEST_HAS_LONG_DOUBLE 1 | |
#elif defined(__SIZEOF_FLOAT128__)&&(__SIZEOF_FLOAT128__<=8) | |
#define IUTEST_HAS_LONG_DOUBLE 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_LONG_DOUBLE | |
#define IUTEST_HAS_LONG_DOUBLE 0 | |
#endif | |
#ifndef IUTEST_HAS_FOPEN | |
#define IUTEST_HAS_FOPEN 1 | |
#endif | |
#ifndef IUTEST_HAS_FILE_STAT | |
#define IUTEST_HAS_FILE_STAT 0 | |
#endif | |
#ifndef IUTEST_HAS_FILENO | |
#define IUTEST_HAS_FILENO 0 | |
#endif | |
#ifndef IUTEST_HAS_CTIME | |
#define IUTEST_HAS_CTIME 1 | |
#endif | |
#ifndef IUTEST_HAS_GETTIMEOFDAY | |
#if IUTEST_HAS_HDR_SYSTIME | |
#define IUTEST_HAS_GETTIMEOFDAY 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_GETTIMEOFDAY | |
#define IUTEST_HAS_GETTIMEOFDAY 0 | |
#endif | |
#ifndef IUTEST_HAS_CLOCK | |
#ifdef CLOCKS_PER_SEC | |
#define IUTEST_HAS_CLOCK 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_CLOCK | |
#define IUTEST_HAS_CLOCK 0 | |
#endif | |
#ifndef IUTEST_CHECK_STRICT | |
#define IUTEST_CHECK_STRICT 1 | |
#endif | |
#ifndef IUTEST_HAS_SOCKET | |
#if defined(IUTEST_OS_LINUX) | |
#define IUTEST_HAS_SOCKET 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_SOCKET | |
#define IUTEST_HAS_SOCKET 0 | |
#endif | |
#ifndef IUTEST_HAS_STREAM_BUFFER | |
#define IUTEST_HAS_STREAM_BUFFER 1 | |
#endif | |
#ifndef IUTEST_HAS_STREAM_RESULT | |
#if IUTEST_HAS_SOCKET | |
#define IUTEST_HAS_STREAM_RESULT 1 | |
#else | |
#define IUTEST_HAS_STREAM_RESULT 0 | |
#endif | |
#endif | |
#include <stdio.h> | |
#include <vector> | |
#include <algorithm> | |
namespace iutest{namespace detail{static void IUTEST_ATTRIBUTE_UNUSED_ iuDebugInitialize(){}static void IUTEST_ATTRIBUTE_UNUSED_ iuDebugBreakAlloc(long n){(void)n;}}}namespace iutest{namespace detail{}} | |
#if IUTEST_HAS_TYPED_TEST_P | |
#if IUTEST_TYPED_TEST_P_STRICT | |
#include <set> | |
#endif | |
#endif | |
namespace iutest{namespace internal{typedef void* TypeId;namespace helper{template<typename T>struct TestTypeIdHelper{public: static bool _dummy;};template<typename T>bool TestTypeIdHelper<T>::_dummy=false;}template<typename T>inline TypeId GetTypeId(){return &(helper::TestTypeIdHelper<T>::_dummy);}inline IUTEST_CXX_CONSTEXPR TypeId GetTestTypeId(){return 0;}}namespace detail{template<typename T>struct ieee754_bits{};template<>struct ieee754_bits<float>{enum{EXP=8,FRAC=23};};template<>struct ieee754_bits<double>{enum{EXP=11,FRAC=52};}; | |
#if IUTEST_HAS_LONG_DOUBLE | |
template<size_t N>struct ieee754_bits_longdouble{};template<>struct ieee754_bits_longdouble<8u>{enum{EXP=11,FRAC=52};};template<>struct ieee754_bits_longdouble<16u>{enum{EXP=15,FRAC=64};};template<>struct ieee754_bits<long double>:ieee754_bits_longdouble<sizeof(long double)>{}; | |
#endif | |
}template<typename RawType>class floating_point{private: typedef floating_point<RawType> _Myt;typedef typename detail::type_fit_t<sizeof(RawType)> type;typedef typename type::Int Int;typedef typename type::UInt UInt;union FInt{Int iv;UInt uv;RawType fv;};public: floating_point(){m_v.uv=0;}floating_point(RawType f){m_v.uv=0;m_v.fv=f;}floating_point(const floating_point& rhs):m_v(rhs.m_v){}public: bool AlmostEquals(const _Myt& rhs)const{if(is_nan()||rhs.is_nan()){return false;}return NanSensitiveAlmostEquals(rhs);}bool NanSensitiveAlmostEquals(const _Myt& rhs)const{const UInt v1=norm(bits());const UInt v2=norm(rhs.bits());const UInt diff=(v1>v2)?v1-v2:v2-v1;if(diff<=kMaxUlps){return true;}return false;}public: bool AlmostNear(const _Myt& rhs,RawType max_abs_error)const{if(is_nan()||rhs.is_nan()){return false;}if(m_v.fv==rhs.m_v.fv){return true;}_Myt abs=Abs(rhs);if(abs.m_v.fv<=max_abs_error){return true;}_Myt abs_error=_Myt(max_abs_error);if(abs.AlmostEquals(abs_error)){return true;}return false;}bool NanSensitiveAlmostNear(const _Myt& rhs,RawType max_abs_error)const{if(is_nan()&&rhs.is_nan()){return true;}return AlmostNear(rhs,max_abs_error);}public: _Myt Abs(const _Myt& rhs)const{if(m_v.fv>rhs.m_v.fv){return _Myt(m_v.fv-rhs.m_v.fv);}else{return _Myt(rhs.m_v.fv-m_v.fv);}}public: UInt bits()const{return m_v.uv&kEnableBitMask;}RawType raw()const{return m_v.fv;}UInt exponent_bits()const{return m_v.uv&kExpMask;}UInt fraction_bits()const{return m_v.uv&kFracMask;}UInt sign_bit()const{return m_v.uv&kSignMask;}bool is_nan()const{return exponent_bits()==kExpMask&&fraction_bits()!=0;}public: static _Myt PINF(){_Myt f;f.m_v.uv=kExpMask;return f;}static _Myt NINF(){_Myt f=PINF();f.m_v.uv|=kSignMask;return f;}static _Myt PNAN(){_Myt f;f.m_v.uv=kExpMask|1;return f;}static _Myt NNAN(){_Myt f=PNAN();f.m_v.uv|=kSignMask;return f;}static _Myt PQNAN(){_Myt f;f.m_v.uv=((1<<(kEXP+1))-1);f.m_v.uv<<=kFRAC-1;return f;}static _Myt NQNAN(){_Myt f=PQNAN();f.m_v.uv|=kSignMask;return f;}public:operator RawType()const{return m_v.fv;}_Myt& operator=(RawType f){m_v.fv=f;return *this;}_Myt& operator=(const _Myt& rhs){m_v.fv=rhs.m_v;return *this;}bool operator==(const _Myt& rhs)const{return m_v.uv==rhs.m_v.uv;}private: enum{kEXP=detail::ieee754_bits<RawType>::EXP,kFRAC=detail::ieee754_bits<RawType>::FRAC,kMaxUlps=4};private: static UInt norm(UInt v){return(v&kSignMask)?(~v+1) :(v|kSignMask);}static const UInt kSignMask=static_cast<UInt>(1u)<<(kEXP+kFRAC);static const UInt kExpMask=((static_cast<UInt>(1u)<<kEXP)-1)<<kFRAC;static const UInt kFracMask=(static_cast<UInt>(1u)<<kFRAC)-1;static const UInt kEnableBitMask=kSignMask|kExpMask|kFracMask;private: FInt m_v;};typedef detail::type_fit_t<4>::Int Int32;typedef detail::type_fit_t<4>::UInt UInt32;typedef detail::type_fit_t<8>::Int Int64;typedef detail::type_fit_t<8>::UInt UInt64;typedef internal::TypeId TestTypeId;typedef void(*SetUpMethod)();typedef void(*TearDownMethod)();typedef detail::type_least_t<8>::UInt TimeInMillisec;typedef detail::type_least_t<8>::Int BiggestInt;} | |
#include <wchar.h> | |
#include <wctype.h> | |
#include <stdarg.h> | |
#include <errno.h> | |
#include <sstream> | |
#include <string> | |
#include <cstring> | |
namespace iutest{namespace detail{inline int iu_stricmp(const char* str1,const char* str2){return strcasecmp(str1,str2);}inline int iu_wcsicmp(const wchar_t * str1,const wchar_t * str2){ | |
#if defined(IUTEST_OS_LINUX) | |
return wcscasecmp(str1,str2); | |
#else | |
const wchar_t* l=str1;const wchar_t* r=str2;while(*l){wchar_t ul=towupper(*l);wchar_t ur=towupper(*r);if(ul<ur){return -1;}if(ul>ur){return 1;}++l;++r;}if(*l<*r){return -1;}if(*l>*r){return 1;}return 0; | |
#endif | |
}namespace wrapper{inline int iu_vsnprintf(char* dst,size_t size,const char* format,va_list va){char buffer[4096];const int ret=vsprintf(buffer,format,va);if(dst!=0){const size_t length=static_cast<size_t>(ret);const size_t write=(size<=length)?size-1:length;strncpy(dst,buffer,write);dst[write]='\0';}return ret;}}inline int iu_vsnprintf(char* dst,size_t size,const char* format,va_list va){if(dst==0&&size>0){return -1;}return vsnprintf(dst,size,format,va);}inline int iu_snprintf(char* dst,size_t size,const char* format,...){va_list va;va_start(va,format);const int ret=iu_vsnprintf(dst,size,format,va);va_end(va);return ret;}inline bool IsEmpty(const char* p){return p==0||*p=='\0';}inline IUTEST_CXX_CONSTEXPR bool IsSpace(char ch){return ch==' ' || ch=='\t';}inline const char* NullableString(const char* str){return str==0?"":str;}inline IUTEST_CXX_CONSTEXPR const char* SkipSpace(const char* p){return p==0?0 :(IsSpace(*p)?SkipSpace(++p):p);}inline IUTEST_CXX_CONSTEXPR const char* FindComma(const char* p){return(p==0||*p=='\0')?0 :((*p==',')?p:FindComma(++p));}inline bool IsStringEqual(const char* str1,const char* str2){return strcmp(str1,str2)==0;}inline bool IsStringEqual(const ::std::string& str1,const char* str2){return str1.compare(str2)==0;}inline bool IsStringEqual(const ::std::string& str1,const ::std::string& str2){return str1.compare(str2)==0;}inline bool IsStringCaseEqual(const char* str1,const char* str2){return iu_stricmp(str1,str2)==0;}inline bool IsStringForwardMatching(const char* str1,const char* str2){return strstr(str1,str2)==str1;}inline bool IsStringForwardMatching(const ::std::string& str1,const char* str2){return str1.find(str2)==0;}inline bool IsStringForwardMatching(const ::std::string& str1,const std::string& str2){return str1.find(str2)==0;}inline bool IsStringContains(const char* str1,const char* str2){return strstr(str1,str2)!=0;}inline bool IsStringContains(const ::std::string& str1,const char* str2){return str1.find(str2)!=::std::string::npos;}inline bool IsStringContains(const ::std::string& str1,const ::std::string& str2){return str1.find(str2)!=::std::string::npos;}inline void StringReplace(::std::string& str,char a,const char* to){::std::string::size_type pos=0;while(static_cast<void>(pos=str.find(a,pos)),pos!=::std::string::npos){str.replace(pos,1,to);++pos;}}inline ::std::string StripLeadingSpace(const ::std::string& str){::std::string::const_iterator it=str.begin();while(it!=str.end()&&IsSpace(*it)){++it;}return ::std::string(it,str.end());}inline ::std::string StripTrailingSpace(const ::std::string& str){::std::string::const_iterator it=str.end()-1;while(it!=str.begin()&&IsSpace(*it)){--it;}return ::std::string(str.begin(),it+1);}inline ::std::string StripSpace(const ::std::string& str){::std::string::const_iterator start=str.begin();while(start!=str.end()&&IsSpace(*start)){++start;}::std::string::const_iterator end=str.end()-1;while(end!=str.begin()&&IsSpace(*end)){--end;}return ::std::string(start,end+1);}inline bool StringIsBlank(const ::std::string& str){::std::string::const_iterator it=str.begin();while(it!=str.end()){const char ch=*it;if(!IsSpace(ch)&&ch!='\r' && ch!='\n'){return false;}++it;}return true;}inline void StringReplaceToLF(::std::string& str){::std::string::size_type pos=0;while(static_cast<void>(pos=str.find("\r\n",pos)),pos!=::std::string::npos){str.replace(pos,2,"\n");++pos;}StringReplace(str,'\r',"\n");}inline ::std::string StringRemoveComment(const ::std::string& str){::std::string r;::std::string::size_type prev=0;::std::string::size_type pos=str.find('\n',0);while(pos!=::std::string::npos){++pos;if(str[prev]!='#'){r+=str.substr(prev,pos-prev);}prev=pos;pos=str.find('\n',pos);}if(str[prev]!='#'){r+=str.substr(prev);}return r;}inline void StringSplit(const ::std::string& str,char delimiter,::std::vector< ::std::string>&dst){::std::string::size_type prev=0;::std::string::size_type pos=0;::std::vector< ::std::string>parsed;while(static_cast<void>(pos=str.find(delimiter,prev)),pos!=::std::string::npos){parsed.push_back(str.substr(prev,pos-prev));++pos;prev=pos;}parsed.push_back(str.substr(prev));dst.swap(parsed);}inline IUTEST_CXX_CONSTEXPR char ToHex(unsigned int n){return(n&0xF)>=0xA?'A'+((n&0xF)-0xA) : '0'+(n&0xF);}template<typename T>inline ::std::string ToHexString(T value){const size_t kN=sizeof(T)*2;char buf[kN+1]={0};for(size_t i=0;i<kN;++i){buf[i]=ToHex(static_cast<unsigned int>((value>>((kN-i-1)*4))));}buf[kN]='\0';return buf;}inline ::std::string FormatIntWidth2(int value){char buf[3]="00";buf[0]=(value/10)%10+'0';buf[1]=(value)%10+'0';return buf;}inline ::std::string ShowStringQuoted(const char* str){::std::string s="\"";s+=str;s+="\"";return s;}inline ::std::string ShowStringQuoted(const ::std::string& str){::std::string s="\"";s+=str;s+="\"";return s;}inline ::std::string StringFormat(const char* format,...){size_t n=strlen(format) * 2;{va_list va;va_start(va,format);const size_t ret=iu_vsnprintf(0,0,format,va);va_end(va);if(ret>0){n=ret;}}for(;;){char* dst=new char[n];va_list va;va_start(va,format);const int written=iu_vsnprintf(dst,n,format,va);va_end(va);if(written<0){ | |
#ifdef EOVERFLOW | |
if(errno==EOVERFLOW){break;} | |
#endif | |
#ifdef E2BIG | |
if(errno==E2BIG){break;} | |
#endif | |
}else if(static_cast<size_t>(written)<n){::std::string s=::std::string(dst,static_cast<size_t>(written));delete[] dst;return s;}delete[] dst;n*=2;}return "";}typedef ::std::stringstream stlstream;}typedef ::std::ostream iu_ostream;typedef ::std::ostream&(*iu_basic_iomanip)(::std::ostream&);typedef detail::stlstream iu_stringstream; | |
#ifndef IUTEST_HAS_BIGGESTINT_OSTREAM | |
#if(defined(_STLPORT_VERSION)&&!defined(_STLP_LONG_LONG))||(0&&0<1310) | |
#define IUTEST_HAS_BIGGESTINT_OSTREAM 0 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_BIGGESTINT_OSTREAM | |
#define IUTEST_HAS_BIGGESTINT_OSTREAM 1 | |
#endif | |
} | |
#ifndef IUTEST_HAS_HDR_TYPETARITS | |
#ifdef __clang__ | |
#if __has_include(<type_traits>)&&IUTEST_HAS_CXX11 | |
#define IUTEST_HAS_HDR_TYPETARITS 1 | |
#endif | |
#elif(defined(__GLIBCXX__)||defined(_LIBCPP_VERSION))&&IUTEST_HAS_CXX11 | |
#define IUTEST_HAS_HDR_TYPETARITS 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_HDR_TYPETARITS | |
#define IUTEST_HAS_HDR_TYPETARITS 0 | |
#endif | |
#ifndef IUTEST_HAS_RVALUE_REFS | |
#if(__GNUC__>4 ||(__GNUC__==4 && __GNUC_MINOR__>2))&&defined(__GXX_EXPERIMENTAL_CXX0X__) | |
#define IUTEST_HAS_RVALUE_REFS 1 | |
#endif | |
#endif | |
#ifndef IUTEST_HAS_RVALUE_REFS | |
#define IUTEST_HAS_RVALUE_REFS 0 | |
#endif | |
#if IUTEST_HAS_HDR_TYPETARITS | |
#include <type_traits> | |
#else | |
#ifndef IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER | |
#define IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER 1 | |
#endif | |
#endif | |
namespace iutest_type_traits{typedef void type_defined_void;template<typename T>struct identity{typedef T type;};template<bool B,typename T>struct enable_if{typedef T type;};template<typename T>struct enable_if<false,T>{};template<class COND,typename T=type_defined_void>struct enable_if_t:public enable_if<COND::value,T>{};template<bool B,typename T>struct disable_if:public enable_if<!B,T>{};template<class COND,typename T=type_defined_void>struct disable_if_t:public disable_if<COND::value,T>{};template<typename T>struct enabler_t{static void* value;};template<typename T>void* enabler_t<T>::value=0;typedef enabler_t<void> enabler;template<typename T>class add_const_to_pointer{template<typename U,typename DMY>struct impl{typedef const U type;};template<typename U,typename DMY>struct impl<U*,DMY>{typedef const U* type;};public: typedef typename impl<T,void>::type type;}; | |
#if defined(IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER)&&IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER | |
template<typename T>struct is_member_function_pointer; | |
#endif | |
#if IUTEST_HAS_HDR_TYPETARITS | |
using ::std::true_type;using ::std::false_type;using ::std::remove_const;using ::std::remove_volatile;using ::std::remove_reference;using ::std::remove_cv;using ::std::remove_pointer;using ::std::is_pointer;using ::std::is_void;using ::std::is_const;using ::std::is_same;using ::std::is_class;using ::std::is_convertible;using ::std::is_base_of;using ::std::add_lvalue_reference; | |
#if IUTEST_HAS_RVALUE_REFS | |
using ::std::add_rvalue_reference; | |
#else | |
template<typename T>struct add_rvalue_reference{typedef T type;}; | |
#endif | |
using ::std::is_function; | |
#if !defined(IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER)||!IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER | |
using ::std::is_member_function_pointer; | |
#endif | |
using ::std::is_member_pointer;template<typename F>struct is_function_pointer:public ::std::integral_constant<bool,::std::is_pointer<F>::value&&::std::is_function<typename ::std::remove_pointer<F>::type >::value>{}; | |
#if defined(__cpp_lib_bool_constant)&&__cpp_lib_bool_constant>=201505 | |
using ::std::bool_constant; | |
#else | |
template<bool B>struct bool_constant : ::std::integral_constant<bool,B>{}; | |
#endif | |
#else | |
template<bool B>struct bool_constant{static const bool value=B;};template<bool B>const bool bool_constant<B>::value;typedef bool_constant<true> true_type;typedef bool_constant<false> false_type;template<typename T>class remove_const{template<typename U>struct impl{typedef U type;};template<typename U>struct impl<const U>{typedef U type;};public: typedef typename impl<T>::type type;};template<typename T>class remove_volatile{template<typename U>struct impl{typedef U type;};template<typename U>struct impl<volatile U>{typedef U type;};public: typedef typename impl<T>::type type;};template<typename T>class remove_reference{template<typename U>struct impl{typedef U type;};template<typename U>struct impl<U&>{typedef U type;}; | |
#if IUTEST_HAS_RVALUE_REFS | |
template<typename U>struct impl<U&&>{typedef U type;}; | |
#endif | |
public: typedef typename impl<T>::type type;};template<typename T>struct remove_cv{typedef typename remove_const<typename remove_volatile<T>::type >::type type;};template<typename T>class remove_pointer{template<typename U>struct impl{typedef U type;};template<typename U>struct impl<U*>{typedef U type;};public: typedef typename impl<T>::type type;};namespace is_pointer_helper{template<typename T>class is_pointer{template<typename U,typename TMP> struct impl{typedef false_type type;};template<typename U,typename TMP> struct impl<U*,TMP>{typedef true_type type;};typedef typename remove_cv<T>::type rmcv_type;public: typedef typename impl<rmcv_type,void>::type type;};}template<typename T>struct is_pointer:public is_pointer_helper::is_pointer<T>::type{};namespace is_reference_helper{template<typename T>class is_reference{template<typename U,typename TMP> struct impl{typedef false_type type;};template<typename U,typename TMP> struct impl<U&,TMP>{typedef true_type type;};typedef typename remove_cv<T>::type rmcv_type;public: typedef typename impl<rmcv_type,void>::type type;};}template<typename T>struct is_reference: public is_reference_helper::is_reference<T>::type{};namespace is_void_helper{template<typename T>class is_void{template<typename U,typename TMP> struct impl{typedef false_type type;};template<typename TMP> struct impl<void,TMP>{typedef true_type type;};typedef typename remove_cv<T>::type rmcv_type;public: typedef typename impl<rmcv_type,void>::type type;};}template<typename T>struct is_void: public is_void_helper::is_void<T>::type{};namespace is_const_helper{template<typename T>class is_const{template<typename U> struct impl{typedef false_type type;};template<typename U> struct impl<U const>{typedef true_type type;};public: typedef typename impl<T>::type type;};}template<typename T>struct is_const: public is_const_helper::is_const<T>::type{};namespace is_same_helper{template<typename T1,typename T2>struct is_same{typedef false_type type;};template<typename T>struct is_same<T,T>{typedef true_type type;};}template<typename T1,typename T2>struct is_same: public is_same_helper::is_same<T1,T2>::type{};namespace is_class_helper{template<typename T>class is_class{template<typename U>static char IsClassHelper(int U::*);template<typename U>static char(&IsClassHelper(...))[2];enum{IsClass=sizeof(IsClassHelper<T>(0))==1 ? true:false};public: typedef bool_constant<IsClass> type;};}template<typename T>struct is_class: public is_class_helper::is_class<T>::type{};namespace is_convertible_helper{template<typename From,typename To>class is_convertible_type{static From MakeFrom();static char IsConvertibleHelper(To);static char(&IsConvertibleHelper(...))[2];enum{IsConvertible=sizeof(IsConvertibleHelper(is_convertible_type::MakeFrom()))==1 ? true:false};public: typedef bool_constant<IsConvertible> type;};}template<typename From,typename To>struct is_convertible: public is_convertible_helper::is_convertible_type<From,To>::type{};namespace is_base_of_helper{template<typename Base,typename Derived>class is_base_of_check{struct no_t{char a[2];};template<typename T>static char CheckSig(Derived const volatile *,T);static no_t CheckSig(Base const volatile *,int);struct host{operator Base const volatile *()const;operator Derived const volatile *();};enum{IsBaseAndDerived=sizeof(CheckSig(host(),0))==1 ? true:false};public: typedef bool_constant<IsBaseAndDerived> type;};template<bool is_class_b,bool is_class_d,bool is_same>struct is_base_of_select{template<typename T,typename U>struct rebind{typedef false_type type;};};template<>struct is_base_of_select<true,true,true>{template<typename T,typename U>struct rebind{typedef true_type type;};};template<>struct is_base_of_select<true,true,false>{template<typename T,typename U>struct rebind{typedef typename is_base_of_check<T,U>::type type;};};template<typename Base,typename Derived>class is_base_of{typedef typename remove_cv<Base>::type B;typedef typename remove_cv<Derived>::type D;typedef is_base_of_select<is_class<Base>::value,is_class<Derived>::value,is_same<Base,Derived>::value> selector;typedef typename selector::template rebind<B,D> binder;public: typedef typename binder::type type;};}template<typename Base,typename Derived>struct is_base_of: public is_base_of_helper::is_base_of<Base,Derived>::type{};template<typename T>class add_lvalue_reference{template<typename U,bool b>struct impl{typedef U type;};template<typename U>struct impl<U,true>{typedef U& type;};public: typedef typename impl<T,!is_void<T>::value&&!is_reference<T>::value >::type type;};template<typename T>class add_rvalue_reference{template<typename U,bool b>struct impl{typedef U type;}; | |
#if IUTEST_HAS_RVALUE_REFS | |
template<typename U>struct impl<U,true>{typedef U&& type;}; | |
#endif | |
public: typedef typename impl<T,!is_void<T>::value&&!is_reference<T>::value >::type type;};namespace is_function_pointer_helper{template<typename T>class is_function_pointer{template<typename U>struct impl:public false_type{}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename R,typename ...Args>struct impl<R(*)(Args...)>:public true_type{};template<typename R,typename ...Args>struct impl<R(*)(Args...,...)>:public true_type{}; | |
#else | |
template<typename R>struct impl<R(*)()>:public true_type{};template<typename R>struct impl<R(*)(...)>:public true_type{}; | |
#define II_D_IS_FP_(n) template<typename R,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(*)(IUTEST_PP_ENUM_PARAMS(n,T))>:public true_type{};template<typename R,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(*)(IUTEST_PP_ENUM_PARAMS(n,T),...)>:public true_type{} | |
II_D_IS_FP_(1);II_D_IS_FP_(2);II_D_IS_FP_(3);II_D_IS_FP_(4);II_D_IS_FP_(5);II_D_IS_FP_(6);II_D_IS_FP_(7);II_D_IS_FP_(8);II_D_IS_FP_(9);II_D_IS_FP_(10);II_D_IS_FP_(11);II_D_IS_FP_(12);II_D_IS_FP_(13);II_D_IS_FP_(14);II_D_IS_FP_(15);II_D_IS_FP_(16);II_D_IS_FP_(17);II_D_IS_FP_(18);II_D_IS_FP_(19);II_D_IS_FP_(20); | |
#undef II_D_IS_FP_ | |
#endif | |
enum{value=impl<typename remove_cv<T>::type >::value};public: typedef bool_constant<value> type;};}template<typename T>struct is_function_pointer: public is_function_pointer_helper::is_function_pointer<T>::type{};namespace is_member_pointer_helper{template<typename T>class is_member_pointer{template<typename U>struct impl:public false_type{};template<typename U,typename C>struct impl<U C::*>:public true_type{};public: typedef bool_constant<impl<typename remove_cv<T>::type >::value|| is_member_function_pointer<T>::value>type;};}template<typename T>struct is_member_pointer: public is_member_pointer_helper::is_member_pointer<T>::type{}; | |
#endif | |
#if defined(IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER)&&IUTEST_USE_OWN_IS_MEMBER_FUNCTION_POINTER | |
namespace is_member_function_pointer_helper{template<typename T>class is_member_function_pointer{template<typename U>struct impl:public false_type{}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#define II_D_IS_M_FP_CV_(CV) template<typename R,typename U,typename ...Args> struct impl<R(U::*)(Args...) CV>:public true_type{};template<typename R,typename U,typename ...Args> struct impl<R(U::*)(Args...,...) CV>:public true_type{} | |
II_D_IS_M_FP_CV_(IUTEST_PP_EMPTY());II_D_IS_M_FP_CV_(const);II_D_IS_M_FP_CV_(volatile);II_D_IS_M_FP_CV_(const volatile); | |
#undef II_D_IS_M_FP_CV_ | |
#else | |
#define II_D_IS_M_FP_VOID_CV_(CV) template<typename R,typename U>struct impl<R(U::*)() CV>:public true_type{};template<typename R,typename U>struct impl<R(U::*)(...) CV>:public true_type{} | |
template<typename R,typename U>struct impl<R(U::*)()>:public true_type{};template<typename R,typename U>struct impl<R(U::*)(...)>:public true_type{};II_D_IS_M_FP_VOID_CV_(const);II_D_IS_M_FP_VOID_CV_(volatile);II_D_IS_M_FP_VOID_CV_(const volatile); | |
#undef II_D_IS_M_FP_VOID_CV_ | |
#define II_D_IS_M_FP_(n) II_D_IS_M_FP_I(n,IUTEST_PP_EMPTY());II_D_IS_M_FP_I(n,const);II_D_IS_M_FP_I(n,volatile);II_D_IS_M_FP_I(n,const volatile) | |
#define II_D_IS_M_FP_I(n,CV) template<typename R,typename U,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(U::*)(IUTEST_PP_ENUM_PARAMS(n,T)) CV>:public true_type{};template<typename R,typename U,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(U::*)(IUTEST_PP_ENUM_PARAMS(n,T),...) CV>:public true_type{} | |
II_D_IS_M_FP_(1);II_D_IS_M_FP_(2);II_D_IS_M_FP_(3);II_D_IS_M_FP_(4);II_D_IS_M_FP_(5);II_D_IS_M_FP_(6);II_D_IS_M_FP_(7);II_D_IS_M_FP_(8);II_D_IS_M_FP_(9);II_D_IS_M_FP_(10);II_D_IS_M_FP_(11);II_D_IS_M_FP_(12);II_D_IS_M_FP_(13);II_D_IS_M_FP_(14);II_D_IS_M_FP_(15);II_D_IS_M_FP_(16);II_D_IS_M_FP_(17);II_D_IS_M_FP_(18);II_D_IS_M_FP_(19);II_D_IS_M_FP_(20); | |
#undef II_D_IS_M_FP_ | |
#undef II_D_IS_M_FP_I | |
#endif | |
public: typedef bool_constant<impl<typename remove_cv<T>::type >::value>type;};}template<typename T>struct is_member_function_pointer: public is_member_function_pointer_helper::is_member_function_pointer<T>::type{}; | |
#endif | |
namespace has_equal_to_operator_helper{typedef char no_t[7];template<typename T1,typename T2>no_t& operator==(const T1& lhs,const T2& rhs);}namespace has_equal_to_operator_impl{using namespace has_equal_to_operator_helper;template<typename T>struct has_equal_to_operator{typedef bool_constant<(sizeof(*(T*)0==*(T*)0)!=sizeof(has_equal_to_operator_helper::no_t))> type;};}template<typename T>struct has_equal_to: public has_equal_to_operator_impl::has_equal_to_operator<T>::type{};namespace has_not_equal_to_operator_helper{typedef char no_t[7];template<typename T1,typename T2>no_t& operator!=(const T1& lhs,const T2& rhs);}namespace has_not_equal_to_operator_impl{using namespace has_not_equal_to_operator_helper;template<typename T>struct has_not_equal_to_operator{typedef bool_constant<(sizeof(*(T*)0!=*(T*)0)!=sizeof(has_not_equal_to_operator_helper::no_t))> type;};}template<typename T>struct has_not_equal_to: public has_not_equal_to_operator_impl::has_not_equal_to_operator<T>::type{};template<typename T>class function_return_type{template<typename U> struct impl{}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename R,typename ...Args>struct impl<R(*)(Args...)>{typedef R type;};template<typename R,typename ...Args>struct impl<R(*)(Args...,...)>{typedef R type;};template<typename R,typename U,typename ...Args>struct impl<R(U::*)(Args...)>{typedef R type;};template<typename R,typename U,typename ...Args>struct impl<R(U::*)(Args...,...)>{typedef R type;}; | |
#define II_D_F_R_T_CV_(CV) template<typename R,typename U,typename ...Args>struct impl<R(U::*)(Args...) CV>{typedef R type;};template<typename R,typename U,typename ...Args>struct impl<R(U::*)(Args...,...) CV>{typedef R type;} | |
II_D_F_R_T_CV_(const);II_D_F_R_T_CV_(volatile);II_D_F_R_T_CV_(const volatile); | |
#undef II_D_F_R_T_CV_ | |
#else | |
#define II_D_F_R_T_(n) template<typename R,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(*)(IUTEST_PP_ENUM_PARAMS(n,T))> {typedef R type;};template<typename R,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(*)(IUTEST_PP_ENUM_PARAMS(n,T),...)> {typedef R type;};II_D_F_R_T_I(n,IUTEST_PP_EMPTY());II_D_F_R_T_I(n,const);II_D_F_R_T_I(n,volatile);II_D_F_R_T_I(n,const volatile) | |
#define II_D_F_R_T_I(n,CV) template<typename R,typename U,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(U::*)(IUTEST_PP_ENUM_PARAMS(n,T)) CV> {typedef R type;};template<typename R,typename U,IUTEST_PP_ENUM_PARAMS(n,typename T)> struct impl<R(U::*)(IUTEST_PP_ENUM_PARAMS(n,T),...) CV> {typedef R type;} | |
template<typename R>struct impl<R(*)()>{typedef R type;};template<typename R,typename U>struct impl<R(U::*)()>{typedef R type;}; | |
#define II_D_F_R_T_VOID_(CV) template<typename R,typename U>struct impl<R(U::*)() CV>{typedef R type;} | |
II_D_F_R_T_VOID_(const);II_D_F_R_T_VOID_(volatile);II_D_F_R_T_VOID_(const volatile); | |
#undef II_D_F_R_T_VOID_ | |
II_D_F_R_T_(1);II_D_F_R_T_(2);II_D_F_R_T_(3);II_D_F_R_T_(4);II_D_F_R_T_(5);II_D_F_R_T_(6);II_D_F_R_T_(7);II_D_F_R_T_(8);II_D_F_R_T_(9);II_D_F_R_T_(10);II_D_F_R_T_(11);II_D_F_R_T_(12);II_D_F_R_T_(13);II_D_F_R_T_(14);II_D_F_R_T_(15);II_D_F_R_T_(16);II_D_F_R_T_(17);II_D_F_R_T_(18);II_D_F_R_T_(19);II_D_F_R_T_(20); | |
#undef II_D_F_R_T_ | |
#undef II_D_F_R_T_I | |
#endif | |
public: typedef typename impl<typename remove_cv<T>::type >::type type;};} | |
#if IUTEST_HAS_EXCEPTIONS | |
#include <exception> | |
namespace iutest{namespace detail{inline ::std::string FormatCxxException(const char* description){iu_stringstream strm;if(description!=0){strm<<"C++ exception with description \"" <<description<<"\"";}else{strm<<"Unknown C++ exception";}return strm.str();}}} | |
#endif | |
#if IUTEST_HAS_HDR_CXXABI | |
#include <cxxabi.h> | |
#endif | |
#define IUTEST_AMBIGUOUS_ELSE_BLOCKER_ switch(::iutest::detail::AlwaysZero()) case 0: default: | |
#define IUTEST_SUPPRESS_UNREACHABLE_CODE_WARNING(st) if(::iutest::detail::AlwaysTrue()) st | |
#define IUTEST_MBS_CODE_UNKNOWN 0 | |
#define IUTEST_MBS_CODE_UTF8 1 | |
#define IUTEST_MBS_CODE_WINDOWS31J 2 | |
#ifndef IUTEST_MBS_CODE | |
#define IUTEST_MBS_CODE IUTEST_MBS_CODE_UTF8 | |
#endif | |
#ifndef IUTEST_BREAK | |
#if defined(__GUNC__)&&(defined(__i386__)||defined(__x86_64__)) | |
#define IUTEST_BREAK() do { __asm { int 3 } } while(::iutest::detail::AlwaysFalse()) | |
#elif defined(__clang__)||defined(__GNUC__) | |
#define IUTEST_BREAK() __builtin_trap() | |
#else | |
#define IUTEST_BREAK() *static_cast<volatile int*>(0)=1 | |
#endif | |
#endif | |
namespace iutest{namespace type_traits=iutest_type_traits;namespace detail{inline bool AlwaysTrue(){return true;}inline bool AlwaysFalse(){return !AlwaysTrue();}inline int AlwaysZero(){return 0;}inline bool IsTrue(bool b){return b;}using namespace iutest_type_traits;template<typename Ite>struct IteratorTraits{typedef typename Ite::value_type type;};template<typename T>struct IteratorTraits<T*>{typedef T type;};template<typename T>struct IteratorTraits<const T*>{typedef T type;};template<typename T>inline void Delete(T* ptr){delete ptr;}class None{};template<typename T>class NoneT1{};template<typename T>struct explicit_type_t{}; | |
#define IUTEST_APPEND_EXPLICIT_TEMPLATE_TYPE_(t) | |
template<typename T>inline explicit_type_t<T>* explicit_type(){return 0;}template<typename T>class TypeUniqueCounter{static size_t value;public: static size_t count(){return value++;}};template<typename T>size_t TypeUniqueCounter<T>::value=0;template<typename T>inline size_t GetTypeUniqueCounter(){return TypeUniqueCounter<T>::count();}template<typename T>class auto_ptr{mutable T* m_ptr;public: explicit auto_ptr(T* p=0):m_ptr(p){}auto_ptr(const auto_ptr& rhs):m_ptr(rhs.m_ptr){rhs.m_ptr=0;}~auto_ptr(){if(m_ptr!=0) delete m_ptr;}T& operator *()const{return *m_ptr;}T* operator->()const{return m_ptr;}auto_ptr& operator=(auto_ptr& rhs){m_ptr=rhs.m_ptr;rhs.m_ptr=0;return *this;}T* get(){return m_ptr;}};template<typename T>class scoped_ptr{T* m_ptr;public: explicit scoped_ptr(T* p=0):m_ptr(p){}~scoped_ptr(){reset();}T& operator *()const{return *m_ptr;}T* operator->()const{return m_ptr;}T* get()const{return m_ptr;}T* release(){T* const p=m_ptr;m_ptr=0;return p;}void reset(T* p=0){if(m_ptr!=p){if(IsTrue(sizeof(T)> 0)){delete m_ptr;}m_ptr=p;}}private: IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(scoped_ptr);};struct IsNullLiteralHelper{class Object;static char IsNullLiteral(Object*);static char(&IsNullLiteral(...))[2];}; | |
#define IUTEST_IS_NULLLITERAL(x) (sizeof(::iutest::detail::IsNullLiteralHelper::IsNullLiteral(x))==1) | |
struct IsContainerHelper{typedef int yes_t;typedef char no_t;template<typename T>static IUTEST_CXX_CONSTEXPR yes_t IsContainer(int IUTEST_APPEND_EXPLICIT_TEMPLATE_TYPE_(T),typename T::iterator* =0,typename T::const_iterator* =0){return 0;}template<typename T>static IUTEST_CXX_CONSTEXPR no_t IsContainer(long IUTEST_APPEND_EXPLICIT_TEMPLATE_TYPE_(T)){return 0;}};template<typename T>inline ::std::string GetTypeName(){ | |
#if IUTEST_HAS_RTTI | |
const char* const name=typeid(T).name(); | |
#if IUTEST_HAS_HDR_CXXABI | |
using abi::__cxa_demangle;int status=1;char* const read_name=__cxa_demangle(name,0,0,&status);::std::string str(status==0 ? read_name:name);free(read_name);return str; | |
#else | |
return name; | |
#endif | |
#else | |
return "<type>"; | |
#endif | |
} | |
#if !IUTEST_HAS_RTTI | |
#define II_GTNS(type) template<>inline ::std::string GetTypeName<type>(){return #type;}template<>inline ::std::string GetTypeName<type*>(){return #type "*";} | |
#define II_GTNS2(type) II_GTNS(type) II_GTNS(unsigned type) | |
II_GTNS2(char)II_GTNS2(short)II_GTNS2(int)II_GTNS2(long)II_GTNS(float)II_GTNS(double)II_GTNS(bool) | |
#undef II_GTNS | |
#undef II_GTNS2 | |
#endif | |
}} | |
#if defined(IUTEST_OS_LINUX) | |
#include <unistd.h> | |
#include <locale.h> | |
#endif | |
#if IUTEST_HAS_FILE_STAT | |
#include <sys/stat.h> | |
#endif | |
#ifndef IUTEST_MAX_PATH | |
#if defined(MAX_PATH)&&MAX_PATH | |
#define IUTEST_MAX_PATH MAX_PATH | |
#elif defined(PATH_MAX)&&PATH_MAX | |
#define IUTEST_MAX_PATH PATH_MAX | |
#elif defined(FILENAME_MAX)&&FILENAME_MAX | |
#define IUTEST_MAX_PATH FILENAME_MAX | |
#else | |
#define IUTEST_MAX_PATH 1024 | |
#endif | |
#endif | |
#define IUTEST_LOG_(level) ::iutest::detail::IUTestLog(::iutest::detail::IUTestLog::LOG_##level,__FILE__,__LINE__).GetStream() | |
#define IUTEST_CHECK_(condition) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(!::iutest::detail::IsTrue(condition)) IUTEST_LOG_(FATAL)<<"Condition " #condition " failed. " | |
namespace iutest{namespace internal{namespace posix{const char* GetEnv(const char* name);int PutEnv(const char* expr);int SetEnv(const char* name,const char* value,int overwrite);const char* GetCWD(char* buf,size_t length);::std::string GetCWD();void SleepMillisec(unsigned int millisec);IUTEST_ATTRIBUTE_NORETURN_ void Abort();inline void Abort(){abort();} | |
#if IUTEST_HAS_FILENO | |
inline int Fileno(FILE* fp){return fileno(fp);} | |
#else | |
inline int Fileno(FILE*){return -1;} | |
#endif | |
#if IUTEST_HAS_FILE_STAT | |
typedef struct stat StatStruct;inline int FileStat(int fd,StatStruct* buf){return fstat(fd,buf);}inline int Stat(const char* path,StatStruct* buf){return stat(path,buf);}inline bool IsDir(const StatStruct& st){return S_ISDIR(st.st_mode);}inline int Stat(FILE* fp,StatStruct* buf){int fd=Fileno(fp);return fd>=0 ? FileStat(fd,buf):fd;} | |
#endif | |
}inline void SleepMilliseconds(int n){posix::SleepMillisec(static_cast<unsigned int>(n));}}namespace detail{namespace posix=internal::posix;char GetPathSeparator() IUTEST_CXX_NOEXCEPT_SPEC;bool IsPathSeparator(char c) IUTEST_CXX_NOEXCEPT_SPEC;bool IsAltPathSeparator(char c) IUTEST_CXX_NOEXCEPT_SPEC;const char* FindLastPathSeparator(const char* path,size_t length) IUTEST_CXX_NOEXCEPT_SPEC;bool SetEnvironmentVariable(const char* name,const char* value);bool GetEnvironmentVariable(const char* name,char* buf,size_t size);template<size_t SIZE>inline bool GetEnvironmentVariable(const char* name,char(&buf)[SIZE]){return GetEnvironmentVariable(name,buf,SIZE);}bool IUTEST_ATTRIBUTE_UNUSED_ GetEnvironmentVariable(const char* name,::std::string& var);bool IUTEST_ATTRIBUTE_UNUSED_ GetEnvironmentInt(const char* name,int& var);class IUTestLog{public: enum Level{LOG_INFO,LOG_WARNING,LOG_ERROR,LOG_FATAL,LOG_LEVEL_NUM};public: IUTestLog(Level level,const char* file,int line);~IUTestLog();public: iu_stringstream& GetStream(){return m_stream;}public: static int GetCount(Level level){return GetCountTable().count[level];}static bool HasWarning(){return GetCount(LOG_WARNING)> 0;}static bool HasError(){return GetCount(LOG_ERROR)> 0||GetCount(LOG_FATAL)> 0;}private: struct Count{int count[LOG_LEVEL_NUM];};static Count& GetCountTable(){static Count count={{0}};return count;}static void CountUp(int level);private: const Level kLevel;iu_stringstream m_stream;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(IUTestLog);}; | |
#if IUTEST_HAS_STREAM_BUFFER | |
template<int SIZE=BUFSIZ>class IUStreamBuffer{public: explicit IUStreamBuffer(FILE* fp):m_fp(fp){m_buf[0]='\0';fflush(fp);setvbuf(fp,m_buf,_IOFBF,SIZE);}~IUStreamBuffer(){fflush(m_fp);setvbuf(m_fp,0,_IONBF,0);}public: ::std::string GetStreamString(){return m_buf;}private: FILE* m_fp;char m_buf[SIZE];}; | |
#endif | |
}}namespace iutest{namespace internal{namespace posix{inline const char* GetEnv(const char* name){ | |
#if defined(__SunOS_5_8)||defined(__SunOS_5_9) | |
const char* env=getenv(name);return(env!=0&&env[0]!='\0')?env:0; | |
#else | |
return getenv(name); | |
#endif | |
}inline int PutEnv(const char* expr){ | |
#if defined(__STRICT_ANSI__) | |
(void)(expr);return -1; | |
#else | |
return putenv(const_cast<char*>(expr)); | |
#endif | |
}inline int SetEnv(const char* name,const char* value,int overwrite){ | |
#if defined(__STRICT_ANSI__) | |
(void)(name);(void)(value);(void)(overwrite);return -1; | |
#else | |
return setenv(name,value,overwrite); | |
#endif | |
}inline const char* GetCWD(char* buf,size_t length){const char* result=getcwd(buf,length);if(result==0&&buf!=0&&length>=1){buf[0]='\0';return buf;}return result;}inline ::std::string GetCWD(){char buf[260]={0};return GetCWD(buf,sizeof(buf));}inline int SleepMillisecFor(unsigned int millisec){volatile int x=0;for(unsigned int i=0;i<millisec;++i){x+=1;}return x;}inline void SleepMillisec(unsigned int millisec){ | |
#if defined(IUTEST_OS_LINUX) | |
#if defined(_POSIX_C_SOURCE)&&_POSIX_C_SOURCE>=199309L | |
const timespec time={0,static_cast<long>(millisec) * 1000 * 1000};nanosleep(&time,0); | |
#elif(defined(_BSD_SOURCE)&&_BSD_SOURCE) | |
||(defined(_XOPEN_SOURCE)&&(_XOPEN_SOURCE>=500||_XOPEN_SOURCE&&_XOPEN_SOURCE_EXTENDED)&&(!defined(_POSIX_C_SOURCE)||!(_POSIX_C_SOURCE>=200809L||_XOPEN_SOURCE>=700)))usleep(millisec*1000); | |
#else | |
(void)SleepMillisecFor(millisec); | |
#endif | |
#else | |
(void)SleepMillisecFor(millisec); | |
#endif | |
}}}namespace detail{inline char GetPathSeparator() IUTEST_CXX_NOEXCEPT_SPEC{return '/';}inline bool IsPathSeparator(char c) IUTEST_CXX_NOEXCEPT_SPEC{return c=='/';}inline bool IsAltPathSeparator(char c) IUTEST_CXX_NOEXCEPT_SPEC{(void)(c);return false;}inline const char* FindLastPathSeparator(const char* path,size_t length) IUTEST_CXX_NOEXCEPT_SPEC{const char* ps=path;const char* pe=ps+length-1;while(pe>=ps){if(IsPathSeparator(*pe)){if((*(pe-1)&0x80)==0){return pe;}--pe;}--pe;}return 0;}inline bool SetEnvironmentVariable(const char* name,const char* value){return internal::posix::SetEnv(name,value,1)==0 ? true:false;}inline bool GetEnvironmentVariable(const char* name,char* buf,size_t size){if(buf==0){return false;}const char* env=internal::posix::GetEnv(name);if(env==0){return false;}const int n=iu_snprintf(buf,size,"%s",env);if(n<0 || static_cast<size_t>(n)>=size){return false;}return true;}inline bool GetEnvironmentVariable(const char* name,::std::string& var){const char* env=internal::posix::GetEnv(name);if(env==0){return false;}var=env;return true;}inline bool GetEnvironmentInt(const char* name,int& var){const char* env=internal::posix::GetEnv(name);if(env==0){return false;}char* end=0;var=static_cast<int>(strtol(env,&end,0));return true;}::std::string FormatFileLocation(const char* file,int line);inline IUTestLog::IUTestLog(Level level,const char* file,int line):kLevel(level){CountUp(level);const char* const tag =(level==LOG_INFO)?"[ INFO ] ": (level==LOG_WARNING)?"[WARNING] ": (level==LOG_ERROR)?"[ ERROR ] ": "[ FATAL ] ";GetStream()<<"\r\n" <<tag<<FormatFileLocation(file,line).c_str()<<": ";}inline IUTestLog::~IUTestLog(){GetStream()<<"\r\n";fprintf(stderr,"%s",m_stream.str().c_str());if(kLevel==LOG_FATAL){fflush(stderr);posix::Abort();}}inline void IUTestLog::CountUp(int level){if(level<LOG_LEVEL_NUM&&level>=0){++GetCountTable().count[level];}}}}namespace iutest{namespace detail{ | |
#if IUTEST_HAS_INLINE_VARIABLE | |
namespace kStrings{static inline const char* const DefaultXmlReportFileName="test_detail.xml";static inline const char* const UnknownFile="unknown file";static inline const char* const Null="(null)";} | |
#else | |
namespace helper{namespace{template<typename DMY>struct kStringsT{static const char* const DefaultXmlReportFileName;static const char* const UnknownFile;static const char* const Null;};template<typename DMY>const char* const kStringsT<DMY>::DefaultXmlReportFileName="test_detail.xml";template<typename DMY>const char* const kStringsT<DMY>::UnknownFile="unknown file";template<typename DMY>const char* const kStringsT<DMY>::Null="(null)";template struct kStringsT<void>;}}typedef helper::kStringsT<void> kStrings; | |
#endif | |
struct kValues{static const size_t MaxPrintContainerCount=32;static const size_t PrintArrayThreshold=18;static const size_t PrintArrayChunksize=PrintArrayThreshold/2;};}} | |
#if IUTEST_HAS_CXX_HDR_CODECVT | |
#include <locale> | |
#include <codecvt> | |
#endif | |
namespace iutest{namespace detail{::std::string WideStringToUTF8(const wchar_t* str,int num=-1);::std::string WideStringToMultiByteString(const wchar_t* str,int num=-1); | |
#if IUTEST_HAS_CHAR16_T | |
::std::string WideStringToUTF8(const char16_t* str,int num=-1);::std::string WideStringToMultiByteString(const char16_t* str,int num=-1); | |
#endif | |
#if IUTEST_HAS_CHAR32_T | |
::std::string WideStringToUTF8(const char32_t* str,int num=-1);::std::string WideStringToMultiByteString(const char32_t* str,int num=-1); | |
#endif | |
::std::wstring MultiByteStringToWideString(const char* str);::std::string MultiByteStringToUTF8(const char* src,int num=-1);template<typename CharType>::std::string ShowWideCString(const CharType* wide_c_str){if(wide_c_str==0){return kStrings::Null;}return WideStringToMultiByteString(wide_c_str);} | |
#if IUTEST_HAS_CXX_HDR_CODECVT | |
template<typename In,typename Out,typename State>struct codecvt:public ::std::codecvt<In,Out,State>{~codecvt(){}};template<typename In,typename Out,typename State>::std::basic_string<Out> CodeConvert(const In* str){::std::wstring_convert<codecvt<In,Out,State>,In> conv;return conv.to_bytes(str);} | |
#endif | |
namespace mbs_ptr_impl{template<typename T>struct to_mbs_ptr{const char* ptr(const char* arg){return arg;}};struct wcs_to_mbs_ptr{::std::string m_arg;const char* ptr(const wchar_t* arg){m_arg=ShowWideCString(arg);return m_arg.c_str();}};template<>struct to_mbs_ptr<wchar_t>:public wcs_to_mbs_ptr{};template<>struct to_mbs_ptr<const wchar_t>:public wcs_to_mbs_ptr{};}template<typename CharType>struct mbs_ptr:public mbs_ptr_impl::to_mbs_ptr<CharType>{};}} | |
#if IUTEST_HAS_CXX_HDR_CUCHAR | |
#include <cuchar> | |
#endif | |
namespace iutest{namespace detail{const UInt32 kMaxCodePoint1=(static_cast<UInt32>(1)<<7)-1;const UInt32 kMaxCodePoint2=(static_cast<UInt32>(1)<<(5+6))-1;const UInt32 kMaxCodePoint3=(static_cast<UInt32>(1)<<(4+2*6))-1;const UInt32 kMaxCodePoint4=(static_cast<UInt32>(1)<<(3+3*6))-1;inline IUTEST_CXX_CONSTEXPR bool IsUtf16SurrogatePair(wchar_t first,wchar_t second){return(sizeof(wchar_t)==2)&&((first&0xFC00)==0xD800)&&((second&0xFC00)==0xDC00);}inline IUTEST_CXX_CONSTEXPR UInt32 CreateCodePointFromUtf16SurrogatePair(wchar_t first,wchar_t second){return(sizeof(wchar_t)==2) ?(((first&0x3FF)<<10)|(second&0x3FF))+0x10000 : static_cast<UInt32>(first);}inline UInt32 ChopLowBits(UInt32* bits,int n){const UInt32 lowbits=*bits&((static_cast<UInt32>(1)<<n)-1);*bits>>=n;return lowbits;}inline char* CodePointToUtf8(UInt32 code_point,char* buf,size_t size){if(code_point<=kMaxCodePoint1){buf[1]='\0';buf[0]=static_cast<char>(code_point);}else if(code_point<=kMaxCodePoint2){buf[2]='\0';buf[1]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[0]=static_cast<char>(0xC0|code_point);}else if(code_point<=kMaxCodePoint3){buf[3]='\0';buf[2]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[1]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[0]=static_cast<char>(0xE0|code_point);}else if(code_point<=kMaxCodePoint4){buf[4]='\0';buf[3]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[2]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[1]=static_cast<char>(0x80|ChopLowBits(&code_point,6));buf[0]=static_cast<char>(0xF0|code_point);}else{iu_snprintf(buf,size,"(Invalid UTF16 0x%X)",code_point);}return buf;}inline ::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToUTF8(const wchar_t* str,int num){if(num==-1){num=static_cast<int>(wcslen(str));} | |
#if IUTEST_HAS_CXX_HDR_CODECVT&&0 | |
#else | |
iu_stringstream ss;for(int i=0;i<num;++i){UInt32 code_point=0;if(str[i]==L'\0'){break;}else if(i+1 <num&&IsUtf16SurrogatePair(str[i],str[i+1])){code_point=CreateCodePointFromUtf16SurrogatePair(str[i],str[i+1]);++i;}else{code_point=static_cast<UInt32>(str[i]);}char buf[32];ss<<CodePointToUtf8(code_point,buf,sizeof(buf));}return ss.str(); | |
#endif | |
}inline ::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToMultiByteString(const wchar_t* str,int num){(void)(num);const size_t length=wcslen(str) * MB_CUR_MAX+1;char* mbs=new char [length];if(wcstombs(mbs,str,length)==static_cast<size_t>(-1)){delete [] mbs;return "(convert error)";}::std::string ret=mbs;delete [] mbs;return ret;} | |
#if IUTEST_HAS_CHAR16_T | |
inline::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToUTF8(const char16_t* str,int num){ | |
#if IUTEST_HAS_CXX_HDR_CUCHAR | |
(void)(num);const size_t length=::std::char_traits<char16_t>::length(str);char16_t lead=0,trail=0;char32_t cp;char mbs[6];mbstate_t state={};IUTEST_CHECK_(mbsinit(&state)!=0);::std::string ret;for(size_t i=0;i<length;++i){lead=str[i];if(lead>0xD800&&lead<0xDC00){++i;trail=str[i];cp=(lead<<10)+trail+0x10000-(0xD800<<10)-0xDC00;}else{cp=lead;}const size_t len=::std::c32rtomb(mbs,cp,&state);if(len!=static_cast<size_t>(-1)){mbs[len]='\0';ret+=mbs;}}return ret; | |
#else | |
return WideStringToUTF8(reinterpret_cast<const wchar_t*>(str),num); | |
#endif | |
}inline::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToMultiByteString(const char16_t* str,int num){ | |
#if IUTEST_HAS_CXX_HDR_CODECVT | |
(void)(num);return CodeConvert<char16_t,char,::std::mbstate_t>(str); | |
#elif IUTEST_HAS_CXX_HDR_CUCHAR | |
(void)(num);const size_t length=::std::char_traits<char16_t>::length(str);char16_t lead=0,trail=0;char32_t cp;char mbs[6];mbstate_t state={};IUTEST_CHECK_(mbsinit(&state)!=0);::std::string ret;for(size_t i=0;i<length;++i){lead=str[i];if(lead>0xD800&&lead<0xDC00){++i;trail=str[i];cp=(lead<<10)+trail+0x10000-(0xD800<<10)-0xDC00;}else{cp=lead;}const size_t len=::std::c32rtomb(mbs,cp,&state);if(len!=static_cast<size_t>(-1)){mbs[len]='\0';ret+=mbs;}}return ret; | |
#else | |
return WideStringToMultiByteString(reinterpret_cast<const wchar_t*>(str),num); | |
#endif | |
} | |
#endif | |
#if IUTEST_HAS_CHAR32_T | |
inline::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToUTF8(const char32_t* str,int num){(void)(num); | |
#if IUTEST_HAS_CXX_HDR_CUCHAR | |
const size_t length=::std::char_traits<char32_t>::length(str);char mbs[6];mbstate_t state={};IUTEST_CHECK_(mbsinit(&state)!=0);::std::string ret;for(size_t i=0;i<length;++i){const size_t len=::std::c32rtomb(mbs,str[i],&state);if(len!=static_cast<size_t>(-1)){mbs[len]='\0';ret+=mbs;}}return ret; | |
#else | |
(void)(str);return "(convert error)"; | |
#endif | |
}inline::std::string IUTEST_ATTRIBUTE_UNUSED_ WideStringToMultiByteString(const char32_t* str,int num){ | |
#if IUTEST_HAS_CXX_HDR_CODECVT | |
(void)(num);return CodeConvert<char32_t,char,::std::mbstate_t>(str); | |
#else | |
return WideStringToUTF8(str,num); | |
#endif | |
} | |
#endif | |
inline ::std::wstring IUTEST_ATTRIBUTE_UNUSED_ MultiByteStringToWideString(const char* str){if(str==0){return L"";}const size_t length=strlen(str)+1;wchar_t* wcs=new wchar_t[length];if(mbstowcs(wcs,str,length)==static_cast<size_t>(-1)){delete[] wcs;return L"(convert error)";}::std::wstring ret=wcs;delete[] wcs;return ret;}inline ::std::string IUTEST_ATTRIBUTE_UNUSED_ MultiByteStringToUTF8(const char* src,int num){ | |
#if(defined(__STDC_ISO_10646__)) | |
if(num==-1){num=static_cast<int>(strlen(src));}::std::string str;const char* p=src;for(const char* end=src+num;p<end;){wchar_t wc=0;const int len=iu_mbtowc(&wc,p,MB_CUR_MAX);if(len>1){str+=WideStringToUTF8(&wc,1);p+=len;}else{str+=*p;++p;}}return str; | |
#else | |
(void)(num);return src; | |
#endif | |
}}} | |
#include <time.h> | |
#if IUTEST_HAS_CXX_HDR_CHRONO | |
#include <chrono> | |
#endif | |
#if IUTEST_HAS_HDR_SYSTIME | |
#include <sys/time.h> | |
#endif | |
#if !defined(IUTEST_GetMillisec)&&!IUTEST_HAS_CXX_HDR_CHRONO&&!IUTEST_HAS_GETTIMEOFDAY&&!IUTEST_HAS_CLOCK | |
#define IUTEST_NO_GETTIMEINMILLIS | |
#endif | |
namespace iutest{namespace detail{bool Localtime(time_t sec,struct tm* dst);::std::string FormatTimeInMillisecAsSecond(TimeInMillisec msec);::std::string FormatTimeInMillisecAsIso8601(TimeInMillisec msec);time_t GetTime();TimeInMillisec GetTimeInMillis();unsigned int GetIndefiniteValue();class iuStopWatch{private: TimeInMillisec m_begin;public: iuStopWatch():m_begin(0){}public: static TimeInMillisec get_millisec(){return GetTimeInMillis();}public: void start(){m_begin=get_millisec();}TimeInMillisec stop()const{return get_millisec()-m_begin;}};}}namespace iutest{namespace detail{inline bool Localtime(time_t sec,struct tm* dst){ | |
#if IUTEST_HAS_CTIME | |
return localtime_r(&sec,dst)!=0; | |
#else | |
(void)(sec);(void)(dst);return false; | |
#endif | |
}inline ::std::string FormatTimeInMillisecAsSecond(TimeInMillisec msec){iu_stringstream ss;ss<<static_cast<double>(msec)*1e-3;return ss.str();}inline ::std::string FormatTimeInMillisecAsIso8601(TimeInMillisec msec){ | |
#if IUTEST_HAS_CTIME | |
time_t sec=static_cast<time_t>(msec / 1000);struct tm t;if(!Localtime(sec,&t)){return FormatTimeInMillisecAsSecond(msec);}iu_stringstream ss;ss<<(t.tm_year+1900);return ss.str()+"-"+ FormatIntWidth2(t.tm_mon+1)+"-"+ FormatIntWidth2(t.tm_mday)+"T"+ FormatIntWidth2(t.tm_hour)+":"+ FormatIntWidth2(t.tm_min)+":"+ FormatIntWidth2(t.tm_sec); | |
#else | |
return FormatTimeInMillisecAsSecond(msec); | |
#endif | |
}inline time_t GetTime(){ | |
#if IUTEST_HAS_CTIME | |
return time(0); | |
#else | |
return 0; | |
#endif | |
}inline TimeInMillisec GetTimeInMillis(){ | |
#ifdef IUTEST_GetMillisec | |
return IUTEST_GetMillisec(); | |
#elif IUTEST_HAS_CXX_HDR_CHRONO | |
return ::std::chrono::duration_cast< ::std::chrono::milliseconds >(::std::chrono::high_resolution_clock::now().time_since_epoch()).count(); | |
#elif IUTEST_HAS_GETTIMEOFDAY | |
timeval tv;gettimeofday(&tv,0);return static_cast<TimeInMillisec>(tv.tv_sec) * 1000+static_cast<TimeInMillisec>(tv.tv_usec) / 1000; | |
#elif IUTEST_HAS_CLOCK | |
return clock() * 1000 / CLOCKS_PER_SEC; | |
#else | |
return GetTime()*1000; | |
#endif | |
}inline unsigned int GetIndefiniteValue(){static unsigned int s=static_cast<unsigned int>(GetTimeInMillis());s=s*1664525+1013904223;return s;}}} | |
#if IUTEST_HAS_CXX_HDR_RANDOM | |
#include <random> | |
#endif | |
namespace iutest{namespace detail{class iuRandom{ | |
#if IUTEST_HAS_CXX_HDR_RANDOM&&defined(IUTEST_USE_RANDOM_ENGINE_TYPENAME) | |
typedef IUTEST_USE_RANDOM_ENGINE_TYPENAME Engine; | |
#else | |
class Engine{public: typedef unsigned int result_type;public: explicit Engine(unsigned int s=0) IUTEST_CXX_NOEXCEPT_SPEC{seed(s);}result_type operator()(){return gen();}bool operator==(const Engine& rhs){return m_v1==rhs.m_v1&&m_v2==rhs.m_v2&&m_v3==rhs.m_v3&&m_v4==rhs.m_v4;}bool operator!=(const Engine& rhs){return m_v1!=rhs.m_v1||m_v2!=rhs.m_v2||m_v3!=rhs.m_v3||m_v4!=rhs.m_v4;}public: void seed(unsigned int s){m_v4=s;m_v3=1812433253 *((m_v4 ^(m_v4>>30))+1);m_v2=1812433253 *((m_v3 ^(m_v3>>30))+2);m_v1=1812433253 *((m_v2 ^(m_v2>>30))+3);}void discard(unsigned int z){for(unsigned int i=0;i<z;++i){gen();}}public:static IUTEST_CXX_CONSTEXPR_OR_CONST result_type _Min=0;static IUTEST_CXX_CONSTEXPR_OR_CONST result_type _Max=static_cast<result_type>(-1);static IUTEST_CXX_CONSTEXPR result_type(min)(){return 0;}static IUTEST_CXX_CONSTEXPR result_type(max)(){return static_cast<result_type>(-1);}private: result_type gen(){const unsigned int t=(m_v1 ^(m_v1<<11));m_v1=m_v2;m_v2=m_v3;m_v3=m_v4;m_v4=(m_v4 ^(m_v4>>19)) ^(t ^(t>>8));return m_v4;}private: unsigned int m_v1,m_v2,m_v3,m_v4;}; | |
#endif | |
Engine m_engine;public: typedef unsigned int result_type;static IUTEST_CXX_CONSTEXPR result_type(min)(){return(Engine::min)();}static IUTEST_CXX_CONSTEXPR result_type(max)(){return(Engine::max)();} | |
#if defined(__clang__)&&(__clang_major__<3 ||(__clang_major__==3 && __clang_minor__<3)) | |
static IUTEST_CXX_CONSTEXPR_OR_CONST result_type _Min=Engine::_Min;static IUTEST_CXX_CONSTEXPR_OR_CONST result_type _Max=Engine::_Max; | |
#endif | |
public: iuRandom(){init();}explicit iuRandom(unsigned int seed){init(seed);}public: void init(){init(GetIndefiniteValue());}void init(unsigned int seed){m_engine=Engine(seed);}public: result_type genrand(){return m_engine();}result_type genrand(unsigned int max){ | |
#if IUTEST_HAS_CXX_HDR_RANDOM | |
::std::uniform_int_distribution<unsigned int> d(0,max-1);return d(m_engine); | |
#else | |
return genrand()%max; | |
#endif | |
}float genrandf(){ | |
#if IUTEST_HAS_CXX_HDR_RANDOM | |
return ::std::uniform_real_distribution<float>(0.0f,1.0f)(m_engine); | |
#else | |
return static_cast<float>(genrand())*(1.0f/4294967295.0f); | |
#endif | |
}template<typename T>T genrand(){return static_cast<T>(genrand(static_cast<unsigned int>(static_cast<T>(-1))));}public: result_type operator()(){return genrand();}result_type operator()(unsigned int max){return genrand(max);}public: template<typename It>void shuffle(It first,It last){ | |
#if IUTEST_HAS_CXX_HDR_RANDOM | |
::std::shuffle(first,last,m_engine); | |
#else | |
::std::random_shuffle(first,last,*this); | |
#endif | |
}}; | |
#define II_WA_GENRAND(type) template<> inline type iuRandom::genrand<type>() | |
II_WA_GENRAND(Int64){return(static_cast<Int64>(genrand())<<32)|genrand();}II_WA_GENRAND(UInt64){return(static_cast<UInt64>(genrand())<<32)|genrand();}II_WA_GENRAND(float){return genrandf();}II_WA_GENRAND(double){return static_cast<double>(genrandf());} | |
#undef II_WA_GENRAND | |
template<typename T>class iuTypedRandom{typedef T result_type;public: iuTypedRandom(){}explicit iuTypedRandom(unsigned int seed):m_rnd(seed){}result_type operator()(){return genrand();}result_type genrand(){return m_rnd.genrand<result_type>();}private: iuRandom m_rnd;};}} | |
#if IUTEST_HAS_CXX_HDR_REGEX | |
#include <regex> | |
#endif | |
namespace iutest{namespace detail{class iuFilterRegex{static bool match_impl(const char* begin,const char* end,const char* src);static bool match_impl_list(const char* begin,const char* end,const char* src);public: static bool match(const char* regex,const char* src);}; | |
#if IUTEST_HAS_CXX_HDR_REGEX | |
class iuRegex{public: iuRegex(const char* pattern){Init(pattern);}iuRegex(const ::std::string& pattern){Init(pattern.c_str());}iuRegex(const iuRegex&rhs):m_re(rhs.m_re),m_pattern(rhs.m_pattern){}public: bool FullMatch(const char* str)const;bool PartialMatch(const char* str)const;const char* pattern()const{return m_pattern.c_str();}private: void Init(const char* pattern);private: ::std::regex m_re;::std::string m_pattern;IUTEST_PP_DISALLOW_ASSIGN(iuRegex);}; | |
#endif | |
}namespace internal{ | |
#if IUTEST_HAS_CXX_HDR_REGEX | |
class RE:public detail::iuRegex{public: RE(const char* pattern):detail::iuRegex(pattern){}RE(const ::std::string& pattern):detail::iuRegex(pattern){}public: static bool FullMatch(const ::std::string& str,const RE& re){return FullMatch(str.c_str(),re);}static bool PartialMatch(const ::std::string& str,const RE& re){return PartialMatch(str.c_str(),re);}static bool FullMatch(const char* str,const RE& re){const detail::iuRegex& r=re;return r.FullMatch(str);}static bool PartialMatch(const char* str,const RE& re){const detail::iuRegex& r=re;return r.PartialMatch(str);}}; | |
#endif | |
}}namespace iutest{namespace detail{inline bool iuFilterRegex::match_impl(const char* begin,const char* end,const char* src){const char* tp=begin;if(*tp=='\0'){return false;}while(tp!=end){if(*tp=='*'){++tp;while(*tp=='*'){++tp;}if(tp==end){return true;}{const char nc=*tp;if(nc=='\0'){return true;}for(;;){while(*src!=nc){++src;if(*src=='\0'){return false;}}if(match_impl(tp+1,end,++src)){return true;}}}}else if(*tp=='?'){if(*src=='\0'){return false;}}else{if(*tp!=*src){return false;}}++tp;++src;}if(*src!='\0'){return false;}return true;}inline bool iuFilterRegex::match_impl_list(const char* begin,const char* end,const char* src){const char* tp=begin;const char* end2=tp;while(end2!=end){++end2;while(*end2!=':' && end2!=end){++end2;}if(match_impl(tp,end2,src)){return true;}tp=end2;if(*tp==':'){++tp;}}return false;}inline bool iuFilterRegex::match(const char* regex,const char* src){const char* tp=regex;const char* end=tp;while(*end!='\0' && *end!='-'){++end;}if(*end=='-'){if(tp!=end&&!match_impl_list(tp,end,src)){return false;}tp=end+1;while(*end!='\0'){++end;}if(match_impl_list(tp,end,src)){return false;}return true;}return match_impl_list(tp,end,src);} | |
#if IUTEST_HAS_CXX_HDR_REGEX | |
inline bool iuRegex::FullMatch(const char* str)const{return(str!=0)?::std::regex_match(str,m_re):false;}inline bool iuRegex::PartialMatch(const char* str)const{return(str!=0)?::std::regex_search(str,m_re):false;}inline void iuRegex::Init(const char* str){m_re.assign(str);m_pattern=str;} | |
#endif | |
}}namespace iutest{class UnitTest;class TestInfo;class TestCase;class TestPartResult;class TestProperty;class TestEventListener;namespace detail{class DefaultGlobalTestPartResultReporter;template<typename T,typename ::std::string(*GetXmlPath)()>class StderrXmlGeneratorListenerBase;}class TestEventListener{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TestEventListener);public: TestEventListener(){}virtual ~TestEventListener(){}public: virtual void OnTestProgramStart(const UnitTest& test)=0;virtual void OnTestIterationStart(const UnitTest& test,int iteration)=0;virtual void OnEnvironmentsSetUpStart(const UnitTest& test)=0;virtual void OnEnvironmentsSetUpEnd(const UnitTest& test)=0;virtual void OnTestCaseStart(const TestCase& test_case)=0;virtual void OnTestStart(const TestInfo& test_info)=0;virtual void OnTestPartResult(const TestPartResult& test_part_result)=0;virtual void OnTestRecordProperty(const TestProperty&){}virtual void OnTestEnd(const TestInfo& test_info)=0;virtual void OnTestCaseEnd(const TestCase& test_case)=0;virtual void OnEnvironmentsTearDownStart(const UnitTest& test)=0;virtual void OnEnvironmentsTearDownEnd(const UnitTest& test)=0;virtual void OnTestIterationEnd(const UnitTest& test,int iteration)=0;virtual void OnTestProgramEnd(const UnitTest& test)=0;};class EmptyTestEventListener:public TestEventListener{public: virtual void OnTestProgramStart(const UnitTest&) IUTEST_CXX_OVERRIDE{}virtual void OnTestIterationStart(const UnitTest&,int) IUTEST_CXX_OVERRIDE{}virtual void OnEnvironmentsSetUpStart(const UnitTest&) IUTEST_CXX_OVERRIDE{}virtual void OnEnvironmentsSetUpEnd(const UnitTest&) IUTEST_CXX_OVERRIDE{}virtual void OnTestCaseStart(const TestCase&) IUTEST_CXX_OVERRIDE{}virtual void OnTestStart(const TestInfo&) IUTEST_CXX_OVERRIDE{}virtual void OnTestPartResult(const TestPartResult&) IUTEST_CXX_OVERRIDE{}virtual void OnTestRecordProperty(const TestProperty&) IUTEST_CXX_OVERRIDE{}virtual void OnTestEnd(const TestInfo&) IUTEST_CXX_OVERRIDE{}virtual void OnTestCaseEnd(const TestCase&) IUTEST_CXX_OVERRIDE{}virtual void OnEnvironmentsTearDownStart(const UnitTest&) IUTEST_CXX_OVERRIDE{}virtual void OnEnvironmentsTearDownEnd(const UnitTest&) IUTEST_CXX_OVERRIDE{}virtual void OnTestIterationEnd(const UnitTest&,int) IUTEST_CXX_OVERRIDE{}virtual void OnTestProgramEnd(const UnitTest&) IUTEST_CXX_OVERRIDE{}};class TestEventRepeater:public TestEventListener{typedef ::std::vector<TestEventListener*> ListenerContainer;public: void Append(TestEventListener* listener){m_listeners.push_back(listener);}TestEventListener* Release(TestEventListener* listener);public: virtual void OnTestProgramStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationStart(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsSetUpStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsSetUpEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseStart(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnTestStart(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestPartResult(const TestPartResult& test_part_result) IUTEST_CXX_OVERRIDE;virtual void OnTestRecordProperty(const TestProperty& test_property) IUTEST_CXX_OVERRIDE;virtual void OnTestEnd(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseEnd(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsTearDownStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsTearDownEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationEnd(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnTestProgramEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;private: ListenerContainer m_listeners;};class TestEventListeners{typedef ::std::vector<TestEventListener*> ListenerContainer;public: TestEventListeners():m_default_result_printer(0),m_default_xml_generator(0){}public: void Append(TestEventListener* listener){m_repeater.Append(listener);}TestEventListener* Release(TestEventListener* listener){return m_repeater.Release(listener);}public: TestEventListener* default_result_printer()const IUTEST_CXX_NOEXCEPT_SPEC{return m_default_result_printer;}TestEventListener* default_xml_generator()const IUTEST_CXX_NOEXCEPT_SPEC{return m_default_xml_generator;}private: TestEventListener* repeater(){return &m_repeater;}void OnTestProgramStart(const UnitTest& test){m_repeater.OnTestProgramStart(test);}void OnTestIterationStart(const UnitTest& test,int iteration){m_repeater.OnTestIterationStart(test,iteration);}void OnEnvironmentsSetUpStart(const UnitTest& test){m_repeater.OnEnvironmentsSetUpStart(test);}void OnEnvironmentsSetUpEnd(const UnitTest& test){m_repeater.OnEnvironmentsSetUpEnd(test);}void OnTestCaseStart(const TestCase& test_case){m_repeater.OnTestCaseStart(test_case);}void OnTestStart(const TestInfo& test_info){m_repeater.OnTestStart(test_info);}void OnTestPartResult(const TestPartResult& test_part_result){m_repeater.OnTestPartResult(test_part_result);}void OnTestRecordProperty(const TestProperty& test_property){m_repeater.OnTestRecordProperty(test_property);}void OnTestEnd(const TestInfo& test_info){m_repeater.OnTestEnd(test_info);}void OnTestCaseEnd(const TestCase& test_case){m_repeater.OnTestCaseEnd(test_case);}void OnEnvironmentsTearDownStart(const UnitTest& test){m_repeater.OnEnvironmentsTearDownStart(test);}void OnEnvironmentsTearDownEnd(const UnitTest& test){m_repeater.OnEnvironmentsTearDownEnd(test);}void OnTestIterationEnd(const UnitTest& test,int iteration){m_repeater.OnTestIterationEnd(test,iteration);}void OnTestProgramEnd(const UnitTest& test){m_repeater.OnTestProgramEnd(test);}private: void set_default_result_printer(TestEventListener* listener);void set_default_xml_generator(TestEventListener* listener);private: friend class UnitTestSource;friend class UnitTestImpl;friend class UnitTest;friend class TestInfo;friend class TestCase;friend class Test;friend class detail::DefaultGlobalTestPartResultReporter;friend class DefaultXmlGeneratorListener;friend class JunitXmlGeneratorListener;friend class DefaultResultPrintListener;template<typename T,typename ::std::string(*GetXmlPath)()>friend class detail::StderrXmlGeneratorListenerBase;TestEventRepeater m_repeater;TestEventListener* m_default_result_printer;TestEventListener* m_default_xml_generator;};}namespace iutest{inline TestEventListener* TestEventRepeater::Release(TestEventListener* listener){ListenerContainer::iterator it=::std::find(m_listeners.begin(),m_listeners.end(),listener);if(it==m_listeners.end()){return 0;}m_listeners.erase(it);return listener;}inline void TestEventRepeater::OnTestProgramStart(const UnitTest& test){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestProgramStart(test);}}inline void TestEventRepeater::OnTestIterationStart(const UnitTest& test,int iteration){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestIterationStart(test,iteration);}}inline void TestEventRepeater::OnEnvironmentsSetUpStart(const UnitTest& test){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnEnvironmentsSetUpStart(test);}}inline void TestEventRepeater::OnEnvironmentsSetUpEnd(const UnitTest& test){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnEnvironmentsSetUpEnd(test);}}inline void TestEventRepeater::OnTestCaseStart(const TestCase& test_case){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestCaseStart(test_case);}}inline void TestEventRepeater::OnTestStart(const TestInfo& test_info){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestStart(test_info);}}inline void TestEventRepeater::OnTestPartResult(const TestPartResult& test_part_result){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestPartResult(test_part_result);}}inline void TestEventRepeater::OnTestRecordProperty(const TestProperty& test_property){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnTestRecordProperty(test_property);}}inline void TestEventRepeater::OnTestEnd(const TestInfo& test_info){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnTestEnd(test_info);}}inline void TestEventRepeater::OnTestCaseEnd(const TestCase& test_case){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnTestCaseEnd(test_case);}}inline void TestEventRepeater::OnEnvironmentsTearDownStart(const UnitTest& test){for(ListenerContainer::iterator it=m_listeners.begin(),end=m_listeners.end();it!=end;++it){(*it)->OnEnvironmentsTearDownStart(test);}}inline void TestEventRepeater::OnEnvironmentsTearDownEnd(const UnitTest& test){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnEnvironmentsTearDownEnd(test);}}inline void TestEventRepeater::OnTestIterationEnd(const UnitTest& test,int iteration){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnTestIterationEnd(test,iteration);}}inline void TestEventRepeater::OnTestProgramEnd(const UnitTest& test){for(ListenerContainer::reverse_iterator it=m_listeners.rbegin(),end=m_listeners.rend();it!=end;++it){(*it)->OnTestProgramEnd(test);}}inline void TestEventListeners::set_default_result_printer(TestEventListener* listener){delete Release(m_default_result_printer);if(listener!=0){Append(listener);}m_default_result_printer=listener;}inline void TestEventListeners::set_default_xml_generator(TestEventListener* listener){delete Release(m_default_xml_generator);if(listener!=0){Append(listener);}m_default_xml_generator=listener;}} | |
#define IUTEST_FLAG(name) II_FLAG(name) | |
#define II_FLAG(name) TestEnv::name() | |
namespace iutest{inline ::std::string EnvironmentString(const char* name){::std::string var;detail::GetEnvironmentVariable(name,var);return var;}class Environment{public: virtual ~Environment(){Release();}virtual void SetUp(){}virtual void TearDown(){}private: void Release();private: struct should_be_SetUp{};virtual should_be_SetUp* Setup() IUTEST_CXX_FINAL{return 0;}};class TestFlag{public: class ScopedGuard{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(ScopedGuard);int m_test_flags;public: ScopedGuard(){m_test_flags=TestFlag::GetInstance().m_test_flags;}~ScopedGuard(){TestFlag::GetInstance().m_test_flags=m_test_flags;}};public: enum Kind{SHUFFLE_TESTS=1,RUN_DISABLED_TESTS=2,FILTERING_TESTS=4,BREAK_ON_FAILURE=0x10,THROW_ON_FAILURE=0x40,WARNING_INTO_ERROR=0x80,CONSOLE_COLOR_ON=0x100,CONSOLE_COLOR_OFF=0x200,CONSOLE_COLOR_ANSI=0x400,PRINT_TIME=0x1000,FILELOCATION_STYLE_MSVC=0x2000,VERBOSE=0x4000,CATCH_EXCEPTION_EACH=0x10000,CATCH_EXCEPTION_GLOBAL=0x20000,CATCH_EXCEPTION=0x30000,SHOW_HELP=0x1000000,SHOW_VERSION=0x2000000,SHOW_FEATURE=0x4000000,SHOW_SPEC=0x8000000,SHOW_TESTS_LIST=0x20000000,SHOW_TESTS_LIST_WITH_WHERE= 0x40000000,SHOW_INFO_MASK=0xF000000,SHOW_MASK=0x7F000000,MASK=0x7FFFFFFF,DEFAULT=CATCH_EXCEPTION|PRINT_TIME};private: TestFlag() IUTEST_CXX_NOEXCEPT_SPEC: m_test_flags(DEFAULT){}public: static TestFlag& GetInstance(){static TestFlag flag;return flag;}public: static void SetFlag(int enable,int mask=-1){GetInstance().m_test_flags|=enable;GetInstance().m_test_flags&=mask;}static bool IsEnableFlag(int flag){return GetInstance().m_test_flags&flag?true:false;}private: template<int KIND>class Fragment{typedef Fragment<KIND> _Myt;public: Fragment() IUTEST_CXX_NOEXCEPT_SPEC{}Fragment(bool enabled){SetFlag(KIND,enabled?-1 : ~KIND);}_Myt& operator=(bool enabled){SetFlag(KIND,enabled?-1 : ~KIND);return *this;}operator bool()const{return IsEnableFlag(KIND);}};private: friend class TestEnv;int m_test_flags;};class TestPartResultReporterInterface;class TestEnv{typedef ::std::vector<Environment*> iuEnvironmentList;public: typedef TestFlag::Fragment<TestFlag::SHUFFLE_TESTS> shuffle;typedef TestFlag::Fragment<TestFlag::RUN_DISABLED_TESTS> also_run_disabled_tests;typedef TestFlag::Fragment<TestFlag::BREAK_ON_FAILURE> break_on_f;typedef TestFlag::Fragment<TestFlag::CATCH_EXCEPTION> catch_exceptions;typedef TestFlag::Fragment<TestFlag::THROW_ON_FAILURE> throw_on_f;typedef TestFlag::Fragment<TestFlag::WARNING_INTO_ERROR> warning_into_error;typedef TestFlag::Fragment<TestFlag::PRINT_TIME> print_time;typedef TestFlag::Fragment<TestFlag::SHOW_TESTS_LIST> list_tests;typedef TestFlag::Fragment<TestFlag::SHOW_TESTS_LIST_WITH_WHERE> list_tests_with_where;typedef TestFlag::Fragment<TestFlag::CATCH_EXCEPTION_EACH> catch_exceptions_each;typedef TestFlag::Fragment<TestFlag::CATCH_EXCEPTION_GLOBAL> catch_exceptions_global;typedef TestFlag::Fragment<TestFlag::FILELOCATION_STYLE_MSVC> file_location_style_msvc;typedef TestFlag::Fragment<TestFlag::VERBOSE> verbose;typedef class RandomSeedSet{public: RandomSeedSet() IUTEST_CXX_NOEXCEPT_SPEC{}RandomSeedSet(unsigned int seed){init_random(seed);}RandomSeedSet& operator=(unsigned int seed){init_random(seed);return *this;}operator unsigned int()const{return get_random_seed();}}random_seed;typedef class RepeatCountSet{public: RepeatCountSet() IUTEST_CXX_NOEXCEPT_SPEC{}RepeatCountSet(int count){set_repeat_count(count);}RepeatCountSet& operator=(int count){set_repeat_count(count);return *this;}operator int()const{return get_repeat_count();}}repeat;private: struct Variable{Variable():m_random_seed(0),m_current_random_seed(0),m_before_origin_random_seed(0),m_repeat_count(1),m_testpartresult_reporter(0){}unsigned int m_random_seed;unsigned int m_current_random_seed;unsigned int m_before_origin_random_seed;int m_repeat_count;::std::string m_output_option;::std::string m_test_filter;::std::string m_flagfile; | |
#if IUTEST_HAS_STREAM_RESULT | |
::std::string m_stream_result_to; | |
#endif | |
::std::string m_default_package_name;detail::iuRandom m_genrand;iuEnvironmentList m_environment_list;TestEventListeners m_event_listeners;TestPartResultReporterInterface* m_testpartresult_reporter;iu_stringstream m_ostream_formatter;};static Variable& get_vars(){static Variable v;return v;}public: static detail::iuRandom& genrand(){return get_vars().m_genrand;}static unsigned int get_random_seed(){return get_vars().m_random_seed;}static unsigned int current_random_seed(){return get_vars().m_current_random_seed;}static int get_repeat_count(){return get_vars().m_repeat_count;}static const char* get_output_option(){return get_vars().m_output_option.c_str();}static const char* get_default_package_name(){return get_vars().m_default_package_name.c_str();}static const char* test_filter(){return get_vars().m_test_filter.c_str();}static const char* get_flagfile(){return get_vars().m_flagfile.c_str();} | |
#if IUTEST_HAS_STREAM_RESULT | |
static const char* get_stream_result_to(){return get_vars().m_stream_result_to.c_str();} | |
#endif | |
static void global_ostream_copyfmt(iu_ostream& os){os.copyfmt(get_vars().m_ostream_formatter);}static ::std::string get_report_xml_filepath();static ::std::string get_report_junit_xml_filepath();static TestEventListeners& event_listeners(){return get_vars().m_event_listeners;}static TestPartResultReporterInterface* GetGlobalTestPartResultReporter(){return get_vars().m_testpartresult_reporter;}static void SetGlobalTestPartResultReporter(TestPartResultReporterInterface* ptr){get_vars().m_testpartresult_reporter=ptr;}static bool has_output_option(){return !get_vars().m_output_option.empty();}private: static void init_random(unsigned int seed){get_vars().m_random_seed=seed;}static void set_repeat_count(int count){get_vars().m_repeat_count=count;}static void set_test_filter(const char* str){get_vars().m_test_filter=str==0?"*":str;TestFlag::SetFlag(TestFlag::FILTERING_TESTS);}static void set_flagfile_path(const char* str){get_vars().m_flagfile=str;}static void set_flagfile(const char* str){ParseFlagFileOption(str);LoadFlagFile();} | |
#if IUTEST_HAS_STREAM_RESULT | |
static void set_stream_result_to(const char* str){get_vars().m_stream_result_to=detail::NullableString(str);} | |
#endif | |
static const char* get_color_option(){if(TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_ANSI)){return "ansi";}else if(TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_ON)){return "yes";}else if(TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_OFF)){return "no";}return "auto";}static void set_color_option(const char* str){ParseColorOption(str);}static void set_output_option(const char* str){get_vars().m_output_option=detail::NullableString(str);}static void set_default_package_name(const char* str){get_vars().m_default_package_name=detail::NullableString(str);}private: typedef const char*(*pfnOptionStringGet)();typedef void(*pfnOptionStringSet)(const char*);template<pfnOptionStringGet G,pfnOptionStringSet S>class OptionString{typedef OptionString<G,S> _Myt;typedef const _Myt& _Argt;protected: ::std::string m_option;public: friend bool operator==(const char* c_str_,_Argt rhs){return rhs.m_option==c_str_;}friend bool operator==(const ::std::string& str,_Argt rhs){return rhs.m_option==str;}friend bool operator==(_Argt lhs,const char* c_str_){return lhs.m_option==c_str_;}friend bool operator==(_Argt lhs,const ::std::string& str){return lhs.m_option==str;}friend bool operator!=(const char* c_str_,_Argt rhs){return rhs.m_option!=c_str_;}friend bool operator!=(const ::std::string& str,_Argt rhs){return rhs.m_option!=str;}friend bool operator!=(_Argt lhs,const char* c_str_){return lhs.m_option!=c_str_;}friend bool operator!=(_Argt lhs,const ::std::string& str){return lhs.m_option!=str;}operator ::std::string()const{return m_option;}public: bool empty()const{return m_option.empty();}const char* c_str()const{return m_option.c_str();}size_t length()const{return m_option.length();}public: OptionString():m_option(G()){}const _Myt& operator=(const char* c_str_){m_option=detail::NullableString(c_str_);S(c_str_);return *this;}const _Myt& operator=(const ::std::string& str){m_option=str;S(str.c_str());return *this;}};public: typedef OptionString<get_color_option,set_color_option> color;typedef OptionString<test_filter,set_test_filter> filter;typedef OptionString<get_flagfile,set_flagfile> flagfile;typedef OptionString<get_output_option,set_output_option> output; | |
#if IUTEST_HAS_STREAM_RESULT | |
typedef OptionString<get_stream_result_to,set_stream_result_to> stream_result_to; | |
#endif | |
typedef OptionString<get_default_package_name,set_default_package_name> default_package_name;typedef class OStreamFormatter:public iu_stringstream{public: OStreamFormatter(){copyfmt(get_vars().m_ostream_formatter);}virtual ~OStreamFormatter(){get_vars().m_ostream_formatter.copyfmt(*this);}}ostream_formatter;private: static iuEnvironmentList& environments(){return get_vars().m_environment_list;}public: static Environment* AddGlobalTestEnvironment(Environment* env){if(env==0){return 0;}environments().push_back(env);return env;}static Environment* ReleaseGlobalTestEnvironment(Environment* env){if(env==0){return 0;}iuEnvironmentList& list=environments();iuEnvironmentList::iterator it=::std::find(list.begin(),list.end(),env);if(it==list.end()){return 0;}list.erase(it);return env;}static ::std::string AddDefaultPackageName(const char* testcase_name);private: static void ReleaseGlobalTestEnvironment(){for(iuEnvironmentList::iterator it=environments().begin();it!=environments().end();){Environment* p=*it;it=environments().erase(it);delete p;}}public: template<typename CharType>static void ParseCommandLine(int* pargc,CharType** argv){if(argv==0){return;}int argc=*pargc;for(int i=0;i<argc;){if(ParseCommandLineElem(argv[i])){--argc;for(int k=i;k<argc;++k){CharType* tmp=argv[k];argv[k]=argv[k+1];argv[k+1]=tmp;}}else{++i;}}*pargc=argc;}template<typename CharType>static void ParseCommandLine(::std::vector< ::std::basic_string<CharType> >& argv){typedef ::std::vector< ::std::basic_string<CharType> > argv_t;for(typename argv_t::iterator it=argv.begin();it!=argv.end();){if(ParseCommandLineElem(it->c_str())){it=argv.erase(it);}else{++it;}}}static bool LoadFlagFile();private: template<typename CharType>static bool ParseCommandLineElem(CharType* argv){typedef typename detail::mbs_ptr<CharType> formatter;formatter argv_format;const char* str=argv_format.ptr(argv);return ParseCommandLineElemA(str);}static bool ParseCommandLineElemA(const char* str);static bool ParseIutestOptionCommandLineElemA(const char* str);static bool SetFlag(int enable,int mask=-1);private: static void LoadEnvironmentVariable();static void SetUp();private: static inline const char* ParseOptionSettingStr(const char* opt){const char* eq=strchr(opt,'=');if(eq==0){return 0;}return eq+1;}static bool ParseColorOption(const char* option);static bool ParseOutputOption(const char* option);static bool ParseFileLocationOption(const char* option);static bool ParseFilterOption(const char* option);static bool ParseFlagFileOption(const char* option);static bool ParseYesNoFlagCommandLine(const char* str,TestFlag::Kind flag,int def);static int ParseYesNoOption(const char* option);static bool IsYes(const char* option);static bool IsNo(const char* option);private: friend class UnitTest;};class iu_global_format_stringstream:public iu_stringstream{public: iu_global_format_stringstream(){TestEnv::global_ostream_copyfmt(*this);}explicit iu_global_format_stringstream(const char* str):iu_stringstream(str){TestEnv::global_ostream_copyfmt(*this);}explicit iu_global_format_stringstream(const ::std::string& str):iu_stringstream(str){TestEnv::global_ostream_copyfmt(*this);}};}namespace iutest{namespace detail{class IOutStream{public: virtual ~IOutStream(){}public: virtual bool Write(const void* buf,size_t size,size_t cnt)=0;public: virtual void Printf(const char* fmt,...){char buf[1024]={0};va_list va;va_start(va,fmt); | |
#ifdef __STRICT_ANSI__ | |
const int len=vsprintf(buf,fmt,va); | |
#else | |
const int len=vsnprintf(buf,sizeof(buf),fmt,va); | |
#endif | |
va_end(va);if(len>0){Write(buf,static_cast<size_t>(len),1);}}};class IInStream{public: virtual ~IInStream(){}public: virtual bool Read(void* buf,size_t size,size_t cnt)=0;virtual size_t GetSize()=0;public: virtual ::std::string ReadAll(){::std::string str;const size_t size=GetSize();if(size!=0){char* buf=new char[size+1];buf[size]='\0';if(Read(buf,size,1)){str=buf;}delete [] buf;}return str;}};class FileOutStream:public IOutStream{protected: FILE* m_fp;public: explicit FileOutStream(FILE* fp) IUTEST_CXX_NOEXCEPT_SPEC: m_fp(fp){}public: virtual bool Write(const void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{if(fwrite(buf,size,cnt,m_fp)<cnt){return false;}return true;}};}}namespace iutest{class IFile:public detail::IOutStream,public detail::IInStream{public: enum OpenFlag{OpenRead=1,OpenWrite=2,OpenAppend=3};public: virtual ~IFile(){}public: virtual bool Open(const char* filename,int mode)=0;virtual void Close()=0;};namespace detail{class IFileSystem{public: IFileSystem(){SetInstance(this);}virtual ~IFileSystem(){SetInstance(0);}public: virtual void Initialize(){}public: static IFileSystem* GetInstance(){return GetInstanceVariable().pInstance;}public: static IFile* New(){IFileSystem* fs=GetInstance();if(fs==0){return 0;}IFile* p=fs->Create();return p;}static void Free(IFile* ptr){IFileSystem* fs=GetInstance();if(fs==0){return;}fs->Delete(ptr);}static bool ReadAll(const char* filename,::std::string& dst){IFile* fp=detail::IFileSystem::New();if(fp==0){return false;}if(!fp->Open(filename,IFile::OpenRead)){detail::IFileSystem::Free(fp);return false;}dst=fp->ReadAll();detail::IFileSystem::Free(fp);return true;}private: virtual IFile* Create()=0;virtual void Delete(IFile*)=0;private: struct InstanceVariable{IFileSystem* pInstance;};static InstanceVariable& GetInstanceVariable(){static InstanceVariable v;return v;}static void SetInstance(IFileSystem* pFileSystem){GetInstanceVariable().pInstance=pFileSystem;}};}}namespace iutest{template<typename FILE>class FileSystem:public detail::IFileSystem{private: virtual IFile* Create() IUTEST_CXX_OVERRIDE{return new FILE;}virtual void Delete(IFile* ptr) IUTEST_CXX_OVERRIDE{detail::Delete<FILE>(static_cast<FILE*>(ptr));}}; | |
#if IUTEST_HAS_FOPEN | |
class StdioFile:public IFile{protected: FILE* m_fp;public: StdioFile() IUTEST_CXX_NOEXCEPT_SPEC:m_fp(0){}virtual ~StdioFile(){Close();}public: virtual bool Open(const char* filename,int mode) IUTEST_CXX_OVERRIDE{Close();switch(mode){case IFile::OpenRead: m_fp=fopen(filename,"rb");break;case IFile::OpenWrite: m_fp=fopen(filename,"wb");break;case IFile::OpenAppend: m_fp=fopen(filename,"ab");break;default: break;}return m_fp!=0;}virtual void Close() IUTEST_CXX_OVERRIDE{if(m_fp!=0){fclose(m_fp);m_fp=0;}}virtual bool Write(const void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{if(fwrite(buf,size,cnt,m_fp)<cnt){return false;}return true;}virtual bool Read(void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{if(fread(buf,size,cnt,m_fp)<cnt){return false;}return true;}virtual size_t GetSize() IUTEST_CXX_OVERRIDE{if(m_fp==0){return 0;}const long pre=ftell(m_fp);if(pre==-1){return GetSize(m_fp);}if(fseek(m_fp,0,SEEK_END)!=0){return GetSize(m_fp);}const size_t size=static_cast<size_t>(ftell(m_fp));IUTEST_UNUSED_RETURN(fseek(m_fp,pre,SEEK_SET));return size;}public: static size_t GetSize(FILE* fp){internal::posix::StatStruct st;if(internal::posix::Stat(fp,&st)!=0){return 0;}return st.st_size;}};class StdErrorFile:public StdioFile{public: StdErrorFile() IUTEST_CXX_NOEXCEPT_SPEC{}virtual ~StdErrorFile(){Close();}public: virtual bool Open(const char*,int) IUTEST_CXX_OVERRIDE{m_fp=stderr;return true;}virtual void Close() IUTEST_CXX_OVERRIDE{m_fp=0;}}; | |
#endif | |
class StringStreamFile:public IFile{public: virtual ~StringStreamFile(){Close();}public: virtual bool Open(const char*,int) IUTEST_CXX_OVERRIDE{ss.clear();return true;}virtual void Close() IUTEST_CXX_OVERRIDE{}virtual bool Write(const void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{for(size_t i=0;i<cnt;++i){ss.write(static_cast<const char*>(buf),size);}return true;}virtual bool Read(void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{char* p=static_cast<char*>(buf);for(size_t i=0;i<cnt;++i){ss.read(p,size);p+=size;}return true;}virtual size_t GetSize() IUTEST_CXX_OVERRIDE{::std::stringstream::pos_type pre=ss.tellg();ss.seekg(0,::std::ios::end);::std::stringstream::pos_type size=ss.tellg();ss.seekg(pre,::std::ios::beg);return static_cast<size_t>(size);}virtual ::std::string ReadAll() IUTEST_CXX_OVERRIDE{return ss.str();}protected: ::std::stringstream ss;};namespace detail{class NoEffectFile:public IFile{public: virtual bool Open(const char*,int) IUTEST_CXX_OVERRIDE{return true;}virtual void Close() IUTEST_CXX_OVERRIDE{}virtual bool Write(const void*,size_t,size_t) IUTEST_CXX_OVERRIDE{return true;}virtual bool Read(void*,size_t,size_t) IUTEST_CXX_OVERRIDE{return true;}virtual size_t GetSize() IUTEST_CXX_OVERRIDE{return 0;}};}}namespace iutest{inline void Environment::Release(){TestEnv::ReleaseGlobalTestEnvironment(this);}inline ::std::string TestEnv::get_report_xml_filepath(){const ::std::string& option=get_vars().m_output_option;const char spec[]="xml";const size_t length=sizeof(spec)-1;if(option.compare(0,length,spec)==0){if((option.length()> length+1)&&(option.at(length)==':')){return option.substr(length+1);}return detail::kStrings::DefaultXmlReportFileName;}return "";}inline::std::string TestEnv::get_report_junit_xml_filepath(){const ::std::string& option=get_vars().m_output_option;const char spec[]="junit";const size_t length=sizeof(spec)-1;if(option.compare(0,length,spec)==0){if((option.length()> length+1)&&(option.at(length)==':')){return option.substr(length+1);}return detail::kStrings::DefaultXmlReportFileName;}return "";}inline::std::string TestEnv::AddDefaultPackageName(const char* testcase_name){::std::string str=TestEnv::get_default_package_name();if(str.empty()){return testcase_name;}if(strchr(testcase_name,'.')!=0){return testcase_name;}str+=".";str+=testcase_name;return str;}inline bool TestEnv::ParseCommandLineElemA(const char* str){if(*str=='-'){++str;if(*str=='-'){++str;bool iuoption=false;{const char* const base_str=str;if(*str=='g'){++str;iuoption=true;}if(*str=='i' && *(str+1)=='u'){str+=2;iuoption=true;}const char option_prefix[]="test_";for(int i=0,size=sizeof(option_prefix)/sizeof(option_prefix[0])-1;i<size;++i,++str){if(*str!=option_prefix[i]){iuoption=false;str=base_str;break;}}}if(iuoption){if(ParseIutestOptionCommandLineElemA(str)){return true;}TestFlag::SetFlag(TestFlag::SHOW_HELP);}else{if(detail::IsStringEqual(str,"help")){return SetFlag(TestFlag::SHOW_HELP);}if(detail::IsStringEqual(str,"version")){return SetFlag(TestFlag::SHOW_VERSION);}if(detail::IsStringEqual(str,"feature")){return SetFlag(TestFlag::SHOW_FEATURE);}if(detail::IsStringEqual(str,"spec")){return SetFlag(TestFlag::SHOW_SPEC);}if(detail::IsStringEqual(str,"verbose")){return SetFlag(TestFlag::VERBOSE);}}}else{if(detail::IsStringEqual(str,"v")){return SetFlag(TestFlag::SHOW_VERSION);}if(detail::IsStringEqual(str,"h")|| detail::IsStringEqual(str,"?")){return SetFlag(TestFlag::SHOW_HELP);}}}return false;}inline bool TestEnv::ParseIutestOptionCommandLineElemA(const char* str){if(detail::IsStringForwardMatching(str,"output")){return ParseOutputOption(ParseOptionSettingStr(str));}if(detail::IsStringEqual(str,"list_tests")){return SetFlag(TestFlag::SHOW_TESTS_LIST);}if(detail::IsStringEqual(str,"list_tests_with_where")){return SetFlag(TestFlag::SHOW_TESTS_LIST_WITH_WHERE);}if(detail::IsStringForwardMatching(str,"color")){return ParseColorOption(ParseOptionSettingStr(str));}if(detail::IsStringEqual(str,"shuffle")){return SetFlag(TestFlag::SHUFFLE_TESTS);}if(detail::IsStringForwardMatching(str,"random_seed")){const char* opt=ParseOptionSettingStr(str);if(opt!=0){char* end=0;const long seed=strtol(opt,&end,0);init_random(static_cast<unsigned int>(seed));return true;}}if(detail::IsStringEqual(str,"also_run_disabled_tests")){return SetFlag(TestFlag::RUN_DISABLED_TESTS);}if(detail::IsStringForwardMatching(str,"break_on_f")){return ParseYesNoFlagCommandLine(str,TestFlag::BREAK_ON_FAILURE,1);}if(detail::IsStringForwardMatching(str,"catch_exceptions")){return ParseYesNoFlagCommandLine(str,TestFlag::CATCH_EXCEPTION,-1);}if(detail::IsStringForwardMatching(str,"throw_on_f")){return ParseYesNoFlagCommandLine(str,TestFlag::THROW_ON_FAILURE,1);}if(detail::IsStringForwardMatching(str,"warning_into_error")){return ParseYesNoFlagCommandLine(str,TestFlag::WARNING_INTO_ERROR,1);}if(detail::IsStringForwardMatching(str,"print_time")){return ParseYesNoFlagCommandLine(str,TestFlag::PRINT_TIME,-1);}if(detail::IsStringForwardMatching(str,"repeat")){const char* opt=ParseOptionSettingStr(str);if(opt!=0){char* end=0;const long count=strtol(opt,&end,0);set_repeat_count(static_cast<int>(count));return true;}}if(detail::IsStringForwardMatching(str,"filter")){return ParseFilterOption(ParseOptionSettingStr(str));}if(detail::IsStringForwardMatching(str,"flagfile")){return ParseFlagFileOption(ParseOptionSettingStr(str));} | |
#if IUTEST_HAS_STREAM_RESULT | |
if(detail::IsStringForwardMatching(str,"stream_result_to")){const char* opt=ParseOptionSettingStr(str);if(opt!=0){set_stream_result_to(opt);return true;}} | |
#endif | |
if(detail::IsStringForwardMatching(str,"file_location")){return ParseFileLocationOption(ParseOptionSettingStr(str));}if(detail::IsStringForwardMatching(str,"default_package_name")){const char* opt=ParseOptionSettingStr(str);if(opt!=0){set_default_package_name(opt);return true;}}return false;}inline bool TestEnv::SetFlag(int enable,int mask){TestFlag::SetFlag(enable,mask);return true;}inline void TestEnv::LoadEnvironmentVariable(){{int var=0;if(detail::GetEnvironmentInt("IUTEST_ALSO_RUN_DISABLED_TESTS",var)|| detail::GetEnvironmentInt("GTEST_ALSO_RUN_DISABLED_TESTS",var)){TestFlag::SetFlag(TestFlag::RUN_DISABLED_TESTS,var?TestFlag::MASK : ~(TestFlag::RUN_DISABLED_TESTS));}if(detail::GetEnvironmentInt("IUTEST_SHUFFLE",var)|| detail::GetEnvironmentInt("GTEST_SHUFFLE",var)){TestFlag::SetFlag(TestFlag::SHUFFLE_TESTS,var?TestFlag::MASK : ~(TestFlag::SHUFFLE_TESTS));}if(detail::GetEnvironmentInt("IUTEST_RANDOM_SEED",var)|| detail::GetEnvironmentInt("GTEST_RANDOM_SEED",var)){init_random((unsigned int)var);}if(detail::GetEnvironmentInt("IUTEST_CATCH_EXCEPTIONS",var)|| detail::GetEnvironmentInt("GTEST_CATCH_EXCEPTIONS",var)){TestFlag::SetFlag(TestFlag::CATCH_EXCEPTION,var?TestFlag::MASK : ~(TestFlag::CATCH_EXCEPTION));}if(detail::GetEnvironmentInt("IUTEST_BREAK_ON_FAILURE",var)|| detail::GetEnvironmentInt("GTEST_BREAK_ON_FAILURE",var)){TestFlag::SetFlag(TestFlag::BREAK_ON_FAILURE,var?TestFlag::MASK : ~(TestFlag::BREAK_ON_FAILURE));}if(detail::GetEnvironmentInt("IUTEST_THROW_ON_FAILURE",var)|| detail::GetEnvironmentInt("GTEST_THROW_ON_FAILURE",var)){TestFlag::SetFlag(TestFlag::THROW_ON_FAILURE,var?TestFlag::MASK : ~(TestFlag::THROW_ON_FAILURE));}if(detail::GetEnvironmentInt("IUTEST_WARNING_INTO_ERROR",var)){TestFlag::SetFlag(TestFlag::WARNING_INTO_ERROR,var?TestFlag::MASK : ~(TestFlag::WARNING_INTO_ERROR));}if(detail::GetEnvironmentInt("IUTEST_PRINT_TIME",var)|| detail::GetEnvironmentInt("GTEST_PRINT_TIME",var)){TestFlag::SetFlag(TestFlag::PRINT_TIME,var?TestFlag::MASK : ~(TestFlag::PRINT_TIME));}if(detail::GetEnvironmentInt("IUTEST_REPEAT",var)|| detail::GetEnvironmentInt("GTEST_REPEAT",var)){set_repeat_count(var);}}{char var[128]={0};if(detail::GetEnvironmentVariable("IUTEST_COLOR",var,sizeof(var))|| detail::GetEnvironmentVariable("GTEST_COLOR",var,sizeof(var))){ParseColorOption(var);}if(detail::GetEnvironmentVariable("IUTEST_FILE_LOCATION",var,sizeof(var))){ParseFileLocationOption(var);}}{char str[260+32]={0};if(detail::GetEnvironmentVariable("IUTEST_OUTPUT",str,sizeof(str))|| detail::GetEnvironmentVariable("GTEST_OUTPUT",str,sizeof(str))){ParseOutputOption(str);}else if(detail::GetEnvironmentVariable("XML_OUTPUT_FILE",str+4,sizeof(str)-4)){memcpy(str,"xml:",4);ParseOutputOption(str);}if(detail::GetEnvironmentVariable("IUTEST_FILTER",str,sizeof(str))|| detail::GetEnvironmentVariable("GTEST_FILTER",str,sizeof(str))){ParseFilterOption(str);}if(detail::GetEnvironmentVariable("IUTEST_DEFAULT_PACKAGE_NAME",str,sizeof(str))){set_default_package_name(str);} | |
#if IUTEST_HAS_STREAM_RESULT | |
if(detail::GetEnvironmentVariable("IUTEST_STREAM_RESULT_TO",str,sizeof(str))|| detail::GetEnvironmentVariable("GTEST_STREAM_RESULT_TO",str,sizeof(str))){set_stream_result_to(str);} | |
#endif | |
if(detail::GetEnvironmentVariable("IUTEST_FLAGFILE",str,sizeof(str))|| detail::GetEnvironmentVariable("GTEST_FLAGFILE",str,sizeof(str))){ParseFlagFileOption(str);}}}inline void TestEnv::SetUp(){unsigned int seed=get_random_seed();if((seed==0)||(get_vars().m_current_random_seed!=0&&TestFlag::IsEnableFlag(TestFlag::SHUFFLE_TESTS))){const unsigned int gen_seeed=detail::GetIndefiniteValue();if(get_vars().m_current_random_seed==gen_seeed|| get_vars().m_before_origin_random_seed==gen_seeed){seed=get_vars().m_current_random_seed;}seed+=gen_seeed;get_vars().m_before_origin_random_seed=gen_seeed;}get_vars().m_current_random_seed=seed;genrand().init(seed);}inline bool TestEnv::ParseColorOption(const char* option){if(option==0){return false;}if(IsYes(option)){TestFlag::SetFlag(TestFlag::CONSOLE_COLOR_ON,~(TestFlag::CONSOLE_COLOR_OFF|TestFlag::CONSOLE_COLOR_ANSI));}else if(IsNo(option)){TestFlag::SetFlag(TestFlag::CONSOLE_COLOR_OFF,~(TestFlag::CONSOLE_COLOR_ON|TestFlag::CONSOLE_COLOR_ANSI));}else if(detail::IsStringCaseEqual(option,"auto")){TestFlag::SetFlag(0,~(TestFlag::CONSOLE_COLOR_ON|TestFlag::CONSOLE_COLOR_OFF|TestFlag::CONSOLE_COLOR_ANSI));}else if(detail::IsStringCaseEqual(option,"ansi")){TestFlag::SetFlag(TestFlag::CONSOLE_COLOR_ON|TestFlag::CONSOLE_COLOR_ANSI,~TestFlag::CONSOLE_COLOR_OFF);}else{return false;}return true;}inline bool TestEnv::ParseOutputOption(const char* option){if(option==0){get_vars().m_output_option="";return false;}get_vars().m_output_option=option;return true;}inline bool TestEnv::ParseFileLocationOption(const char* option){if(option==0){return false;}if(detail::IsStringCaseEqual(option,"auto")){TestFlag::SetFlag(0,~TestFlag::FILELOCATION_STYLE_MSVC);}else if(detail::IsStringCaseEqual(option,"vs")){TestFlag::SetFlag(TestFlag::FILELOCATION_STYLE_MSVC);}else if(detail::IsStringCaseEqual(option,"gcc")){TestFlag::SetFlag(0,~TestFlag::FILELOCATION_STYLE_MSVC);}else{return false;}return true;}inline bool TestEnv::ParseFilterOption(const char* option){if(option!=0&&*option=='@'){const char* path=option+1;::std::string filter;if(!detail::IFileSystem::ReadAll(path,filter)){fprintf(stderr,"Unable to open filter file \"%s\".\n",path);fflush(stderr);return false;}detail::StringReplaceToLF(filter);filter=detail::StringRemoveComment(filter);detail::StringReplace(filter,'\n',":");set_test_filter(filter.c_str());return true;}set_test_filter(option);return true;}inline bool TestEnv::ParseFlagFileOption(const char* option){if(option==0||option[0]=='\0'){return false;}set_flagfile_path(option);return true;}inline bool TestEnv::LoadFlagFile(){const char* path=get_flagfile();if(path==0||path[0]=='\0'){return true;}::std::string flags;if(!detail::IFileSystem::ReadAll(path,flags)){fprintf(stderr,"Unable to open flag file \"%s\".\n",path);fflush(stderr);return false;}detail::StringReplaceToLF(flags);::std::vector< ::std::string>argv;detail::StringSplit(flags,'\n',argv);ParseCommandLine(argv);return true;}inline bool TestEnv::ParseYesNoFlagCommandLine(const char* str,TestFlag::Kind flag,int def){const char* option=ParseOptionSettingStr(str);const int yesno=option!=0?ParseYesNoOption(option):def;if(yesno<0){return false;}TestFlag::SetFlag(flag,yesno?TestFlag::MASK : ~(flag));return true;}inline int TestEnv::ParseYesNoOption(const char* option){if(option!=0){if(IsYes(option)){return 1;}if(IsNo(option)){return 0;}}return -1;}inline bool TestEnv::IsYes(const char* option){if(detail::IsStringCaseEqual(option,"yes")|| detail::IsStringCaseEqual(option,"y")|| detail::IsStringCaseEqual(option,"on")|| detail::IsStringCaseEqual(option,"true")|| detail::IsStringCaseEqual(option,"t")|| detail::IsStringEqual(option,"1")){return true;}return false;}inline bool TestEnv::IsNo(const char* option){if(detail::IsStringCaseEqual(option,"no")|| detail::IsStringCaseEqual(option,"n")|| detail::IsStringCaseEqual(option,"off")|| detail::IsStringCaseEqual(option,"false")|| detail::IsStringCaseEqual(option,"f")|| detail::IsStringEqual(option,"0")){return true;}return false;}}namespace iutest{namespace detail{::std::string FormatFileLocation(const char* file,int line);::std::string FormatCompilerIndependentFileLocation(const char* file,int line);class iuStreamMessage{public: iuStreamMessage(){}explicit iuStreamMessage(const char* message):m_stream(message){}iuStreamMessage(const iuStreamMessage& rhs):m_stream(rhs.GetString()){}public: ::std::string GetString()const{return m_stream.str();}public: template<typename T>iuStreamMessage& operator<<(const T& value){m_stream<<value;return *this;}template<typename T>iuStreamMessage& operator<<(T* const& value){if(value==0){m_stream<<kStrings::Null;}else{m_stream<<value;}return *this;}iuStreamMessage& operator<<(bool b){m_stream<<(b?"true" : "false");return *this;}iuStreamMessage& operator<<(char* str){append(str);return *this;}iuStreamMessage& operator<<(const char* str){append(str);return *this;}iuStreamMessage& operator<<(wchar_t* str){m_stream<<ShowWideCString(str);return *this;}iuStreamMessage& operator<<(const wchar_t* str){m_stream<<ShowWideCString(str);return *this;}iuStreamMessage& operator<<(const iuStreamMessage& message){m_stream<<message.GetString();return *this;}iuStreamMessage& operator<<(iu_basic_iomanip val){m_stream<<val;return *this;}public: void add_message(const char* str){append(str);}private: void append(const char* str);private: iuStreamMessage& operator=(const iuStreamMessage&);private: iu_global_format_stringstream m_stream;};inline iu_ostream& operator<<(iu_ostream& os,const iuStreamMessage& msg){return os<<msg.GetString();}class iuCodeMessage{::std::string m_message;const char* m_file;int m_line;public: iuCodeMessage(const char* file,int line,const char* message):m_message(message),m_file(file?file:kStrings::UnknownFile),m_line(line){}iuCodeMessage(const char* file,int line,const iuStreamMessage& message):m_message(message.GetString()),m_file(file?file:kStrings::UnknownFile),m_line(line){}public: const char* message()const{return m_message.c_str();}const char* file_name()const IUTEST_CXX_NOEXCEPT_SPEC{return m_file;}int line_number()const IUTEST_CXX_NOEXCEPT_SPEC{return m_line;}public: template<typename T>iuCodeMessage& operator<<(const T& value){m_message+=(iuStreamMessage()<<value).GetString();return *this;}public: void add_message(const ::std::string& str);public: ::std::string make_message()const;::std::string make_newline_message()const{return make_message()+"\n";}};}}namespace iutest{namespace detail{inline void iuStreamMessage::append(const char* str){if(str==0){m_stream<<kStrings::Null;}else{m_stream<<str;}}inline ::std::string iuCodeMessage::make_message()const{::std::string str=FormatFileLocation(m_file,m_line);str+=": ";str+=message();return str;}inline ::std::string FormatFileLocation(const char* file,int line){const char* const file_name=file==0?kStrings::UnknownFile:file;if(line<0){return file_name;}iu_stringstream strm;if(TestFlag::IsEnableFlag(TestFlag::FILELOCATION_STYLE_MSVC)){strm<<file_name<<"(" <<line<<")";}else{strm<<file_name<<":" <<line;}return strm.str();}inline ::std::string FormatCompilerIndependentFileLocation(const char* file,int line){const char* const file_name=file==0?kStrings::UnknownFile:file;if(line<0){return file_name;}iu_stringstream strm;strm<<file_name<<":" <<line;return strm.str();}inline void iuCodeMessage::add_message(const ::std::string& str){m_message+=str;}}namespace detail{class DefaultGlobalTestPartResultReporter;}class TestPartResultReporterInterface{public: virtual ~TestPartResultReporterInterface(){}virtual void ReportTestPartResult(const TestPartResult& result)=0;};class TestPartResult:public detail::iuCodeMessage{public: enum Type{kAssumeFailure=-3,kSkip=-2,kWarning=-1,kSuccess,kNonFatalFailure,kFatalFailure};public: TestPartResult(const char* file,int line,const char* message,Type type):detail::iuCodeMessage(file,line,message),m_type(type){}TestPartResult(const TestPartResult& rhs):detail::iuCodeMessage(rhs),m_type(rhs.m_type){}public: static bool type_is_failed(Type type) IUTEST_CXX_NOEXCEPT_SPEC{if(iutest::IUTEST_FLAG(warning_into_error)){if(type==kWarning){return true;}}return type>kSuccess;}public: bool failed()const IUTEST_CXX_NOEXCEPT_SPEC{return type_is_failed(m_type);;}bool passed()const IUTEST_CXX_NOEXCEPT_SPEC{return !failed();}bool warning()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kWarning;}bool skipped()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kSkip;}bool assume_failed()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kAssumeFailure;}bool succeeded()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kSuccess;}bool nonfatally_failed()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kNonFatalFailure;}bool fatally_failed()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type==kFatalFailure;}const char* summary()const{return message();}Type type()const IUTEST_CXX_NOEXCEPT_SPEC{return m_type;}private: Type m_type;};inline iu_ostream& operator<<(iu_ostream& os,const TestPartResult& result){return os<<result.make_message();}class TestProperty{public: TestProperty(const ::std::string& key,const ::std::string& value):m_key(key),m_value(value){}public: void SetValue(const ::std::string& value){m_value=value;}const char* key()const{return m_key.c_str();}const char* value()const{return m_value.c_str();}public: bool Validate(const char** ban_list,size_t size)const{return ValidateName(m_key,ban_list,ban_list+size);}template<typename Ite>static bool ValidateName(const ::std::string& name,Ite begin,Ite end){return ::std::find(begin,end,name)==end;}template<typename T,size_t N>static bool ValidateName(const ::std::string& name,T(&ar)[N]){return ValidateName(name,ar,ar+N);}private: friend class TestResult;::std::string m_key;::std::string m_value;};class TestResult{typedef ::std::vector<TestPartResult> TestPartResults;typedef ::std::vector<TestProperty> TestPropertys;public: TestResult():m_elapsedmsec(0){}public: bool Passed()const{return !Failed();}bool Failed()const{for(TestPartResults::const_iterator it=m_test_part_results.begin(),end=m_test_part_results.end();it!=end;++it){if(it->failed()){return true;}}return false;}bool Skipped()const{for(TestPartResults::const_iterator it=m_test_part_results.begin(),end=m_test_part_results.end();it!=end;++it){if(it->skipped()||it->assume_failed()){return Passed();}}return false;}bool HasFatalFailure()const{return HasResult(TestPartResult::kFatalFailure);}bool HasNonfatalFailure()const{return HasResult(TestPartResult::kNonFatalFailure);}bool HasAssumeFailure()const{return HasResult(TestPartResult::kAssumeFailure);}bool HasWarning()const{return HasResult(TestPartResult::kWarning);}TimeInMillisec elapsed_time()const IUTEST_CXX_NOEXCEPT_SPEC{return m_elapsedmsec;}int total_part_count()const{return static_cast<int>(m_test_part_results.size());}int test_property_count()const{return static_cast<int>(m_test_propertys.size());}const TestPartResult& GetTestPartResult(int index)const{return m_test_part_results[index];}const TestProperty& GetTestProperty(int index)const{return m_test_propertys[index];}public: int total_error_count()const{int count=0;for(TestPartResults::const_iterator it=m_test_part_results.begin(),end=m_test_part_results.end();it!=end;++it){if(it->failed()){++count;}}return count;}private: void AddTestPartResult(const TestPartResult& result){m_test_part_results.push_back(result);}void set_elapsed_time(TimeInMillisec time) IUTEST_CXX_NOEXCEPT_SPEC{m_elapsedmsec=time;}private: void RecordProperty(const TestProperty& prop){for(TestPropertys::iterator it=m_test_propertys.begin(),end=m_test_propertys.end();it!=end;++it){if(detail::IsStringEqual(it->key(),prop.key())){it->m_value=prop.m_value;return;}}m_test_propertys.push_back(prop);}void ClearResult(){m_test_part_results.clear();}void Clear(){m_test_part_results.clear();m_test_propertys.clear();m_elapsedmsec=0;}bool HasResult(TestPartResult::Type eType)const{for(TestPartResults::const_iterator it=m_test_part_results.begin(),end=m_test_part_results.end();it!=end;++it){if(it->type()==eType){return true;}}return false;}private: friend class UnitTestImpl;friend class TestInfo;friend class TestCase;friend class detail::DefaultGlobalTestPartResultReporter;TestPartResults m_test_part_results;TestPropertys m_test_propertys;TimeInMillisec m_elapsedmsec;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TestResult);};}namespace iutest{template<typename T>std::string PrintToString(const T& v);namespace detail{inline void PrintBytesInObjectTo(const unsigned char* buf,size_t size,iu_ostream* os){const size_t kMaxCount=detail::kValues::MaxPrintContainerCount;*os<<size<<"-Byte object < ";for(size_t i=0;i<size;++i){const unsigned char n=buf[i];*os<<detail::ToHex((n>>4)&0xF)<<ToHex(n&0xF)<<" ";if(i==kMaxCount){*os<<"... ";break;}}*os<<">";}namespace printer_internal{namespace formatter{template<bool convertible>struct Printer{template<typename T>static void Print(const T& value,iu_ostream* os){const unsigned char* ptr=const_cast<const unsigned char*>(reinterpret_cast<const volatile unsigned char*>(&value));const size_t size=sizeof(T);PrintBytesInObjectTo(ptr,size,os);}};template<>struct Printer<true>{template<typename T>static void Print(const T& value,iu_ostream* os){ | |
#if IUTEST_HAS_BIGGESTINT_OSTREAM | |
const BiggestInt v=value; | |
#else | |
const Int32 v=value; | |
#endif | |
*os<<v;}};}class TypeWithoutFormatter{public: template<typename T>static void PrintValue(const T& value,iu_ostream* os){formatter::Printer<iutest_type_traits::is_convertible<const T&,BiggestInt>::value>::Print(value,os);}};template<typename Elem,typename Traits,typename T>::std::basic_ostream<Elem,Traits>& operator<<(::std::basic_ostream<Elem,Traits>& os,const T& value){TypeWithoutFormatter::PrintValue(value,&os);return os;}}namespace printer_internal2{template<typename T>void DefaultPrintNonContainerTo(const T& value,iu_ostream* os){using namespace ::iutest::detail::printer_internal;*os<<value;}}template<typename T>void UniversalPrint(const T& value,iu_ostream* os);template<typename T>inline void DefaultPrintTo(IsContainerHelper::yes_t,iutest_type_traits::false_type,const T& container,iu_ostream* os){const size_t kMaxCount=kValues::MaxPrintContainerCount;size_t count=0;*os<<"{";for(typename T::const_iterator it=container.begin(),end=container.end();it!=end;++it,++count){if(count>0){*os<<",";if(count==kMaxCount){*os<<" ...";break;}}*os<<" ";UniversalPrint(*it,os);}if(count>0){*os<<" ";}*os<<"}";}template<typename T>inline void DefaultPrintTo(IsContainerHelper::no_t,iutest_type_traits::false_type,const T& value,iu_ostream* os){printer_internal2::DefaultPrintNonContainerTo(value,os);}template<typename T>inline void DefaultPtrPrintTo(T* ptr,iu_ostream* os,typename iutest_type_traits::enable_if_t<iutest_type_traits::is_convertible<T*,const void*> >::type*& = iutest_type_traits::enabler::value){*os<<ptr;}template<typename T>inline void DefaultPtrPrintTo(T* ptr,iu_ostream* os,typename iutest_type_traits::disable_if_t<iutest_type_traits::is_convertible<T*,const void*> >::type*& = iutest_type_traits::enabler::value){*os<<reinterpret_cast<const void*>(reinterpret_cast<type_least_t<8>::UInt>(ptr));}template<typename T>inline void DefaultPrintTo(IsContainerHelper::no_t,iutest_type_traits::true_type,T* ptr,iu_ostream* os){if(ptr==0){*os<<kStrings::Null;}else{DefaultPtrPrintTo<T>(ptr,os);}}template<typename T>inline void PrintTo(const T& value,iu_ostream* os){DefaultPrintTo(IsContainerHelper::IsContainer<T>(0),iutest_type_traits::is_pointer<T>(),value,os);}inline void PrintTo(bool b,iu_ostream* os){*os<<(b?"true" : "false");}inline void PrintTo(const char* c,iu_ostream* os){*os<<c;}inline void PrintTo(const ::std::string& str,iu_ostream* os){*os<<str.c_str();}template<typename T>inline void PrintTo(const floating_point<T>& f,iu_ostream* os){*os<<f.raw()<<"(0x" <<ToHexString(f.bits())<<")";}template<typename T1,typename T2>inline void PrintTo(const ::std::pair<T1,T2>& value,iu_ostream* os){*os<<"(";UniversalPrint(value.first,os);*os<<", ";UniversalPrint(value.second,os);*os<<")";}inline void PrintTo(const char value,iu_ostream* os){if(value==0){*os<<"\\0";}else if(value<0x20){*os<<static_cast<int>(value);}else{*os<<"\'" <<value<<"\'";}}inline void PrintTo(const wchar_t value,iu_ostream* os){if(value==0){*os<<"\\0";}else if(value<0x20){*os<<static_cast<int>(value);}else{*os<<"\'" <<value<<"\'";}}inline void PrintTo(const unsigned char value,iu_ostream* os){*os<<static_cast<unsigned int>(value);} | |
#if IUTEST_HAS_NULLPTR | |
inline void PrintTo(const ::std::nullptr_t&,iu_ostream* os){*os<<"nullptr";} | |
#endif | |
#if IUTEST_HAS_TUPLE | |
template<typename T,int I,int SIZE>inline void PrintTupleElemTo(const T& t,iu_ostream* os,typename iutest_type_traits::enable_if<I==0,void>::type*& = iutest_type_traits::enabler::value){(void)(t);(void)(os);}template<typename T,int I,int SIZE>inline void PrintTupleElemTo(const T& t,iu_ostream* os,typename iutest_type_traits::enable_if<I==1,void>::type*& = iutest_type_traits::enabler::value){PrintTo(tuples::get<SIZE-I>(t),os);}template<typename T,int I,int SIZE>inline void PrintTupleElemTo(const T& t,iu_ostream* os,typename iutest_type_traits::enable_if<(I&(~1))!=0,void>::type*& = iutest_type_traits::enabler::value){PrintTo(tuples::get<SIZE-I>(t),os);*os<<", ";PrintTupleElemTo<T,I-1,SIZE>(t,os);}template<typename T>inline void PrintTupleTo(const T& t,iu_ostream* os){*os<<"(";PrintTupleElemTo<T,tuples::tuple_size<T>::value,tuples::tuple_size<T>::value>(t,os);*os<<")";} | |
#if IUTEST_HAS_VARIADIC_TEMPLATES&&IUTEST_HAS_TUPLE | |
template<typename ...Args>inline void PrintTo(const tuples::tuple<Args...>& t,iu_ostream* os){PrintTupleTo(t,os);} | |
#else | |
#define II_D_T_PT(n) template<IUTEST_PP_ENUM_PARAMS(n,typename A)>inline void PrintTo(const tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,A)>& t,iu_ostream* os){PrintTupleTo(t,os);} | |
inline void PrintTo(const tuples::tuple<>& t,iu_ostream* os){PrintTupleTo(t,os);}II_D_T_PT(1)II_D_T_PT(2)II_D_T_PT(3)II_D_T_PT(4)II_D_T_PT(5)II_D_T_PT(6)II_D_T_PT(7)II_D_T_PT(8)II_D_T_PT(9) | |
#undef II_D_T_PT | |
#endif | |
#endif | |
template<typename T>inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalTersePrint(const T& value,iu_ostream* os){UniversalPrint(value,os);}inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalTersePrint(const char* str,iu_ostream* os){if(str==0){*os<<kStrings::Null;}else{UniversalPrint(::std::string(str),os);}}inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalTersePrint(const wchar_t* str,iu_ostream* os){UniversalPrint(detail::ShowWideCString(str),os);} | |
#if IUTEST_HAS_CHAR16_T | |
inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalTersePrint(const char16_t* str,iu_ostream* os){UniversalPrint(detail::ShowWideCString(str),os);} | |
#endif | |
#if IUTEST_HAS_CHAR32_T&&(IUTEST_HAS_CXX_HDR_CUCHAR||IUTEST_HAS_CXX_HDR_CODECVT) | |
inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalTersePrint(const char32_t* str,iu_ostream* os){UniversalPrint(detail::ShowWideCString(str),os);} | |
#endif | |
template<typename T>inline void PrintRawArrayTo(const T* a,size_t cnt,iu_ostream* os){UniversalPrint<T>(a[0],os);for(size_t i=1;i<cnt;++i){*os<<", ";UniversalPrint<T>(a[i],os);}}template<typename T>inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalPrintArray(const T* begin,size_t N,iu_ostream* os){if(N==0){*os<<"{}";}else{*os<<"{";const size_t kThreshold=kValues::PrintArrayThreshold;const size_t kChunksize=kValues::PrintArrayChunksize;if(N<=kThreshold){PrintRawArrayTo(begin,N,os);}else{PrintRawArrayTo(begin,kChunksize,os);*os<<", ..., ";PrintRawArrayTo(begin+N - kChunksize,kChunksize,os);}*os<<"}";}}inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalPrintArray(const char* begin,size_t N,iu_ostream* os){(void)(N);UniversalTersePrint(begin,os);}inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalPrintArray(const wchar_t* begin,size_t N,iu_ostream* os){(void)(N);UniversalTersePrint(begin,os);}template<typename T>inline void IUTEST_ATTRIBUTE_UNUSED_ UniversalPrintTo(const T& value,iu_ostream* os){PrintTo(value,os);}template<typename T>class iuUniversalPrinter{public: static void Print(const T& value,iu_ostream* os){UniversalPrintTo(value,os);}};template<typename T,size_t SIZE>class iuUniversalPrinter<T[SIZE]>{public: static void Print(const T(&a)[SIZE],iu_ostream* os){UniversalPrintArray(a,SIZE,os);}};template<typename T>inline void UniversalPrint(const T& value,iu_ostream* os){iuUniversalPrinter<T>::Print(value,os);}}template<typename T>inline ::std::string PrintToString(const T& v){iu_global_format_stringstream strm;detail::UniversalTersePrint(v,&strm);return strm.str();} | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename T>inline ::std::string PrintToStrings(const char* separate,const T& v){(void)(separate);return PrintToString(v);}template<typename T,typename ...Args>inline ::std::string PrintToStrings(const char* separate,const T& v,Args... args){::std::string str=PrintToString(v);str+=separate;str+=PrintToStrings(separate,args...);return str;} | |
#endif | |
}namespace iutest{namespace detail{template<typename TN>class iu_list_node{typedef TN *value_ptr;typedef iu_list_node<TN> _Myt;public: value_ptr next;value_ptr prev;protected: iu_list_node() IUTEST_CXX_NOEXCEPT_SPEC:next(0),prev(0){}};template<typename NODE,typename NODE_PTR,typename NODE_REF>class iu_list_iterator{typedef iu_list_iterator<NODE,NODE_PTR,NODE_REF> _Myt;public: typedef NODE value_type;typedef NODE_PTR value_ptr;typedef NODE_REF value_ref;typedef value_ptr pointer;typedef value_ref reference;typedef int distance_type;typedef int difference_type;public: value_ptr m_node;public: iu_list_iterator(value_ptr p=0) IUTEST_CXX_NOEXCEPT_SPEC:m_node(p){}iu_list_iterator(const iu_list_iterator& rhs) IUTEST_CXX_NOEXCEPT_SPEC:m_node(rhs.m_node){}iu_list_iterator& operator=(const iu_list_iterator& rhs) IUTEST_CXX_NOEXCEPT_SPEC{m_node=rhs.m_node;return *this;}public: bool operator==(const _Myt& it)const{return this->m_node==it.m_node;}bool operator!=(const _Myt& it)const{return this->m_node!=it.m_node;}_Myt& operator++(){m_node=m_node->next;return *this;}_Myt& operator--(){m_node=m_node->prev;return *this;}value_ptr operator->() IUTEST_CXX_NOEXCEPT_SPEC{return ptr();}value_ref operator *() IUTEST_CXX_NOEXCEPT_SPEC{return *m_node;}value_ptr ptr()const IUTEST_CXX_NOEXCEPT_SPEC{return m_node;}operator value_ptr(){return ptr();}_Myt operator+(int n){if(n==0){return *this;}if(n>0){return this->operator +(static_cast<unsigned int>(n));}_Myt ret(*this);n=-n;for(int i=0;i<n && ret.m_node!=0;++i){ret.m_node=ret.m_node->prev;}return ret;}_Myt operator+(unsigned int n){_Myt ret(*this);for(unsigned int i=0;i<n && ret.m_node!=0;++i){ret.m_node=ret.m_node->next;}return ret;}};template<typename NODE>class iu_list{typedef NODE *node_ptr;typedef iu_list<NODE> _Myt;protected: node_ptr m_node;public: typedef iu_list_iterator<NODE,NODE*,NODE&> iterator;typedef iu_list_iterator<NODE,const NODE*,const NODE&> const_iterator;public: explicit iu_list(node_ptr p=0) IUTEST_CXX_NOEXCEPT_SPEC:m_node(p){}public: unsigned int count()const IUTEST_CXX_NOEXCEPT_SPEC{unsigned int cnt=0;node_ptr cur=m_node;while(cur!=0){++cnt;cur=cur->next;}return cnt;}unsigned int size()const IUTEST_CXX_NOEXCEPT_SPEC{return count();}public: void sort_insert(node_ptr p){if(p==0){return;}if(m_node==0){m_node=p;return;}if(*p<*m_node){node_ptr next=m_node;m_node=p;p->next=next;next->prev=p;}else{node_ptr prev=m_node;node_ptr cur=m_node->next;while(cur!=0){if(*p<*cur){break;}prev=cur;cur=prev->next;}prev->next=p;p->prev=prev;p->next=cur;if(cur!=0){cur->prev=p;}}}void push_back(node_ptr p){if(p==0){return;}if(m_node==0){m_node=p;return;}node_ptr prev=m_node;node_ptr cur=m_node->next;while(cur!=0){if(prev==p){return;}prev=cur;cur=prev->next;}prev->next=p;p->prev=prev;}void erase(node_ptr p){if(p==0){return;}if(m_node==0){return;}if(p->prev==0){m_node=p->next;if(m_node!=0){m_node->prev=0;}}else{p->prev->next=p->next;if(p->next!=0){p->next->prev=p->prev;}}p->prev=p->next=0;}void erase(iterator it){erase(it.ptr());}public: template<typename F>void shuffle(F& r){for(unsigned int i=2,n=count();i<n;++i){swap(begin()+(i-2),begin()+r(i) % i);}}public: void swap(iterator a,iterator b){if(a==b){return;}if(a.ptr()==m_node){m_node=b.ptr();}else if(b.ptr()==m_node){m_node=a.ptr();}if(a->next==b.ptr()){a->next=b->next;b->next=a.ptr();b->prev=a->prev;a->prev=b.ptr();if(a->next!=0){a->next->prev=a.ptr();}if(b->prev!=0){b->prev->next=b.ptr();}}else if(a->prev==b.ptr()){b->next=a->next;a->next=b.ptr();a->prev=b->prev;b->prev=a.ptr();if(b->next!=0){b->next->prev=b.ptr();}if(a->prev!=0){a->prev->next=a.ptr();}}else{node_ptr tmp=a->next;a->next=b->next;b->next=tmp;tmp=a->prev;a->prev=b->prev;b->prev=tmp;if(a->next!=0){a->next->prev=a.ptr();}if(b->next!=0){b->next->prev=b.ptr();}if(a->prev!=0){a->prev->next=a.ptr();}if(b->prev!=0){b->prev->next=b.ptr();}}}public: iterator begin() IUTEST_CXX_NOEXCEPT_SPEC{return m_node;}iterator end() IUTEST_CXX_NOEXCEPT_SPEC{return iterator(0);}const_iterator begin()const IUTEST_CXX_NOEXCEPT_SPEC{return m_node;}const_iterator end()const IUTEST_CXX_NOEXCEPT_SPEC{return const_iterator(0);}public: struct EqualOp{template<typename T>bool operator()(const T* lhs,const T* rhs)const{return *lhs==*rhs;}};public: template<typename FUNC>node_ptr find(node_ptr p,FUNC& f)const{node_ptr cur=m_node;while(cur!=0){if(f(cur,p)){return cur;}cur=cur->next;}return 0;}template<typename FUNC>node_ptr find(FUNC& f)const{node_ptr cur=m_node;while(cur!=0){if(f(cur)){return cur;}cur=cur->next;}return 0;}public: node_ptr operator->(){return m_node;}node_ptr operator&(){return m_node;}NODE& operator *(){return *m_node;}node_ptr operator [](int index)const{node_ptr cur=m_node;for(int i=0;i<index;++i){cur=cur->next;if(cur==0){break;}}return cur;}bool operator==(node_ptr p)const{return m_node==p;}bool operator!=(node_ptr p)const{return m_node!=p;}private:};IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_NOEXCEPT_TPYE()template<typename It>void RandomShuffle(It begin,It last,iuRandom& r){r.shuffle(begin,last);}template<typename Node,typename Fn>void RandomShuffle(iu_list<Node>& list,Fn& r){list.shuffle(r);}template<typename Node,typename Fn>void RandomShuffle(::std::vector<Node>& list,Fn& r){RandomShuffle(list.begin(),list.end(),r);}template<typename Node,typename Fn>Node* FindList(const iu_list<Node>& list,Fn& f){return list.find(f);}template<typename Node,typename Fn>Node FindList(const ::std::vector<Node>& list,Fn& f){for(typename ::std::vector<Node>::const_iterator it=list.begin(),end=list.end();it!=end;++it){if(f(*it)){return *it;}}return 0;}template<typename Node,typename Fn>int CountIf(const iu_list<Node>& list,Fn f){int count=0;for(typename iu_list<Node>::const_iterator it=list.begin(),end=list.end();it!=end;++it){if(f(it)){++count;}}return count;}template<typename Node,typename Fn>int SumOverList(const iu_list<Node>& list,Fn f){int count=0;for(typename iu_list<Node>::const_iterator it=list.begin(),end=list.end();it!=end;++it){count+=((*it).*f)();}return count;}template<typename Node,typename Fn>int CountIfOverList(const iu_list<Node>& list,Fn f){int count=0;for(typename iu_list<Node>::const_iterator it=list.begin(),end=list.end();it!=end;++it){if(((*it).*f)()){++count;}}return count;}template<typename Node,typename Fn>bool AnyOverList(const iu_list<Node>& list,Fn f){for(typename iu_list<Node>::const_iterator it=list.begin(),end=list.end();it!=end;++it){if(((*it).*f)()){return true;}}return false;}IUTEST_PRAGMA_WARN_POP()}}namespace iutest{typedef detail::iuStreamMessage Message;template<typename T>inline ::std::string StreamableToString(const T& value){return(Message()<<value).GetString();}namespace detail{void DefaultReportTestPartResult(const TestPartResult& test_part_result);}class AssertionResult{public: AssertionResult(bool result):m_result(result){}AssertionResult(const AssertionResult& rhs):m_message(rhs.m_message),m_result(rhs.m_result){}bool failed()const IUTEST_CXX_NOEXCEPT_SPEC{return !m_result;}bool passed()const IUTEST_CXX_NOEXCEPT_SPEC{return m_result;}const char* message()const{return m_message.c_str();}const char* failure_message()const{return message();}IUTEST_CXX_EXPLICIT_CONVERSION operator bool()const{return m_result;}public: template<typename T>AssertionResult& operator<<(const T& value){Message msg;msg<<value;m_message+=msg.GetString();return *this;}public: AssertionResult operator !()const{return AssertionResult(failed())<<message();}AssertionResult operator&&(const AssertionResult& rhs)const{return AssertionResult(m_result&&rhs.passed())<<message()<<" && " <<rhs.message();}AssertionResult operator||(const AssertionResult& rhs)const{return AssertionResult(m_result||rhs.passed())<<message()<<" || " <<rhs.message();}public: static AssertionResult Success(){return AssertionResult(true);}static AssertionResult Failure(){return AssertionResult(false);}template<typename T>static AssertionResult Is(const T& b){return AssertionResult(b?true:false);}static AssertionResult Is(const AssertionResult& ar){return AssertionResult(ar);}private: IUTEST_PP_DISALLOW_ASSIGN(AssertionResult);::std::string m_message;bool m_result;}; | |
#if IUTEST_HAS_ASSERTION_RETURN | |
template<typename R>struct AssertionReturnType{R value;AssertionReturnType(){}AssertionReturnType(const R& v):value(v){}};template<>struct AssertionReturnType<void>{AssertionReturnType(){}};template<typename T>inline AssertionReturnType<T> AssertionReturn(const T& ret){return AssertionReturnType<T>(ret);}inline AssertionReturnType<void> AssertionReturn(void){return AssertionReturnType<void>();} | |
#endif | |
class AssertionHelper{public: AssertionHelper(const char* file,int line,const char* message,TestPartResult::Type type):m_part_result(file,line,message,type){}AssertionHelper(const char* file,int line,const ::std::string& message,TestPartResult::Type type):m_part_result(file,line,message.c_str(),type){}public: class ScopedMessage:public detail::iu_list_node<ScopedMessage>,public detail::iuCodeMessage{public: ScopedMessage(const detail::iuCodeMessage& msg):detail::iuCodeMessage(msg){ScopedTrace::GetInstance().list.push_back(this);}~ScopedMessage(){ScopedTrace::GetInstance().list.erase(this);}};private: class ScopedTrace{public: typedef detail::iu_list<ScopedMessage> msg_list;msg_list list;static ScopedTrace& GetInstance(){static ScopedTrace inst;return inst;}public: void append_message(TestPartResult& part_result){if(list.count()){part_result.add_message("\niutest trace:");for(msg_list::iterator it=list.begin(),end=list.end();it!=end;++it){part_result.add_message("\n");part_result.add_message(it->make_message().c_str());}}}}; | |
#if IUTEST_HAS_ASSERTION_RETURN | |
private: template<typename R>struct ReturnTypedFixed; | |
#endif | |
public: class Fixed:public Message{public: template<typename T>Fixed& operator<<(T val){Message::operator<<(val);return *this;}Fixed& operator<<(iu_basic_iomanip val){Message::operator<<(val);return *this;} | |
#if IUTEST_HAS_ASSERTION_RETURN | |
Fixed& operator<<(const AssertionReturnType<void>&){return *this;}template<typename R>ReturnTypedFixed<R> operator<<(const AssertionReturnType<R>& ret){return ReturnTypedFixed<R>(*this,ret);} | |
#endif | |
}; | |
#if IUTEST_HAS_ASSERTION_RETURN | |
private: template<typename R>struct ReturnTypedFixed{Fixed fixed;AssertionReturnType<R> ret;ReturnTypedFixed(const Fixed& f,const AssertionReturnType<R>& r):fixed(f),ret(r){}}; | |
#endif | |
public: void operator=(const Fixed& fixed){OnFixed(fixed); | |
#if IUTEST_HAS_EXCEPTIONS&&IUTEST_USE_THROW_ON_ASSERTION_FAILURE | |
{switch(m_part_result.type()){case TestPartResult::kSkip: case TestPartResult::kAssumeFailure: case TestPartResult::kFatalFailure: throw m_part_result.type();default: break;}} | |
#endif | |
} | |
#if IUTEST_HAS_ASSERTION_RETURN | |
template<typename R>R operator=(const ReturnTypedFixed<R>& fixed){this->operator=(fixed.fixed);return fixed.ret.value;} | |
#endif | |
private: void OnFixed(const Fixed& fixed){const ::std::string append_message=fixed.GetString();if(!append_message.empty()){m_part_result.add_message(" " + append_message);}ScopedTrace::GetInstance().append_message(m_part_result);if(TestEnv::GetGlobalTestPartResultReporter()!=0){TestEnv::GetGlobalTestPartResultReporter()->ReportTestPartResult(m_part_result);}else{detail::DefaultReportTestPartResult(m_part_result);}if(m_part_result.failed()&& TestFlag::IsEnableFlag(iutest::TestFlag::BREAK_ON_FAILURE)){IUTEST_BREAK();}}private: friend class TestInfo;TestPartResult m_part_result;private: IUTEST_PP_DISALLOW_MOVE_AND_COPY_AND_ASSIGN(AssertionHelper);};}namespace iutest{inline AssertionResult AssertionSuccess(){return AssertionResult::Success();}inline AssertionResult AssertionFailure(){return AssertionResult::Failure();}inline const char* GetAssertionResultMessage(const AssertionResult& ar){return ar.message();}namespace internal{template<typename T1,typename T2>inline ::std::string FormatForComparisonFailureMessage(const T1& value,const T2&){return PrintToString(value);}inline ::std::string GetBooleanAssertionFailureMessage(const AssertionResult& ar,const char* expr,const char* actual,const char* expected){::std::string str="error: Value of: ";str+=expr;str+="\n Actual: ";str+=actual;if(!detail::IsEmpty(ar.message())){str+=" (";str+=ar.message();str+=")";}str+="\nExpected: ";str+=expected;return str;}inline AssertionResult EqFailure(const char* expected_expression,const char* actual_expression,const ::std::string& expected,const ::std::string& actual,bool ignoring_case=false){iu_global_format_stringstream strm;strm<<"error: Value of " <<actual_expression<< "\n Actual: " <<actual<< "\nExpected: " <<expected_expression;if(ignoring_case){strm<<" (ignoring case)";}if(!detail::IsStringEqual(expected_expression,expected.c_str())){strm<<"\nWhich is: " <<expected;}return AssertionFailure()<<strm.str();}template<typename T1,typename T2>inline AssertionResult CmpHelperOpFailure(const char* expr1,const char* expr2,const char* op,const T1& val1,const T2& val2){return AssertionFailure()<<"error: Expected: " <<expr1<<" " <<op<<" " <<expr2<< "\n Actual: " <<FormatForComparisonFailureMessage(val1,val2)<< " vs " <<FormatForComparisonFailureMessage(val2,val1);} | |
#define II_D_C_H_I_(op_name,op,type1,type2) inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelper##op_name(const char* expr1,const char* expr2,type1 val1,type2 val2){if(val1 op val2){return AssertionSuccess();}else{return CmpHelperOpFailure(expr1,expr2,#op,val1,val2);}} | |
#define II_D_C_H_(op_name,op) template<typename T1,typename T2> II_D_C_H_I_(op_name,op,const T1&,const T2&) II_D_C_H_I_(op_name,op,BiggestInt,BiggestInt) | |
II_D_C_H_(NE,!=)II_D_C_H_(LE,<=)II_D_C_H_(LT,<)II_D_C_H_(GE,>=)II_D_C_H_(GT,>) | |
#undef II_D_C_H_I_ | |
#undef II_D_C_H_ | |
template<bool IsNullLiteral>class NullHelper{public: template<typename T>static AssertionResult CompareEq(const char* expr,const T* val){if(0==val){return AssertionSuccess();}return AssertionFailure()<<"error: Value of " <<expr<< "\n Actual: " <<val<< "\nExpected: 0";}template<typename T>static AssertionResult CompareNe(const char* expr,const T* val){if(0!=val){return AssertionSuccess();}return AssertionFailure()<<"error: Value of " <<expr<< "\n Actual: 0\nExpected: not 0";}};template<>class NullHelper<true>{public: static AssertionResult CompareEq(const char*,void*){return AssertionSuccess();}static AssertionResult CompareNe(const char* expr,void*){return AssertionFailure()<<"error: Value of " <<expr<< "\n Actual: 0\nExpected: not 0";}};template<typename T1,typename T2>inline AssertionResult CmpHelperSame(const char* exp_s,const char* act_s,const T1& expected,const T2& actual){if(&expected==&actual){return AssertionSuccess();}return AssertionFailure()<<"error: Expected: &(" <<exp_s<<") == &(" <<act_s<< ")\n Actual: " <<FormatForComparisonFailureMessage(&expected,&actual)<< " vs " <<FormatForComparisonFailureMessage(&actual,&expected);}template<typename T1,typename T2>inline AssertionResult CmpHelperEQ(const char* exp_s,const char* act_s,const T1& expected,const T2& actual){(void)(exp_s);IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE()if(actual==expected){return AssertionSuccess();}return EqFailure(exp_s,act_s,FormatForComparisonFailureMessage(expected,actual),FormatForComparisonFailureMessage(actual,expected));IUTEST_PRAGMA_WARN_POP()}template<typename T>inline AssertionResult CmpHelperMemCmpEQ(const char* exp_s,const char* act_s,const T& expected,const T& actual){(void)(exp_s);IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE()if(memcmp(&actual,&expected,sizeof(T))==0){return AssertionSuccess();}return EqFailure(exp_s,act_s,FormatForComparisonFailureMessage(expected,actual),FormatForComparisonFailureMessage(actual,expected));IUTEST_PRAGMA_WARN_POP()}template<typename T>inline AssertionResult CmpHelperMemCmpNE(const char* exp_s,const char* act_s,const T& expected,const T& actual){IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE()if(memcmp(&actual,&expected,sizeof(T))!=0){return AssertionSuccess();}return AssertionFailure()<<"error: Expected: " <<exp_s<<" != " <<act_s<< "\n Actual: " <<FormatForComparisonFailureMessage(expected,actual);IUTEST_PRAGMA_WARN_POP()}template<bool IsNullLiteral>class EqHelper{ | |
#if IUTEST_HAS_ASSERTION_NOEQUALTO_OBJECT | |
template<typename T,bool has_equal_to_operator>struct CmpHelper{static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelperEQ(expr1,expr2,val1,val2);}};template<typename T>struct CmpHelper<T,false>{static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelperMemCmpEQ(expr1,expr2,val1,val2);}};public: template<typename T>static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelper<T,detail::has_equal_to<T>::value>::Compare(expr1,expr2,val1,val2);} | |
#endif | |
public: template<typename T1,typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,const T1& val1,const T2& val2){return CmpHelperEQ(expr1,expr2,val1,val2);}};template<>class EqHelper<true>{public:template<typename T1,typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,const T1& val1,const T2& val2,typename detail::enable_if< !detail::is_pointer<T2>::value,void>::type*& = detail::enabler::value){return CmpHelperEQ(expr1,expr2,val1,val2);}template<typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,detail::IsNullLiteralHelper::Object* val1,T2* val2){(void)(val1);return CmpHelperEQ(expr1,expr2,static_cast<T2*>(0),val2);}};template<bool IsNullLiteral>class NeHelper{ | |
#if IUTEST_HAS_ASSERTION_NOEQUALTO_OBJECT | |
template<typename T,bool has_not_equal_to_operator>struct CmpHelper{static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelperNE(expr1,expr2,val1,val2);}};template<typename T>struct CmpHelper<T,false>{static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelperMemCmpNE(expr1,expr2,val1,val2);}};public: template<typename T>static AssertionResult Compare(const char* expr1,const char* expr2,const T& val1,const T& val2){return CmpHelper<T,detail::has_not_equal_to<T>::value>::Compare(expr1,expr2,val1,val2);} | |
#endif | |
public: template<typename T1,typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,const T1& val1,const T2& val2){return CmpHelperNE(expr1,expr2,val1,val2);}};template<>class NeHelper<true>{public:template<typename T1,typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,const T1& val1,const T2& val2,typename detail::enable_if< !detail::is_pointer<T2>::value,void>::type*& = detail::enabler::value){return CmpHelperNE(expr1,expr2,val1,val2);}template<typename T2>static AssertionResult Compare(const char* expr1,const char* expr2,detail::IsNullLiteralHelper::Object* val1,T2* val2){(void)(val1);return CmpHelperNE(expr1,expr2,static_cast<T2*>(0),val2);}};template<typename RawType>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperNearFloatingPoint(const char* expr1,const char* expr2,const char* absc,RawType val1,RawType val2,RawType abs_v){RawType diff=val1>val2?val1-val2:val2-val1;if(diff<abs_v){return AssertionSuccess();}floating_point<RawType> f1(diff),f2(abs_v);if(f1.AlmostEquals(f2)){return AssertionSuccess();}return AssertionFailure()<<"error: Value of: abs(" <<expr1<<" - " <<expr2<<") <= " <<absc<< "\n Actual: abs(" <<val1<<" - " <<val2<<") : " <<diff<< "\nExpected: " <<FormatForComparisonFailureMessage(abs_v,diff);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ DoubleNearPredFormat(const char* expr1,const char* expr2,const char* absc,double val1,double val2,double abs_v){return CmpHelperNearFloatingPoint(expr1,expr2,absc,val1,val2,abs_v);}template<typename T,typename A>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperNear(const char* expr1,const char* expr2,const char* absc,const T& val1,const T& val2,const A& abs_v){T diff=val1>val2?val1-val2:val2-val1;if(diff<=abs_v){return AssertionSuccess();}return AssertionFailure()<<"error: Value of: abs(" <<expr1<<" - " <<expr2<<") <= " <<absc<< "\n Actual: abs(" <<val1<<" - " <<val2<<") : " <<diff<< "\nExpected: " <<FormatForComparisonFailureMessage(abs_v,diff);}template<typename A>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperNear(const char* expr1,const char* expr2,const char* absc,double val1,double val2,const A& abs_v){return CmpHelperNearFloatingPoint<double>(expr1,expr2,absc,val1,val2,static_cast<double>(abs_v));}template<typename A>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperNear(const char* expr1,const char* expr2,const char* absc,float val1,float val2,const A& abs_v){return CmpHelperNearFloatingPoint<float>(expr1,expr2,absc,val1,val2,static_cast<float>(abs_v));}namespace StrEqHelper{inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const char* val1,const char* val2){if(val1==0||val2==0){return val1==val2;}return strcmp(val1,val2)==0;}inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const wchar_t* val1,const wchar_t* val2){if(val1==0||val2==0){return val1==val2;}return wcscmp(val1,val2)==0;}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return val1==val2;}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return val2==val1;}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return val1==val2;} | |
#if IUTEST_HAS_CHAR16_T | |
inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const char16_t* val1,const char16_t* val2){if(val1==0||val2==0){return val1==val2;}::std::u16string v1=val1;return Compare(v1,val2);} | |
#endif | |
#if IUTEST_HAS_CHAR32_T | |
inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const char32_t* val1,const char32_t* val2){if(val1==0||val2==0){return val1==val2;}::std::u32string v1=val1;return Compare(v1,val2);} | |
#endif | |
template<typename T1,typename T2>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* expr1,const char* expr2,const T1& val1,const T2& val2){if(Compare(val1,val2)){return AssertionSuccess();}return EqFailure(expr1,expr2,detail::ShowStringQuoted(FormatForComparisonFailureMessage(val1,val2)),detail::ShowStringQuoted(FormatForComparisonFailureMessage(val2,val1)));}}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const char* val1,const char* val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const wchar_t* val1,const wchar_t* val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);} | |
#if IUTEST_HAS_CHAR16_T | |
inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const char16_t* val1,const char16_t* val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);} | |
#endif | |
#if IUTEST_HAS_CHAR32_T | |
inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTREQ(const char* expr1,const char* expr2,const char32_t* val1,const char32_t* val2){return StrEqHelper::Assertion(expr1,expr2,val1,val2);} | |
#endif | |
namespace StrNeHelper{template<typename T1,typename T2>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const T1& val1,const T2& val2){return !StrEqHelper::Compare(val1,val2);}template<typename T1,typename T2>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* expr1,const char* expr2,const T1& val1,const T2& val2){if(Compare(val1,val2)){return AssertionSuccess();}return AssertionFailure()<<"error: Expected: " <<expr1<<" != " <<expr2<< "\n Actual: " <<detail::ShowStringQuoted(FormatForComparisonFailureMessage(val2,val1))<< " vs " <<detail::ShowStringQuoted(FormatForComparisonFailureMessage(val1,val2));}}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const char* val1,const char* val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const wchar_t* val1,const wchar_t* val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);} | |
#if IUTEST_HAS_CHAR16_T | |
inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const char16_t* val1,const char16_t* val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);} | |
#endif | |
#if IUTEST_HAS_CHAR32_T | |
inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNE(const char* expr1,const char* expr2,const char32_t* val1,const char32_t* val2){return StrNeHelper::Assertion(expr1,expr2,val1,val2);} | |
#endif | |
namespace StrCaseEqHelper{inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const char* val1,const char* val2){if(val1==0||val2==0){return val1==val2;}return detail::iu_stricmp(val1,val2)==0;}inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const wchar_t* val1,const wchar_t* val2){if(val1==0||val2==0){return val1==val2;}return detail::iu_wcsicmp(val1,val2)==0;}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return Compare(val1.c_str(),val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return Compare(val1,val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return Compare(val1.c_str(),val2);}template<typename T1,typename T2>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* expr1,const char* expr2,const T1& val1,const T2& val2){if(Compare(val1,val2)){return AssertionSuccess();}return EqFailure(expr1,expr2,detail::ShowStringQuoted(FormatForComparisonFailureMessage(val1,val2)),detail::ShowStringQuoted(FormatForComparisonFailureMessage(val2,val1)),true);}}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASEEQ(const char* expr1,const char* expr2,const char* val1,const char* val2){return StrCaseEqHelper::Assertion(expr1,expr2,val1,val2);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASEEQ(const char* expr1,const char* expr2,const wchar_t* val1,const wchar_t* val2){return StrCaseEqHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASEEQ(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return CmpHelperSTRCASEEQ(expr1,expr2,val1.c_str(),val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASEEQ(const char* expr1,const char* expr2,const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return CmpHelperSTRCASEEQ(expr1,expr2,val1,val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASEEQ(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return CmpHelperSTRCASEEQ(expr1,expr2,val1.c_str(),val2);}namespace StrCaseNeHelper{template<typename T1,typename T2>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const T1& val1,const T2& val2){return !StrCaseEqHelper::Compare(val1,val2);}template<typename T1,typename T2>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* expr1,const char* expr2,const T1& val1,const T2& val2){if(Compare(val1,val2)){return AssertionSuccess();}return AssertionFailure()<<"error: Expected: " <<expr1<<" != " <<expr2<<" (ignoring case)"<< "\n Actual: " <<detail::ShowStringQuoted(FormatForComparisonFailureMessage(val2,val1))<< " vs " <<detail::ShowStringQuoted(FormatForComparisonFailureMessage(val1,val2));}}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASENE(const char* expr1,const char* expr2,const char* val1,const char* val2){return StrCaseNeHelper::Assertion(expr1,expr2,val1,val2);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASENE(const char* expr1,const char* expr2,const wchar_t* val1,const wchar_t* val2){return StrCaseNeHelper::Assertion(expr1,expr2,val1,val2);}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASENE(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return CmpHelperSTRCASENE(expr1,expr2,val1.c_str(),val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASENE(const char* expr1,const char* expr2,const Elem* val1,const ::std::basic_string<Elem,Traits,Ax>& val2){return CmpHelperSTRCASENE(expr1,expr2,val1,val2.c_str());}template<typename Elem,typename Traits,typename Ax>inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRCASENE(const char* expr1,const char* expr2,const ::std::basic_string<Elem,Traits,Ax>& val1,const Elem* val2){return CmpHelperSTRCASENE(expr1,expr2,val1.c_str(),val2);}template<typename RawType>static AssertionResult CmpHelperFloatingPointEQ(const char* expr1,const char* expr2,RawType val1,RawType val2){floating_point<RawType> f1(val1),f2(val2);if(f1.AlmostEquals(f2)){return AssertionSuccess();}return EqFailure(expr1,expr2,detail::ShowStringQuoted(FormatForComparisonFailureMessage(f1,f2)),detail::ShowStringQuoted(FormatForComparisonFailureMessage(f2,f1)));}template<typename RawType>static AssertionResult CmpHelperFloatingPointLE(const char* expr1,const char* expr2,RawType val1,RawType val2){if(val1<val2){return AssertionSuccess();}floating_point<RawType> f1(val1),f2(val2);if(f1.AlmostEquals(f2)){return AssertionSuccess();}return EqFailure(expr1,expr2,detail::ShowStringQuoted(FormatForComparisonFailureMessage(f1,f2)),detail::ShowStringQuoted(FormatForComparisonFailureMessage(f2,f1)));}}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ FloatLE(const char* expr1,const char* expr2,float val1,float val2){return internal::CmpHelperFloatingPointLE<float>(expr1,expr2,val1,val2);}inline AssertionResult IUTEST_ATTRIBUTE_UNUSED_ DoubleLE(const char* expr1,const char* expr2,double val1,double val2){return internal::CmpHelperFloatingPointLE<double>(expr1,expr2,val1,val2);}} | |
#define IUTEST_ASSERT_PRED1(pred,v1) IUTEST_PRED1_(pred,v1,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED1(pred,v1) IUTEST_PRED1_(pred,v1,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED1(pred,v1) IUTEST_PRED1_(pred,v1,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED1(pred,v1) IUTEST_PRED1_(pred,v1,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED_FORMAT1(pd_fmt,v1) IUTEST_PRED_FORMAT1_(pd_fmt,v1,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED_FORMAT1(pd_fmt,v1) IUTEST_PRED_FORMAT1_(pd_fmt,v1,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED_FORMAT1(pd_fmt,v1) IUTEST_PRED_FORMAT1_(pd_fmt,v1,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED_FORMAT1(pd_fmt,v1) IUTEST_PRED_FORMAT1_(pd_fmt,v1,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED2(pred,v1,v2) IUTEST_PRED2_(pred,v1,v2,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED2(pred,v1,v2) IUTEST_PRED2_(pred,v1,v2,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED2(pred,v1,v2) IUTEST_PRED2_(pred,v1,v2,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED2(pred,v1,v2) IUTEST_PRED2_(pred,v1,v2,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED_FORMAT2(pd_fmt,v1,v2) IUTEST_PRED_FORMAT2_(pd_fmt,v1,v2,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED_FORMAT2(pd_fmt,v1,v2) IUTEST_PRED_FORMAT2_(pd_fmt,v1,v2,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED_FORMAT2(pd_fmt,v1,v2) IUTEST_PRED_FORMAT2_(pd_fmt,v1,v2,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED_FORMAT2(pd_fmt,v1,v2) IUTEST_PRED_FORMAT2_(pd_fmt,v1,v2,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED3(pred,v1,v2,v3) IUTEST_PRED3_(pred,v1,v2,v3,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED3(pred,v1,v2,v3) IUTEST_PRED3_(pred,v1,v2,v3,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED3(pred,v1,v2,v3) IUTEST_PRED3_(pred,v1,v2,v3,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED3(pred,v1,v2,v3) IUTEST_PRED3_(pred,v1,v2,v3,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED_FORMAT3(pd_fmt,v1,v2,v3) IUTEST_PRED_FORMAT3_(pd_fmt,v1,v2,v3,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED_FORMAT3(pd_fmt,v1,v2,v3) IUTEST_PRED_FORMAT3_(pd_fmt,v1,v2,v3,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED_FORMAT3(pd_fmt,v1,v2,v3) IUTEST_PRED_FORMAT3_(pd_fmt,v1,v2,v3,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED_FORMAT3(pd_fmt,v1,v2,v3) IUTEST_PRED_FORMAT3_(pd_fmt,v1,v2,v3,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED4(pred,v1,v2,v3,v4) IUTEST_PRED4_(pred,v1,v2,v3,v4,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED4(pred,v1,v2,v3,v4) IUTEST_PRED4_(pred,v1,v2,v3,v4,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED4(pred,v1,v2,v3,v4) IUTEST_PRED4_(pred,v1,v2,v3,v4,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED4(pred,v1,v2,v3,v4) IUTEST_PRED4_(pred,v1,v2,v3,v4,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED_FORMAT4(pd_fmt,v1,v2,v3,v4) IUTEST_PRED_FORMAT4_(pd_fmt,v1,v2,v3,v4,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED_FORMAT4(pd_fmt,v1,v2,v3,v4) IUTEST_PRED_FORMAT4_(pd_fmt,v1,v2,v3,v4,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED_FORMAT4(pd_fmt,v1,v2,v3,v4) IUTEST_PRED_FORMAT4_(pd_fmt,v1,v2,v3,v4,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED_FORMAT4(pd_fmt,v1,v2,v3,v4) IUTEST_PRED_FORMAT4_(pd_fmt,v1,v2,v3,v4,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED5(pred,v1,v2,v3,v4,v5) IUTEST_PRED5_(pred,v1,v2,v3,v4,v5,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED5(pred,v1,v2,v3,v4,v5) IUTEST_PRED5_(pred,v1,v2,v3,v4,v5,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED5(pred,v1,v2,v3,v4,v5) IUTEST_PRED5_(pred,v1,v2,v3,v4,v5,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED5(pred,v1,v2,v3,v4,v5) IUTEST_PRED5_(pred,v1,v2,v3,v4,v5,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_ASSERT_PRED_FORMAT5(pd_fmt,v1,v2,v3,v4,v5) IUTEST_PRED_FORMAT5_(pd_fmt,v1,v2,v3,v4,v5,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_PRED_FORMAT5(pd_fmt,v1,v2,v3,v4,v5) IUTEST_PRED_FORMAT5_(pd_fmt,v1,v2,v3,v4,v5,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_PRED_FORMAT5(pd_fmt,v1,v2,v3,v4,v5) IUTEST_PRED_FORMAT5_(pd_fmt,v1,v2,v3,v4,v5,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_PRED_FORMAT5(pd_fmt,v1,v2,v3,v4,v5) IUTEST_PRED_FORMAT5_(pd_fmt,v1,v2,v3,v4,v5,IUTEST_ASSUME_FAILURE) | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#define IUTEST_ASSERT_PRED(pred,...) IUTEST_PRED_(pred,IUTEST_ASSERT_FAILURE,__VA_ARGS__) | |
#define IUTEST_EXPECT_PRED(pred,...) IUTEST_PRED_(pred,IUTEST_EXPECT_FAILURE,__VA_ARGS__) | |
#define IUTEST_INFORM_PRED(pred,...) IUTEST_PRED_(pred,IUTEST_INFORM_FAILURE,__VA_ARGS__) | |
#define IUTEST_ASSUME_PRED(pred,...) IUTEST_PRED_(pred,IUTEST_ASSUME_FAILURE,__VA_ARGS__) | |
#endif | |
#define IUTEST_ASSERT_PRED_FORMAT(pd_fmt,...) IUTEST_PRED_FORMAT_(pd_fmt,IUTEST_ASSERT_FAILURE,__VA_ARGS__) | |
#define IUTEST_EXPECT_PRED_FORMAT(pd_fmt,...) IUTEST_PRED_FORMAT_(pd_fmt,IUTEST_EXPECT_FAILURE,__VA_ARGS__) | |
#define IUTEST_INFORM_PRED_FORMAT(pd_fmt,...) IUTEST_PRED_FORMAT_(pd_fmt,IUTEST_INFORM_FAILURE,__VA_ARGS__) | |
#define IUTEST_ASSUME_PRED_FORMAT(pd_fmt,...) IUTEST_PRED_FORMAT_(pd_fmt,IUTEST_ASSUME_FAILURE,__VA_ARGS__) | |
#define IUTEST_ASSERT_THROW_PRED_FORMAT2(pd_fmt,st,exp_e,exp_e_v) IUTEST_THROW_PRED_FORMAT2_(pd_fmt,st,exp_e,exp_e_v,IUTEST_ASSERT_FAILURE) | |
#define IUTEST_EXPECT_THROW_PRED_FORMAT2(pd_fmt,st,exp_e,exp_e_v) IUTEST_THROW_PRED_FORMAT2_(pd_fmt,st,exp_e,exp_e_v,IUTEST_EXPECT_FAILURE) | |
#define IUTEST_INFORM_THROW_PRED_FORMAT2(pd_fmt,st,exp_e,exp_e_v) IUTEST_THROW_PRED_FORMAT2_(pd_fmt,st,exp_e,exp_e_v,IUTEST_INFORM_FAILURE) | |
#define IUTEST_ASSUME_THROW_PRED_FORMAT2(pd_fmt,st,exp_e,exp_e_v) IUTEST_THROW_PRED_FORMAT2_(pd_fmt,st,exp_e,exp_e_v,IUTEST_ASSUME_FAILURE) | |
#define IUTEST_PRED1_(pred,v1,on_f) IUTEST_TEST_ASSERT_(::iutest::AssertPred1Helper(#pred,#v1,pred,v1),on_f) | |
#define IUTEST_PRED_FORMAT1_(pd_fmt,v1,on_f) IUTEST_TEST_ASSERT_(pd_fmt(#v1,v1),on_f) | |
#define IUTEST_PRED2_(pred,v1,v2,on_f) IUTEST_TEST_ASSERT_(::iutest::AssertPred2Helper(#pred,#v1,#v2,pred,v1,v2),on_f) | |
#define IUTEST_PRED_FORMAT2_(pd_fmt,v1,v2,on_f) IUTEST_TEST_ASSERT_(pd_fmt(#v1,#v2,v1,v2),on_f) | |
#define IUTEST_PRED3_(pred,v1,v2,v3,on_f) IUTEST_TEST_ASSERT_(::iutest::AssertPred3Helper(#pred,#v1,#v2,#v3,pred,v1,v2,v3),on_f) | |
#define IUTEST_PRED_FORMAT3_(pd_fmt,v1,v2,v3,on_f) IUTEST_TEST_ASSERT_(pd_fmt(#v1,#v2,#v3,v1,v2,v3),on_f) | |
#define IUTEST_PRED4_(pred,v1,v2,v3,v4,on_f) IUTEST_TEST_ASSERT_(::iutest::AssertPred4Helper(#pred,#v1,#v2,#v3,#v4,pred,v1,v2,v3,v4),on_f) | |
#define IUTEST_PRED_FORMAT4_(pd_fmt,v1,v2,v3,v4,on_f) IUTEST_TEST_ASSERT_(pd_fmt(#v1,#v2,#v3,#v4,v1,v2,v3,v4),on_f) | |
#define IUTEST_PRED5_(pred,v1,v2,v3,v4,v5,on_f) IUTEST_TEST_ASSERT_(::iutest::AssertPred5Helper(#pred,#v1,#v2,#v3,#v4,#v5,pred,v1,v2,v3,v4,v5),on_f) | |
#define IUTEST_PRED_FORMAT5_(pd_fmt,v1,v2,v3,v4,v5,on_f) IUTEST_TEST_ASSERT_(pd_fmt(#v1,#v2,#v3,#v4,#v5,v1,v2,v3,v4,v5),on_f) | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
#define IUTEST_PRED_(pred,on_f,...) IUTEST_TEST_ASSERT_(::iutest::AssertPredVariadicHelper(#pred,#__VA_ARGS__,pred,__VA_ARGS__),on_f) | |
#endif | |
#define IUTEST_PRED_FORMAT_(pd_fmt,on_f,...) IUTEST_TEST_ASSERT_(pd_fmt(#__VA_ARGS__,__VA_ARGS__),on_f) | |
#define IUTEST_THROW_PRED_FORMAT2_(pd_fmt,st,exp_e,exp_e_v,on_f) IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f,pd_fmt) | |
namespace iutest{template<typename PRED,typename T1>AssertionResult AssertPred1Helper(const char* pred_str,const char* expr1,PRED pred,T1 val1){if((*pred)(val1)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"(" <<expr1<<") evaluates to false, where "<< "\n" <<expr1<<" : " <<val1;}template<typename PRED,typename T1,typename T2>AssertionResult AssertPred2Helper(const char* pred_str,const char* expr1,const char* expr2,PRED pred,T1 val1,T2 val2){if((*pred)(val1,val2)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"("<<expr1<<", " <<expr2<< ") evaluates to false, where "<< "\n" <<expr1<<" : " <<val1<< "\n" <<expr2<<" : " <<val2;}template<typename PRED,typename T1,typename T2,typename T3>AssertionResult AssertPred3Helper(const char* pred_str,const char* expr1,const char* expr2,const char* expr3,PRED pred,T1 val1,T2 val2,T3 val3){if((*pred)(val1,val2,val3)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"("<<expr1<<", " <<expr2<<", " <<expr3<< ") evaluates to false, where "<< "\n" <<expr1<<" : " <<val1<< "\n" <<expr2<<" : " <<val2<< "\n" <<expr3<<" : " <<val3;}template<typename PRED,typename T1,typename T2,typename T3,typename T4>AssertionResult AssertPred4Helper(const char* pred_str,const char* expr1,const char* expr2,const char* expr3,const char* expr4,PRED pred,T1 val1,T2 val2,T3 val3,T4 val4){if((*pred)(val1,val2,val3,val4)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"("<<expr1<<", " <<expr2<<", " <<expr3<<", " <<expr4<< ") evaluates to false, where "<< "\n" <<expr1<<" : " <<val1<< "\n" <<expr2<<" : " <<val2<< "\n" <<expr3<<" : " <<val3<< "\n" <<expr4<<" : " <<val4;}template<typename PRED,typename T1,typename T2,typename T3,typename T4,typename T5>AssertionResult AssertPred5Helper(const char* pred_str,const char* expr1,const char* expr2,const char* expr3,const char* expr4,const char* expr5,PRED pred,T1 val1,T2 val2,T3 val3,T4 val4,T5 val5){if((*pred)(val1,val2,val3,val4,val5)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"("<<expr1<<", " <<expr2<<", " <<expr3<<", " <<expr4<<", " <<expr5<< ") evaluates to false, where "<< "\n" <<expr1<<" : " <<val1<< "\n" <<expr2<<" : " <<val2<< "\n" <<expr3<<" : " <<val3<< "\n" <<expr4<<" : " <<val4<< "\n" <<expr5<<" : " <<val5;} | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename PRED,typename ...Args>AssertionResult AssertPredVariadicHelper(const char* pred_str,const char* params,PRED pred,Args... args){if((*pred)(args...)){return AssertionSuccess();}return AssertionFailure()<<"error: " <<pred_str<<"("<<params<<") evaluates to false, where "<< "\n" <<PrintToStrings("\n",args...);} | |
#endif | |
} | |
#define IUTEST_PACKAGE(name) II_PKG_(name) | |
#if IUTEST_HAS_PACKAGE | |
#define IUTEST_CONCAT_PACKAGE_(tcn_) II_CC_PKG_I(tcn_) | |
#define II_CC_PKG_I(tcn_) iuTest_ConcatTestCaseName(iuTest_GetTestCasePackageName(static_cast<iuTest_TestCasePackage*>(0)) ,#tcn_) | |
#define IUTEST_GET_PACKAGENAME_() iuTest_GetTestCasePackageName(static_cast<iuTest_TestCasePackage*>(0)) | |
#define II_PKG_C_NS_(name) class iuTest_TestCasePackage;namespace{const int IUTEST_PP_CAT(k_iutest_package_##name##_dummy_,IUTEST_PP_UNIQUEID) IUTEST_ATTRIBUTE_UNUSED_=::iutest::detail::package_name_server< iuTest_TestCasePackage>::setname(iuTest_GetTestCaseParentPackageName(static_cast<iuTest_TestCaseParentPackage*>(0))+#name ".");} | |
#define II_PKG_P_NS_(name) class iuTest_TestCaseParentPackage;namespace{const int IUTEST_PP_CAT(k_iutest_package_##name##_parent_dummy_,IUTEST_PP_UNIQUEID) IUTEST_ATTRIBUTE_UNUSED_=::iutest::detail::package_name_server<iuTest_TestCaseParentPackage> ::setname(iuTest_GetTestCasePackageName(static_cast<iuTest_TestCasePackage*>(0)));} | |
#define II_PKG_(name) namespace name{II_PKG_C_NS_(name) II_PKG_P_NS_(name) }namespace name | |
#else | |
#define IUTEST_CONCAT_PACKAGE_(tcn_) II_CC_PKG_I(tcn_) | |
#define II_CC_PKG_I(tcn_) #tcn_ | |
#define II_PKG_(name) namespace name | |
#define IUTEST_GET_PACKAGENAME_() "" | |
#endif | |
#if IUTEST_HAS_PACKAGE | |
class iuTest_TestCasePackage;class iuTest_TestCaseParentPackage;namespace iutest{namespace detail{template<typename T>class package_name_server{static ::std::string& getname_(){static ::std::string s;return s;}public: static ::std::string getname(){return getname_();}static int setname(const ::std::string& s){::std::string& name=getname_();if(name.empty()){name=s;}return 0;}};}}template<typename T>::std::string iuTest_GetTestCasePackageName(T*){return ::iutest::detail::package_name_server<T>::getname();}template<typename T>::std::string iuTest_GetTestCaseParentPackageName(T*){return ::iutest::detail::package_name_server<T>::getname();}inline ::std::string IUTEST_ATTRIBUTE_UNUSED_ iuTest_ConcatTestCaseName(const ::std::string& package,const char* testcase_name){return package+testcase_name;} | |
#endif | |
#define IUTEST_TEST_CLASS_NAME_(testcase_,tn_) II_T_C_N_I(II_TO_VN_(testcase_),II_TO_VN_(tn_)) | |
#define II_T_C_N_I(testcase_,tn_) II_T_C_N_I_(testcase_,tn_) | |
#define II_T_C_N_I_(testcase_,tn_) iu_##testcase_##_x_iutest_x_##tn_##_Test | |
#define IUTEST_TEST_INSTANCE_NAME_(testcase_,tn_) II_T_INST_N_I(II_TO_VN_(testcase_),II_TO_VN_(tn_)) | |
#define II_T_INST_N_I(testcase_,tn_) II_T_INST_N_I_(testcase_,tn_) | |
#define II_T_INST_N_I_(testcase_,tn_) s_##testcase_##_x_iutest_x_##tn_##_Instance | |
#if IUTEST_HAS_TESTNAME_ALIAS | |
#define II_TO_VN_(name_) II_TO_VN_I((II_A_TN_PP_##name_,name_,dummy_)) | |
#define II_TO_VN_I(tuple_) IUTEST_PP_EXPAND(II_TO_VN_I_ tuple_) | |
#define II_TO_VN_I_(dummy,name_,...) name_ | |
#define II_TO_N_(name_) II_TO_N_I((II_A_TN_PP_##name_,name_,name_,dummy_)) | |
#define II_TO_N_I(tuple_) IUTEST_PP_EXPAND(II_TO_N_I_ tuple_) | |
#define II_TO_N_I_(dummy,dummy_2,name_,...) name_ | |
#define II_TO_N_STR_(name_) IUTEST_PP_TOSTRING(II_TO_N_(name_)) | |
#define II_A_TN_PP_UNPAREN_(...) __VA_ARGS__ | |
#define IUTEST_ALIAS_TESTNAME_(name_) UNPAREN_(dummy,IUTEST_PP_CAT(iutest_japanese_var,__LINE__),name_) | |
#define IUTEST_ALIAS_TESTNAME_F_(name_,var_) UNPAREN_(dummy,var_,name_) | |
#else | |
#define II_TO_VN_(name_) name_ | |
#define II_TO_N_(name_) name_ | |
#define II_TO_N_STR_(name_) #name_ | |
#endif | |
#define II_CK_TF_I(tf_) IUTEST_STATIC_ASSERT_MSG((! ::iutest::detail::is_useful_testfixture<void(int(tf_))>::value) ,#tf_ " is fixture class, mistake the IUTEST_F?"); | |
#define II_CK_TF_(tf_) II_CK_TF_I(tf_) | |
#define II_CK_TF(tf_) II_CK_TF_(II_TO_VN_(tf_)) | |
#ifndef IUTEST_TEST_STRICT_ | |
#if IUTEST_CHECK_STRICT | |
#define IUTEST_TEST_STRICT_(testcase_,tn_,parent_class_,type_id_) II_CK_TF(testcase_) IUTEST_TEST_(testcase_,tn_,parent_class_,type_id_) | |
#else | |
#define IUTEST_TEST_STRICT_ IUTEST_TEST_ | |
#endif | |
#endif | |
#define II_TEST_F_(macro,tf_,tn_) macro(tf_,tn_,II_TO_VN_(tf_) ,::iutest::internal::GetTypeId<II_TO_VN_(tf_)>()) | |
#if IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define II_TEST_F_A_(macro,tf_,tn_) II_TEST_F_(macro,IUTEST_PP_IF(IUTEST_PP_IS_BEGIN_PARENS(tf_) ,IUTEST_ALIAS_TESTNAME_F_,IUTEST_PP_EMPTY()) tf_,tn_) | |
#define IUTEST_TEST_F_(tf_,tn_) II_TEST_F_A_(IUTEST_TEST_,tf_,tn_) | |
#else | |
#define IUTEST_TEST_F_(tf_,tn_) II_TEST_F_(IUTEST_TEST_,tf_,tn_) | |
#endif | |
#define IUTEST_TEST_(testcase_,tn_,parent_class_,type_id_) class IUTEST_TEST_CLASS_NAME_(testcase_,tn_):public parent_class_{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(IUTEST_TEST_CLASS_NAME_(testcase_,tn_));public: IUTEST_TEST_CLASS_NAME_(testcase_,tn_)(){}protected: virtual void Body() IUTEST_CXX_OVERRIDE;};::iutest::detail::TestInstance<IUTEST_TEST_CLASS_NAME_(testcase_,tn_)> IUTEST_TEST_INSTANCE_NAME_(testcase_,tn_)(IUTEST_CONCAT_PACKAGE_(II_TO_N_(testcase_)),II_TO_N_STR_(tn_) ,type_id_,parent_class_::SetUpTestCase,parent_class_::TearDownTestCase);void IUTEST_TEST_CLASS_NAME_(testcase_,tn_)::Body() | |
#define IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_) II_PMZ_T_C_N_I(II_TO_VN_(testcase_),II_TO_VN_(tn_)) | |
#define II_PMZ_T_C_N_I(testcase_,tn_) II_PMZ_T_C_N_I_(testcase_,tn_) | |
#define II_PMZ_T_C_N_I_(testcase_,tn_) IUTEST_PP_CAT(IUTEST_PP_CAT(iu_##testcase_##_x_Test_,tn_),__LINE__) | |
#define II_TEST_PMZ_(testcase_,tn_,method_,parent_class_,type_id_,...) class IUTEST_TEST_CLASS_NAME_(testcase_,tn_);class IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_):public parent_class_{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_));public: IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_)(){}static ::std::string MakeTestName(){return ::iutest::detail::MakeIndexTestName(II_TO_N_STR_(tn_),::iutest::detail::GetTypeUniqueCounter< IUTEST_TEST_CLASS_NAME_(testcase_,tn_)>());}protected: virtual void Body() IUTEST_CXX_OVERRIDE{method_(__VA_ARGS__);}};::iutest::detail::TestInstance<IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_)> IUTEST_PP_CAT(IUTEST_TEST_INSTANCE_NAME_(testcase_,tn_),__LINE__)(IUTEST_CONCAT_PACKAGE_(II_TO_N_(testcase_)) ,IUTEST_PMZ_TEST_CLASS_NAME_(testcase_,tn_)::MakeTestName().c_str() ,#__VA_ARGS__,type_id_,parent_class_::SetUpTestCase,parent_class_::TearDownTestCase) | |
#define IUTEST_CLASS_INITIALIZE(methodName) static void SetUpTestCase(){methodName();}static void methodName() | |
#define IUTEST_CLASS_CLEANUP(methodName) static void TearDownTestCase(){methodName();}static void methodName() | |
#define IUTEST_METHOD_INITIALIZE(methodName) virtual void SetUp() IUTEST_CXX_OVERRIDE { methodName();} void methodName() | |
#define IUTEST_METHOD_CLEANUP(methodName) virtual void TearDown() IUTEST_CXX_OVERRIDE { methodName();} void methodName() | |
#define IUTEST_MESSAGE_AT(file_,line_,msg_,result_type_) ::iutest::AssertionHelper(file_,line_,msg_,result_type_)=::iutest::AssertionHelper::Fixed() | |
#define IUTEST_MESSAGE(msg_,result_type_) IUTEST_MESSAGE_AT(__FILE__,__LINE__,msg_,result_type_) | |
#define IUTEST_ASSERT_FAILURE(msg) IUTEST_ASSERT_FAILURE_AT(msg,__FILE__,__LINE__) | |
#define IUTEST_ASSERT_FAILURE_AT(msg,file,line) return IUTEST_MESSAGE_AT(file,line,msg,::iutest::TestPartResult::kFatalFailure) | |
#define IUTEST_EXPECT_FAILURE(msg) IUTEST_EXPECT_FAILURE_AT(msg,__FILE__,__LINE__) | |
#define IUTEST_EXPECT_FAILURE_AT(msg,file,line) IUTEST_MESSAGE_AT(file,line,msg,::iutest::TestPartResult::kNonFatalFailure) | |
#define IUTEST_INFORM_FAILURE(msg) IUTEST_INFORM_FAILURE_AT(msg,__FILE__,__LINE__) | |
#define IUTEST_INFORM_FAILURE_AT(msg,file,line) IUTEST_MESSAGE_AT(file,line,msg,::iutest::TestPartResult::kWarning) | |
#define IUTEST_ASSUME_FAILURE(msg) IUTEST_ASSUME_FAILURE_AT(msg,__FILE__,__LINE__) | |
#define IUTEST_ASSUME_FAILURE_AT(msg,file,line) return IUTEST_MESSAGE_AT(file,line,msg,::iutest::TestPartResult::kAssumeFailure) | |
#define IUTEST_SKIP_MESSAGE(msg) IUTEST_SKIP_MESSAGE_AT(msg,__FILE__,__LINE__) | |
#define IUTEST_SKIP_MESSAGE_AT(msg,file,line) return IUTEST_MESSAGE_AT(file,line,msg,::iutest::TestPartResult::kSkip) | |
#ifndef IUTEST_MAKE_ASSERTIONRESULT_ | |
#define IUTEST_MAKE_ASSERTIONRESULT_(ar) ar | |
#endif | |
#define IUTEST_TEST_ASSERT_(expression,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(const ::iutest::AssertionResult iutest_ar=IUTEST_MAKE_ASSERTIONRESULT_(expression)) ;else on_f(iutest_ar.message()) | |
#if IUTEST_HAS_EXCEPTIONS | |
#if IUTEST_HAS_CATCH_SEH_EXCEPTION_ASSERTION | |
#define II_SEH_THROUGH(st) ::iutest::detail::seh_passthrough([&](){(void)(st);}) | |
#else | |
#define II_SEH_THROUGH(st) (void)(st) | |
#endif | |
#define IUTEST_TEST_THROW_(st,exp_e,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(const char* msg=""){try{IUTEST_SUPPRESS_UNREACHABLE_CODE_WARNING(II_SEH_THROUGH(st));msg="\nExpected: " #st " throws an exception of type " #exp_e ".\n Actual: it throws nothing.";goto IUTEST_PP_CAT(iutest_label_throw,__LINE__);}catch(exp_e const&){}catch(...){msg="\nExpected: " #st " throws an exception of type " #exp_e ".\n Actual: it throws a different type.";goto IUTEST_PP_CAT(iutest_label_throw,__LINE__);}}else IUTEST_PP_CAT(iutest_label_throw,__LINE__):on_f(msg) | |
#define IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f,pd_fmt) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::AssertionResult iutest_ar=::iutest::AssertionSuccess()){try{IUTEST_SUPPRESS_UNREACHABLE_CODE_WARNING(II_SEH_THROUGH(st));iutest_ar<<"\nExpected: " #st " throws an exception of type " #exp_e ".\n Actual: it throws nothing.";goto IUTEST_PP_CAT(iutest_label_throw_value,__LINE__);}catch(exp_e const& e){if(const ::iutest::AssertionResult ar = pd_fmt("e",#exp_e_v,e,exp_e_v)){}else{iutest_ar<<"\nExpected: " #st " throws an exception of value\n" <<ar.message();goto IUTEST_PP_CAT(iutest_label_throw_value,__LINE__);}}catch(...){iutest_ar<<"\nExpected: " #st " throws an exception of type " #exp_e ".\n Actual: it throws a different type.";goto IUTEST_PP_CAT(iutest_label_throw_value,__LINE__);}}else IUTEST_PP_CAT(iutest_label_throw_value,__LINE__):on_f(iutest_ar.message()) | |
#define IUTEST_TEST_THROW_VALUE_EQ_(st,exp_e,exp_e_v,on_f) IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f ,::iutest::internal::EqHelper<IUTEST_IS_NULLLITERAL(exp_e_v)>::Compare) | |
#define IUTEST_TEST_THROW_VALUE_NE_(st,exp_e,exp_e_v,on_f) IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f ,::iutest::internal::NeHelper<IUTEST_IS_NULLLITERAL(exp_e_v)>::Compare) | |
#define IUTEST_TEST_THROW_VALUE_STREQ_(st,exp_e,exp_e_v,on_f) IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f ,::iutest::internal::CmpHelperSTREQ) | |
#define IUTEST_TEST_THROW_VALUE_STRCASEEQ_(st,exp_e,exp_e_v,on_f) IUTEST_TEST_THROW_VALUE_(st,exp_e,exp_e_v,on_f ,::iutest::internal::CmpHelperSTRCASEEQ) | |
#define IUTEST_TEST_ANY_THROW_(st,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::detail::AlwaysTrue()){try{II_SEH_THROUGH(st);goto IUTEST_PP_CAT(iutest_label_anythrow,__LINE__);}catch(...){}}else IUTEST_PP_CAT(iutest_label_anythrow,__LINE__):on_f("\nExpected: " #st " throws an exception.\n Actual: it doesn's throws.") | |
#define IUTEST_TEST_NO_THROW_(st,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::AssertionResult iutest_ar=::iutest::AssertionSuccess()){try{II_SEH_THROUGH(st);}catch(const ::std::exception& e){iutest_ar<<"\nExpected: " #st " doesn't throw an exception.\n Actual: it throws. what is \"" <<e.what()<<"\"";goto IUTEST_PP_CAT(iutest_label_nothrow,__LINE__);}catch(const char *e){iutest_ar<<"\nExpected: " #st " doesn't throw an exception.\n Actual: it throws. \"" <<e<<"\"";goto IUTEST_PP_CAT(iutest_label_nothrow,__LINE__);}catch(...){iutest_ar<<"\nExpected: " #st " doesn't throw an exception.\n Actual: it throws.";goto IUTEST_PP_CAT(iutest_label_nothrow,__LINE__);}}else IUTEST_PP_CAT(iutest_label_nothrow,__LINE__):on_f(iutest_ar.message()) | |
#endif | |
#define IUTEST_TEST_BOOLEAN_(expression,text,actual,expected,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(const ::iutest::AssertionResult iutest_ar=::iutest::AssertionResult::Is(expression)) ;else on_f(::iutest::internal::GetBooleanAssertionFailureMessage(iutest_ar,text,#actual,#expected).c_str()) | |
#define IUTEST_ASSERT_EXIT(cond) do { if(!(cond)){ IUTEST_MESSAGE(#cond,::iutest::TestPartResult::kFatalFailure);exit(1);}}while(::iutest::detail::AlwaysFalse()) | |
#define II_S() IUTEST_MESSAGE("Succeeded.\n",::iutest::TestPartResult::kSuccess) | |
#define II_F() IUTEST_ASSERT_FAILURE("Failed.\n") | |
#define II_ADD_F() IUTEST_EXPECT_FAILURE("Failed.\n") | |
#define II_ADD_F_AT(file_,line_) IUTEST_EXPECT_FAILURE_AT("Failed.\n",file_,line_) | |
#define II_S_MSG(msg_) const ::iutest::AssertionHelper::ScopedMessage IUTEST_PP_CAT(scoped_message_,IUTEST_PP_COUNTER)=::iutest::detail::iuCodeMessage(__FILE__,__LINE__,::iutest::Message()<<(msg_)) | |
#define IUTEST_THROUGH_ANALYSIS_ASSUME_(expr,todo) todo | |
#define IUTEST_TEST_EQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::EqHelper<IUTEST_IS_NULLLITERAL(expected)>::Compare ,expected,actual,on_f) | |
#define IUTEST_TEST_NE(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::NeHelper<IUTEST_IS_NULLLITERAL(v1)>::Compare ,v1,v2,on_f) | |
#define IUTEST_TEST_LE(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperLE ,v1,v2,on_f) | |
#define IUTEST_TEST_LT(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperLT ,v1,v2,on_f) | |
#define IUTEST_TEST_GE(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperGE ,v1,v2,on_f) | |
#define IUTEST_TEST_GT(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperGT ,v1,v2,on_f) | |
#define IUTEST_TEST_TRUE(expr,text,on_f) IUTEST_TEST_BOOLEAN_(expr,text,false,true,on_f) | |
#define IUTEST_TEST_FALSE(expr,text,on_f) IUTEST_TEST_BOOLEAN_(!(expr),text,true,false,on_f) | |
#define IUTEST_TEST_FLOAT_EQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperFloatingPointEQ<float> ,expected,actual,on_f) | |
#define IUTEST_TEST_DOUBLE_EQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperFloatingPointEQ<double> ,expected,actual,on_f) | |
#if IUTEST_HAS_LONG_DOUBLE | |
#define IUTEST_TEST_LONG_DOUBLE_EQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperFloatingPointEQ<long double> ,expected,actual,on_f) | |
#endif | |
#define IUTEST_TEST_NEAR(v1,v2,abs_v,on_f) IUTEST_PRED_FORMAT3_(::iutest::internal::CmpHelperNear ,v1,v2,abs_v,on_f) | |
#define IUTEST_TEST_STREQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperSTREQ ,expected,actual,on_f) | |
#define IUTEST_TEST_STRNE(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperSTRNE ,v1,v2,on_f) | |
#define IUTEST_TEST_STRCASEEQ(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperSTRCASEEQ ,expected,actual,on_f) | |
#define IUTEST_TEST_STRCASENE(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperSTRCASENE ,v1,v2,on_f) | |
#define IUTEST_TEST_HRESULT_SUCCEEDED(hr,on_f) IUTEST_PRED_FORMAT1_(::iutest::internal::IsHRESULTSuccess ,hr,on_f) | |
#define IUTEST_TEST_HRESULT_FAILED(hr,on_f) IUTEST_PRED_FORMAT1_(::iutest::internal::IsHRESULTFailure ,hr,on_f) | |
#define IUTEST_TEST_SAME(v1,v2,on_f) IUTEST_PRED_FORMAT2_(::iutest::internal::CmpHelperSame ,v1,v2,on_f) | |
#define IUTEST_TEST_NULL(v,on_f) IUTEST_THROUGH_ANALYSIS_ASSUME_(v==IUTEST_NULLPTR ,IUTEST_PRED_FORMAT1_(::iutest::internal::NullHelper<IUTEST_IS_NULLLITERAL(v)>::CompareEq ,v,on_f)) | |
#define IUTEST_TEST_NOTNULL(v,on_f) IUTEST_THROUGH_ANALYSIS_ASSUME_(v!=IUTEST_NULLPTR ,IUTEST_PRED_FORMAT1_(::iutest::internal::NullHelper<IUTEST_IS_NULLLITERAL(v)>::CompareNe ,v,on_f)) | |
#define IUTEST_TEST_NO_FAILURE_(st,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::detail::AlwaysTrue()){::iutest::detail::NewTestPartResultCheckHelper::Counter< ::iutest::detail::NewTestPartResultCheckHelper::CondGt< ::iutest::TestPartResult::kSuccess> > iutest_failure_checker;IUTEST_SUPPRESS_UNREACHABLE_CODE_WARNING({(void)0;st;}) if(iutest_failure_checker.count()> 0){goto IUTEST_PP_CAT(iutest_label_test_no_failure_,__LINE__);}}else IUTEST_PP_CAT(iutest_label_test_no_failure_,__LINE__):on_f("\nExpected: " #st " doesn't generate new failure.\n Actual: it does.") | |
#define IUTEST_TEST_NO_FATAL_FAILURE_(st,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::detail::AlwaysTrue()){::iutest::detail::NewTestPartResultCheckHelper::Counter< ::iutest::detail::NewTestPartResultCheckHelper::CondEq< ::iutest::TestPartResult::kFatalFailure> > iutest_failure_checker;IUTEST_SUPPRESS_UNREACHABLE_CODE_WARNING({(void)0;st;}) if(iutest_failure_checker.count()> 0){goto IUTEST_PP_CAT(iutest_label_test_no_fatalfailure_,__LINE__);}}else IUTEST_PP_CAT(iutest_label_test_no_fatalfailure_,__LINE__):on_f("\nExpected: " #st " doesn't generate new fatal failure.\n Actual: it does.") | |
#define IUTEST_TEST_SKIP() IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if((::iutest::UnitTest::current_test_result()->Failed()) ||(::iutest::UnitTest::SkipTest(),::iutest::detail::AlwaysTrue())) IUTEST_SKIP_MESSAGE(::iutest::UnitTest::current_test_result()->Failed()?"Skipped. but already failed. " : "Skipped. ") | |
#define IUTEST_TEST_COMPILEERROR(e) IUTEST_PRAGMA_MESSAGE("IUTEST_TEST_COMPILEERROR( " #e " )") | |
#if IUTEST_HAS_STATIC_ASSERT | |
#define IUTEST_TEST_STATICASSERT(e) IUTEST_TEST_COMPILEERROR(e) | |
#else | |
#define IUTEST_TEST_STATICASSERT(e) IUTEST_TEST_COMPILEERROR("static_assert") | |
#endif | |
namespace iutest{namespace detail{ | |
#ifndef IUTEST_VPRINTF | |
#define IUTEST_VPRINTF(f,a) vprintf(f,a) | |
#endif | |
#ifndef IUTEST_HAS_COLORCONSOLE | |
#define IUTEST_HAS_COLORCONSOLE 1 | |
#endif | |
class iuLogger{public: virtual ~iuLogger() IUTEST_CXX_DEFAULT_FUNCTION virtual void output(const char* fmt,...){va_list va;va_start(va,fmt);voutput(fmt,va);va_end(va);}virtual void voutput(const char* fmt,va_list va)=0;};class iuConsole{public: enum Color{black,red,green,yellow,blue,magenta,cyan,white};public: static inline void output(const char *fmt,...);static inline void voutput(const char* fmt,va_list va);static inline void color_output(Color color,const char *fmt,...);public: static inline void nl_output(const char *fmt,...);static inline void nl_voutput(const char* fmt,va_list va);public: static iuLogger* SetLogger(iuLogger* logger){iuLogger* pre=GetLoggerInstanceVariable().pInstance;GetLoggerInstanceVariable().pInstance=logger;return pre;}public: static bool IsColorModeOff(){return TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_OFF);}static bool IsColorModeOn(){return TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_ON);}static bool IsColorModeAnsi(){return TestFlag::IsEnableFlag(TestFlag::CONSOLE_COLOR_ANSI);}private: static inline void color_output_impl(Color color,const char* fmt,va_list va);static inline bool IsShouldUseColor(bool use_color);static inline bool HasColorConsole();static inline bool IsStringEqual(const char* str1,const char* str2){return strcmp(str1,str2)==0;}private: struct LoggerInstanceVariable{iuLogger* pInstance;};static LoggerInstanceVariable& GetLoggerInstanceVariable(){static LoggerInstanceVariable v;return v;}static iuLogger* GetLogger(){return GetLoggerInstanceVariable().pInstance;}};inline void iuConsole::output(const char *fmt,...){va_list va;va_start(va,fmt);voutput(fmt,va);va_end(va);}inline void iuConsole::voutput(const char* fmt,va_list va){iuLogger* pLogger=GetLogger();if(pLogger!=0){pLogger->voutput(fmt,va);}else{nl_voutput(fmt,va);}}inline void iuConsole::color_output(Color color,const char *fmt,...){va_list va;va_start(va,fmt);if(IsShouldUseColor(true)){color_output_impl(color,fmt,va);}else{voutput(fmt,va);}va_end(va);}inline void iuConsole::nl_output(const char *fmt,...){va_list va;va_start(va,fmt);nl_voutput(fmt,va);va_end(va);}inline void iuConsole::nl_voutput(const char* fmt,va_list va){IUTEST_VPRINTF(fmt,va);}inline void iuConsole::color_output_impl(Color color,const char* fmt,va_list va){(void)(fmt);(void)(va);{output("\033[1;3%cm",'0' + color);voutput(fmt,va);output("\033[m");}}inline bool iuConsole::IsShouldUseColor(bool use_color){if(IsColorModeOn()){return true;}else if(IsColorModeOff()){return false;}static bool has_color=HasColorConsole();return use_color&&has_color;}inline bool iuConsole::HasColorConsole(){ | |
#if !IUTEST_HAS_COLORCONSOLE | |
return false; | |
#else | |
const char* env=internal::posix::GetEnv("TERM");const bool term_conf=(env!=0)&&(IsStringEqual(env,"xterm")|| IsStringEqual(env,"xterm-color")|| IsStringEqual(env,"xterm-256color")|| IsStringEqual(env,"screen")|| IsStringEqual(env,"screen-256color")|| IsStringEqual(env,"tmux")|| IsStringEqual(env,"tmux-256color")|| IsStringEqual(env,"rxvt-unicode")|| IsStringEqual(env,"rxvt-unicode-256color")|| IsStringEqual(env,"linux")|| IsStringEqual(env,"cygwin"));return term_conf; | |
#endif | |
}}}namespace iutest{namespace detail{class iuOptionMessage{public: static void ShowHelp();static void ShowVersion();static void ShowFeature();static void ShowSpec();};inline void iuOptionMessage::ShowHelp(){const char* readme ="--------------------------------------------------\nName\n iutest - iris unit test framework\n--------------------------------------------------\nCommand Line Options\n\n --help, -h : Generate help message.\n --iutest_list_tests : List up tests.\n --iutest_list_tests_with_where : List up tests with where.\n --iutest_color=<yes|no|auto|ansi>: Console color enable.\n --iutest_flagfile=<file> : Set the flag from the file.\n --iutest_filter=<filter> : Select the test run.\n --iutest_shuffle : Do shuffle test.\n --iutest_random_seed=<seed> : Set random seed.\n --iutest_also_run_disabled_tests : Run disabled tests.\n --iutest_break_on_f[=0|1] : When that failed to break.\n --iutest_throw_on_f[=0|1] : When that failed to throw.\n --iutest_catch_exceptions=<0|1> : Catch exceptions enable.\n --iutest_print_time=<0|1> : Setting the display of elapsed time.\n --iutest_default_package_name=<name>\n : Set default root package name.\n --iutest_output=<xml|junit>[:path]\n : Path of xml report.\n --iutest_repeat=<count>\n : Set the number of repetitions of the test.\n use a negative count to repeat forever.\n" | |
#if IUTEST_HAS_STREAM_RESULT | |
" --iutest_stream_result_to=<host:port>\n : Set stream test results server.\n" | |
#endif | |
" --iutest_file_location=<auto|vs|gcc>\n : Format file location messages.\n --verbose : Verbose option.\n --feature : Show iutest feature.\n --version, -v : Show iutest version.\n\n--------------------------------------------------\nLicense\n\n Copyright (c) 2011-2018, Takazumi-Shirayanagi\n\n This software is released under the new BSD License, see LICENSE\n\n";detail::iuConsole::color_output(detail::iuConsole::cyan,readme);}inline void iuOptionMessage::ShowVersion(){detail::iuConsole::output("iutest version %x.%x.%x.%x\n",IUTEST_MAJORVER,IUTEST_MINORVER,IUTEST_BUILD,IUTEST_REVISION);} | |
#define II_S_M(macro) II_S_M_I(#macro,IUTEST_PP_TOSTRING(macro)) | |
#define II_S_M_I(name,value) detail::iuConsole::output("#define %s %s\n",name,value) | |
#define II_S_E_M(macro) IUTEST_PP_IF(macro,II_S_M_I(#macro,IUTEST_PP_TOSTRING(macro)),IUTEST_PP_EMPTY()) | |
#define II_S_D_M(macro) IUTEST_PP_IF(macro,IUTEST_PP_EMPTY(),II_S_M_I(#macro,IUTEST_PP_TOSTRING(macro))) | |
#define II_S_F_M(m) m(IUTEST_HAS_ANY_PARAM_TEST);m(IUTEST_HAS_ASSERTION_NOEQUALTO_OBJECT);m(IUTEST_HAS_ASSERTION_RETURN);m(IUTEST_HAS_AUTOFIXTURE_PARAM_TEST);m(IUTEST_HAS_COMBINE);m(IUTEST_HAS_CONCAT);m(IUTEST_HAS_CSVPARAMS);m(IUTEST_HAS_EXCEPTIONS);m(IUTEST_HAS_GENRAND);m(IUTEST_HAS_IGNORE_TEST);m(IUTEST_HAS_LONG_DOUBLE);m(IUTEST_HAS_LIB);m(IUTEST_HAS_MATCHERS);m(IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF);m(IUTEST_HAS_MATCHER_ELEMENTSARE);m(IUTEST_HAS_MATCHER_REGEX);m(IUTEST_HAS_MINIDUMP);m(IUTEST_HAS_PACKAGE);m(IUTEST_HAS_PAIRWISE);m(IUTEST_HAS_PARAM_METHOD_TEST);m(IUTEST_HAS_PARAM_TEST);m(IUTEST_HAS_PARAM_TEST_PARAM_NAME_GENERATOR);m(IUTEST_HAS_PEEP);m(IUTEST_HAS_PEEP_CLASS);m(IUTEST_HAS_PEEP_FUNC);m(IUTEST_HAS_PEEP_STATIC_FUNC);m(IUTEST_HAS_PRINT_TO);m(IUTEST_HAS_RANDOMVALUES);m(IUTEST_HAS_REGEX);m(IUTEST_HAS_REPORT_SKIPPED);m(IUTEST_HAS_SOCKET);m(IUTEST_HAS_SPI_LAMBDA_SUPPORT);m(IUTEST_HAS_STATIC_ASSERT);m(IUTEST_HAS_STATIC_ASSERT_TYPEEQ);m(IUTEST_HAS_STREAM_BUFFER);m(IUTEST_HAS_STREAM_RESULT);m(IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE);m(IUTEST_HAS_TESTNAME_ALIAS);m(IUTEST_HAS_TESTNAME_ALIAS_JP);m(IUTEST_HAS_TYPED_TEST);m(IUTEST_HAS_TYPED_TEST_APPEND_TYPENAME);m(IUTEST_HAS_TYPED_TEST_P);m(IUTEST_HAS_VALUESGEN);m(IUTEST_HAS_VARIADIC_COMBINE);m(IUTEST_HAS_VARIADIC_PAIRWISE);m(IUTEST_HAS_VARIADIC_VALUES) | |
inline void iuOptionMessage::ShowFeature(){II_S_F_M(II_S_E_M);II_S_F_M(II_S_D_M);}inline void iuOptionMessage::ShowSpec(){II_S_M(IUTEST_PLATFORM);II_S_M(IUTEST_CHECK_STRICT);II_S_M(IUTEST_HAS_ANALYSIS_ASSUME);II_S_M(IUTEST_HAS_ATTRIBUTE);II_S_M(IUTEST_HAS_AUTO);II_S_M(IUTEST_HAS_CATCH_SEH_EXCEPTION_ASSERTION);II_S_M(IUTEST_HAS_CHAR16_T);II_S_M(IUTEST_HAS_CHAR32_T);II_S_M(IUTEST_HAS_CLOCK);II_S_M(IUTEST_HAS_CONSTEXPR);II_S_M(IUTEST_HAS_CONSTEXPR_IF);II_S_M(IUTEST_HAS_COUNTER_MACRO);II_S_M(IUTEST_HAS_CTIME);II_S_M(IUTEST_HAS_CXX_HDR_ARRAY);II_S_M(IUTEST_HAS_CXX_HDR_CHRONO);II_S_M(IUTEST_HAS_CXX_HDR_CODECVT);II_S_M(IUTEST_HAS_CXX_HDR_CSTDINT);II_S_M(IUTEST_HAS_CXX_HDR_CUCHAR);II_S_M(IUTEST_HAS_CXX_HDR_RANDOM);II_S_M(IUTEST_HAS_CXX_HDR_REGEX);II_S_M(IUTEST_HAS_CXX11);II_S_M(IUTEST_HAS_DECLTYPE);II_S_M(IUTEST_HAS_DELETED_FUNCTIONS);II_S_M(IUTEST_HAS_EXCEPTIONS);II_S_M(IUTEST_HAS_EXPLICIT_CONVERSION);II_S_M(IUTEST_HAS_EXTERN_TEMPLATE);II_S_M(IUTEST_HAS_GETTIMEOFDAY);II_S_M(IUTEST_HAS_HDR_CXXABI);II_S_M(IUTEST_HAS_HDR_SYSTIME);II_S_M(IUTEST_HAS_IF_EXISTS);II_S_M(IUTEST_HAS_INITIALIZER_LIST);II_S_M(IUTEST_HAS_INLINE_VARIABLE);II_S_M(IUTEST_HAS_INT128);II_S_M(IUTEST_HAS_LAMBDA);II_S_M(IUTEST_HAS_LAMBDA_STATEMENTS);II_S_M(IUTEST_HAS_NOEXCEPT);II_S_M(IUTEST_HAS_NULLPTR);II_S_M(IUTEST_HAS_OVERRIDE_AND_FINAL);II_S_M(IUTEST_HAS_RTTI);II_S_M(IUTEST_HAS_RVALUE_REFS);II_S_M(IUTEST_HAS_SEH);II_S_M(IUTEST_HAS_STD_BEGIN_END);II_S_M(IUTEST_HAS_STD_DECLVAL);II_S_M(IUTEST_HAS_STD_EMPLACE);II_S_M(IUTEST_HAS_STD_QUICK_EXIT);II_S_M(IUTEST_HAS_STD_STR_TO_VALUE);II_S_M(IUTEST_HAS_STRINGSTREAM);II_S_M(IUTEST_HAS_STRONG_ENUMS);II_S_M(IUTEST_HAS_STRSTREAM);II_S_M(IUTEST_HAS_TUPLE);II_S_M(IUTEST_HAS_VARIADIC_TEMPLATES);II_S_M(IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES);II_S_M(IUTEST_USE_THROW_ON_ASSERTION_FAILURE); | |
#ifdef IUTEST_LIBSTDCXX_VERSION | |
II_S_M(IUTEST_LIBSTDCXX_VERSION); | |
#endif | |
#ifdef __GLIBCXX__ | |
II_S_M(__GLIBCXX__); | |
#endif | |
#ifdef __GLIBCPP__ | |
II_S_M(__GLIBCPP__); | |
#endif | |
#ifdef _LIBCPP_VERSION | |
II_S_M(_LIBCPP_VERSION); | |
#endif | |
#ifdef __POSIX_VISIBLE | |
II_S_M(__POSIX_VISIBLE); | |
#endif | |
#undef II_S_M | |
}}}namespace iutest{class TestInfo;class TestCase;class TestPartResult;namespace detail{class iuITestInfoMediator{protected: TestInfo* m_test_info;public: explicit iuITestInfoMediator(TestInfo* p=0) IUTEST_CXX_NOEXCEPT_SPEC:m_test_info(p){}public: virtual ~iuITestInfoMediator() IUTEST_CXX_DEFAULT_FUNCTION virtual bool HasFatalFailure()const=0;virtual bool HasNonfatalFailure()const=0;virtual bool HasFailure()const=0;virtual bool IsSkipped()const=0;TestInfo* ptr()const IUTEST_CXX_NOEXCEPT_SPEC{return m_test_info;}};class iuITestCaseMediator{protected: TestCase* m_test_case;public: explicit iuITestCaseMediator(TestCase* p=0) IUTEST_CXX_NOEXCEPT_SPEC:m_test_case(p){}public: virtual ~iuITestCaseMediator() IUTEST_CXX_DEFAULT_FUNCTION virtual const char* test_case_name()const=0;virtual const char* type_param()const=0;TestCase* ptr()const IUTEST_CXX_NOEXCEPT_SPEC{return m_test_case;}};}}namespace iutest{template<typename T>class WithParamInterface;template<typename T>class TestWithParam;namespace detail{::std::string MakeIndexName(size_t index);}class Test{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(Test);public: Test():test_info_(0),m_test_info(0) | |
#if IUTEST_HAS_GENRAND | |
,m_random_seed(0) | |
#endif | |
{CurrentTestObserver::s_current=this;}virtual ~Test(){CurrentTestObserver::s_current=0;}public: static const TestInfo* GetCurrentTestInfo(){const Test* curr=GetCurrentTest();if(curr==0||curr->m_test_info==0){return 0;}return curr->m_test_info->ptr();}static Test* GetCurrentTest(){return CurrentTestObserver::GetCurrentTest();}static bool HasFatalFailure(){return GetCurrentTest()->m_test_info->HasFatalFailure();}static bool HasNonfatalFailure(){return GetCurrentTest()->m_test_info->HasNonfatalFailure();}static bool HasFailure(){return GetCurrentTest()->m_test_info->HasFailure();}static bool IsSkipped(){return GetCurrentTest()->m_test_info->IsSkipped();}static void RecordProperty(const ::std::string& key,const ::std::string& value);template<typename T>static void RecordProperty(const ::std::string& key,const T& value){RecordPropertyString(key,PrintToString(value));} | |
#if IUTEST_HAS_GENRAND | |
unsigned int genrand(){return m_random.genrand();}unsigned int genrand(unsigned int max){return m_random.genrand(max);}float genrandf(){return m_random.genrandf();}unsigned int random_seed()const IUTEST_CXX_NOEXCEPT_SPEC{return m_random_seed;}detail::iuRandom& random_engine(){return m_random;} | |
#endif | |
protected: virtual void SetUp(){} | |
#if IUTEST_HAS_AUTOFIXTURE_PARAM_TEST | |
virtual void Body(){} | |
#else | |
virtual void Body()=0; | |
#endif | |
virtual void TearDown(){}public: static void SetUpTestCase(){}static void TearDownTestCase(){}private: void Run(detail::iuITestInfoMediator* test_info);static void RecordPropertyString(const ::std::string& key,const ::std::string& value);private: struct should_be_SetUp{};virtual should_be_SetUp* Setup() IUTEST_CXX_FINAL{return 0;}private: template<typename DMY>class Observer{public: static Test* s_current;public: static Test* GetCurrentTest() IUTEST_CXX_NOEXCEPT_SPEC{return s_current;}};typedef Observer<void> CurrentTestObserver;private: class TestRecordPropertyHelper{public: static void RecordProperty(const TestProperty& prop);};protected: const TestInfo* test_info_;private: friend class UnitTest;friend class UnitTestImpl;friend class TestInfo;detail::iuITestInfoMediator* m_test_info; | |
#if IUTEST_HAS_GENRAND | |
detail::iuRandom m_random;unsigned int m_random_seed; | |
#endif | |
};template<typename ParamType>struct TestParamInfo{TestParamInfo(const ParamType& p,size_t i):param(p),index(i){}ParamType param;size_t index;};template<typename T>class WithParamInterface{public: typedef T ParamType;protected: virtual ~WithParamInterface(){}public: static const ParamType& GetParam(){IUTEST_CHECK_(s_params!=0)<<"GetParam() can only use the value-parameterized test";;return *s_params;} | |
#if IUTEST_HAS_TUPLE | |
template<int N>static const typename tuples::tuple_element<N,ParamType>::type& GetParam(){return tuples::get<N>(GetParam());} | |
#endif | |
static const ::std::string MakeTestParamName(const TestParamInfo<ParamType>& info){return detail::MakeIndexName(info.index);}static void SetParam(const ParamType* params) IUTEST_CXX_NOEXCEPT_SPEC{s_params=params;}private: static const ParamType* s_params;};template<typename T>const T* WithParamInterface<T>::s_params=0;template<typename T>class TestWithParam:public Test,public WithParamInterface<T>{};namespace detail{template<typename T>class is_useful_testfixture:public iutest_type_traits::false_type{};namespace is_useful_tf_helper{template<typename T>class is_override_setup{template<bool b,typename U>struct impl{typedef iutest_type_traits::false_type type;};template<typename U>struct impl<true,U>{typedef int yes_t;typedef char no_t;static no_t check(void(Test::*)());static yes_t check(...);typedef iutest_type_traits::bool_constant<sizeof(check(&U::SetUp))==sizeof(yes_t)> type;};public: typedef typename impl<iutest_type_traits::is_base_of<Test,T>::value,T>::type type;};}template<typename T>class is_useful_testfixture<void(int(T))>:public is_useful_tf_helper::is_override_setup<T>::type{};inline bool IsDisableTestName(const ::std::string& name){if(detail::IsStringForwardMatching(name,"DISABLED_")|| detail::IsStringContains(name,"/DISABLED_")){return true;}return false;}}}template<typename DMY>::iutest::Test* ::iutest::Test::Observer<DMY>::s_current=0;namespace iutest{inline void Test::RecordPropertyString(const ::std::string& key,const ::std::string& value){TestProperty prop(key,value);TestRecordPropertyHelper::RecordProperty(prop);}inline void Test::RecordProperty(const ::std::string& key,const ::std::string& value){RecordPropertyString(key,value);}inline void Test::Run(detail::iuITestInfoMediator* test_info){m_test_info=test_info;test_info_=test_info->ptr(); | |
#if IUTEST_HAS_GENRAND | |
unsigned int seed=TestEnv::get_random_seed();if(seed==0){seed=detail::GetIndefiniteValue();}m_random_seed=seed;m_random.init(seed); | |
#endif | |
SetUp();if(!HasFailure()&&!IsSkipped()){Body();}TearDown();test_info_=0;m_test_info=0;}}namespace iutest{class Test;namespace detail{class iuFactoryBase{IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(iuFactoryBase);public: iuFactoryBase() IUTEST_CXX_NOEXCEPT_SPEC{}virtual ~iuFactoryBase(){}public: virtual auto_ptr<Test> Create()=0;};template<class Tester>class iuFactory:public iuFactoryBase{public: virtual auto_ptr<Test> Create() IUTEST_CXX_OVERRIDE{auto_ptr<Test> p(new Tester());return p;}};template<typename ParamType>class iuParamTestFactoryBase:public iuFactoryBase{public: iuParamTestFactoryBase():m_param(){}explicit iuParamTestFactoryBase(ParamType param):m_param(param){}public: void SetParam(ParamType param){m_param=param;}const ParamType& GetParam()const{return m_param;}protected: ParamType m_param;};template<class Tester>class iuParamTestFactory:public iuParamTestFactoryBase<typename Tester::ParamType>{typedef typename Tester::ParamType ParamType;typedef iuParamTestFactoryBase<ParamType> _Mybase;public: iuParamTestFactory() IUTEST_CXX_DEFAULT_FUNCTION explicit iuParamTestFactory(ParamType param):_Mybase(param){}public: virtual auto_ptr<Test> Create() IUTEST_CXX_OVERRIDE{Tester::SetParam(&this->m_param);auto_ptr<Test> p(new Tester());return p;}};}}namespace iutest{class TestInfo: public detail::iu_list_node<TestInfo>{public: TestInfo(detail::iuITestCaseMediator* testcase,const ::std::string& name,detail::iuFactoryBase* factory):m_testname(name),m_factory(factory),m_testcase(testcase),m_should_run(true),m_ran(false),m_disable(detail::IsDisableTestName(name)),m_skip(false),m_matches_filter(true){m_mediator.SetPointer(this);}public: const char* test_case_name()const{return m_testcase->test_case_name();}const char* name()const{return m_testname.c_str();}bool should_run()const IUTEST_CXX_NOEXCEPT_SPEC{return m_should_run;}bool is_ran()const IUTEST_CXX_NOEXCEPT_SPEC{return m_ran;}bool is_disabled_test()const IUTEST_CXX_NOEXCEPT_SPEC{return m_disable;}bool is_skipped()const IUTEST_CXX_NOEXCEPT_SPEC{return m_skip||m_test_result.Skipped();}bool is_reportable()const IUTEST_CXX_NOEXCEPT_SPEC{return m_matches_filter;}TimeInMillisec elapsed_time()const{return m_test_result.elapsed_time();}const TestResult* result()const IUTEST_CXX_NOEXCEPT_SPEC{return &m_test_result;}const char* value_param()const{return m_value_param.empty()?0:m_value_param.c_str();}const char* type_param()const{return m_testcase->type_param();}::std::string testcase_name_with_default_package_name()const{return TestEnv::AddDefaultPackageName(test_case_name());}public: bool HasFatalFailure()const{return m_test_result.HasFatalFailure();}bool HasNonfatalFailure()const{return m_test_result.HasNonfatalFailure();}bool HasFailure()const{return m_test_result.Failed();}bool HasWarning()const{return m_test_result.HasWarning();}bool Passed()const{if(is_skipped()){return false;}return m_test_result.Passed();}public: ::std::string test_full_name()const{::std::string fullname=test_case_name();fullname+=".";fullname+=name();return fullname;}::std::string test_name_with_where()const{::std::string str=m_testname;if(value_param()!=0){str+=", where GetParam() = ";str+=m_value_param;}return str;}public: static bool ValidateTestPropertyName(const ::std::string& name){const char* ban[]={"name","status","time","classname","type_param","value_param"};return TestProperty::ValidateName(name,ban);}public: void set_value_param(const char* str){m_value_param=str;}private: bool Run();private: void RunImpl();private: void clear();bool filter();void skip(){m_skip=true;}private: class Mediator IUTEST_CXX_FINAL:public detail::iuITestInfoMediator{public: explicit Mediator(TestInfo* p=0) IUTEST_CXX_NOEXCEPT_SPEC:iuITestInfoMediator(p){}public: virtual bool HasFatalFailure()const IUTEST_CXX_OVERRIDE{return ptr()->HasFatalFailure();}virtual bool HasNonfatalFailure()const IUTEST_CXX_OVERRIDE{return ptr()->HasNonfatalFailure();}virtual bool HasFailure()const IUTEST_CXX_OVERRIDE{return ptr()->HasFailure();}virtual bool IsSkipped()const IUTEST_CXX_OVERRIDE{return ptr()->is_skipped();}public: void SetPointer(TestInfo* p){m_test_info=p;}};private: friend class UnitTestImpl;friend class UnitTest;friend class TestCase;::std::string m_testname;::std::string m_value_param;TestResult m_test_result;Mediator m_mediator;detail::iuFactoryBase* m_factory;detail::iuITestCaseMediator* m_testcase;bool m_should_run;bool m_ran;bool m_disable;bool m_skip;bool m_matches_filter;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TestInfo);};}namespace iutest{inline bool TestInfo::Run(){if(!should_run()){return true;}TestEnv::event_listeners().OnTestStart(*this);RunImpl();TestEnv::event_listeners().OnTestEnd(*this);return !HasFailure();}inline void TestInfo::RunImpl(){detail::iuStopWatch sw;TimeInMillisec elapsedmsec=0;m_ran=true; | |
#if IUTEST_HAS_EXCEPTIONS | |
if(TestFlag::IsEnableFlag(TestFlag::CATCH_EXCEPTION_EACH)){detail::auto_ptr<Test> p=m_factory->Create();try{sw.start();p->Run(&m_mediator);elapsedmsec=sw.stop();}catch(const ::std::exception& e){elapsedmsec=sw.stop();iutest::AssertionHelper(0,-1,detail::FormatCxxException(e.what()),TestPartResult::kFatalFailure).OnFixed(AssertionHelper::Fixed());if(TestFlag::IsEnableFlag(TestFlag::THROW_ON_FAILURE)){throw;}}catch(const TestPartResult::Type& eType){elapsedmsec=sw.stop();if(TestPartResult::type_is_failed(eType)&&TestFlag::IsEnableFlag(TestFlag::THROW_ON_FAILURE)){throw;}}catch(...){elapsedmsec=sw.stop();iutest::AssertionHelper(0,-1,detail::FormatCxxException(0),TestPartResult::kFatalFailure).OnFixed(AssertionHelper::Fixed());if(TestFlag::IsEnableFlag(TestFlag::THROW_ON_FAILURE)){throw;}}}else | |
#endif | |
{detail::auto_ptr<Test> p=m_factory->Create();sw.start();p->Run(&m_mediator);elapsedmsec=sw.stop();}m_test_result.set_elapsed_time(elapsedmsec);if(HasFailure()&&TestFlag::IsEnableFlag(TestFlag::THROW_ON_FAILURE)){ | |
#if IUTEST_HAS_EXCEPTIONS | |
throw HasFatalFailure()?TestPartResult::kFatalFailure:TestPartResult::kNonFatalFailure; | |
#else | |
exit(1); | |
#endif | |
}}inline void TestInfo::clear(){m_ran=false;m_skip=false;m_test_result.Clear();}inline bool TestInfo::filter(){bool run=true;if(!TestFlag::IsEnableFlag(TestFlag::RUN_DISABLED_TESTS)&& is_disabled_test()){run=false;}bool match=true;if(TestFlag::IsEnableFlag(TestFlag::FILTERING_TESTS)){if(!detail::iuFilterRegex::match(TestEnv::test_filter(),test_full_name().c_str())){match=false;run=false;}}m_matches_filter=match;m_should_run=run;return m_should_run;}}namespace iutest{class TestCase: public detail::iu_list_node<TestCase>{protected: typedef detail::iu_list<TestInfo> iuTestInfos;protected: TestCase(const ::std::string& testcase_name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):m_testcase_name(testcase_name),m_setup(setup),m_teardown(teardown),m_id(id),m_disable_num(0),m_should_run_num(0),m_elapsedmsec(0),m_start_timestamp(0),m_disable(detail::IsDisableTestName(testcase_name)){}public: virtual ~TestCase(){}public: const char* name()const{return m_testcase_name.c_str();}int total_test_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_testinfos.size();}int reportable_test_count()const;int test_to_run_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_should_run_num;}int failed_test_count()const;int disabled_test_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_disable_num;}int reportable_disabled_test_count()const;int successful_test_count()const;int skip_test_count()const;int reportable_skip_test_count()const;int test_run_skipped_count()const;int reportable_test_run_skipped_count()const;TimeInMillisec elapsed_time()const IUTEST_CXX_NOEXCEPT_SPEC{return m_elapsedmsec;}TimeInMillisec start_timestamp()const IUTEST_CXX_NOEXCEPT_SPEC{return m_start_timestamp;}const TestInfo* GetTestInfo(int index)const{return m_testinfos[index];}bool should_run()const IUTEST_CXX_NOEXCEPT_SPEC{return m_should_run_num!=0;}bool Passed()const{return failed_test_count()==0 && m_ad_hoc_testresult.Passed();}bool Failed()const{return !Passed();}virtual const char* type_param()const{return 0;}::std::string testcase_name_with_where()const{::std::string str=m_testcase_name;if(type_param()!=0){str+=", where TypeParam = ";str+=type_param();}return str;}::std::string testcase_name_with_default_package_name()const{return TestEnv::AddDefaultPackageName(name());}const TestResult* ad_hoc_testresult()const IUTEST_CXX_NOEXCEPT_SPEC{return ad_hoc_test_result();}const TestResult* ad_hoc_test_result()const IUTEST_CXX_NOEXCEPT_SPEC{return &m_ad_hoc_testresult;}public: static bool ValidateTestPropertyName(const ::std::string& name){const char* ban[]={"name","tests","failures","disabled","skip","errors","time"};return TestProperty::ValidateName(name,ban);}private: bool Run();bool RunImpl();private: bool CheckSetUpSkipped();public: struct FindOp{TestTypeId m_id;const char* m_name;bool operator()(const TestCase* p)const{if(p->get_typeid()==m_id&&detail::IsStringEqual(p->m_testcase_name,m_name)){return true;}return false;}};private: void clear();bool filter();private: friend bool operator==(const TestCase& lhs,const TestCase& rhs){return(lhs.m_id==rhs.m_id)&&(strcmp(lhs.name(),rhs.name())==0);}void push_back(TestInfo* p){m_testinfos.push_back(p);}private: iuTestInfos::const_iterator begin()const{return m_testinfos.begin();}iuTestInfos::const_iterator end()const{return m_testinfos.end();}TestTypeId get_typeid()const IUTEST_CXX_NOEXCEPT_SPEC{return m_id;}private: bool HasWarning()const{return m_ad_hoc_testresult.HasWarning()||detail::AnyOverList(m_testinfos,&TestInfo::HasWarning);}private: static bool IsSuccessfulTest(const TestInfo* p){return p->is_ran()&&p->Passed();}static bool IsFailedTest(const TestInfo* p){return p->should_run()&&p->HasFailure();}static bool IsSkipTest(const TestInfo* p){return !p->is_ran()||p->is_skipped();}static bool IsReportableSkipTest(const TestInfo* p){return p->is_reportable()&&IsSkipTest(p);}static bool IsRunSkippedTest(const TestInfo* p){return p->should_run()&&p->is_skipped();}static bool IsReportableRunSkippedTest(const TestInfo* p){return p->is_reportable()&&IsRunSkippedTest(p);}static bool IsReportableDisabledTest(const TestInfo* p){return p->is_reportable()&&p->is_disabled_test();}private: friend class UnitTestImpl;friend class UnitTest;::std::string m_testcase_name;iuTestInfos m_testinfos;SetUpMethod m_setup;TearDownMethod m_teardown;TestTypeId m_id;int m_disable_num;int m_should_run_num;TimeInMillisec m_elapsedmsec;TimeInMillisec m_start_timestamp;bool m_disable;TestResult m_ad_hoc_testresult;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TestCase);};template<typename T>class TypedTestCase:public TestCase{public: typedef T TypeParam;protected: TypedTestCase(const ::std::string& testcase_name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):TestCase(testcase_name,id,setup,teardown),m_type_param(detail::GetTypeName<TypeParam>()){}public: virtual const char* type_param()const IUTEST_CXX_OVERRIDE{return m_type_param.empty()?0:m_type_param.c_str();}private: friend class UnitTestImpl;::std::string m_type_param;};namespace detail{class TestCaseMediator IUTEST_CXX_FINAL:public detail::iuITestCaseMediator{public: explicit TestCaseMediator(TestCase* p) IUTEST_CXX_NOEXCEPT_SPEC:iuITestCaseMediator(p){}public: virtual const char* test_case_name()const IUTEST_CXX_OVERRIDE{return m_test_case->name();}virtual const char* type_param()const IUTEST_CXX_OVERRIDE{return m_test_case->type_param();}};}}namespace iutest{inline bool TestCase::Run(){if(!should_run()){return true;}if(TestFlag::IsEnableFlag(TestFlag::SHUFFLE_TESTS)){detail::RandomShuffle(m_testinfos,TestEnv::genrand());}bool result=false;m_start_timestamp=detail::GetTimeInMillis();TestEnv::event_listeners().OnTestCaseStart(*this); | |
#if IUTEST_HAS_EXCEPTIONS | |
if(TestFlag::IsEnableFlag(TestFlag::CATCH_EXCEPTION_EACH)){try{result=RunImpl();}catch(const TestPartResult::Type& eType){CheckSetUpSkipped();if(TestPartResult::type_is_failed(eType)&&TestFlag::IsEnableFlag(TestFlag::THROW_ON_FAILURE)){throw;}}catch(...){throw;}}else | |
#endif | |
{result=RunImpl();}TestEnv::event_listeners().OnTestCaseEnd(*this);return result;}inline bool TestCase::RunImpl(){bool result=true;m_elapsedmsec=0;m_setup();if(m_ad_hoc_testresult.HasFatalFailure()){return false;}if(CheckSetUpSkipped()){return true;}{detail::iuStopWatch sw;sw.start();for(iuTestInfos::iterator it=m_testinfos.begin(),end=m_testinfos.end();it!=end;++it){if(!(it)->Run()){result=false;}}m_elapsedmsec=sw.stop();}m_teardown();if(m_ad_hoc_testresult.HasFatalFailure()){return false;}return result;}inline bool TestCase::CheckSetUpSkipped(){if(m_ad_hoc_testresult.Skipped()){for(iuTestInfos::iterator it=m_testinfos.begin(),end=m_testinfos.end();it!=end;++it){(it)->skip();}return true;}return false;}inline void TestCase::clear(){m_ad_hoc_testresult.Clear();for(iuTestInfos::iterator it=m_testinfos.begin(),end=m_testinfos.end();it!=end;++it){(it)->clear();}}inline bool TestCase::filter(){m_should_run_num=0;m_disable_num=0;for(iuTestInfos::iterator it=m_testinfos.begin(),end=m_testinfos.end();it!=end;++it){if(m_disable){(it)->m_disable=true;}if((it)->is_disabled_test()){++m_disable_num;}if((it)->filter()){++m_should_run_num;}}return should_run();}inline int TestCase::reportable_test_count()const{return detail::CountIfOverList(m_testinfos,&TestInfo::is_reportable);}inline int TestCase::failed_test_count()const{if(!should_run()){return 0;}return detail::CountIf(m_testinfos,IsFailedTest);}inline int TestCase::successful_test_count()const{if(!should_run()){return 0;}return detail::CountIf(m_testinfos,IsSuccessfulTest);}inline int TestCase::skip_test_count()const{if(!should_run()){return total_test_count();}return detail::CountIf(m_testinfos,IsSkipTest);}inline int TestCase::reportable_skip_test_count()const{if(!should_run()){return reportable_test_count();}return detail::CountIf(m_testinfos,IsReportableSkipTest);}inline int TestCase::test_run_skipped_count()const{if(!should_run()){return 0;}return detail::CountIf(m_testinfos,IsRunSkippedTest);}inline int TestCase::reportable_test_run_skipped_count()const{if(!should_run()){return 0;}return detail::CountIf(m_testinfos,IsReportableRunSkippedTest);}inline int TestCase::reportable_disabled_test_count()const{return detail::CountIf(m_testinfos,IsReportableDisabledTest);}}namespace iutest{class UnitTestImpl{protected: typedef detail::iu_list<TestCase> iuTestCases;typedef ::std::vector<Environment*> iuEnvironmentList;protected: UnitTestImpl():m_total_test_num(0),m_disable_num(0),m_should_run_num(0),m_current_testcase(0),m_elapsedmsec(0){ptr()=this;}~UnitTestImpl(){TerminateImpl();}public: static TestResult* current_test_result();public: static bool ValidateTestPropertyName(const ::std::string& name){const char* ban[]={"name","tests","failures","disabled","skip","errors","time","timestamp","random_seed"};return TestProperty::ValidateName(name,ban);}public: template<typename T>TestCase* AddTestCase(const ::std::string& testcase_name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown IUTEST_APPEND_EXPLICIT_TEMPLATE_TYPE_(T)){TestCase* p=FindTestCase(testcase_name,id);if(p==0){p=new T(testcase_name,id,setup,teardown);m_testcases.push_back(p);}return p;}void AddTestInfo(TestCase* pCase,TestInfo* pInfo);static void SkipTest();protected: int Listup()const;int ListupWithWhere()const;bool PreRunner();void ClearNonAdHocTestResult();void ClearAdHocTestResult(){m_ad_hoc_testresult.Clear();}private: static void RecordProperty(const TestProperty& prop);TestCase* FindTestCase(const ::std::string& testcase_name,TestTypeId id);bool DoInfoOptions();private: void InitializeImpl();void TerminateImpl();private:private: static UnitTestImpl*& ptr() IUTEST_CXX_NOEXCEPT_SPEC{static UnitTestImpl* ptr=0;return ptr;}protected: friend class UnitTestSource;friend class Test::TestRecordPropertyHelper;int m_total_test_num;int m_disable_num;int m_should_run_num;TestCase* m_current_testcase;TimeInMillisec m_elapsedmsec;iuTestCases m_testcases;TestResult m_ad_hoc_testresult;};namespace detail{::std::string MakeIndexName(size_t index);::std::string MakeIndexTestName(const char* basename,size_t index);::std::string MakeParamTestName(const ::std::string& basename,const ::std::string& parame_name);template<typename T>::std::string MakeIndexTypedTestName(const char* basename,size_t index){ | |
#if IUTEST_HAS_RTTI | |
::std::string name=MakeIndexTestName(basename,index);name+="/";name+=GetTypeName<T>();return name; | |
#else | |
return MakeIndexTestName(basename,index); | |
#endif | |
}::std::string MakePrefixedIndexTestName(const char* prefix,const char* basename,size_t index);template<typename T>::std::string MakePrefixedIndexTypedTestName(const char* prefix,const char* basename,size_t index){ | |
#if IUTEST_HAS_RTTI | |
::std::string name=prefix;if(!name.empty()){name+="/";}name+=MakeIndexTypedTestName<T>(basename,index);return name; | |
#else | |
return MakePrefixedIndexTestName(prefix,basename,index); | |
#endif | |
}}}namespace iutest{inline TestResult* UnitTestImpl::current_test_result(){if(Test::GetCurrentTestInfo()){return &(Test::GetCurrentTest()->m_test_info->ptr()->m_test_result);}UnitTestImpl* p=ptr();if(p==0){return 0;}if(p->m_current_testcase!=0){return &p->m_current_testcase->m_ad_hoc_testresult;}return &p->m_ad_hoc_testresult;}inline void UnitTestImpl::AddTestInfo(TestCase* pCase,TestInfo* pInfo){++m_total_test_num;pCase->push_back(pInfo);}inline void UnitTestImpl::SkipTest(){const Test* test=Test::GetCurrentTest();if(test!=0&&test->m_test_info->ptr()!=0){test->m_test_info->ptr()->skip();}}inline int UnitTestImpl::Listup()const{detail::iuConsole::output("%d tests from %d testcase\n",m_total_test_num,m_testcases.size());for(iuTestCases::const_iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){detail::iuConsole::output((it)->name());detail::iuConsole::output("\n");for(TestCase::iuTestInfos::const_iterator it2=(it)->begin(),end2=(it)->end();it2!=end2;++it2){detail::iuConsole::output(" ");detail::iuConsole::output((it2)->name());detail::iuConsole::output("\n");}}return 0;}inline int UnitTestImpl::ListupWithWhere()const{detail::iuConsole::output("%d tests from %d testcase\n",m_total_test_num,m_testcases.size());for(iuTestCases::const_iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){detail::iuConsole::output((it)->testcase_name_with_where().c_str());detail::iuConsole::output("\n");for(TestCase::iuTestInfos::const_iterator it2=(it)->begin(),end2=(it)->end();it2!=end2;++it2){detail::iuConsole::output(" ");detail::iuConsole::output((it2)->test_name_with_where().c_str());detail::iuConsole::output("\n");}}return 0;}inline bool UnitTestImpl::PreRunner(){InitializeImpl();if(DoInfoOptions()){TestFlag::SetFlag(0,~TestFlag::SHOW_MASK);return false;}return true;}inline void UnitTestImpl::ClearNonAdHocTestResult(){for(iuTestCases::iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){(it)->clear();}}inline void UnitTestImpl::RecordProperty(const TestProperty& prop){UnitTestImpl* p=ptr();TestResult* tr=0;if(Test::GetCurrentTestInfo()){tr=&(Test::GetCurrentTest()->m_test_info->ptr()->m_test_result);if(!TestInfo::ValidateTestPropertyName(prop.key())){II_ADD_F()<<"Reserved key used in RecordProperty(): " <<prop.key();return;}}else if(p->m_current_testcase!=0){tr=&p->m_current_testcase->m_ad_hoc_testresult;if(!TestCase::ValidateTestPropertyName(prop.key())){II_ADD_F()<<"Reserved key used in RecordProperty(): " <<prop.key();return;}}else{tr =&p->m_ad_hoc_testresult;if(!ValidateTestPropertyName(prop.key())){II_ADD_F()<<"Reserved key used in RecordProperty(): " <<prop.key();return;}}tr->RecordProperty(prop);TestEnv::event_listeners().OnTestRecordProperty(prop);}inline TestCase* UnitTestImpl::FindTestCase(const ::std::string& testcase_name,TestTypeId id){TestCase::FindOp func ={id,testcase_name.c_str()};return detail::FindList(m_testcases,func);}inline bool UnitTestImpl::DoInfoOptions(){if(TestFlag::IsEnableFlag(TestFlag::SHOW_INFO_MASK)){if(TestFlag::IsEnableFlag(TestFlag::SHOW_HELP)){detail::iuOptionMessage::ShowHelp();}if(TestFlag::IsEnableFlag(TestFlag::SHOW_VERSION)){detail::iuOptionMessage::ShowVersion();}if(TestFlag::IsEnableFlag(TestFlag::SHOW_FEATURE)){detail::iuOptionMessage::ShowFeature();}if(TestFlag::IsEnableFlag(TestFlag::SHOW_SPEC)){detail::iuOptionMessage::ShowSpec();}return true;}if(TestFlag::IsEnableFlag(TestFlag::SHOW_TESTS_LIST_WITH_WHERE)){ListupWithWhere();return true;}if(TestFlag::IsEnableFlag(TestFlag::SHOW_TESTS_LIST)){Listup();return true;}return false;}inline void UnitTestImpl::InitializeImpl(){}inline void UnitTestImpl::TerminateImpl(){for(iuTestCases::iterator it=m_testcases.begin();it!=m_testcases.end();it=m_testcases.begin()){TestCase* p=(it);m_testcases.erase(it);delete p;}}namespace detail{inline ::std::string MakeIndexName(size_t index){iu_global_format_stringstream strm;strm<<index;return strm.str();}inline ::std::string MakeIndexTestName(const char* basename,size_t index){::std::string name=basename;name+="/";name+=MakeIndexName(index);return name;}inline::std::string MakeParamTestName(const ::std::string& basename,const ::std::string& param_name){if(param_name.empty()){return basename;}::std::string name=basename;name+="/";name+=param_name;return name;}inline ::std::string MakePrefixedIndexTestName(const char* prefix,const char* basename,size_t index){::std::string name=prefix;if(!name.empty()){name+="/";}name+=MakeIndexTestName(basename,index);return name;}}inline void Test::TestRecordPropertyHelper::RecordProperty(const TestProperty& prop){iutest::UnitTestImpl::RecordProperty(prop);}}namespace iutest{namespace detail{class DefaultGlobalTestPartResultReporter:public TestPartResultReporterInterface{public: virtual ~DefaultGlobalTestPartResultReporter() IUTEST_CXX_OVERRIDE{}virtual void ReportTestPartResult(const TestPartResult& test_part_result) IUTEST_CXX_OVERRIDE{DefaultReportTestPartResult(test_part_result);}static void DefaultReportTestPartResult(const TestPartResult& test_part_result){TestResult* result=UnitTestImpl::current_test_result();if(result){result->AddTestPartResult(test_part_result);}else{iuConsole::output(test_part_result.make_newline_message().c_str());}TestEnv::event_listeners().OnTestPartResult(test_part_result);}};class NoTestPartResultReporter:public TestPartResultReporterInterface{public: virtual ~NoTestPartResultReporter() IUTEST_CXX_OVERRIDE{}virtual void ReportTestPartResult(const TestPartResult& result) IUTEST_CXX_OVERRIDE{(void)(result);}};class NewTestPartResultCheckHelper{public: template<TestPartResult::Type Type>struct CondEq{bool operator()(const TestPartResult& result){return result.type()==Type;}};template<TestPartResult::Type Type>struct CondNe{bool operator()(const TestPartResult& result){return result.type()!=Type;}};template<TestPartResult::Type Type>struct CondGt{bool operator()(const TestPartResult& result){return result.type()> Type;}};public: class ReporterHolder{public: ReporterHolder():m_origin(0){}virtual ~ReporterHolder(){Detach();}void Attach(TestPartResultReporterInterface* p){m_origin=TestEnv::GetGlobalTestPartResultReporter();TestEnv::SetGlobalTestPartResultReporter(p);}void Detach(){TestEnv::SetGlobalTestPartResultReporter(m_origin);}public: void ReportTestPartResultOrigin(const TestPartResult& result){if(m_origin){m_origin->ReportTestPartResult(result);}}private: TestPartResultReporterInterface* m_origin;};public: template<typename COND,typename REPORTER=DefaultGlobalTestPartResultReporter>class Counter:public REPORTER{typedef REPORTER _Mybase;public: Counter():m_count(0){m_holder.Attach(this);}virtual void ReportTestPartResult(const TestPartResult& result) IUTEST_CXX_OVERRIDE{if(m_cond(result)){++m_count;}_Mybase::ReportTestPartResult(result);}public: int count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_count;}private: ReporterHolder m_holder;COND m_cond;int m_count;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(Counter);};template<typename REPORTER=DefaultGlobalTestPartResultReporter>class Collector:public REPORTER{typedef REPORTER _Mybase;typedef ::std::vector<TestPartResult> TestPartResults;public: Collector(){m_holder.Attach(this);}public: virtual void ReportTestPartResult(const TestPartResult& result) IUTEST_CXX_OVERRIDE{m_results.push_back(result);_Mybase::ReportTestPartResult(result);}public: size_t count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_results.size();}const TestPartResult& GetTestPartResult(int index)const{return m_results[index];}void ReportTestPartResult(){for(TestPartResults::iterator it=m_results.begin();it!=m_results.end();++it){m_holder.ReportTestPartResultOrigin(*it);}}private: ReporterHolder m_holder;TestPartResults m_results;};};inline void DefaultReportTestPartResult(const TestPartResult& test_part_result){DefaultGlobalTestPartResultReporter::DefaultReportTestPartResult(test_part_result);}}} | |
#if IUTEST_HAS_PARAM_TEST | |
namespace iutest{namespace detail{ | |
#if IUTEST_HAS_CONCAT | |
template<typename Generator1,typename Generator2>class iuConcatParamHolder; | |
#endif | |
template<typename T>class iuIParamGenerator{public: typedef T type;public: typedef iuIParamGenerator<T>*(*Generator)();public: virtual ~iuIParamGenerator(){}public: virtual void Begin()=0;virtual T GetCurrent()const=0;virtual void Next()=0;virtual bool IsEnd()const=0;};template<typename T>class iuParamGenerator:public iuIParamGenerator<T>{typedef iuIParamGenerator<T> _Interface;typedef iuParamGenerator<T> _Myt;public: typedef T type;public: iuParamGenerator(_Interface* pInterface=0):m_pInterface(pInterface){}public: operator iuIParamGenerator<T>*()const{return m_pInterface;}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#endif | |
public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_pInterface->Begin();}virtual T GetCurrent()const IUTEST_CXX_OVERRIDE{return m_pInterface->GetCurrent();}virtual void Next() IUTEST_CXX_OVERRIDE{m_pInterface->Next();}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return m_pInterface->IsEnd();}private: _Interface* m_pInterface;};template<typename T>class iuRangeParamsGenerator:public iuIParamGenerator<T>{T m_begin;T m_end;T m_step;T m_cur;public: iuRangeParamsGenerator(T begin,T end,T step):m_begin(begin),m_end(end),m_step(step),m_cur(begin){}public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_cur=m_begin;}virtual T GetCurrent()const IUTEST_CXX_OVERRIDE{return m_cur;}virtual void Next() IUTEST_CXX_OVERRIDE{m_cur=static_cast<T>(m_cur+m_step);}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return !(m_cur<m_end);}};class iuBoolParamsGenerator:public iuIParamGenerator<bool>{int m_n;bool m_cur;public: iuBoolParamsGenerator():m_n(0),m_cur(false){}public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_cur=false;m_n=0;}virtual bool GetCurrent()const IUTEST_CXX_OVERRIDE{return m_cur;}virtual void Next() IUTEST_CXX_OVERRIDE{++m_n;m_cur=!m_cur;}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return m_n>=2;}};template<typename T>class iuValuesInParamsGenerator:public iuIParamGenerator<T>{typedef ::std::vector<T> params_t;params_t m_values;typename params_t::const_iterator m_it;public: explicit iuValuesInParamsGenerator(const params_t& values):m_values(values){}template<typename Container>explicit iuValuesInParamsGenerator(const Container& values){m_values.insert(m_values.end(),values.begin(),values.end());}template<typename TT,size_t SIZE>explicit iuValuesInParamsGenerator(const TT(&values)[SIZE]){m_values.insert(m_values.end(),values,values+SIZE);}template<typename Ite>iuValuesInParamsGenerator(Ite begin,Ite end){m_values.insert(m_values.end(),begin,end);} | |
#if IUTEST_HAS_INITIALIZER_LIST | |
iuValuesInParamsGenerator(::std::initializer_list<T> l){m_values.insert(m_values.end(),l.begin(),l.end());} | |
#endif | |
public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_it=m_values.begin();}virtual T GetCurrent()const IUTEST_CXX_OVERRIDE{return *m_it;}virtual void Next() IUTEST_CXX_OVERRIDE{++m_it;}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return(m_it==m_values.end());}}; | |
#if IUTEST_HAS_CONCAT | |
template<typename G1,typename G2>class iuConcatParamHolder{typedef iuConcatParamHolder<G1,G2> _Myt;public: iuConcatParamHolder(const G1& g1,const G2& g2):m_g1(g1),m_g2(g2){}public: template<typename T>operator iuIParamGenerator<T>*(){params_t<T> params;params.append(m_g1);params.append(m_g2);return new iuValuesInParamsGenerator<T>(params.val);}template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);}private: template<typename T>struct params_t{::std::vector<T> val;void append(iuIParamGenerator<T>* gen){for(gen->Begin();!gen->IsEnd();gen->Next()){val.push_back(gen->GetCurrent());}}template<typename U>void append(iuParamGenerator<U>& gen){for(gen.Begin();!gen.IsEnd();gen.Next()){val.push_back(static_cast<T>(gen.GetCurrent()));}}};private: G1 m_g1;G2 m_g2;}; | |
#endif | |
#if IUTEST_HAS_VARIADIC_VALUES | |
template<typename... Args>class iuValueArray{typedef tuples::tuple<Args...> _MyTuple;typedef iuValueArray<Args...> _Myt;template<typename T>struct make_array{T val[sizeof...(Args)];template<typename U>void operator()(int index,const U& value){val[index]=value;}explicit make_array(const _MyTuple& t){tuples::tuple_foreach(t,*this);}};public: explicit iuValueArray(const Args&... args):v(args...){} | |
#if defined(__clang__)&&defined(IUTEST_LIBSTDCXX_VERSION)&&IUTEST_LIBSTDCXX_VERSION>=40900 | |
#if IUTEST_HAS_RVALUE_REFS | |
iuValueArray(const iuValueArray& rhs):v(rhs.v){}iuValueArray(iuValueArray&& rhs):v(rhs.v){} | |
#endif | |
#endif | |
public: template<typename T>operator iuIParamGenerator<T>*()const{make_array<T> ar(v);return new iuValuesInParamsGenerator<T>(ar.val);}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#endif | |
private: _MyTuple v;}; | |
#else | |
#define II_D_VA_CONSTRUCT_(i,p1,p2) IUTEST_PP_CAT(p1,i)(IUTEST_PP_CAT(p2,i)) | |
#define II_D_VA_STATICCAST_(i,p1,p2) static_cast<p1>(IUTEST_PP_CAT(p2,i)) | |
#define II_D_VA_VARIABLE_(i,p1,p2) IUTEST_PP_CAT(p1,i) IUTEST_PP_CAT(p2,i); | |
#if IUTEST_HAS_CONCAT | |
#define II_D_VA_CONCAT_() template<typename Other> iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#else | |
#define II_D_VA_CONCAT_() | |
#endif | |
#define II_D_VA_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename A)> class IUTEST_PP_CAT(iuValueArray,n){typedef IUTEST_PP_CAT(iuValueArray,n)<IUTEST_PP_ENUM_PARAMS(n,A)> _Myt;public: IUTEST_PP_CAT(iuValueArray,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,A,a)) : IUTEST_PP_ENUM_BINARY(n,II_D_VA_CONSTRUCT_,v,a){}template<typename T>operator iuIParamGenerator<T>*()const{const T val[]={IUTEST_PP_ENUM_BINARY(n,II_D_VA_STATICCAST_,T,v)};return new iuValuesInParamsGenerator<T>(val);}II_D_VA_CONCAT_() private: IUTEST_PP_REPEAT_BINARY(n,II_D_VA_VARIABLE_,A,v) } | |
II_D_VA_(1);II_D_VA_(2);II_D_VA_(3);II_D_VA_(4);II_D_VA_(5);II_D_VA_(6);II_D_VA_(7);II_D_VA_(8);II_D_VA_(9);II_D_VA_(10);II_D_VA_(11);II_D_VA_(12);II_D_VA_(13);II_D_VA_(14);II_D_VA_(15);II_D_VA_(16);II_D_VA_(17);II_D_VA_(18);II_D_VA_(19);II_D_VA_(20);II_D_VA_(21);II_D_VA_(22);II_D_VA_(23);II_D_VA_(24);II_D_VA_(25);II_D_VA_(26);II_D_VA_(27);II_D_VA_(28);II_D_VA_(29);II_D_VA_(30);II_D_VA_(31);II_D_VA_(32);II_D_VA_(33);II_D_VA_(34);II_D_VA_(35);II_D_VA_(36);II_D_VA_(37);II_D_VA_(38);II_D_VA_(39);II_D_VA_(40);II_D_VA_(41);II_D_VA_(42);II_D_VA_(43);II_D_VA_(44);II_D_VA_(45);II_D_VA_(46);II_D_VA_(47);II_D_VA_(48);II_D_VA_(49);II_D_VA_(50); | |
#undef II_D_VA_CONSTRUCT_ | |
#undef II_D_VA_STATICCAST_ | |
#undef II_D_VA_VARIABLE_ | |
#undef II_D_VA_CONCAT_ | |
#undef II_D_VA_ | |
#endif | |
#if IUTEST_HAS_COMBINE | |
#if IUTEST_HAS_VARIADIC_COMBINE | |
template<typename... Args>class iuCartesianProductGenerator:public iuIParamGenerator<tuples::tuple<Args...> >{typedef tuples::tuple<iuParamGenerator<Args>... > _MyTuple;static const int kCount=sizeof...(Args);struct begin_func{template<typename T>void operator()(int,T& value)const{value.Begin();}};template<int index,int end,typename Tuple>bool is_end_foreach(Tuple& t,typename detail::enable_if<index!=end,void>::type*& = detail::enabler::value)const{const bool b=tuples::get<index>(t).IsEnd();return b&&is_end_foreach<index+1,end>(t);}template<int index,int end,typename Tuple>bool is_end_foreach(Tuple&,typename detail::enable_if<index==end,void>::type*& = detail::enabler::value)const{return true;}template<int index,int end,typename Tuple>void next_foreach(Tuple& t,typename detail::enable_if<index!=end,void>::type*& = detail::enabler::value){next_foreach<index+1,end>(t);if(is_end_foreach<index+1,end>(t)){tuples::get<index>(t).Next();if(!tuples::get<index>(t).IsEnd()){tuples::tuple_foreach<index+1>(t,begin_func());}}}template<int index,int end,typename Tuple>void next_foreach(Tuple&,typename detail::enable_if<index==end,void>::type*& = detail::enabler::value){}template<int index,int end,typename T1,typename ...TArgs>tuples::tuple<T1,TArgs...> current_foreach(typename detail::enable_if<index!=end-1,void>::type*& = detail::enabler::value)const{return ::std::tuple_cat(tuples::tuple<T1>(tuples::get<index>(v).GetCurrent()),current_foreach<index+1,end,TArgs...>());}template<int index,int end,typename T1,typename ...TArgs>tuples::tuple<T1> current_foreach(typename detail::enable_if<index==end-1,void>::type*& = detail::enabler::value)const{return tuples::tuple<T1>(tuples::get<index>(v).GetCurrent());}public: typedef tuples::tuple<Args...> ParamType;public: iuCartesianProductGenerator(){}public: virtual void Begin() IUTEST_CXX_OVERRIDE{tuples::tuple_foreach(v,begin_func());}virtual void Next() IUTEST_CXX_OVERRIDE{if(!IsEnd()){next_foreach<0,kCount>(v);}}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return is_end_foreach<0,kCount>(v);}virtual ParamType GetCurrent()const IUTEST_CXX_OVERRIDE{return current_foreach<0,kCount,Args...>();}_MyTuple& generators(){return v;}private: _MyTuple v;};template<typename... Generator>class iuCartesianProductHolder{typedef iuCartesianProductHolder<Generator...> _Myt;typedef tuples::tuple<const Generator...> _MyTuple;public: explicit iuCartesianProductHolder(const Generator&... generators):v(generators...){}public: template<typename... Args>operator iuIParamGenerator<tuples::tuple<Args...> >*()const{iuCartesianProductGenerator<Args...>* p=new iuCartesianProductGenerator<Args...>();tuples::tuple_cast_copy(p->generators(),v);return p;}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#endif | |
private: void operator=(const _Myt&);private: _MyTuple v;}; | |
#else | |
template<typename Generator1,typename Generator2,typename ParamType>class iuICartesianProductGeneratorBase:public iuIParamGenerator<ParamType >{public: iuICartesianProductGeneratorBase(const Generator1& g1,const Generator2& g2):m_g1(g1),m_g2(g2){}public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_g1.Begin();m_g2.Begin();}virtual void Next() IUTEST_CXX_OVERRIDE{if(m_g2.IsEnd()){return;}m_g2.Next();if(m_g2.IsEnd()){m_g1.Next();if(!m_g1.IsEnd()){m_g2.Begin();}}}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return m_g1.IsEnd()&&m_g2.IsEnd();}protected: Generator1 m_g1;Generator2 m_g2;};template<typename T1,typename T2>class iuCartesianProductGenerator2: public iuICartesianProductGeneratorBase<iuParamGenerator<T1>,iuParamGenerator<T2>,tuples::tuple<T1,T2> >{typedef iuICartesianProductGeneratorBase<iuParamGenerator<T1>,iuParamGenerator<T2>,tuples::tuple<T1,T2> > _Mybase;typedef iuParamGenerator<T1> Generator1;typedef iuParamGenerator<T2> Generator2;public: typedef tuples::tuple<T1,T2> ParamType;public: iuCartesianProductGenerator2(const Generator1 &g1,const Generator2 &g2):_Mybase(g1,g2){}public: virtual ParamType GetCurrent()const IUTEST_CXX_OVERRIDE{return ParamType(this->m_g1.GetCurrent(),this->m_g2.GetCurrent());}}; | |
#define II_D_C_P_GEN_TYPEDEF_(i,p1,p2) typedef iuParamGenerator<IUTEST_PP_CAT(p1,i)> IUTEST_PP_CAT(p2,i); | |
#define II_D_C_P_GEN_TUPLEGET_(i,param) tuples::get<i>(param) | |
#define II_D_C_P_GEN_BASE_(n) iuICartesianProductGeneratorBase<iuParamGenerator<T0> ,IUTEST_PP_CAT(iuCartesianProductGenerator,IUTEST_PP_DEC(n))< IUTEST_PP_ENUM_SHIFTED_PARAMS(IUTEST_PP_DEC(n),T)> ,tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> > | |
#define II_D_C_P_GEN_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> class IUTEST_PP_CAT(iuCartesianProductGenerator,n) : public II_D_C_P_GEN_BASE_(n){typedef II_D_C_P_GEN_BASE_(n) _Mybase;IUTEST_PP_REPEAT_BINARY(n,II_D_C_P_GEN_TYPEDEF_,T,Generator) public: typedef tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> ParamType;IUTEST_PP_CAT(iuCartesianProductGenerator,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,const Generator,&g)) : _Mybase(g0,IUTEST_PP_CAT(iuCartesianProductGenerator,IUTEST_PP_DEC(n))< IUTEST_PP_ENUM_SHIFTED_PARAMS(IUTEST_PP_DEC(n),T)> (IUTEST_PP_ENUM_SHIFTED_PARAMS(IUTEST_PP_DEC(n),g))){}virtual ParamType GetCurrent()const IUTEST_CXX_OVERRIDE{tuples::tuple<IUTEST_PP_ENUM_SHIFTED_PARAMS(IUTEST_PP_DEC(n),T)> params(this->m_g2.GetCurrent());return ParamType(this->m_g1.GetCurrent(),IUTEST_PP_ENUM(IUTEST_PP_DEC(n) ,II_D_C_P_GEN_TUPLEGET_,params));}} | |
II_D_C_P_GEN_(3);II_D_C_P_GEN_(4);II_D_C_P_GEN_(5);II_D_C_P_GEN_(6);II_D_C_P_GEN_(7);II_D_C_P_GEN_(8);II_D_C_P_GEN_(9); | |
#undef II_D_C_P_GEN_TYPEDEF_ | |
#undef II_D_C_P_GEN_TUPLEGET_ | |
#undef II_D_C_P_GEN_BASE_ | |
#undef II_D_C_P_GEN_ | |
#define II_D_C_P_HLR_CONSTRUCT_(i,p1,p2) IUTEST_PP_CAT(p1,i)(IUTEST_PP_CAT(p2,i)) | |
#define II_D_C_P_HLR_STATICCAST_(i,p1,p2) static_cast<iuIParamGenerator<IUTEST_PP_CAT(p1,i)>* >(IUTEST_PP_CAT(p2,i)) | |
#define II_D_C_P_HLR_VARIABLE_(i,p1,p2) IUTEST_PP_CAT(p1,i) IUTEST_PP_CAT(p2,i); | |
#if IUTEST_HAS_CONCAT | |
#define II_D_C_P_HLR_CONCAT_() template<typename Other> iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#else | |
#define II_D_C_P_HLR_CONCAT_() | |
#endif | |
#define II_D_C_P_HLR_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename Generator)> class IUTEST_PP_CAT(iuCartesianProductHolder,n){typedef IUTEST_PP_CAT(iuCartesianProductHolder,n)<IUTEST_PP_ENUM_PARAMS(n,Generator)> _Myt;public: IUTEST_PP_CAT(iuCartesianProductHolder,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,const Generator,&g)) : IUTEST_PP_ENUM_BINARY(n,II_D_C_P_HLR_CONSTRUCT_,m_g,g){}template<IUTEST_PP_ENUM_PARAMS(n,typename T)> operator iuIParamGenerator<tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> >*()const{return new IUTEST_PP_CAT(iuCartesianProductGenerator,n)<IUTEST_PP_ENUM_PARAMS(n,T)>(IUTEST_PP_ENUM_BINARY(n,II_D_C_P_HLR_STATICCAST_,T,m_g));}II_D_C_P_HLR_CONCAT_() private: void operator=(const _Myt&){}IUTEST_PP_REPEAT_BINARY(n,II_D_C_P_HLR_VARIABLE_,const Generator,m_g) } | |
II_D_C_P_HLR_(2);II_D_C_P_HLR_(3);II_D_C_P_HLR_(4);II_D_C_P_HLR_(5);II_D_C_P_HLR_(6);II_D_C_P_HLR_(7);II_D_C_P_HLR_(8);II_D_C_P_HLR_(9); | |
#undef II_D_C_P_HLR_CONSTRUCT_ | |
#undef II_D_C_P_HLR_STATICCAST_ | |
#undef II_D_C_P_HLR_VARIABLE_ | |
#undef II_D_C_P_HLR_CONCAT_ | |
#undef II_D_C_P_HLR_ | |
#endif | |
#endif | |
#if IUTEST_HAS_PAIRWISE | |
class iuPairwiseGeneratorBase{protected: template<int N>struct ParamIndexes{int index[N];ParamIndexes(){for(int i=0;i<N;++i) index[i]=-1;}};private: struct PairInfo{PairInfo(int r1,int r2,int i1,int i2):raw1(r1),raw2(r2),idx1(i1),idx2(i2){}int raw1,raw2;int idx1,idx2;};protected: template<typename T1>static void MakeParamVector(::std::vector<T1>& list,iuParamGenerator<T1>& g1){for(g1.Begin();!g1.IsEnd();g1.Next()){list.push_back(g1.GetCurrent());}}template<typename T1,typename T2>static void MakePairList(::std::vector< ::std::pair<T1,T2> >& list,iuParamGenerator<T1>& g1,iuParamGenerator<T2>& g2){for(g1.Begin();!g1.IsEnd();g1.Next()){T1 t1=g1.GetCurrent();for(g2.Begin();!g2.IsEnd();g2.Next()){ | |
#if IUTEST_HAS_STD_EMPLACE | |
list.emplace_back(t1,g2.GetCurrent()); | |
#else | |
list.push_back(::std::pair<T1,T2>(t1,g2.GetCurrent())); | |
#endif | |
}}}template<int N>static void MakeIndexList(::std::vector<ParamIndexes<N> >& list,int* count_list){typedef typename ::std::vector<ParamIndexes<N> >::iterator list_iterator;list.clear();::std::vector<PairInfo> pair_list;for(int i=0;i<N;++i){int l=count_list[i];for(int j=i+1;j<N;++j){int r=count_list[j];for(int li=0;li<l;++li){for(int ri=0;ri<r;++ri){ | |
#if IUTEST_HAS_STD_EMPLACE | |
pair_list.emplace_back(i,j,li,ri); | |
#else | |
PairInfo info(i,j,li,ri);pair_list.push_back(info); | |
#endif | |
}}}}iuRandom random;unsigned int seed=TestEnv::get_random_seed();if(seed!=0){random.init(seed);}random.shuffle(pair_list.begin(),pair_list.end());for(::std::vector<PairInfo>::const_iterator it=pair_list.begin();it!=pair_list.end();++it){const PairInfo& pair_info=*it;list_iterator find=Find(list,pair_info,list.begin());if(find==list.end()){find=FindFree(list,pair_info,list.begin());if(find==list.end()){ParamIndexes<N> params;params.index[pair_info.raw1]=pair_info.idx1;params.index[pair_info.raw2]=pair_info.idx2;list.push_back(params);}else{ParamIndexes<N>& params=*find;params.index[pair_info.raw1]=pair_info.idx1;params.index[pair_info.raw2]=pair_info.idx2;}}}}template<int N,typename Fn>static int GetParamIndex(const ParamIndexes<N>& indexes,int raw,size_t count,Fn& func){return indexes.index[raw]==-1?func(count):indexes.index[raw];}template<int N,typename T>static T GetParam(const ::std::vector<T>& params,const ParamIndexes<N>& indexes,int raw){const int index=GetParamIndex(indexes,raw,params.size(),TestEnv::genrand());return params[index];}private: template<int N>static typename ::std::vector<ParamIndexes<N> >::iterator Find(::std::vector<ParamIndexes<N> >& list,const PairInfo& pair_info,typename ::std::vector<ParamIndexes<N> >::iterator start){typedef typename ::std::vector<ParamIndexes<N> >::iterator iterator;for(iterator it=start,end=list.end();it!=end;++it){ParamIndexes<N>& indexes=*it;if(indexes.index[pair_info.raw1]==pair_info.idx1&& indexes.index[pair_info.raw2]==pair_info.idx2){return it;}}return list.end();}template<int N>static typename ::std::vector<ParamIndexes<N> >::iterator FindFree(::std::vector<ParamIndexes<N> >& list,const PairInfo& pair_info,typename ::std::vector<ParamIndexes<N> >::iterator start){typedef typename ::std::vector<ParamIndexes<N> >::iterator iterator;iterator find=list.end();UInt32 max_overlap=static_cast<UInt32>(-1);for(iterator it=start,end=list.end();it!=end;++it){ParamIndexes<N>& indexes=*it;int free_raw=-1;int free_idx=-1;if(indexes.index[pair_info.raw1]==-1&&indexes.index[pair_info.raw2]==pair_info.idx2){free_raw=pair_info.raw1;free_idx=pair_info.idx1;}if(indexes.index[pair_info.raw2]==-1&&indexes.index[pair_info.raw1]==pair_info.idx1){free_raw=pair_info.raw2;free_idx=pair_info.idx2;}if(free_raw!=-1){UInt32 overlap=0;for(int i=0;i<N;++i){if(indexes.index[i]==-1||i==free_raw){continue;}PairInfo tmp(i,free_raw,indexes.index[i],free_idx);iterator it2=Find(list,tmp,list.begin());while(it2!=end){++overlap;++it2;it2=Find(list,tmp,it2);}}if(overlap==0){return it;}if(find==list.end()||(overlap<max_overlap)){find=it;max_overlap=overlap;}}}if(find!=list.end()){return find;}typedef typename ::std::vector<ParamIndexes<N> >::iterator iterator;for(iterator it=start,end=list.end();it!=end;++it){ParamIndexes<N>& indexes=*it;if(indexes.index[pair_info.raw1]==-1&&indexes.index[pair_info.raw2]==-1){return it;}}return list.end();}}; | |
#if IUTEST_HAS_VARIADIC_PAIRWISE | |
template<typename... Args>class iuPairwiseGenerator:public iuPairwiseGeneratorBase{typedef tuples::tuple<Args... > ParamType;typedef tuples::tuple<iuParamGenerator<Args>... > GeneratorTuple;static const int kRAW_COUNT=sizeof...(Args);typedef ParamIndexes<kRAW_COUNT> _MyParamIndexes;typedef ::std::vector<_MyParamIndexes>ParamIndexesList;typedef tuples::tuple< ::std::vector<Args>... > ParamsTuple;public: static iuIParamGenerator<ParamType >* Create(GeneratorTuple& generators){ParamIndexesList list;ParamVecotrs param_vectors(generators);MakeIndexList(list,param_vectors.count_list);::std::vector<ParamType> params;for(typename ParamIndexesList::const_iterator it=list.begin(),end=list.end();it!=end;++it){const _MyParamIndexes& indexes=*it;params.push_back(MakeParam<0,Args...>(param_vectors.params_list,indexes));}return new iuValuesInParamsGenerator<ParamType >(params);}private: template<int N,typename T1,typename... TArgs>static tuples::tuple<T1,TArgs...> MakeParam(ParamsTuple& list,const _MyParamIndexes& indexes,typename detail::disable_if<N==kRAW_COUNT -1,void>::type*& = detail::enabler::value){return ::std::tuple_cat(tuples::tuple<T1>(GetParam(tuples::get<N>(list),indexes,N)),MakeParam<N+1,TArgs...>(list,indexes));}template<int N,typename T1,typename... TArgs>static tuples::tuple<T1> MakeParam(ParamsTuple& list,const _MyParamIndexes& indexes,typename detail::enable_if<N==kRAW_COUNT -1,void>::type*& = detail::enabler::value){return tuples::tuple<T1>(GetParam(tuples::get<N>(list),indexes,N));}struct ParamVecotrs{ParamsTuple params_list;int count_list[kRAW_COUNT];template<int N>void MakeParamVecotrs(GeneratorTuple& generators,typename detail::disable_if<N==kRAW_COUNT -1,void>::type*& = detail::enabler::value){MakeParamVector(tuples::get<N>(params_list),tuples::get<N>(generators));count_list[N]=static_cast<int>(tuples::get<N>(params_list).size());MakeParamVecotrs<N+1>(generators);}template<int N>void MakeParamVecotrs(GeneratorTuple& generators,typename detail::enable_if<N==kRAW_COUNT -1,void>::type*& = detail::enabler::value){MakeParamVector(tuples::get<N>(params_list),tuples::get<N>(generators));count_list[N]=static_cast<int>(tuples::get<N>(params_list).size());}explicit ParamVecotrs(GeneratorTuple& generators){MakeParamVecotrs<0>(generators);}};};template<typename... Generator>class iuPairwiseHolder{typedef iuPairwiseHolder<Generator...> _Myt;typedef tuples::tuple<const Generator...> _MyTuple;public: explicit iuPairwiseHolder(const Generator&... generators):v(generators...){}public: template<typename... Args>operator iuIParamGenerator<tuples::tuple<Args...> >*()const{tuples::tuple<iuParamGenerator<Args>... > generators;tuples::tuple_cast_copy(generators,v);return iuPairwiseGenerator<Args...>::Create(generators);}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#endif | |
private: void operator=(const _Myt&);private: _MyTuple v;}; | |
#else | |
template<typename T1,typename T2>class iuPairwiseGenerator2:public iuIParamGenerator<tuples::tuple<T1,T2> >{typedef iuParamGenerator<T1> Generator1;typedef iuParamGenerator<T2> Generator2;public: typedef tuples::tuple<T1,T2> ParamType;public: iuPairwiseGenerator2(const Generator1& g1,const Generator2& g2):m_g1(g1),m_g2(g2){}static iuIParamGenerator<ParamType >* Create(const Generator1& g1,const Generator2& g2){return new iuPairwiseGenerator2<T1,T2>(g1,g2);}public: virtual void Begin() IUTEST_CXX_OVERRIDE{m_g1.Begin();m_g2.Begin();}virtual void Next() IUTEST_CXX_OVERRIDE{if(m_g2.IsEnd()){return;}m_g2.Next();if(m_g2.IsEnd()){m_g1.Next();if(!m_g1.IsEnd()){m_g2.Begin();}}}virtual bool IsEnd()const IUTEST_CXX_OVERRIDE{return m_g1.IsEnd()&&m_g2.IsEnd();}virtual ParamType GetCurrent()const IUTEST_CXX_OVERRIDE{return ParamType(this->m_g1.GetCurrent(),this->m_g2.GetCurrent());}private: Generator1 m_g1;Generator2 m_g2;}; | |
#define II_D_PW_GEN_TEMPLATE_T_(i,p1,p2) p1<IUTEST_PP_CAT(T,i)> IUTEST_PP_CAT(p2,i); | |
#define II_D_PW_GEN_MAKEPARAM_VECTOR_(i,p1,p2) MakeParamVector(IUTEST_PP_CAT(p1,i),IUTEST_PP_CAT(p2,i)); | |
#define II_D_PW_GEN_PARAM_SIZE_(i,param) static_cast<int>(IUTEST_PP_CAT(param,i).size()) | |
#define II_D_PW_GEN_GETPARAM_(i,param) GetParam(IUTEST_PP_CAT(param,i),indexes,i) | |
#define II_D_PW_GEN_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> class IUTEST_PP_CAT(iuPairwiseGenerator,n):public iuPairwiseGeneratorBase{IUTEST_PP_REPEAT_BINARY(n,II_D_PW_GEN_TEMPLATE_T_,typedef iuParamGenerator,Generator) typedef ParamIndexes<n> _MyParamIndexes;typedef ::std::vector<_MyParamIndexes>ParamIndexesList;public: typedef tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> ParamType;static iuIParamGenerator<ParamType >* Create(IUTEST_PP_ENUM_BINARY_PARAMS(n,Generator,g)){ParamIndexesList list;IUTEST_PP_REPEAT_BINARY(n,II_D_PW_GEN_TEMPLATE_T_,::std::vector,params) IUTEST_PP_REPEAT_BINARY(n,II_D_PW_GEN_MAKEPARAM_VECTOR_,params,g) int count_list[]={IUTEST_PP_ENUM(n,II_D_PW_GEN_PARAM_SIZE_,params)};MakeIndexList(list,count_list);::std::vector<ParamType> params;for(typename ParamIndexesList::const_iterator it=list.begin(),end=list.end();it!=end;++it){const _MyParamIndexes& indexes=*it;params.push_back(ParamType(IUTEST_PP_ENUM(n,II_D_PW_GEN_GETPARAM_,params)));}return new iuValuesInParamsGenerator<ParamType >(params);}} | |
II_D_PW_GEN_(3);II_D_PW_GEN_(4);II_D_PW_GEN_(5);II_D_PW_GEN_(6);II_D_PW_GEN_(7);II_D_PW_GEN_(8);II_D_PW_GEN_(9); | |
#undef II_D_PW_GEN_TEMPLATE_T_ | |
#undef II_D_PW_GEN_MAKEPARAM_VECTOR_ | |
#undef II_D_PW_GEN_PARAM_SIZE_ | |
#undef II_D_PW_GEN_GETPARAM_ | |
#undef II_D_PW_GEN_ | |
#define II_D_PW_HLR_CONSTRUCT_(i,p1,p2) IUTEST_PP_CAT(p1,i)(IUTEST_PP_CAT(p2,i)) | |
#define II_D_PW_HLR_STATICCAST_(i,p1,p2) static_cast<iuIParamGenerator<IUTEST_PP_CAT(p1,i)>* >(IUTEST_PP_CAT(p2,i)) | |
#define II_D_PW_HLR_VARIABLE_(i,p1,p2) IUTEST_PP_CAT(p1,i) IUTEST_PP_CAT(p2,i); | |
#if IUTEST_HAS_CONCAT | |
#define II_D_PW_HLR_CONCAT_() template<typename Other> iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#else | |
#define II_D_PW_HLR_CONCAT_() | |
#endif | |
#define II_D_PW_HLR_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename Generator)> class IUTEST_PP_CAT(iuPairwiseHolder,n){typedef IUTEST_PP_CAT(iuPairwiseHolder,n)<IUTEST_PP_ENUM_PARAMS(n,Generator)> _Myt;public: IUTEST_PP_CAT(iuPairwiseHolder,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,const Generator,&g)) : IUTEST_PP_ENUM_BINARY(n,II_D_PW_HLR_CONSTRUCT_,m_g,g){}template<IUTEST_PP_ENUM_PARAMS(n,typename T)> operator iuIParamGenerator<tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> >*()const{return IUTEST_PP_CAT(iuPairwiseGenerator,n)<IUTEST_PP_ENUM_PARAMS(n,T)>::Create(IUTEST_PP_ENUM_BINARY(n,II_D_PW_HLR_STATICCAST_,T,m_g));}II_D_PW_HLR_CONCAT_() private: void operator=(const _Myt&){}IUTEST_PP_REPEAT_BINARY(n,II_D_PW_HLR_VARIABLE_,const Generator,m_g) } | |
II_D_PW_HLR_(2);II_D_PW_HLR_(3);II_D_PW_HLR_(4);II_D_PW_HLR_(5);II_D_PW_HLR_(6);II_D_PW_HLR_(7);II_D_PW_HLR_(8);II_D_PW_HLR_(9); | |
#undef II_D_PW_HLR_CONSTRUCT_ | |
#undef II_D_PW_HLR_STATICCAST_ | |
#undef II_D_PW_HLR_VARIABLE_ | |
#undef II_D_PW_HLR_CONCAT_ | |
#undef II_D_PW_HLR_ | |
#endif | |
#endif | |
#if IUTEST_HAS_VALUESGEN | |
template<typename StdGenerator>class iuValuesParamsGeneratorHolder{typedef iuValuesParamsGeneratorHolder<StdGenerator> _Myt;public: iuValuesParamsGeneratorHolder(size_t num,const StdGenerator& g):m_num(num),m_g(g){}public: template<typename T>operator iuIParamGenerator<T>*()const{::std::vector<T> params(m_num);::std::generate(params.begin(),params.end(),m_g);return new iuValuesInParamsGenerator<T>(params);}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<_Myt,Other> operator+(const Other& g)const{return iuConcatParamHolder<_Myt,Other>(*this,g);} | |
#endif | |
private: size_t m_num;StdGenerator m_g;};template<typename T,typename F>class iuRandomFilterParamGenerator{typedef T type;public: iuRandomFilterParamGenerator(const F& fn,unsigned int seed):m_fn(fn),m_rnd(seed){}type operator()(){type val=m_rnd.genrand();for(;!(m_fn)(val);val=m_rnd.genrand()){}return val;}private: F m_fn;iuTypedRandom<type> m_rnd;}; | |
#endif | |
#if IUTEST_HAS_RANDOMVALUES | |
class iuRandomParamsHolder{public: explicit iuRandomParamsHolder(size_t num,unsigned int seed=0) IUTEST_CXX_NOEXCEPT_SPEC: m_num(num),m_seed(seed){}public: template<typename T>operator iuIParamGenerator<T>*()const{unsigned int seed=m_seed;if(seed==0){seed=GetIndefiniteValue();}iuValuesParamsGeneratorHolder<iuTypedRandom<T> > gen(m_num,iuTypedRandom<T>(seed));return gen;}public: | |
#if IUTEST_HAS_CONCAT | |
template<typename Other>iuConcatParamHolder<iuRandomParamsHolder,Other> operator+(const Other& g)const{return iuConcatParamHolder<iuRandomParamsHolder,Other>(*this,g);} | |
#endif | |
private: size_t m_num;unsigned int m_seed;}; | |
#endif | |
}} | |
#endif | |
#if IUTEST_HAS_CSVPARAMS | |
namespace iutest{namespace detail{template<typename T>class iuCsvFileParamsGenerator:public iuValuesInParamsGenerator<T>{typedef ::std::vector<T> params_t;public: explicit iuCsvFileParamsGenerator(const ::std::string& path,char delimiter=','):iuValuesInParamsGenerator<T>(ReadParams(path,delimiter)){}private: bool ToParam(const ::std::string& data,T& param){::std::istringstream strm(data);if(strm>>param){return true;}return false;}private: void AppendParams(params_t& params,const ::std::string& data){if(StringIsBlank(data)){return;}T param;if(!ToParam(data,param)){return;}params.push_back(param);}params_t ReadParams(const ::std::string& path,char delimiter=','){params_t params;IFile* fp=detail::IFileSystem::New();if(fp!=0){if(fp->Open(path.c_str(),IFile::OpenRead)){const ::std::string dataset=fp->ReadAll();::std::string::size_type prev=0;::std::string::size_type pos=0;while(static_cast<void>(pos=dataset.find(delimiter,prev)),pos!=::std::string::npos){const ::std::string data=dataset.substr(prev,pos-prev);AppendParams(params,data);++pos;prev=pos;}AppendParams(params,dataset.substr(prev));}else{fprintf(stderr,"Unable to open file \"%s\".\n",path.c_str());fflush(stderr);}detail::IFileSystem::Free(fp);}IUTEST_CHECK_(!params.empty());return params;}};template<>inline bool iuCsvFileParamsGenerator<float>::ToParam(const ::std::string& data,float& param){ | |
#if IUTEST_HAS_STD_STR_TO_VALUE | |
param=::std::stof(data);return true; | |
#else | |
::std::istringstream strm(data);if(!(strm>>param)){param=static_cast<float>(atof(data.c_str()));}return true; | |
#endif | |
}}} | |
#endif | |
#if IUTEST_HAS_PARAM_TEST | |
#include <vector> | |
namespace iutest{namespace detail{class iuIObject{public: virtual ~iuIObject(){}};class iuPool{typedef ::std::vector<iuIObject*> pool;pool m_pool;public: typedef iuIObject *value_ptr;public: ~iuPool(){for(pool::iterator it=m_pool.begin();it!=m_pool.end();){value_ptr p=*it;it=m_pool.erase(it);delete p;}}public: void push(value_ptr ptr){m_pool.push_back(ptr);}public: static iuPool& GetInstance(){static iuPool inst;return inst;}};}}namespace iutest{namespace detail{class IParamTestInfoData{public: class EachTestBase:public iuIObject{};template<typename T>class ParamEachTestBase:public EachTestBase{public: virtual void SetParam(const T& param)=0;};public: explicit IParamTestInfoData(const char* name):m_name(name){}virtual ~IParamTestInfoData() IUTEST_CXX_DEFAULT_FUNCTION virtual TestCase* MakeTestCase(const ::std::string&,TestTypeId,SetUpMethod,TearDownMethod)const=0;virtual EachTestBase* RegisterTest(TestCase*,const ::std::string&)const=0;const char* GetName()const{return m_name.c_str();}protected: ::std::string m_name;};class IParamTestCaseInfo{public: virtual ~IParamTestCaseInfo(){}protected: IParamTestCaseInfo(const ::std::string& base_name,const ::std::string& package_name):m_testcase_base_name(base_name),m_package_name(package_name){}IParamTestCaseInfo(const char* base_name,const char* package_name):m_testcase_base_name(base_name),m_package_name(package_name){}public: void AddTestPattern(IParamTestInfoData* testinfo){m_testinfos.push_back(testinfo);}public: void RegisterTests()const{for(TestInfoContainer::const_iterator it=m_testinfos.begin(),end=m_testinfos.end();it!=end;++it){OnRegisterTests(*it);}}::std::string GetTestCaseBaseName()const{return m_testcase_base_name;}::std::string GetPackageName()const{return m_package_name;}public: bool is_same(const ::std::string& base_name,const ::std::string& package_name){return m_testcase_base_name==base_name&&m_package_name==package_name;}bool is_same(const char* base_name,const char* package_name){return m_testcase_base_name==base_name&&m_package_name==package_name;}private: virtual void OnRegisterTests(IParamTestInfoData*)const=0;private: typedef ::std::vector<IParamTestInfoData*> TestInfoContainer;TestInfoContainer m_testinfos;protected: ::std::string m_testcase_base_name;::std::string m_package_name;};template<class T>class ParamTestCaseInfo:public IParamTestCaseInfo{typedef T Tester;typedef typename Tester::ParamType ParamType;typedef detail::iuIParamGenerator<ParamType> ParamGenerator;typedef typename ParamGenerator::Generator Generator;typedef IParamTestInfoData::ParamEachTestBase<ParamType> EachTest;typedef ::std::vector<IParamTestInfoData*> TestInfoContainer;typedef ParamGenerator*(*pfnCreateGeneratorFunc)();typedef ::std::string(*pfnParamNameGeneratorFunc)(const TestParamInfo<ParamType>&);class Functor{public: Functor():CreateGen(0),ParamNameGen(0){}Functor(pfnCreateGeneratorFunc c,pfnParamNameGeneratorFunc p):CreateGen(c),ParamNameGen(p){}pfnCreateGeneratorFunc CreateGen;pfnParamNameGeneratorFunc ParamNameGen;};public: ParamTestCaseInfo(const ::std::string& testcase_name,const ::std::string& package_name):IParamTestCaseInfo(testcase_name,package_name){}ParamTestCaseInfo(const char* testcase_name,const char* package_name):IParamTestCaseInfo(testcase_name,package_name){}virtual ~ParamTestCaseInfo(){}int AddTestCaseInstantiation(::std::string name,pfnCreateGeneratorFunc create_func,pfnParamNameGeneratorFunc paramname_func){ | |
#if IUTEST_HAS_STD_EMPLACE | |
m_instantiation.emplace_back(name,Functor(create_func,paramname_func)); | |
#else | |
m_instantiation.push_back(InstantiationPair(name,Functor(create_func,paramname_func))); | |
#endif | |
return 0;}virtual void OnRegisterTests(IParamTestInfoData* infodata)const IUTEST_CXX_OVERRIDE{for(typename InstantiationContainer::const_iterator gen_it=m_instantiation.begin(),gen_end=m_instantiation.end();gen_it!=gen_end;++gen_it){detail::scoped_ptr<ParamGenerator> p((gen_it->second.CreateGen)());const ::std::string testcase_name=CreateTestCaseName(gen_it->first);TestCase* testcase=infodata->MakeTestCase(testcase_name,internal::GetTypeId<Tester>(),Tester::SetUpTestCase,Tester::TearDownTestCase);if(p.get()!=0){size_t i=0;for(p->Begin();!p->IsEnd();p->Next()){const ::std::string name=MakeParamTestName(infodata->GetName(),gen_it->second.ParamNameGen(TestParamInfo<ParamType>(p->GetCurrent(),i))); | |
#if IUTEST_CHECK_STRICT | |
if(!CheckTestName(testcase,name)){IUTEST_LOG_(WARNING)<<testcase_name<<"." <<name<<" is already exist.";} | |
#endif | |
EachTest* test=static_cast<EachTest*>(infodata->RegisterTest(testcase,name));test->SetParam(p->GetCurrent());++i;}}}}static ::std::string DefaultParamNameFunc(const TestParamInfo<ParamType>& info){return Tester::MakeTestParamName(info);}template<typename ParamNameFunctor>static ParamNameFunctor GetParamNameGen(ParamNameFunctor func){return func;}static pfnParamNameGeneratorFunc GetParamNameGen(){return DefaultParamNameFunc;}private: ::std::string CreateTestCaseName(const ::std::string& generator_name)const{::std::string testcase_name=m_package_name;if(!generator_name.empty()){testcase_name+=generator_name;testcase_name+="/";}testcase_name+=m_testcase_base_name;return testcase_name;}private: static bool CheckTestName(const TestCase* testcase,const::std::string& name){const int count=testcase->total_test_count();for(int i=0;i<count;++i){if(detail::IsStringEqual(name.c_str(),testcase->GetTestInfo(i)->name())){return false;}}return true;}private: typedef ::std::pair< ::std::string,Functor>InstantiationPair;typedef ::std::vector<InstantiationPair> InstantiationContainer;InstantiationContainer m_instantiation;};class ParamTestCaseHolder{private: ~ParamTestCaseHolder(){for(TestCaseInfoContainer::const_iterator it=m_testcase_infos.begin(),end=m_testcase_infos.end();it!=end;++it){delete *it;}}public: template<typename T>ParamTestCaseInfo<T>* GetTestCasePatternHolder(const ::std::string& testcase,const ::std::string& package IUTEST_APPEND_EXPLICIT_TEMPLATE_TYPE_(T)){ParamTestCaseInfo<T>* p=static_cast<ParamTestCaseInfo<T>*>(FindTestCasePatternHolder(testcase,package));if(p==0){p=new ParamTestCaseInfo<T>(testcase,package);m_testcase_infos.push_back(p);}return p;}private: template<typename T>IParamTestCaseInfo* FindTestCasePatternHolder(const T& testcase,const T& package){for(TestCaseInfoContainer::iterator it=m_testcase_infos.begin(),end=m_testcase_infos.end();it!=end;++it){if((*it)->is_same(testcase,package)){return(*it);}}return 0;}public: size_t count()const{return m_testcase_infos.size();}private: struct RegisterTestsFunctor{inline void operator()(const IParamTestCaseInfo* p)const{p->RegisterTests();}};void RegisterTests(){::std::for_each(m_testcase_infos.begin(),m_testcase_infos.end(),RegisterTestsFunctor());}private: friend class ::iutest::UnitTest;typedef ::std::vector<IParamTestCaseInfo*> TestCaseInfoContainer;TestCaseInfoContainer m_testcase_infos;};}} | |
#endif | |
namespace iutest{class UnitTest:public UnitTestImpl{public: static UnitTest& instance(){static UnitTest inst;return inst;}static UnitTest* GetInstance(){return &instance();}public: const TestCase* current_test_case()const{return m_current_testcase;}const TestInfo* current_test_info()const{return Test::GetCurrentTestInfo();}unsigned int random_seed()const{return TestEnv::current_random_seed();}int repeat_counter()const IUTEST_CXX_NOEXCEPT_SPEC{return m_repeat_counter;}int repeat_count()const IUTEST_CXX_NOEXCEPT_SPEC{return TestEnv::get_repeat_count();}public: int total_test_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_total_test_num;}int reportable_test_count()const;int test_to_run_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_should_run_num;}int failed_test_count()const;int disabled_test_count()const IUTEST_CXX_NOEXCEPT_SPEC{return m_disable_num;}int reportable_disabled_test_count()const;int successful_test_count()const;int skip_test_count()const;int reportable_skip_test_count()const;int test_run_skipped_count()const;int reportable_test_run_skipped_count()const;int total_test_case_count()const{return m_testcases.size();}int test_case_to_run_count()const;int successful_test_case_count()const;int failed_test_case_count()const;const TestResult* ad_hoc_testresult()const IUTEST_CXX_NOEXCEPT_SPEC{return ad_hoc_test_result();}const TestResult* ad_hoc_test_result()const IUTEST_CXX_NOEXCEPT_SPEC{return &m_ad_hoc_testresult;}TimeInMillisec elapsed_time()const IUTEST_CXX_NOEXCEPT_SPEC{return m_elapsedmsec;}TimeInMillisec start_timestamp()const IUTEST_CXX_NOEXCEPT_SPEC{return m_start_timestamp;}const TestCase* GetTestCase(int index)const{return m_testcases[index];}bool Passed()const;bool Failed()const{return !Passed();}TestEventListeners& listeners()const{return TestEnv::event_listeners();}protected: int Run();private:int RunImpl();bool RunOnce();private: void TestProgramStart();void SetUpTestIteration();void EnvironmentSetUp();void EnvironmentTearDown();void TestProgramEnd();private: static void OnExit(){instance().TestProgramEnd();}private: UnitTest():m_repeat_counter(0),m_init_iutest_count(0),m_test_started(false),m_start_timestamp(0){TestEnv::SetGlobalTestPartResultReporter(&m_default_test_part_result_reporter);TestEnv::LoadEnvironmentVariable();}~UnitTest(){TestEnv::ReleaseGlobalTestEnvironment();TestEnv::SetGlobalTestPartResultReporter(0);}private: void Initialize(); | |
#if IUTEST_HAS_PARAM_TEST | |
public: detail::ParamTestCaseHolder& parameterized_test_registry() IUTEST_CXX_NOEXCEPT_SPEC{return m_param_testcase_holder;}private: detail::ParamTestCaseHolder m_param_testcase_holder; | |
#endif | |
private: friend class UnitTestSource;int m_repeat_counter;int m_init_iutest_count;bool m_test_started;TimeInMillisec m_start_timestamp;detail::DefaultGlobalTestPartResultReporter m_default_test_part_result_reporter;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(UnitTest);};namespace detail{template<class Tester>class TestInstance{public: TestInstance(const char* testcase,const char* name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):m_mediator(AddTestCase(testcase,id,setup,teardown)),m_info(&m_mediator,name,&m_factory){UnitTest::instance().AddTestInfo(m_mediator.ptr(),&m_info);}TestInstance(const ::std::string& testcase,const char* name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):m_mediator(AddTestCase(testcase,id,setup,teardown)),m_info(&m_mediator,name,&m_factory){UnitTest::instance().AddTestInfo(m_mediator.ptr(),&m_info);}TestInstance(const char* testcase,const char* name,const char* value_params,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):m_mediator(AddTestCase(testcase,id,setup,teardown)),m_info(&m_mediator,name,&m_factory){m_info.set_value_param(value_params);UnitTest::instance().AddTestInfo(m_mediator.ptr(),&m_info);}TestInstance(const ::std::string& testcase,const char* name,const char* value_params,TestTypeId id,SetUpMethod setup,TearDownMethod teardown):m_mediator(AddTestCase(testcase,id,setup,teardown)),m_info(&m_mediator,name,&m_factory){m_info.set_value_param(value_params);UnitTest::instance().AddTestInfo(m_mediator.ptr(),&m_info);}private: TestCase* AddTestCase(const char* testcase,TestTypeId id,SetUpMethod setup,TearDownMethod teardown){return UnitTest::instance().AddTestCase<TestCase>(testcase,id,setup,teardown);}TestCase* AddTestCase(const ::std::string& testcase,TestTypeId id,SetUpMethod setup,TearDownMethod teardown){return UnitTest::instance().AddTestCase<TestCase>(testcase,id,setup,teardown);}private: TestCaseMediator m_mediator;TestInfo m_info;iuFactory<Tester> m_factory;};}}namespace iutest{inline int UnitTest::reportable_test_count()const{return detail::SumOverList(m_testcases,&TestCase::reportable_test_count);}inline int UnitTest::failed_test_count()const{return detail::SumOverList(m_testcases,&TestCase::failed_test_count);}inline int UnitTest::reportable_disabled_test_count()const{return detail::SumOverList(m_testcases,&TestCase::reportable_disabled_test_count);}inline int UnitTest::successful_test_count()const{return detail::SumOverList(m_testcases,&TestCase::successful_test_count);}inline int UnitTest::skip_test_count()const{return detail::SumOverList(m_testcases,&TestCase::skip_test_count);}inline int UnitTest::reportable_skip_test_count()const{return detail::SumOverList(m_testcases,&TestCase::reportable_skip_test_count);}inline int UnitTest::test_run_skipped_count()const{return detail::SumOverList(m_testcases,&TestCase::test_run_skipped_count);}inline int UnitTest::reportable_test_run_skipped_count()const{return detail::SumOverList(m_testcases,&TestCase::reportable_test_run_skipped_count);}inline int UnitTest::test_case_to_run_count()const{return detail::CountIfOverList(m_testcases,&TestCase::should_run);}inline int UnitTest::successful_test_case_count()const{return detail::CountIfOverList(m_testcases,&TestCase::Passed);}inline int UnitTest::failed_test_case_count()const{return detail::CountIfOverList(m_testcases,&TestCase::Failed);}inline bool UnitTest::Passed()const{if(m_ad_hoc_testresult.Failed()){return false;}for(iuTestCases::const_iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){if((it)->Failed()){return false;}}return true;}inline int UnitTest::Run(){if(m_init_iutest_count==0){{detail::iuConsole::output("This test program did NOT call ::iutest::InitIrisUnitTest before calling IUTEST_RUN_ALL_TESTS(). Please fix it.\n");return 1;}}if(!PreRunner()){return Passed()?0:1;} | |
#if IUTEST_HAS_EXCEPTIONS | |
if(TestFlag::IsEnableFlag(TestFlag::CATCH_EXCEPTION_GLOBAL)){int ret=1;try{ret=RunImpl();}catch(...){}return ret;} | |
#endif | |
return RunImpl();}inline int UnitTest::RunImpl(){m_repeat_counter=0;int repeat=TestEnv::get_repeat_count();bool result=true;if(repeat!=0){m_start_timestamp=detail::GetTimeInMillis();TestProgramStart();while(repeat){SetUpTestIteration();listeners().OnTestIterationStart(*this,m_repeat_counter);if(!RunOnce()){result=false;}listeners().OnTestIterationEnd(*this,m_repeat_counter);++m_repeat_counter;if(repeat>0){--repeat;}}TestProgramEnd();}if(!result){return 1;}if(detail::IUTestLog::HasError()){return 1;}if(IUTEST_FLAG(warning_into_error)){if(detail::IUTestLog::HasWarning()){return 1;}}return 0;}inline bool UnitTest::RunOnce(){m_elapsedmsec=0;ClearNonAdHocTestResult();if(test_to_run_count()==0){return Passed();}if(TestFlag::IsEnableFlag(TestFlag::SHUFFLE_TESTS)){detail::RandomShuffle(m_testcases,TestEnv::genrand());}EnvironmentSetUp();if(m_ad_hoc_testresult.HasFatalFailure()){return false;}{detail::iuStopWatch sw;sw.start();for(iuTestCases::iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){m_current_testcase=it;(it)->Run();m_current_testcase=0;}m_elapsedmsec=sw.stop();}EnvironmentTearDown();return Passed();}inline void UnitTest::TestProgramStart(){m_should_run_num=0;m_disable_num=0;for(iuTestCases::iterator it=m_testcases.begin(),end=m_testcases.end();it!=end;++it){(it)->filter();m_should_run_num+=(it)->test_to_run_count();m_disable_num+=(it)->disabled_test_count();}atexit(OnExit); | |
#if IUTEST_HAS_STD_QUICK_EXIT | |
::std::at_quick_exit(OnExit); | |
#endif | |
m_test_started=true;listeners().OnTestProgramStart(*this);}inline void UnitTest::SetUpTestIteration(){TestEnv::SetUp();}inline void UnitTest::EnvironmentSetUp(){listeners().OnEnvironmentsSetUpStart(*this);for(iuEnvironmentList::iterator it=TestEnv::environments().begin(),end=TestEnv::environments().end();it!=end;++it){(*it)->SetUp();}listeners().OnEnvironmentsSetUpEnd(*this);}inline void UnitTest::EnvironmentTearDown(){listeners().OnEnvironmentsTearDownStart(*this);for(iuEnvironmentList::reverse_iterator it=TestEnv::environments().rbegin(),end=TestEnv::environments().rend();it!=end;++it){(*it)->TearDown();}listeners().OnEnvironmentsTearDownEnd(*this);}inline void UnitTest::TestProgramEnd(){if(!m_test_started){return;}if(current_test_info()!=0){IUTEST_EXPECT_FAILURE("program exit.");}listeners().OnTestProgramEnd(*this);m_test_started=false;}inline void UnitTest::Initialize(){m_init_iutest_count++;ClearAdHocTestResult();if(detail::IFileSystem::GetInstance()==0){ | |
#ifdef IUTEST_FILE | |
static FileSystem<IUTEST_FILE> filesystem;filesystem.Initialize(); | |
#elif IUTEST_HAS_FOPEN | |
static FileSystem<StdioFile> filesystem;filesystem.Initialize(); | |
#endif | |
}if(m_init_iutest_count!=1){return;} | |
#if IUTEST_HAS_PARAM_TEST | |
m_param_testcase_holder.RegisterTests(); | |
#endif | |
}}namespace iutest{class any{typedef internal::TypeId type_id;public: any():content(0){}template<typename T>any(const T& rhs):content(new holder<T>(rhs)){}any(const any& rhs):content(rhs.content==0?0:rhs.content->clone()){}~any(){delete content;}public: any& swap(any& rhs){::std::swap(content,rhs.content);return *this;}bool empty()const{return content==0;}void clear(){any().swap(*this);}type_id type()const{return content==0?internal::GetTypeId<void>():content->type();}template<typename T>bool type_equal()const{return type()==internal::GetTypeId<T>();}public: template<typename T>any& operator=(const T& rhs){any(rhs).swap(*this);return *this;}any& operator=(const any& rhs){any(rhs).swap(*this);return *this;}template<typename T>friend T* any_cast(any*);template<typename T>friend T* unsafe_any_cast(any*);private: class placeholder{public: virtual ~placeholder(){}virtual type_id type()const=0;virtual placeholder* clone()const=0;};template<typename T>class holder:public placeholder{public: explicit holder(const T& v):held(v){}public: virtual type_id type()const IUTEST_CXX_OVERRIDE{return internal::GetTypeId<T>();}virtual placeholder* clone()const IUTEST_CXX_OVERRIDE{return new holder<T>(held);}public: T held;private: holder& operator=(const holder&);};private: placeholder* content;}; | |
#if IUTEST_HAS_EXCEPTIONS | |
class bad_any_cast:public ::std::bad_cast{}; | |
#endif | |
inline void swap(any& lhs,any& rhs){lhs.swap(rhs);}template<typename T>T* any_cast(any* p){return p!=0&&p->type_equal<T>() ?&(static_cast<any::holder<T>* >(p->content)->held):0;}template<typename T>inline const T* any_cast(const any* p){return any_cast<T>(const_cast<any*>(p));}template<typename T>inline T any_cast(any& value){typedef typename type_traits::remove_reference<T>::type nonref_t;nonref_t* p=any_cast<nonref_t>(&value); | |
#if IUTEST_HAS_EXCEPTIONS | |
if(p==0){throw bad_any_cast();} | |
#endif | |
return static_cast<nonref_t&>(*p);}template<typename T>inline T any_cast(const any& value){return any_cast<T>(const_cast<any&>(value));}template<typename T>T* unsafe_any_cast(any* p){return p!=0 ?&(static_cast<any::holder<T>* >(p->content)->held):0;}template<typename T>inline const T* unsafe_any_cast(const any* p){return unsafe_any_cast<T>(const_cast<any*>(p));}template<typename T>inline T unsafe_any_cast(any& value){typedef typename type_traits::remove_reference<T>::type nonref_t;nonref_t* p=unsafe_any_cast<nonref_t>(&value);return static_cast<nonref_t&>(*p);}template<typename T>inline T unsafe_any_cast(const any& value){return unsafe_any_cast<T>(const_cast<any&>(value));}} | |
#if IUTEST_HAS_PARAM_TEST | |
#if IUTEST_HAS_PARAM_TEST_PARAM_NAME_GENERATOR | |
#define IUTEST_INSTANTIATE_TEST_CASE_P(prefix_,tf_,generator_,...) II_INST_TC_P_(prefix_,tf_,generator_,__VA_ARGS__) | |
#else | |
#define IUTEST_INSTANTIATE_TEST_CASE_P(prefix_,tf_,generator_) II_INST_TC_P_(prefix_,tf_,generator_) | |
#endif | |
#define IUTEST_P(tf_,tn_) IUTEST_TEST_P_(tf_,tn_) | |
#if IUTEST_HAS_ANY_PARAM_TEST | |
#define IUTEST_INSTANTIATE_TEST_CASE_AP(prefix_,testcase_,generator_) II_INST_TC_P_(prefix_,IUTEST_ALIAS_TESTNAME_F(testcase_,iuTestWithAny),generator_) | |
#define IUTEST_AP(testcase_,tn_) IUTEST_TEST_P_(IUTEST_ALIAS_TESTNAME_F(testcase_,iuTestWithAny),tn_) | |
#endif | |
#define II_GTCPH(T,testcase_,package_) ::iutest::UnitTest::GetInstance()->parameterized_test_registry().GetTestCasePatternHolder<T>(testcase_,package_) | |
#if IUTEST_HAS_AUTOFIXTURE_PARAM_TEST | |
#define II_T_P_FX_D_(testcase_) | |
#define II_T_P_B_FX(testcase_) ::iutest::detail::paramtest_select_base_testcase<void(int(II_TO_VN_(testcase_)))>::type | |
#else | |
#define II_T_P_FX_D_(testcase_) | |
#define II_T_P_B_FX(testcase_) II_TO_VN_(testcase_) | |
#endif | |
#if IUTEST_HAS_PARAM_TEST_PARAM_NAME_GENERATOR | |
#define II_INST_TC_P_(prefix_,testcase_,generator_,...) II_INST_TC_P_I(prefix_,testcase_,generator_,GetParamNameGen(__VA_ARGS__)) | |
#else | |
#define II_INST_TC_P_(prefix_,testcase_,generator_) II_INST_TC_P_I(prefix_,testcase_,generator_,GetParamNameGen()) | |
#endif | |
#if IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define II_INST_TC_P_I(prefix_,testcase_,generator_,paramname_generator_) II_INST_TC_P_II(prefix_,IUTEST_PP_IF(IUTEST_PP_IS_BEGIN_PARENS(testcase_) ,IUTEST_ALIAS_TESTNAME_F_,IUTEST_PP_EMPTY()) testcase_,generator_,paramname_generator_) | |
#else | |
#define II_INST_TC_P_I(prefix_,testcase_,generator_,paramname_generator_) II_INST_TC_P_II(prefix_,testcase_,generator_,paramname_generator_) | |
#endif | |
#define II_INST_TC_P_II(prefix_,testcase_,generator_,paramname_generator_) II_INST_TC_P_III(prefix_,testcase_,II_T_P_B_FX(testcase_) ,generator_,paramname_generator_) | |
#define II_INST_TC_P_III(prefix_,testcase_,basefixture_,generator_,paramname_generator_) II_T_P_FX_D_(testcase_) static ::iutest::detail::iuIParamGenerator<basefixture_::ParamType >* II_T_P_EGEN_N_(prefix_,testcase_)(){return generator_;}static ::std::string II_T_P_PGEN_N_(prefix_,testcase_)(const ::iutest::TestParamInfo<basefixture_::ParamType>&info){return ::iutest::detail::ParamTestCaseInfo<basefixture_ >::paramname_generator_(info);}int II_T_P_INST_R_N_(prefix_,testcase_)(){::iutest::detail::ParamTestCaseInfo<basefixture_ >* p=II_GTCPH(basefixture_,II_TO_N_STR_(testcase_),IUTEST_GET_PACKAGENAME_());return p->AddTestCaseInstantiation(#prefix_ ,II_T_P_EGEN_N_(prefix_,testcase_) ,II_T_P_PGEN_N_(prefix_,testcase_));}II_T_P_INST_R_(prefix_,testcase_) | |
#define II_TEST_P_I_(classname_,testcase_,tcn_,tn_) II_T_P_FX_D_(testcase_) class classname_:public testcase_{public: classname_(){}protected: virtual void Body() IUTEST_CXX_OVERRIDE;private: static int AddRegister(){static ::iutest::detail::ParamTestInstance<classname_>testinfo(tn_);II_GTCPH(testcase_,tcn_ ,IUTEST_GET_PACKAGENAME_())->AddTestPattern(&testinfo);return 0;}static int dummy_;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(classname_);};int classname_::dummy_ IUTEST_ATTRIBUTE_UNUSED_=classname_::AddRegister();void classname_::Body() | |
#define II_TEST_P_(macro,testcase_,tn_) macro(IUTEST_TEST_CLASS_NAME_(testcase_,tn_) ,II_T_P_B_FX(testcase_) ,II_TO_N_STR_(testcase_),II_TO_N_STR_(tn_)) | |
#if IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define II_TEST_P_A_(macro,testcase_,tn_) II_TEST_P_(macro,IUTEST_PP_IF(IUTEST_PP_IS_BEGIN_PARENS(testcase_) ,IUTEST_ALIAS_TESTNAME_F_,IUTEST_PP_EMPTY()) testcase_,tn_) | |
#define IUTEST_TEST_P_(testcase_,tn_) II_TEST_P_A_(II_TEST_P_I_,testcase_,tn_) | |
#else | |
#define IUTEST_TEST_P_(testcase_,tn_) II_TEST_P_(II_TEST_P_I_,testcase_,tn_) | |
#endif | |
#define II_T_P_EGEN_N_(prefix_,testcase_) II_T_P_EGEN_N_I(prefix_,II_TO_VN_(testcase_)) | |
#define II_T_P_EGEN_N_I(prefix_,testcase_) II_T_P_EGEN_N_I_(prefix_,testcase_) | |
#define II_T_P_EGEN_N_I_(prefix_,testcase_) s_##prefix_##_x_iutest_x_##testcase_##_EvalGenerator_ | |
#define II_T_P_PGEN_N_(prefix_,testcase_) II_T_P_PGEN_N_I(prefix_,II_TO_VN_(testcase_)) | |
#define II_T_P_PGEN_N_I(prefix_,testcase_) II_T_P_PGEN_N_I_(prefix_,testcase_) | |
#define II_T_P_PGEN_N_I_(prefix_,testcase_) s_##prefix_##_x_iutest_x_##testcase_##_ParamGenerator_ | |
#define II_T_P_INST_R_N_(prefix_,testcase_) II_T_P_INST_R_N_I(prefix_,II_TO_VN_(testcase_)) | |
#define II_T_P_INST_R_N_I(prefix_,testcase_) II_T_P_INST_R_N_I_(prefix_,testcase_) | |
#define II_T_P_INST_R_N_I_(prefix_,testcase_) prefix_##_x_iutest_x_##testcase_##_TestCaseInstantiationRegister | |
#define II_T_P_INST_R_(prefix_,testcase_) II_T_P_INST_R_I(prefix_,II_TO_VN_(testcase_),II_T_P_INST_R_N_(prefix_,testcase_)) | |
#define II_T_P_INST_R_I(prefix_,testcase_,register_) II_T_P_INST_R_I_(prefix_,testcase_,register_) | |
#define II_T_P_INST_R_I_(prefix_,testcase_,register_) int s_##prefix_##_x_iutest_x_##testcase_##_dummy=register_() | |
namespace iutest{namespace detail{template<typename T>class ParamTestInstance:public IParamTestInfoData{typedef T Tester;typedef typename Tester::ParamType ParamType;typedef detail::iuParamTestFactory<T> Factory;class EachTest IUTEST_CXX_FINAL:public IParamTestInfoData::ParamEachTestBase<ParamType>{public: EachTest(TestCase* testcase,const ::std::string& name):m_mediator(testcase),m_info(&m_mediator,name,&m_factory){UnitTest::instance().AddTestInfo(testcase,&m_info);}private: virtual void SetParam(const ParamType& param) IUTEST_CXX_OVERRIDE{m_factory.SetParam(param);m_info.set_value_param(PrintToString(param).c_str());}private: TestCaseMediator m_mediator;Factory m_factory;TestInfo m_info;};public: explicit ParamTestInstance(const char* testcase_name):IParamTestInfoData(testcase_name){}private: virtual TestCase* MakeTestCase(const ::std::string& testcase_name,TestTypeId id,SetUpMethod setup,TearDownMethod teardown)const IUTEST_CXX_OVERRIDE{return UnitTest::instance().AddTestCase<TestCase>(testcase_name,id,setup,teardown);}virtual IParamTestInfoData::EachTestBase* RegisterTest(TestCase* testcase,const ::std::string& name)const IUTEST_CXX_OVERRIDE{EachTest* test=new EachTest(testcase,name);detail::iuPool::GetInstance().push(test);return test;}};}class TestWithAny:public Test,public WithParamInterface<any>{public: static const ParamType& GetParam(){return WithParamInterface<any>::GetParam();}template<typename T>static T GetParam(){return unsafe_any_cast<T>(WithParamInterface<any>::GetParam());}};namespace detail{template<typename T>struct paramtest_select_base_testcase;template<>struct paramtest_select_base_testcase<void(int)>{typedef TestWithAny type;};template<typename T>struct paramtest_select_base_testcase<void(int(T))>{typedef T type;};}template<typename T>detail::iuParamGenerator<T> IUTEST_ATTRIBUTE_UNUSED_ Range(T begin,T end,T step=static_cast<T>(1)){return new detail::iuRangeParamsGenerator<T>(begin,end,step);}inline detail::iuParamGenerator<bool> IUTEST_ATTRIBUTE_UNUSED_ Bool(){return new detail::iuBoolParamsGenerator();} | |
#if IUTEST_HAS_VALUESGEN | |
template<typename StdGenerator>inline detail::iuValuesParamsGeneratorHolder<StdGenerator> IUTEST_ATTRIBUTE_UNUSED_ ValuesGen(size_t num,const StdGenerator& generator){return detail::iuValuesParamsGeneratorHolder<StdGenerator>(num,generator);}template<typename T,typename Filter>inline detail::iuRandomFilterParamGenerator<T,Filter> IUTEST_ATTRIBUTE_UNUSED_ RandomGenerator(const Filter& filter,unsigned int seed=0){if(seed==0){seed=detail::GetIndefiniteValue();}return detail::iuRandomFilterParamGenerator<T,Filter>(filter,seed);} | |
#endif | |
#if IUTEST_HAS_RANDOMVALUES | |
inline detail::iuRandomParamsHolder IUTEST_ATTRIBUTE_UNUSED_ RandomValues(size_t num,unsigned int seed=0){return detail::iuRandomParamsHolder(num,seed);} | |
#endif | |
template<typename Container>inline detail::iuParamGenerator<typename Container::value_type>IUTEST_ATTRIBUTE_UNUSED_ ValuesIn(Container container){return new detail::iuValuesInParamsGenerator<typename Container::value_type >(container);}template<typename T,size_t SIZE>inline detail::iuParamGenerator<T> IUTEST_ATTRIBUTE_UNUSED_ ValuesIn(const T(&v)[SIZE]){return new detail::iuValuesInParamsGenerator<T>(v,v+SIZE);}template<typename Ite>inline detail::iuParamGenerator<typename detail::IteratorTraits<Ite>::type>IUTEST_ATTRIBUTE_UNUSED_ ValuesIn(Ite begin,Ite end){return new detail::iuValuesInParamsGenerator<typename detail::IteratorTraits<Ite>::type >(begin,end);} | |
#if IUTEST_HAS_INITIALIZER_LIST | |
template<typename T>inline detail::iuParamGenerator<T> IUTEST_ATTRIBUTE_UNUSED_ ValuesIn(::std::initializer_list<T> l){return new detail::iuValuesInParamsGenerator<T>(l);} | |
#endif | |
#if IUTEST_HAS_VARIADIC_VALUES | |
template<typename ...Args>inline detail::iuValueArray<Args...> IUTEST_ATTRIBUTE_UNUSED_ Values(Args... args){return detail::iuValueArray<Args...>(args...);} | |
#else | |
#define II_D_V_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> inline detail::iuValueArray##n<IUTEST_PP_ENUM_PARAMS(n,T)> IUTEST_ATTRIBUTE_UNUSED_ Values(IUTEST_PP_ENUM_BINARY_PARAMS(n,T,t)){return detail::iuValueArray##n<IUTEST_PP_ENUM_PARAMS(n,T)>(IUTEST_PP_ENUM_PARAMS(n,t));} | |
II_D_V_(1)II_D_V_(2)II_D_V_(3)II_D_V_(4)II_D_V_(5)II_D_V_(6)II_D_V_(7)II_D_V_(8)II_D_V_(9)II_D_V_(10)II_D_V_(11)II_D_V_(12)II_D_V_(13)II_D_V_(14)II_D_V_(15)II_D_V_(16)II_D_V_(17)II_D_V_(18)II_D_V_(19)II_D_V_(20)II_D_V_(21)II_D_V_(22)II_D_V_(23)II_D_V_(24)II_D_V_(25)II_D_V_(26)II_D_V_(27)II_D_V_(28)II_D_V_(29)II_D_V_(30)II_D_V_(31)II_D_V_(32)II_D_V_(33)II_D_V_(34)II_D_V_(35)II_D_V_(36)II_D_V_(37)II_D_V_(38)II_D_V_(39)II_D_V_(40)II_D_V_(41)II_D_V_(42)II_D_V_(43)II_D_V_(44)II_D_V_(45)II_D_V_(46)II_D_V_(47)II_D_V_(48)II_D_V_(49)II_D_V_(50) | |
#undef II_D_V_ | |
#endif | |
#if IUTEST_HAS_CONCAT | |
template<typename Generator1,typename Generator2>detail::iuConcatParamHolder<Generator1,Generator2> Concat(const Generator1& g1,const Generator2& g2){return detail::iuConcatParamHolder<Generator1,Generator2>(g1,g2);} | |
#endif | |
#if IUTEST_HAS_COMBINE | |
#if IUTEST_HAS_VARIADIC_COMBINE | |
template<typename ...Generator>detail::iuCartesianProductHolder<Generator...> Combine(const Generator&... generators){return detail::iuCartesianProductHolder<Generator...>(generators...);} | |
#else | |
#define II_D_C_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> inline IUTEST_PP_CAT(detail::iuCartesianProductHolder,n)<IUTEST_PP_ENUM_PARAMS(n,T)> Combine(IUTEST_PP_ENUM_BINARY_PARAMS(n,const T,&t)){return IUTEST_PP_CAT(detail::iuCartesianProductHolder,n) <IUTEST_PP_ENUM_PARAMS(n,T)>(IUTEST_PP_ENUM_PARAMS(n,t));} | |
II_D_C_(2)II_D_C_(3)II_D_C_(4)II_D_C_(5)II_D_C_(6)II_D_C_(7)II_D_C_(8)II_D_C_(9) | |
#undef II_D_C_ | |
#endif | |
#endif | |
#if IUTEST_HAS_PAIRWISE | |
#if IUTEST_HAS_VARIADIC_PAIRWISE | |
template<typename ...Generator>detail::iuPairwiseHolder<Generator...> Pairwise(const Generator&... generators){return detail::iuPairwiseHolder<Generator...>(generators...);} | |
#else | |
#define II_D_PW_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> inline IUTEST_PP_CAT(detail::iuPairwiseHolder,n)<IUTEST_PP_ENUM_PARAMS(n,T)> Pairwise(IUTEST_PP_ENUM_BINARY_PARAMS(n,const T,&t)){return IUTEST_PP_CAT(detail::iuPairwiseHolder,n) <IUTEST_PP_ENUM_PARAMS(n,T)>(IUTEST_PP_ENUM_PARAMS(n,t));} | |
II_D_PW_(2)II_D_PW_(3)II_D_PW_(4)II_D_PW_(5)II_D_PW_(6)II_D_PW_(7)II_D_PW_(8)II_D_PW_(9) | |
#undef II_D_PW__ | |
#endif | |
#endif | |
#if IUTEST_HAS_CSVPARAMS | |
template<typename T>detail::iuParamGenerator<T> IUTEST_ATTRIBUTE_UNUSED_ CSV(const char* path,char delimiter=','){return new detail::iuCsvFileParamsGenerator<T>(path,delimiter);}template<typename T>detail::iuParamGenerator<T> IUTEST_ATTRIBUTE_UNUSED_ CSV(const char* relative_path,const char* test_file,char delimiter=','){const char* sep=detail::FindLastPathSeparator(test_file,strlen(test_file));::std::string path;if(sep!=0){const size_t length=::std::distance(test_file,sep);path+=::std::string(test_file,length);path+=detail::GetPathSeparator();}path+=relative_path;return new detail::iuCsvFileParamsGenerator<T>(path,delimiter);} | |
#endif | |
} | |
#if IUTEST_HAS_ANY_PARAM_TEST | |
typedef ::iutest::TestWithAny iuTestWithAny; | |
#endif | |
#endif | |
namespace iutest{namespace detail{template<typename TypeList,size_t N>class typelist_get{template<typename T,size_t I>struct impl{typedef typename impl<typename T::Tail,I-1>::type type;};template<typename T>struct impl<T,0>{typedef typename T::Head type;};public: typedef typename impl<TypeList,N>::type type;};struct TypeList0{};template<typename T1>struct TypeList1{typedef T1 Head;typedef TypeList0 Tail;}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename T,typename ...Args>struct VariadicTypeList{typedef T Head;typedef VariadicTypeList<Args...> Tail;};template<typename T>struct VariadicTypeList<T>{typedef T Head;typedef TypeList0 Tail;}; | |
#else | |
#define II_D_TL_(n) II_D_TL_I(n,IUTEST_PP_DEC(n)) | |
#define II_D_TL_I(n,m) template<typename T0,IUTEST_PP_ENUM_SHIFTED_PARAMS(m,typename T)> struct IUTEST_PP_CAT(TypeList,n){typedef T0 Head;typedef IUTEST_PP_CAT(TypeList,m)<IUTEST_PP_ENUM_SHIFTED_PARAMS(m,T)> Tail;} | |
II_D_TL_(2);II_D_TL_(3);II_D_TL_(4);II_D_TL_(5);II_D_TL_(6);II_D_TL_(7);II_D_TL_(8);II_D_TL_(9);II_D_TL_(10);II_D_TL_(11);II_D_TL_(12);II_D_TL_(13);II_D_TL_(14);II_D_TL_(15);II_D_TL_(16);II_D_TL_(17);II_D_TL_(18);II_D_TL_(19);II_D_TL_(20);II_D_TL_(21);II_D_TL_(22);II_D_TL_(23);II_D_TL_(24);II_D_TL_(25);II_D_TL_(26);II_D_TL_(27);II_D_TL_(28);II_D_TL_(29);II_D_TL_(30);II_D_TL_(31);II_D_TL_(32);II_D_TL_(33);II_D_TL_(34);II_D_TL_(35);II_D_TL_(36);II_D_TL_(37);II_D_TL_(38);II_D_TL_(39);II_D_TL_(40);II_D_TL_(41);II_D_TL_(42);II_D_TL_(43);II_D_TL_(44);II_D_TL_(45);II_D_TL_(46);II_D_TL_(47);II_D_TL_(48);II_D_TL_(49);II_D_TL_(50); | |
#undef II_D_TL_ | |
#endif | |
#define II_TEMPLATE_TPARAM1 template<typename XXX> class | |
template<II_TEMPLATE_TPARAM1 U>struct TemplateTypeSel{template<typename T>struct bind{typedef U<T> type;};};struct TemplateTypeList0{}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES | |
template<II_TEMPLATE_TPARAM1 T1,II_TEMPLATE_TPARAM1 ...Types>struct VariadicTemplateTypeList{typedef TemplateTypeSel<T1> Head;typedef VariadicTemplateTypeList<Types...> Tail;};template<II_TEMPLATE_TPARAM1 T1>struct VariadicTemplateTypeList<T1>{typedef TemplateTypeSel<T1> Head;typedef TemplateTypeList0 Tail;}; | |
#else | |
template<II_TEMPLATE_TPARAM1 T1>struct TemplateTypeList1{typedef TemplateTypeSel<T1> Head;typedef TemplateTypeList0 Tail;}; | |
#define II_D_TTL_(n) II_D_TTL_I(n,IUTEST_PP_DEC(n)) | |
#define II_D_TTL_I(n,m) template<II_TEMPLATE_TPARAM1 T0,IUTEST_PP_ENUM_SHIFTED_PARAMS(m,II_TEMPLATE_TPARAM1 T)> struct IUTEST_PP_CAT(TemplateTypeList,n){typedef TemplateTypeSel<T0> Head;typedef IUTEST_PP_CAT(TemplateTypeList,m)<IUTEST_PP_ENUM_SHIFTED_PARAMS(m,T)> Tail;} | |
II_D_TTL_(2);II_D_TTL_(3);II_D_TTL_(4);II_D_TTL_(5);II_D_TTL_(6);II_D_TTL_(7);II_D_TTL_(8);II_D_TTL_(9);II_D_TTL_(10);II_D_TTL_(11);II_D_TTL_(12);II_D_TTL_(13);II_D_TTL_(14);II_D_TTL_(15);II_D_TTL_(16);II_D_TTL_(17);II_D_TTL_(18);II_D_TTL_(19);II_D_TTL_(20);II_D_TTL_(21);II_D_TTL_(22);II_D_TTL_(23);II_D_TTL_(24);II_D_TTL_(25);II_D_TTL_(26);II_D_TTL_(27);II_D_TTL_(28);II_D_TTL_(29);II_D_TTL_(30);II_D_TTL_(31);II_D_TTL_(32);II_D_TTL_(33);II_D_TTL_(34);II_D_TTL_(35);II_D_TTL_(36);II_D_TTL_(37);II_D_TTL_(38);II_D_TTL_(39);II_D_TTL_(40);II_D_TTL_(41);II_D_TTL_(42);II_D_TTL_(43);II_D_TTL_(44);II_D_TTL_(45);II_D_TTL_(46);II_D_TTL_(47);II_D_TTL_(48);II_D_TTL_(49);II_D_TTL_(50); | |
#undef II_D_TTL_ | |
#endif | |
}}namespace iutest{ | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...Args>struct Types{typedef detail::VariadicTypeList<Args...> type;template<size_t N>struct get:public detail::typelist_get<type,N>{};}; | |
#else | |
#define II_D_DEF_A_(i,param) IUTEST_PP_CAT(param,i)=detail::None | |
template<IUTEST_PP_ENUM(50,II_D_DEF_A_,typename T)>struct Types{typedef detail::TypeList50<IUTEST_PP_ENUM_PARAMS(50,T)> type;template<size_t N>struct get:public detail::typelist_get<type,N>{};}; | |
#undef II_D_DEF_A_ | |
#define II_D_S_NN_(i,param) param | |
#define II_D_T_(n,m) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> struct Types<IUTEST_PP_ENUM_PARAMS(n,T) ,IUTEST_PP_ENUM(m,II_D_S_NN_,detail::None)>{typedef IUTEST_PP_CAT(detail::TypeList,n)< IUTEST_PP_ENUM_PARAMS(n,T)> type;template<size_t N>struct get:public detail::typelist_get<type,N>{};} | |
template<>struct Types<IUTEST_PP_ENUM(50,II_D_S_NN_,detail::None)>{typedef detail::TypeList0 type;};II_D_T_(1,49);II_D_T_(2,48);II_D_T_(3,47);II_D_T_(4,46);II_D_T_(5,45);II_D_T_(6,44);II_D_T_(7,43);II_D_T_(8,42);II_D_T_(9,41);II_D_T_(10,40);II_D_T_(11,39);II_D_T_(12,38);II_D_T_(13,37);II_D_T_(14,36);II_D_T_(15,35);II_D_T_(16,34);II_D_T_(17,33);II_D_T_(18,32);II_D_T_(19,31);II_D_T_(20,30);II_D_T_(21,29);II_D_T_(22,28);II_D_T_(23,27);II_D_T_(24,26);II_D_T_(25,25);II_D_T_(26,24);II_D_T_(27,23);II_D_T_(28,22);II_D_T_(29,21);II_D_T_(30,20);II_D_T_(31,19);II_D_T_(32,18);II_D_T_(33,17);II_D_T_(34,16);II_D_T_(35,15);II_D_T_(36,14);II_D_T_(37,13);II_D_T_(38,12);II_D_T_(39,11);II_D_T_(40,10);II_D_T_(41,9);II_D_T_(42,8);II_D_T_(43,7);II_D_T_(44,6);II_D_T_(45,5);II_D_T_(46,4);II_D_T_(47,3);II_D_T_(48,2);II_D_T_(49,1); | |
#undef II_D_S_NN_ | |
#undef II_D_T_ | |
#endif | |
namespace detail{ | |
#if IUTEST_HAS_VARIADIC_TEMPLATE_TEMPLATES | |
template<II_TEMPLATE_TPARAM1 ...Types>struct Templates{typedef VariadicTemplateTypeList<Types...> type;}; | |
#else | |
#define II_D_DEF_A_(i,param) IUTEST_PP_CAT(param,i)=detail::NoneT1 | |
template<IUTEST_PP_ENUM(50,II_D_DEF_A_,II_TEMPLATE_TPARAM1 T)>struct Templates{typedef detail::TemplateTypeList50<IUTEST_PP_ENUM_PARAMS(50,T)> type;}; | |
#undef II_D_DEF_A_ | |
#define II_D_S_NN_(i,param) param | |
#define II_D_TPL_(n,m) template<IUTEST_PP_ENUM_PARAMS(n,II_TEMPLATE_TPARAM1 T)> struct Templates<IUTEST_PP_ENUM_PARAMS(n,T) ,IUTEST_PP_ENUM(m,II_D_S_NN_,detail::NoneT1)>{typedef IUTEST_PP_CAT(detail::TemplateTypeList,n)< IUTEST_PP_ENUM_PARAMS(n,T)> type;} | |
template<>struct Templates<IUTEST_PP_ENUM(50,II_D_S_NN_,detail::NoneT1)>{typedef detail::TemplateTypeList0 type;};II_D_TPL_(1,49);II_D_TPL_(2,48);II_D_TPL_(3,47);II_D_TPL_(4,46);II_D_TPL_(5,45);II_D_TPL_(6,44);II_D_TPL_(7,43);II_D_TPL_(8,42);II_D_TPL_(9,41);II_D_TPL_(10,40);II_D_TPL_(11,39);II_D_TPL_(12,38);II_D_TPL_(13,37);II_D_TPL_(14,36);II_D_TPL_(15,35);II_D_TPL_(16,34);II_D_TPL_(17,33);II_D_TPL_(18,32);II_D_TPL_(19,31);II_D_TPL_(20,30);II_D_TPL_(21,29);II_D_TPL_(22,28);II_D_TPL_(23,27);II_D_TPL_(24,26);II_D_TPL_(25,25);II_D_TPL_(26,24);II_D_TPL_(27,23);II_D_TPL_(28,22);II_D_TPL_(29,21);II_D_TPL_(30,20);II_D_TPL_(31,19);II_D_TPL_(32,18);II_D_TPL_(33,17);II_D_TPL_(34,16);II_D_TPL_(35,15);II_D_TPL_(36,14);II_D_TPL_(37,13);II_D_TPL_(38,12);II_D_TPL_(39,11);II_D_TPL_(40,10);II_D_TPL_(41,9);II_D_TPL_(42,8);II_D_TPL_(43,7);II_D_TPL_(44,6);II_D_TPL_(45,5);II_D_TPL_(46,4);II_D_TPL_(47,3);II_D_TPL_(48,2);II_D_TPL_(49,1); | |
#undef II_D_S_NN_ | |
#undef II_D_TPL_ | |
#endif | |
template<typename T>struct TypeList{typedef detail::TypeList1<T> type;}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...Args>struct TypeList<Types<Args...> >{typedef typename Types<Args...>::type type;}; | |
#else | |
template<IUTEST_PP_ENUM_PARAMS(50,typename T)>struct TypeList<Types<IUTEST_PP_ENUM_PARAMS(50,T)> >{typedef typename Types<IUTEST_PP_ENUM_PARAMS(50,T)>::type type;}; | |
#endif | |
}} | |
#if IUTEST_HAS_TYPED_TEST | |
#define IUTEST_TYPED_TEST_CASE(testcase_,...) II_T_TC_(testcase_,__VA_ARGS__) | |
#define IUTEST_TYPED_TEST(testcase_,tn_) IUTEST_TYPED_TEST_(testcase_,tn_) | |
#define IUTEST_T(testcase_,tn_) IUTEST_TYPED_TEST_(testcase_,tn_) | |
#if IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define II_T_T_PRMS_(testcase_) II_T_T_PRMS_I_(IUTEST_PP_IF(IUTEST_PP_IS_BEGIN_PARENS(testcase_) ,IUTEST_ALIAS_TESTNAME_F_,IUTEST_PP_EMPTY()) testcase_) | |
#else | |
#define II_T_T_PRMS_(testcase_) II_T_T_PRMS_I_(testcase_) | |
#endif | |
#define II_T_T_PRMS_I_(testcase_) II_T_T_PRMS_II_(II_TO_VN_(testcase_)) | |
#define II_T_T_PRMS_II_(testcase_) II_T_T_PRMS_III_(testcase_) | |
#define II_T_T_PRMS_III_(testcase_) iutest_types_params_##testcase_ | |
#define II_T_TC_(testcase_,...) typedef ::iutest::detail::TypeList<__VA_ARGS__ >::type II_T_T_PRMS_(testcase_) | |
#define II_T_T_I(classname_,testcase_,tcn_,tn_) template<typename iutest_TypeParam> class classname_:public testcase_<iutest_TypeParam>{typedef testcase_<iutest_TypeParam> TestFixture;typedef iutest_TypeParam TypeParam;protected: virtual void Body() IUTEST_CXX_OVERRIDE;};::iutest::detail::TypeParamTestInstance<classname_,II_T_T_PRMS_(testcase_)> IUTEST_TEST_INSTANCE_NAME_(testcase_,tn_)(IUTEST_CONCAT_PACKAGE_(tcn_),II_TO_N_STR_(tn_));template<typename iutest_TypeParam> void classname_<iutest_TypeParam>::Body() | |
#define II_T_T_(macro,testcase_,tn_) macro(IUTEST_TEST_CLASS_NAME_(testcase_,tn_) ,II_TO_VN_(testcase_),II_TO_N_(testcase_) ,tn_) | |
#if IUTEST_HAS_TESTFIXTURE_ALIAS_BY_TUPLE | |
#define II_T_T_A_(macro,testcase_,tn_) II_T_T_(macro,IUTEST_PP_IF(IUTEST_PP_IS_BEGIN_PARENS(testcase_) ,IUTEST_ALIAS_TESTNAME_F_,IUTEST_PP_EMPTY()) testcase_,tn_) | |
#define IUTEST_TYPED_TEST_(testcase_,tn_) II_T_T_A_(II_T_T_I,testcase_,tn_) | |
#else | |
#define IUTEST_TYPED_TEST_(testcase_,tn_) II_T_T_(II_T_T_I,testcase_,tn_) | |
#endif | |
#endif | |
#if IUTEST_HAS_TYPED_TEST_P | |
#define IUTEST_TYPED_TEST_CASE_P(testcase_) II_T_TC_P_(testcase_) | |
#define IUTEST_TYPED_TEST_P(testcase_,tn_) II_T_T_P_(testcase_,tn_) | |
#define IUTEST_TP(testcase_,tn_) II_T_T_P_(testcase_,tn_) | |
#define IUTEST_REGISTER_TYPED_TEST_CASE_P(testcase_,...) II_R_T_TC_P_(testcase_,__VA_ARGS__) | |
#define IUTEST_INSTANTIATE_TYPED_TEST_CASE_P(prefix_,testcase_,...) II_INST_T_TC_P_(prefix_,testcase_,__VA_ARGS__) | |
#define II_T_TC_PS_N_(testcase_) s_iutest_typed_test_case_p_state_##testcase_##_ | |
#define II_T_T_P_NS_(testcase_) iutest_typed_test_case_p_name_##testcase_##_ | |
#define II_T_T_P_ADD_TN(testcase_,tn_) static const int s_iutest_##tn_##_defined_dummy_ IUTEST_ATTRIBUTE_UNUSED_=II_T_TC_PS_N_(testcase_).AddTestName(__FILE__,__LINE__,#testcase_,#tn_) | |
#define II_T_TC_P_(testcase_) static ::iutest::detail::TypedTestCasePState II_T_TC_PS_N_(testcase_) | |
#define II_T_T_P_(testcase_,tn_) namespace II_T_T_P_NS_(testcase_){template<typename iutest_TypeParam> class tn_:public testcase_<iutest_TypeParam>{typedef testcase_<iutest_TypeParam> TestFixture;typedef iutest_TypeParam TypeParam;protected: virtual void Body() IUTEST_CXX_OVERRIDE;};II_T_T_P_ADD_TN(testcase_,tn_);}template<typename iutest_TypeParam> void II_T_T_P_NS_(testcase_)::tn_<iutest_TypeParam>::Body() | |
#define II_R_T_TC_P_(testcase_,...) namespace II_T_T_P_NS_(testcase_){typedef ::iutest::detail::Templates<__VA_ARGS__ >::type iutest_AllTests_;}static const bool s_iutest_##testcase_##_register_dummy_ IUTEST_ATTRIBUTE_UNUSED_=II_T_TC_PS_N_(testcase_).VerifyTestNames(__FILE__,__LINE__,#__VA_ARGS__) | |
#define II_INST_T_TC_P_(prefix_,testcase_,...) const bool iutest_##prefix_##_##testcase_ IUTEST_ATTRIBUTE_UNUSED_=::iutest::detail::TypeParameterizedTestCase<testcase_ ,II_T_T_P_NS_(testcase_)::iutest_AllTests_ ,::iutest::detail::TypeList<__VA_ARGS__ >::type >::Register(#prefix_,II_TO_N_STR_(testcase_),IUTEST_GET_PACKAGENAME_() ,II_T_TC_PS_N_(testcase_).names()) | |
#endif | |
namespace iutest{namespace detail{ | |
#if IUTEST_HAS_TYPED_TEST | |
template<template <typename T> class Tester,typename TypeParams>class TypeParamTestInstance{template<typename TT,typename DMY>class EachTest{typedef typename TT::Head TypeParam;typedef Tester<TypeParam> TestBody;typedef TypedTestCase<TypeParam> _MyTestCase;public: EachTest(const char* testcase,const char* name,size_t index):m_mediator(AddTestCase(testcase,index)),m_info(&m_mediator,name,&m_factory),m_next(testcase,name,index+1){}EachTest(const ::std::string& testcase,const char* name,size_t index):m_mediator(AddTestCase(testcase,index)),m_info(&m_mediator,name,&m_factory),m_next(testcase,name,index+1){}private: static TestCase* AddTestCase(const char* testcase,size_t index){return UnitTest::instance().AddTestCase<_MyTestCase>( | |
#if IUTEST_HAS_TYPED_TEST_APPEND_TYPENAME | |
detail::MakeIndexTypedTestName<TypeParam>(testcase,index) | |
#else | |
detail::MakeIndexTestName(testcase,index) | |
#endif | |
,internal::GetTypeId<detail::None>(),TestBody::SetUpTestCase,TestBody::TearDownTestCase);}static TestCase* AddTestCase(const ::std::string& testcase,size_t index){return AddTestCase(testcase.c_str(),index);}public: void AddTest(){UnitTest::instance().AddTestInfo(m_mediator.ptr(),&m_info);m_next.AddTest();}private: TestCaseMediator m_mediator;TestInfo m_info;detail::iuFactory<TestBody> m_factory;EachTest<typename TT::Tail,void> m_next;};template<typename DMY>class EachTest<detail::TypeList0,DMY>{public: EachTest(const char*,const char*,size_t){}EachTest(const ::std::string&,const char*,size_t){}void AddTest(){}};public: TypeParamTestInstance(const char* testcase,const char* name):m_tests(testcase,name,0){m_tests.AddTest();}TypeParamTestInstance(const std::string& testcase,const char* name):m_tests(testcase,name,0){m_tests.AddTest();}private: EachTest<TypeParams,void> m_tests;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TypeParamTestInstance);}; | |
#endif | |
#if IUTEST_HAS_TYPED_TEST_P | |
class TypedTestCasePState{ | |
#if IUTEST_TYPED_TEST_P_STRICT | |
typedef ::std::set<const char*> nameset_t; | |
#endif | |
public: TypedTestCasePState():m_names(0){}public: const char* names()const{return m_names;}public: bool AddTestName(const char* file,int line,const char* testcase_name,const char* test_name){if(m_names!=0){IUTEST_LOG_(WARNING)<<detail::FormatCompilerIndependentFileLocation(file,line)<< ": Test \"" <<test_name<<"\" must be defined before IUTEST_REGISTER_TYPED_TEST_CASE_P("<<testcase_name<<", ...).\n";} | |
#if IUTEST_TYPED_TEST_P_STRICT | |
m_list.insert(test_name); | |
#endif | |
return true;}bool VerifyTestNames(const char* file,int line,const char* test_names){m_names=test_names; | |
#if IUTEST_TYPED_TEST_P_STRICT | |
bool ret=true;for(nameset_t::iterator it=m_list.begin(),end=m_list.end();it!=end;++it){const char* test_name=*it;const char* p=strstr(test_names,test_name);if(p!=0){const size_t len=strlen(test_name);if(p[len]=='\0' || p[len]==',' || detail::IsSpace(p[len])){continue;}IUTEST_LOG_(FATAL)<<detail::FormatCompilerIndependentFileLocation(file,line)<< ": Test \"" <<test_name<<"\" is find in \"" <<test_names<< "\". expected whitespace or comma : " <<p[len]<<"(" <<static_cast<int>(p[len])<<")\n";}IUTEST_LOG_(WARNING)<<detail::FormatCompilerIndependentFileLocation(file,line)<< ": Test \"" <<test_name<<"\" has not been registered.\n" << " TestNames: " <<test_names;ret=false;}return ret; | |
#else | |
(void)(file);(void)(line);return true; | |
#endif | |
}private: const char* m_names; | |
#if IUTEST_TYPED_TEST_P_STRICT | |
nameset_t m_list; | |
#endif | |
IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(TypedTestCasePState);};template<template<typename T> class Fixture,typename Tests,typename Types>class TypeParameterizedTestCase{template<typename TypeParam,typename TestsList>class EachTest:public iuIObject{typedef typename TestsList::Head TypeSel;typedef typename TypeSel::template bind<TypeParam>::type TestBody;typedef detail::iuFactory<TestBody> Factory;typedef EachTest<TypeParam,TestsList> _Myt;EachTest(TestCase* testcase,const ::std::string& name):m_mediator(testcase),m_info(&m_mediator,name,&m_factory){UnitTest::instance().AddTestInfo(testcase,&m_info);}public: static void Register(TestCase* testcase,const char* test_names){IUTEST_CHECK_(test_names!=0);const char* str=detail::SkipSpace(test_names);const char* comma=strchr(str,',');::std::string test_name;if(comma==0){test_name=str;}else{test_name=::std::string(str,static_cast<size_t>(comma-str));++comma;}_Myt* test=new EachTest(testcase,StripTrailingSpace(test_name));detail::iuPool::GetInstance().push(test);EachTest<TypeParam,typename TestsList::Tail>::Register(testcase,detail::SkipSpace(comma));}private: TestCaseMediator m_mediator;Factory m_factory;TestInfo m_info;};template<typename TypeParam>class EachTest<TypeParam,detail::TemplateTypeList0>{public: static void Register(TestCase*,const char*){}};public: static bool Register(const char* prefix,const char* testcase_name,const ::std::string& package_name,const char* names,size_t index=0){ | |
#if IUTEST_HAS_EXCEPTIONS | |
try{return Register_(prefix,testcase_name,package_name,names,index);}catch(const ::std::exception& e){IUTEST_LOG_(FATAL)<<"IUTEST_INSTANTIATE_TYPED_TEST_CASE_P register tests failed...\n"<<e.what();}catch(...){IUTEST_LOG_(FATAL)<<"IUTEST_INSTANTIATE_TYPED_TEST_CASE_P register tests failed...\n";}return false; | |
#else | |
return Register_(prefix,testcase_name,package_name,names,index); | |
#endif | |
}private: static bool Register_(const char* prefix,const char* testcase_name,const ::std::string& package_name,const char* names,size_t index){typedef typename Types::Head TypeParam;typedef typename Tests::Head Head;typedef Fixture<Head> FixtureClass;typedef TypedTestCase<TypeParam> _MyTestCase;::std::string full_testcase_name=package_name;full_testcase_name+= | |
#if IUTEST_HAS_TYPED_TEST_APPEND_TYPENAME | |
detail::MakePrefixedIndexTypedTestName<TypeParam>(prefix,testcase_name,index); | |
#else | |
detail::MakePrefixedIndexTestName(prefix,testcase_name,index); | |
#endif | |
TestCase* testcase =UnitTest::instance().AddTestCase<_MyTestCase>(full_testcase_name,internal::GetTypeId<FixtureClass>(),FixtureClass::SetUpTestCase,FixtureClass::TearDownTestCase);EachTest<TypeParam,Tests>::Register(testcase,names);return TypeParameterizedTestCase<Fixture,Tests,typename Types::Tail>::Register(prefix,testcase_name,package_name,names,index+1);}};template<template<typename T> class Fixture,typename Tests>class TypeParameterizedTestCase<Fixture,Tests,detail::TypeList0>{public: static bool Register(const char*,const char*,const ::std::string&,const char*,size_t index=0){(void)(index);return true;}}; | |
#endif | |
}} | |
#define IUTEST_FRIEND_TEST(tcn_,tn_) friend class IUTEST_TEST_CLASS_NAME_(tcn_,tn_) | |
#if IUTEST_HAS_TYPED_TEST | |
#define IUTEST_FRIEND_TYPED_TEST(tcn_,tn_) template<typename T>IUTEST_FRIEND_TEST(tcn_,tn_) | |
#endif | |
#if IUTEST_HAS_TYPED_TEST_P | |
#define IUTEST_FRIEND_TYPED_TEST_P_DECLARATION(tcn_,tn_) namespace II_T_T_P_NS_(tcn_){template<typename T>class tn_;} | |
#define IUTEST_FRIEND_TYPED_TEST_P(tcn_,tn_) template<typename T>friend class II_T_T_P_NS_(tcn_)::tn_ | |
#endif | |
#define IUTEST_MAKE_PEEP(member_type,class_name,member_name) IUTEST_MAKE_PEEP_TAG_(member_type,class_name,member_name) | |
#define IUTEST_PEEP_GET(v,class_name,member_name) (v.*::iutest::detail::peep_tag<II_PE_T_N_(class_name,member_name)<class_name> >::value) | |
#define IUTEST_PEEP_STATIC_GET(class_name,member_name) (*::iutest::detail::peep_tag<II_PE_T_N_(class_name,member_name)<class_name> >::value) | |
#if IUTEST_HAS_PEEP_CLASS | |
#define IUTEST_PEEP(class_name,member_name) ::iutest::Peep<class_name,II_PE_T_N_(class_name,member_name)<class_name> >::type | |
#endif | |
#define IUTEST_MAKE_PEEP_TAG_(member_type,class_name,member_name) template<typename T>struct II_PE_T_N_(class_name,member_name);template<>struct II_PE_T_N_(class_name,member_name)<class_name>{typedef ::iutest_type_traits::identity<member_type>::type type;};template<typename T,typename Tag,typename Tag::type X> struct II_PE_S_N_(class_name,member_name){II_PE_S_N_(class_name,member_name)(){::iutest::detail::peep_tag<Tag>::value=X;}static II_PE_S_N_(class_name,member_name) instance;};template<typename T,typename Tag,typename Tag::type X> II_PE_S_N_(class_name,member_name)<T,Tag,X> II_PE_S_N_(class_name,member_name)<T,Tag,X>::instance;template struct II_PE_S_N_(class_name,member_name)<class_name ,II_PE_T_N_(class_name,member_name)<class_name>,&class_name::member_name> | |
#define II_PE_T_N_(class_name,member_name) iu_peep_tag_##member_name | |
#define II_PE_S_N_(class_name,member_name) IUTEST_PP_CAT(IUTEST_PP_CAT(iu_peep_set_,member_name),__LINE__) | |
namespace iutest{namespace detail{template<typename Tag>struct peep_tag{static typename Tag::type value;};template<typename Tag>typename Tag::type peep_tag<Tag>::value;} | |
#if IUTEST_HAS_PEEP_CLASS | |
template<typename T,typename Tag>class Peep{private: typedef Tag peep_tag;typedef typename Tag::type peep_type;private: template<typename U,typename Type>class peep_member_function_impl{private: typedef typename type_traits::function_return_type<Type>::type return_type;private: U* m_ptr;public: explicit peep_member_function_impl(U* ptr):m_ptr(ptr){} | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
public: template<typename ...Args>return_type operator()(Args... args){return((*m_ptr).*detail::peep_tag<peep_tag>::value)(::std::forward<Args>(args)...);} | |
#else | |
#define II_D_PE_M_F_(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)>return_type operator()(IUTEST_PP_ENUM_BINARY_PARAMS(n,T,t)){return((*m_ptr).*detail::peep_tag<peep_tag>::value)(IUTEST_PP_ENUM_PARAMS(n,t));} | |
return_type operator()(){return((*m_ptr).*detail::peep_tag<peep_tag>::value)();}II_D_PE_M_F_(1)II_D_PE_M_F_(2)II_D_PE_M_F_(3)II_D_PE_M_F_(4)II_D_PE_M_F_(5)II_D_PE_M_F_(6)II_D_PE_M_F_(7)II_D_PE_M_F_(8)II_D_PE_M_F_(9)II_D_PE_M_F_(10)II_D_PE_M_F_(11)II_D_PE_M_F_(12)II_D_PE_M_F_(13)II_D_PE_M_F_(14)II_D_PE_M_F_(15)II_D_PE_M_F_(16)II_D_PE_M_F_(17)II_D_PE_M_F_(18)II_D_PE_M_F_(19)II_D_PE_M_F_(20) | |
#undef II_D_PE_M_F_ | |
#endif | |
};template<typename U,typename Type,bool is_const>class peep_member_object_impl{typedef Type value_type;private: U* m_ptr;public: explicit peep_member_object_impl(U* ptr):m_ptr(ptr){}private: peep_member_object_impl(const peep_member_object_impl&);public: operator value_type()const{return(*m_ptr).*detail::peep_tag<peep_tag>::value;}peep_member_object_impl& operator=(const value_type& value) IUTEST_CXX_DELETED_FUNCTION;};template<typename U,typename Type>class peep_member_object_impl<U,Type,false>{typedef Type value_type;private: U* m_ptr;public: explicit peep_member_object_impl(U* ptr):m_ptr(ptr){}private: peep_member_object_impl(const peep_member_object_impl&);public: operator value_type()const{return(*m_ptr).*detail::peep_tag<peep_tag>::value;}operator value_type&(){return(*m_ptr).*detail::peep_tag<peep_tag>::value;}peep_member_object_impl& operator=(const value_type& value){(*m_ptr).*detail::peep_tag<peep_tag>::value=value;return *this;}};template<typename U,typename Type,bool Func>struct peep_member_impl{typedef peep_member_function_impl<U,Type> type;};template<typename U,typename Type>struct peep_member_impl<U,Type U::*,false>{typedef peep_member_object_impl<U,Type,type_traits::is_const<Type>::value> type;};private: template<typename U,typename Type,bool Func>class peep_static_impl{typedef typename type_traits::remove_pointer<Type>::type value_type;public: peep_static_impl(){}peep_static_impl(const value_type& value){*detail::peep_tag<peep_tag>::value=value;}peep_static_impl(const peep_static_impl&){}public: operator value_type()const{return *detail::peep_tag<peep_tag>::value;}operator value_type&(){return *detail::peep_tag<peep_tag>::value;}peep_static_impl& operator=(const value_type& value){*detail::peep_tag<peep_tag>::value=value;return *this;}};template<typename U,typename Type>class peep_static_impl<U,Type,true>{public: operator Type(){return *detail::peep_tag<peep_tag>::value;}};private: template<typename U,typename Type,bool is_member_ptr>struct peep_impl{typedef peep_static_impl<U,Type,type_traits::is_function_pointer<Type>::value>type;};template<typename U,typename Type>struct peep_impl<U,Type,true>{typedef typename peep_member_impl<U,Type,type_traits::is_member_function_pointer<Type>::value >::type type;};public: typedef typename peep_impl<T,peep_type,type_traits::is_member_pointer<peep_type>::value >::type type;}; | |
#endif | |
} | |
#define IUTEST_OPERAND(op) op II_EXPR_DEC() | |
#define IUTEST_EXPRESSION(expr) (II_EXPR_DEC() expr).GetResult() | |
#if IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE | |
#define II_EXPR_DEC() ::iutest::detail::ExpressionDecomposer()->* | |
#else | |
#define II_EXPR_DEC() ::iutest::detail::ExpressionDecomposer()>> | |
#endif | |
#define II_T_EXPR_UNPAREN_(...) __VA_ARGS__ | |
#define II_T_EXPR_E_E(expr) II_T_EXPR_E_E_(UNPAREN_ expr) | |
#define II_T_EXPR_E_E_(expr) II_T_EXPR_##expr | |
#define II_T_EXPR_(expr,expected,on_f) IUTEST_TEST_TRUE((II_EXPR_DEC() expr).GetResult(expected),#expr,on_f) | |
#define IUTEST_TEST_EXPRESSION_(expr,expected,on_f) II_T_EXPR_(II_T_EXPR_E_E(expr),expected,on_f) | |
#define II_D_EP_R_OP(op) template<typename RHS>ExpressionResult operator op(const RHS& rhs)const{const bool b=result() op rhs?true:false;return ExpressionResult(AssertionResult(b) <<m_result.message()<<" " #op " " <<rhs);}ExpressionResult operator op(const ExpressionResult& rhs)const{const bool b=result() op rhs.result()?true:false;return ExpressionResult(AssertionResult(b) <<m_result.message()<<" " #op " " <<rhs.message());}ExpressionResult operator op(const AssertionResult& rhs)const{const bool b=result() op rhs.passed()?true:false;return ExpressionResult(AssertionResult(b) <<m_result.message()<<" " #op " " <<rhs.message());} | |
#define II_D_EP_OP(op) template<typename RHS>ExpressionResult operator op(const RHS& rhs)const{const bool b=(m_lhs op rhs)?true:false;return ExpressionResult(AssertionResult(b)<<m_message<<" " #op " " <<rhs);} | |
#if IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE||IUTEST_HAS_BITWISE_EXPRESSION_DECOMPOSE | |
#if IUTEST_HAS_DECLTYPE&&IUTEST_HAS_STD_DECLVAL | |
#define II_D_EP_OP_LHS(op) template<typename RHS>auto operator op(const RHS& rhs)const -> ExpressionLHS<decltype(expression_op_helper::operand_result((::std::declval<T>() op rhs)))>{return OperandResult(m_lhs op rhs)<<" " #op " " <<rhs;} | |
#else | |
#define II_D_EP_OP_LHS(op) template<typename RHS>ExpressionLHS<RHS> operator op(const RHS& rhs)const{return OperandResult(m_lhs op rhs)<<" " #op " " <<rhs;} | |
#endif | |
#endif | |
namespace iutest{namespace detail{class ExpressionResult{public: explicit ExpressionResult(const AssertionResult& ar):m_result(ar){}public: II_D_EP_R_OP(||)II_D_EP_R_OP(&&)public: AssertionResult GetResult(bool expected)const{return AssertionResult(result()==expected)<<"expansion: " <<m_result.message();}AssertionResult GetResult()const{return AssertionResult(result())<<m_result.message();}private: bool result()const{return m_result.passed();}const char* message()const{return m_result.message();}private: AssertionResult m_result;};namespace expression_op_helper{template<typename T>T operand_result(const T&);}template<typename T>class ExpressionLHS{typedef ExpressionLHS<T> _Myt;public: | |
#if IUTEST_HAS_RVALUE_REFS | |
explicit ExpressionLHS(T&& lhs):m_lhs(::std::forward<T>(lhs)){AppendMessage(m_lhs);} | |
#else | |
explicit ExpressionLHS(T lhs):m_lhs(lhs){AppendMessage(lhs);} | |
#endif | |
ExpressionLHS(T lhs,const ::std::string& msg):m_lhs(lhs),m_message(msg){}public: II_D_EP_OP(==)II_D_EP_OP(!=)II_D_EP_OP(<)II_D_EP_OP(<=)II_D_EP_OP(>)II_D_EP_OP(>=)II_D_EP_OP(&&)II_D_EP_OP(||) | |
#if IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE | |
II_D_EP_OP_LHS(+)II_D_EP_OP_LHS(-)II_D_EP_OP_LHS(*)II_D_EP_OP_LHS(/)II_D_EP_OP_LHS(%) | |
#endif | |
#if IUTEST_HAS_BITWISE_EXPRESSION_DECOMPOSE | |
II_D_EP_OP_LHS(&)II_D_EP_OP_LHS(|)II_D_EP_OP_LHS(^)II_D_EP_OP_LHS(<<)II_D_EP_OP_LHS(>>) | |
#endif | |
private: template<typename U>ExpressionLHS<U> OperandResult(const U& lhs)const{return ExpressionLHS<U>(lhs,m_message);}public: template<typename U>_Myt& operator<<(const U& value){AppendMessage(value);return *this;}public: AssertionResult GetResult(bool expected)const{const bool b=m_lhs?true:false;return AssertionResult(b==expected)<<"expansion: " <<m_message;}AssertionResult GetResult()const{const bool b=m_lhs?true:false;return AssertionResult(b)<<m_message;}private: template<typename U>void AppendMessage(const U& value){Message msg;msg<<value;m_message+=msg.GetString();}private: IUTEST_PP_DISALLOW_ASSIGN(ExpressionLHS);private: T m_lhs;::std::string m_message;}; | |
#undef II_D_EP_R_OP | |
#undef II_D_EP_OP | |
#ifdef II_D_EP_OP_LHS | |
#undef II_D_EP_OP_LHS | |
#endif | |
class ExpressionDecomposer{public: | |
#if IUTEST_HAS_ARITHMETIC_EXPRESSION_DECOMPOSE | |
#if IUTEST_HAS_RVALUE_REFS | |
template<typename T>ExpressionLHS<T> operator ->*(T&& expr){return ExpressionLHS<T>(::std::forward<T>(expr));} | |
#else | |
template<typename T>ExpressionLHS<const T&> operator ->*(const T& expr){return ExpressionLHS<const T&>(expr);} | |
#endif | |
#else | |
template<typename T>ExpressionLHS<const T&> operator >>(const T& expr){return ExpressionLHS<const T&>(expr);} | |
#endif | |
};}} | |
#if IUTEST_HAS_MATCHERS | |
#define IUTEST_TEST_THAT(actual,matcher,on_f) IUTEST_AMBIGUOUS_ELSE_BLOCKER_ if(::iutest::AssertionResult iutest_ar=matcher(actual)){}else on_f(::iutest::detail::MatcherAssertionFailureMessage(::iutest::PrintToString(actual).c_str(),#matcher,iutest_ar)) | |
namespace iutest{namespace detail{inline ::std::string MatcherAssertionFailureMessage(const char* actual,const char* matcher_str,const AssertionResult& ar){iu_global_format_stringstream strm;strm<<"error: Expected: " <<matcher_str<< "\n Actual: " <<actual<< "\nWhich is: " <<ar.message();return strm.str();}IUTEST_PRAGMA_ASSIGNMENT_OPERATOR_COULD_NOT_GENERATE_WARN_DISABLE_BEGIN()class IMatcher{IMatcher& operator=(const IMatcher&);public: template<typename T>struct is_matcher:public iutest_type_traits::is_base_of<IMatcher,T>{};public: IMatcher(){}IMatcher(const IMatcher&){}virtual ~IMatcher(){}virtual ::std::string WhichIs()const=0;};inline iu_ostream& operator<<(iu_ostream& os,const IMatcher& msg){return os<<msg.WhichIs();} | |
#define II_D_COMP_M(name,op) template<typename T>class IUTEST_PP_CAT(name,Matcher):public IMatcher{public: explicit IUTEST_PP_CAT(name,Matcher)(const T& v):m_expected(v){}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<#name ": " <<m_expected;return strm.str();}template<typename U>AssertionResult operator()(const U& actual)const{if(actual op m_expected) return AssertionSuccess();return AssertionFailure()<<WhichIs();}private: const T& m_expected;} | |
#define II_D_COMP_M2(name,op) class IUTEST_PP_CAT(Twofold,IUTEST_PP_CAT(name,Matcher)):public IMatcher{public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return #name;}template<typename T,typename U>AssertionResult operator() (const T& actual,const U& expected)const{if(actual op expected) return AssertionSuccess();return AssertionFailure()<<WhichIs()<<": " <<actual<<" vs " <<expected;}} | |
IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE()II_D_COMP_M(Ne,!=);II_D_COMP_M(Le,<=);II_D_COMP_M(Lt,<);II_D_COMP_M(Ge,>=);II_D_COMP_M(Gt,>);II_D_COMP_M2(Eq,==);II_D_COMP_M2(Ne,!=);II_D_COMP_M2(Le,<=);II_D_COMP_M2(Lt,<);II_D_COMP_M2(Ge,>=);II_D_COMP_M2(Gt,>);IUTEST_PRAGMA_WARN_POP() | |
#undef II_D_COMP_M | |
#undef II_D_COMP_M2 | |
#define II_D_S_COMP_M(name) template<typename T>class IUTEST_PP_CAT(name,Matcher):public IMatcher{public: IUTEST_PP_CAT(name,Matcher)(const T& value):m_expected(value){}template<typename U>AssertionResult operator()(const U& actual)const{if(internal::IUTEST_PP_CAT(name,Helper)::Compare(actual,m_expected)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<#name ": " <<m_expected;return strm.str();}private: const T& m_expected;} | |
II_D_S_COMP_M(StrEq);II_D_S_COMP_M(StrNe);II_D_S_COMP_M(StrCaseEq);II_D_S_COMP_M(StrCaseNe); | |
#undef II_D_COMP_M | |
class IsNullMatcher:public IMatcher{public: template<typename U>AssertionResult operator()(const U* actual)const{if(actual==0){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return "Is Null";}};class NotNullMatcher:public IMatcher{public: template<typename U>AssertionResult operator()(const U* actual)const{if(actual!=0){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return "Not Null";}};template<typename T>class FloatingPointEqMatcher:public IMatcher{public: explicit FloatingPointEqMatcher(const T& value):m_expected(value){}public: template<typename U>AssertionResult operator()(const U& actual)const{floating_point<T> f2(actual);if(m_expected.AlmostEquals(f2)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Eq: " <<PrintToString(m_expected);return strm.str();}private: floating_point<T> m_expected;};template<typename T>class NanSensitiveFloatingPointEqMatcher:public IMatcher{public: explicit NanSensitiveFloatingPointEqMatcher(const T& value):m_expected(value){}public: template<typename U>AssertionResult operator()(const U& actual)const{floating_point<T> f2(actual);if(m_expected.NanSensitiveAlmostEquals(f2)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"NanSensitive Eq: " <<PrintToString(m_expected);return strm.str();}private: floating_point<T> m_expected;};template<typename T>class FloatingPointNearMatcher:public IMatcher{public: explicit FloatingPointNearMatcher(const T& value,const T& abs_error):m_expected(value),m_max_abs_error(abs_error){}public: template<typename U>AssertionResult operator()(const U& actual)const{floating_point<T> a(actual);if(m_expected.AlmostNear(a,m_max_abs_error)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Near: " <<PrintToString(m_expected)<<"(abs error <= " <<m_max_abs_error<<")";return strm.str();}private: floating_point<T> m_expected;T m_max_abs_error;};template<typename T>class NanSensitiveFloatingPointNearMatcher:public IMatcher{public: explicit NanSensitiveFloatingPointNearMatcher(const T& value,const T& abs_error):m_expected(value),m_max_abs_error(abs_error){}public: template<typename U>AssertionResult operator()(const U& actual)const{floating_point<T> a(actual);if(m_expected.NanSensitiveAlmostNear(a,m_max_abs_error)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"NanSensitive Near: " <<PrintToString(m_expected)<<"(abs error <= " <<m_max_abs_error<<")";return strm.str();}private: floating_point<T> m_expected;T m_max_abs_error;};template<typename T>class StartsWithMatcher:public IMatcher{public: explicit StartsWithMatcher(T str):m_expected(str){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(StartsWith(actual,m_expected)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"StartsWith: " <<m_expected;return strm.str();}private: static bool StartsWith(const char* actual,const char* start){return strstr(actual,start)==actual;}static bool StartsWith(const ::std::string& actual,const char* start){const char* p=actual.c_str();return StartsWith(p,start);}static bool StartsWith(const char* actual,const ::std::string& start){const char* p=start.c_str();return StartsWith(actual,p);}static bool StartsWith(const ::std::string& actual,const ::std::string& start){const char* p=start.c_str();return StartsWith(actual,p);}private: T m_expected;};template<typename T>class HasSubstrMatcher:public IMatcher{public: explicit HasSubstrMatcher(T expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(HasSubstr(actual,m_expected)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"HasSubstr: " <<m_expected;return strm.str();}private: static bool HasSubstr(const char* actual,const char* expected){return strstr(actual,expected)!=0;}static bool HasSubstr(const ::std::string& actual,const char* expected){const char* p=actual.c_str();return HasSubstr(p,expected);}static bool HasSubstr(const char* actual,const ::std::string& expected){const char* p=expected.c_str();return HasSubstr(actual,p);}static bool HasSubstr(const ::std::string& actual,const ::std::string& expected){const char* p=expected.c_str();return HasSubstr(actual,p);}private: T m_expected;};template<typename T>class EndsWithMatcher:public IMatcher{public: explicit EndsWithMatcher(T str):m_expected(str){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(EndsWith(actual,m_expected)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"EndsWith: " <<m_expected;return strm.str();}private: static bool EndsWith(const char* actual,const char* end){const size_t len=strlen(end);const size_t actual_len=strlen(actual);if(len>actual_len){return false;}const char* p=actual+actual_len-1;const char* q=end+len-1;for(size_t i=0;i<len;++i,--p,--q){if(*p!=*q){return false;}}return true;}static bool EndsWith(const ::std::string& actual,const char* end){const char* p=actual.c_str();return EndsWith(p,end);}static bool EndsWith(const char* actual,const ::std::string& end){const char* p=end.c_str();return EndsWith(actual,p);}static bool EndsWith(const ::std::string& actual,const ::std::string& end){const char* p=end.c_str();return EndsWith(actual,p);}private: T m_expected;};template<typename T>class EqMatcher:public IMatcher{public: explicit EqMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(Equals(actual,m_expected)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Eq: " <<m_expected;return strm.str();}private: template<typename A,typename B>static bool Equals(const A& actual,const B& expected){IUTEST_PRAGMA_WARN_PUSH()IUTEST_PRAGMA_WARN_DISABLE_SIGN_COMPARE()return actual==expected;IUTEST_PRAGMA_WARN_POP()}static bool Equals(const char* actual,const char* expected){return strcmp(actual,expected)==0;}static bool Equals(const ::std::string& actual,const char* expected){const char* p=actual.c_str();return Equals(p,expected);}static bool Equals(const ::std::string& actual,const ::std::string& expected){const char* p=expected.c_str();return Equals(actual,p);}private: const T& m_expected;};template<typename T>class TypedEqMatcher:public EqMatcher<T>{public: explicit TypedEqMatcher(T expected):EqMatcher<T>(m_expected),m_expected(expected){}public: AssertionResult operator()(const T& actual){return EqMatcher<T>::operator()(actual);}template<typename U>AssertionResult operator()(const U&)const;private: T m_expected;};template<typename T>T& CastToMatcher(T& matcher,typename detail::enable_if_t<IMatcher::is_matcher<T> >::type*& = detail::enabler::value){return matcher;}template<typename T>EqMatcher<T> CastToMatcher(const T& value,typename detail::disable_if_t<IMatcher::is_matcher<T> >::type*& = detail::enabler::value){return EqMatcher<T>(value);}template<typename T>class ContainsMatcher:public IMatcher{public: explicit ContainsMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){IUTEST_USING_BEGIN_END();if(Contains(begin(actual),end(actual))){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Contains: " <<m_expected;return strm.str();}private: template<typename Ite>bool Contains(Ite begin,Ite end){for(Ite it=begin;it!=end;++it){if(CastToMatcher(m_expected)(*it)){return true;}}return false;}private: T m_expected;};template<typename T>class EachMatcher:public IMatcher{public: explicit EachMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){IUTEST_USING_BEGIN_END();if(Each(begin(actual),end(actual))){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Each: " <<m_expected;return strm.str();}private: template<typename Ite>bool Each(Ite begin,Ite end){for(Ite it=begin;it!=end;++it){if(!CastToMatcher(m_expected)(*it)){return false;}}return true;}private: T m_expected;};template<typename T>class ContainerEqMatcher:public IMatcher{public: explicit ContainerEqMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){IUTEST_USING_BEGIN_END();if(Check(begin(m_expected),end(m_expected),begin(actual),end(actual))){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"ContainerEq: " <<PrintToString(m_expected);strm<<" (" <<m_whichIs<<")";return strm.str();}private: template<typename Ite1,typename Ite2>bool Check(Ite1 b1,Ite1 e1,Ite2 b2,Ite2 e2){size_t elem=0;bool result=true;Message ar;for(elem=0;b1!=e1&&b2!=e2;++b1,++b2,++elem){if(!internal::EqHelper<false>::Compare("","",*b1,*b2)){result=false;ar<<"\nMismatch in a position " <<elem<<": "<< ::iutest::internal::FormatForComparisonFailureMessage(*b1,*b2)<< " vs " << ::iutest::internal::FormatForComparisonFailureMessage(*b2,*b1);}}if(b1!=e1||b2!=e2){const size_t elem1=elem+::std::distance(b1,e1);const size_t elem2=elem+::std::distance(b2,e2);result=false;ar<<"\nMismatch element : " <<elem1<<" vs " <<elem2;}m_whichIs=ar.GetString();return result;}private: const T& m_expected;::std::string m_whichIs;};template<typename M,typename T>class PointwiseMatcher:public IMatcher{public: PointwiseMatcher(const M& matcher,const T& expected):m_matcher(matcher),m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){IUTEST_USING_BEGIN_END();if(Check(begin(m_expected),end(m_expected),begin(actual),end(actual))){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Pointwise: " <<m_matcher<<": " <<PrintToString(m_expected);strm<<" (" <<m_whichIs<<")";return strm.str();}private: template<typename Ite1,typename Ite2>bool Check(Ite1 b1,Ite1 e1,Ite2 b2,Ite2 e2){size_t elem=0;bool result=true;Message ar;for(elem=0;b1!=e1&&b2!=e2;++b1,++b2,++elem){const AssertionResult r=m_matcher(*b2,*b1);if(r.failed()){result=false;ar<<"\nMismatch in a position " <<elem<<": " <<r.message();}}if(b1!=e1||b2!=e2){const size_t elem1=elem+::std::distance(b1,e1);const size_t elem2=elem+::std::distance(b2,e2);result=false;ar<<"\nMismatch element : " <<elem1<<" vs " <<elem2;}m_whichIs=ar.GetString();return result;}private: M m_matcher;const T& m_expected;::std::string m_whichIs;};class IsEmptyMatcher:public IMatcher{public: template<typename U>AssertionResult operator()(const U& actual){if((actual).empty()){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return "Is Empty";}};template<typename T>class SizeIsMatcher:public IMatcher{public: explicit SizeIsMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(Check(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Size is: " <<m_expected;return strm.str();}private: template<typename Container>bool Check(const Container& actual){return static_cast<bool>(CastToMatcher(m_expected)(actual.size()));}template<typename U,size_t SIZE>bool Check(const U(&)[SIZE]){return static_cast<bool>(CastToMatcher(m_expected)(SIZE));}private: T m_expected;};template<typename T>class AtMatcher:public IMatcher{public: AtMatcher(size_t index,const T& expected):m_index(index),m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(CastToMatcher(m_expected)(actual[m_index])){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"At " <<m_index<<": " <<m_expected;return strm.str();}private: size_t m_index;T m_expected;};template<typename T>class ElementsAreArrayMatcher:public IMatcher{public: template<typename It>ElementsAreArrayMatcher(It begin,It end,bool expected_elem_count=true):m_expected_elem_count(expected_elem_count){m_expected.insert(m_expected.end(),begin,end);}public: template<typename U>AssertionResult operator()(const U& actual){IUTEST_USING_BEGIN_END();return Check(begin(actual),end(actual));}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return WhichIs(PrintToString(m_expected));}::std::string WhichIs(const ::std::string& msg)const{iu_global_format_stringstream strm;if(m_expected_elem_count){strm<<"ElementsAreArray: ";}else{strm<<"ElementsAreArrayForward: ";}strm<<msg;return strm.str();}private: template<typename Ite>AssertionResult Check(Ite actual_begin,Ite actual_end){const size_t actual_cnt=::std::distance(actual_begin,actual_end);const size_t expected_cnt=m_expected.size();if(actual_cnt<expected_cnt){iu_global_format_stringstream stream;stream<<"actual argument[" <<actual_cnt<<"] is less than " <<expected_cnt;return AssertionFailure()<<WhichIs(stream.str());}if(m_expected_elem_count&&actual_cnt>expected_cnt){iu_global_format_stringstream stream;stream<<"actual argument[" <<actual_cnt<<"] is greater than " <<expected_cnt;return AssertionFailure()<<WhichIs(stream.str());}Ite it_a=actual_begin;typename ::std::vector<T>::iterator it_e=m_expected.begin();for(int i=0;it_e!=m_expected.end();++it_e,++it_a,++i){if(*it_a!=*it_e){return AssertionFailure()<<WhichIs();}}return AssertionSuccess();}private: ::std::vector<T> m_expected;bool m_expected_elem_count;}; | |
#if IUTEST_HAS_MATCHER_ELEMENTSARE | |
class ElementsAreMatcherBase:public IMatcher{protected: template<typename T,typename U>static AssertionResult Check(T& matchers,const U& actual){IUTEST_USING_BEGIN_END();return Check<0,tuples::tuple_size<T>::value-1>(begin(actual),end(actual),matchers);}template<int N,typename T>static ::std::string WhichIs(const T& matchers){::std::string str="ElementsAre: {";str+=WhichIs_<T,N,tuples::tuple_size<T>::value-1>(matchers);str+="}";return str;}private: template<int N,int LAST,typename Ite,typename M>static AssertionResult Check(Ite it,Ite end,M& matchers){const size_t cnt=::std::distance(it,end);if(cnt<LAST+1){return AssertionFailure()<<"ElementsAre: argument[" <<cnt<<"] is less than " <<LAST+1;}return CheckElem<N,LAST>(it,end,matchers);}template<int N,int LAST,typename Ite,typename M>static AssertionResult CheckElem(Ite it,Ite end,M& matchers,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){for(int index=N;it!=end;++it,++index){AssertionResult ar=CastToMatcher(tuples::get<N>(matchers))(*it);if(!ar){return AssertionFailure()<<WhichIsElem<N>(matchers,index);}}return AssertionSuccess();}template<int N,int LAST,typename Ite,typename M>static AssertionResult CheckElem(Ite it,Ite end,M& matchers,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){AssertionResult ar=CastToMatcher(tuples::get<N>(matchers))(*it);if(ar){return CheckElem<N+1,LAST>(++it,end,matchers);}return AssertionFailure()<<WhichIsElem<N>(matchers,N);}template<int N,typename T>static ::std::string WhichIsElem(const T& matchers,int index){iu_global_format_stringstream strm;strm<<"ElementsAre(" <<index<<"): " <<tuples::get<N>(matchers);return strm.str();}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){return StreamableToString(tuples::get<N>(matchers));}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){return StreamableToString(tuples::get<N>(matchers))+", " + WhichIs_<T,N+1,LAST>(matchers);}}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...T>class ElementsAreMatcher:public ElementsAreMatcherBase{public: explicit ElementsAreMatcher(T... t):m_matchers(t...){}public: template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return ElementsAreMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<T...> m_matchers;}; | |
#else | |
#define II_D_EA_MATCHER(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> class IUTEST_PP_CAT(ElementsAreMatcher,n):public ElementsAreMatcherBase{public: IUTEST_PP_CAT(ElementsAreMatcher,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,T,m)) : m_matchers(IUTEST_PP_ENUM_PARAMS(n,m)){}template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return ElementsAreMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> m_matchers;} | |
II_D_EA_MATCHER(1);II_D_EA_MATCHER(2);II_D_EA_MATCHER(3);II_D_EA_MATCHER(4);II_D_EA_MATCHER(5);II_D_EA_MATCHER(6);II_D_EA_MATCHER(7);II_D_EA_MATCHER(8);II_D_EA_MATCHER(9);II_D_EA_MATCHER(10); | |
#undef II_D_EA_MATCHER | |
#endif | |
#endif | |
template<typename F,typename T>class FieldMatcher:public IMatcher{public: FieldMatcher(const F& field,const T& expected):m_field(field),m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(Check(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Field: " <<m_expected;return strm.str();}private:template<typename U>bool Check(const U& actual,typename detail::disable_if_t<detail::is_pointer<U> >::type*& = detail::enabler::value){return static_cast<bool>(CastToMatcher(m_expected)(actual.*m_field));}template<typename U>bool Check(const U& actual,typename detail::enable_if_t<detail::is_pointer<U> >::type*& = detail::enabler::value){return static_cast<bool>(CastToMatcher(m_expected)(actual->*m_field));}private: const F& m_field;T m_expected;};template<typename F,typename T>class PropertyMatcher:public IMatcher{public: PropertyMatcher(const F& prop,const T& expected):m_property(prop),m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(Check(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Property: " <<m_expected;return strm.str();}private:template<typename U>bool Check(const U& actual,typename detail::disable_if_t<detail::is_pointer<U> >::type*& = detail::enabler::value){return static_cast<bool>(CastToMatcher(m_expected)((actual.*m_property)()));}template<typename U>bool Check(const U& actual,typename detail::enable_if_t<detail::is_pointer<U> >::type*& = detail::enabler::value){return static_cast<bool>(CastToMatcher(m_expected)((actual->*m_property)()));}private: const F& m_property;T m_expected;};template<typename T>class KeyMatcher:public IMatcher{public: explicit KeyMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(CastToMatcher(m_expected)(actual.first)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Key: " <<m_expected;return strm.str();}private: const T& m_expected;};template<typename T1,typename T2>class PairMatcher:public IMatcher{public: PairMatcher(const T1& m1,const T2& m2):m_m1(m1),m_m2(m2){}public: template<typename U>AssertionResult operator()(const U& actual){if(!CheckElem(actual.first,m_m1)){return AssertionFailure()<<WhichIs();}if(!CheckElem(actual.second,m_m2)){return AssertionFailure()<<WhichIs();}return AssertionSuccess();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Pair: (" <<m_m1<<", " <<m_m2<<")";return strm.str();}private: template<typename T,typename U>bool CheckElem(const T& actual,U& matcher){return static_cast<bool>(CastToMatcher(matcher)(actual));}private: T1 m_m1;T2 m_m2;};template<typename F,typename T>class ResultOfMatcher:public IMatcher{public: ResultOfMatcher(F& func,const T& expected):m_func(func),m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(Check(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Result of: " <<m_expected;return strm.str();}private: template<typename U>bool Check(const U& actual){return static_cast<bool>(CastToMatcher(m_expected)((*m_func)(actual)));}private: F& m_func;T m_expected;};template<typename T>class PointeeMatcher:public IMatcher{public: explicit PointeeMatcher(const T& expected):m_expected(expected){}public: template<typename U>AssertionResult operator()(const U& actual){if(Check(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Points To: " <<m_expected;return strm.str();}private: template<typename U>bool Check(const U& actual){return static_cast<bool>(CastToMatcher(m_expected)(*actual));}private: T m_expected;};template<typename T>class NotMatcher:public IMatcher{public: explicit NotMatcher(const T& unexpected):m_unexpected(unexpected){}public: template<typename U>AssertionResult operator()(const U& actual){if(!CastToMatcher(m_unexpected)(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"Not: (" <<m_unexpected<<")";return strm.str();}private: T m_unexpected;};template<typename T>class AnyMatcher:public IMatcher{public: AssertionResult operator()(const T&)const{return AssertionSuccess();}template<typename U>AssertionResult operator()(const U&)const;public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;strm<<"A: " <<detail::GetTypeName<T>();return strm.str();}};class AnythingMatcher:public IMatcher{public: AnythingMatcher(){}public: template<typename U>AssertionResult operator()(const U&)const{return AssertionSuccess();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return "_";}}; | |
#if IUTEST_HAS_MATCHER_REGEX | |
class RegexMatcher:public IMatcher{public: RegexMatcher(const detail::iuRegex& expected,bool full_match):m_expected(expected),m_full_match(full_match){}public: template<typename U>AssertionResult operator()(const U& actual)const{if(Regex(actual)){return AssertionSuccess();}return AssertionFailure()<<WhichIs();}public: ::std::string WhichIs()const IUTEST_CXX_OVERRIDE{iu_global_format_stringstream strm;if(m_full_match){strm<<"MatchesRegex: " <<m_expected.pattern();}else{strm<<"ContainsRegex: " <<m_expected.pattern();}return strm.str();}private: bool Regex(const char* actual)const{return m_full_match?m_expected.FullMatch(actual):m_expected.PartialMatch(actual);}bool Regex(const ::std::string& actual)const{return m_full_match?m_expected.FullMatch(actual.c_str()):m_expected.PartialMatch(actual.c_str());}private: detail::iuRegex m_expected;bool m_full_match;}; | |
#endif | |
#if IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF | |
class AllOfMatcherBase:public IMatcher{protected: template<typename T,typename U>static AssertionResult Check(T& matchers,const U& actual){return Check_<T,U,0,tuples::tuple_size<T>::value-1>(matchers,actual);}template<int N,typename T>static ::std::string WhichIs(const T& matchers){return WhichIs_<T,N,tuples::tuple_size<T>::value-1>(matchers);}private: template<typename T,typename U,int N,int LAST>static AssertionResult Check_(T& matchers,const U& actual,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){AssertionResult ar=tuples::get<N>(matchers)(actual);if(ar){return ar;}return AssertionFailure()<<WhichIs_<T,0,N>(matchers);}template<typename T,typename U,int N,int LAST>static AssertionResult Check_(T& matchers,const U& actual,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){AssertionResult ar=tuples::get<N>(matchers)(actual);if(ar){return Check_<T,U,N+1,LAST>(matchers,actual);}return AssertionFailure()<<WhichIs_<T,0,N>(matchers);}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){return tuples::get<N>(matchers).WhichIs();}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){return tuples::get<N>(matchers).WhichIs()+" and " + WhichIs_<T,N+1,LAST>(matchers);}}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...T>class AllOfMatcher:public AllOfMatcherBase{public: explicit AllOfMatcher(T... t):m_matchers(t...){}public: template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return AllOfMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<T...> m_matchers;}; | |
#else | |
#define II_D_ALL_M(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> class IUTEST_PP_CAT(AllOfMatcher,n):public AllOfMatcherBase{public: IUTEST_PP_CAT(AllOfMatcher,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,T,m)) : m_matchers(IUTEST_PP_ENUM_PARAMS(n,m)){}template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return AllOfMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> m_matchers;} | |
II_D_ALL_M(2);II_D_ALL_M(3);II_D_ALL_M(4);II_D_ALL_M(5);II_D_ALL_M(6);II_D_ALL_M(7);II_D_ALL_M(8);II_D_ALL_M(9);II_D_ALL_M(10); | |
#undef II_D_ALL_M | |
#endif | |
class AnyOfMatcherBase:public IMatcher{protected: template<typename T,typename U>static AssertionResult Check(T& matchers,const U& actual){return Check_<T,U,0,tuples::tuple_size<T>::value-1>(matchers,actual);}template<int N,typename T>static ::std::string WhichIs(const T& matchers){return WhichIs_<T,N,tuples::tuple_size<T>::value-1>(matchers);}private: template<typename T,typename U,int N,int LAST>static AssertionResult Check_(T& matchers,const U& actual,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){AssertionResult ar=tuples::get<N>(matchers)(actual);if(ar){return ar;}return AssertionFailure()<<WhichIs_<T,0,N>(matchers);}template<typename T,typename U,int N,int LAST>static AssertionResult Check_(T& matchers,const U& actual,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){AssertionResult ar=tuples::get<N>(matchers)(actual);if(ar){return ar;}return Check_<T,U,N+1,LAST>(matchers,actual);}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::enable_if<N==LAST,void>::type*& = detail::enabler::value){return tuples::get<N>(matchers).WhichIs();}template<typename T,int N,int LAST>static ::std::string WhichIs_(const T& matchers,typename detail::disable_if<N==LAST,void>::type*& = detail::enabler::value){return tuples::get<N>(matchers).WhichIs()+" or " + WhichIs_<T,N+1,LAST>(matchers);}}; | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...T>class AnyOfMatcher:public AnyOfMatcherBase{public: explicit AnyOfMatcher(T... t):m_matchers(t...){}public: template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return AnyOfMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<T...> m_matchers;}; | |
#else | |
#define II_D_ANY_M(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> class IUTEST_PP_CAT(AnyOfMatcher,n):public AnyOfMatcherBase{public: IUTEST_PP_CAT(AnyOfMatcher,n)(IUTEST_PP_ENUM_BINARY_PARAMS(n,T,m)) : m_matchers(IUTEST_PP_ENUM_PARAMS(n,m)){}template<typename U>AssertionResult operator()(const U& actual){return Check(m_matchers,actual);}::std::string WhichIs()const IUTEST_CXX_OVERRIDE{return AnyOfMatcherBase::WhichIs<0>(m_matchers);}private: tuples::tuple<IUTEST_PP_ENUM_PARAMS(n,T)> m_matchers;} | |
II_D_ANY_M(2);II_D_ANY_M(3);II_D_ANY_M(4);II_D_ANY_M(5);II_D_ANY_M(6);II_D_ANY_M(7);II_D_ANY_M(8);II_D_ANY_M(9);II_D_ANY_M(10); | |
#undef II_D_ANY_M | |
#endif | |
#endif | |
IUTEST_PRAGMA_ASSIGNMENT_OPERATOR_COULD_NOT_GENERATE_WARN_DISABLE_END()}namespace matchers{template<typename T>detail::EqMatcher<T> Equals(const T& expected){return detail::EqMatcher<T>(expected);}template<typename T>detail::EqMatcher<T> Eq(const T& expected){return detail::EqMatcher<T>(expected);}template<typename T>detail::NeMatcher<T> Ne(const T& expected){return detail::NeMatcher<T>(expected);}template<typename T>detail::LeMatcher<T> Le(const T& expected){return detail::LeMatcher<T>(expected);}template<typename T>detail::LtMatcher<T> Lt(const T& expected){return detail::LtMatcher<T>(expected);}template<typename T>detail::GeMatcher<T> Ge(const T& expected){return detail::GeMatcher<T>(expected);}template<typename T>detail::GtMatcher<T> Gt(const T& expected){return detail::GtMatcher<T>(expected);}inline detail::TwofoldEqMatcher Eq(){return detail::TwofoldEqMatcher();}inline detail::TwofoldNeMatcher Ne(){return detail::TwofoldNeMatcher();}inline detail::TwofoldLeMatcher Le(){return detail::TwofoldLeMatcher();}inline detail::TwofoldLtMatcher Lt(){return detail::TwofoldLtMatcher();}inline detail::TwofoldGeMatcher Ge(){return detail::TwofoldGeMatcher();}inline detail::TwofoldGtMatcher Gt(){return detail::TwofoldGtMatcher();}inline detail::IsNullMatcher IsNull(){return detail::IsNullMatcher();}inline detail::NotNullMatcher NotNull(){return detail::NotNullMatcher();}template<typename T,typename U>detail::TypedEqMatcher<T> TypedEq(const U& expected){return detail::TypedEqMatcher<T>(static_cast<T>(expected));}template<typename T>inline detail::FloatingPointEqMatcher<T> FloatingPointEq(T expected){return detail::FloatingPointEqMatcher<T>(expected);}inline detail::FloatingPointEqMatcher<float> FloatEq(float expected){return detail::FloatingPointEqMatcher<float>(expected);}inline detail::FloatingPointEqMatcher<double> DoubleEq(double expected){return detail::FloatingPointEqMatcher<double>(expected);} | |
#if IUTEST_HAS_LONG_DOUBLE | |
inline detail::FloatingPointEqMatcher<long double> LongDoubleEq(long double expected){return detail::FloatingPointEqMatcher<long double>(expected);} | |
#endif | |
template<typename T>inline detail::NanSensitiveFloatingPointEqMatcher<T> NanSensitiveFloatingPointEq(T expected){return detail::NanSensitiveFloatingPointEqMatcher<T>(expected);}inline detail::NanSensitiveFloatingPointEqMatcher<float> NanSensitiveFloatEq(float expected){return detail::NanSensitiveFloatingPointEqMatcher<float>(expected);}inline detail::NanSensitiveFloatingPointEqMatcher<double> NanSensitiveDoubleEq(double expected){return detail::NanSensitiveFloatingPointEqMatcher<double>(expected);} | |
#if IUTEST_HAS_LONG_DOUBLE | |
inline detail::NanSensitiveFloatingPointEqMatcher<long double> NanSensitiveLongDoubleEq(long double expected){return detail::NanSensitiveFloatingPointEqMatcher<long double>(expected);} | |
#endif | |
template<typename T>inline detail::FloatingPointNearMatcher<T> FloatingPointNear(T expected,T max_abs_error){return detail::FloatingPointNearMatcher<T>(expected,max_abs_error);}inline detail::FloatingPointNearMatcher<float> FloatNear(float expected,float max_abs_error){return detail::FloatingPointNearMatcher<float>(expected,max_abs_error);}inline detail::FloatingPointNearMatcher<double> DoubleNear(double expected,double max_abs_error){return detail::FloatingPointNearMatcher<double>(expected,max_abs_error);} | |
#if IUTEST_HAS_LONG_DOUBLE | |
inline detail::FloatingPointNearMatcher<long double> LongDoubleNear(long double expected,long double max_abs_error){return detail::FloatingPointNearMatcher<long double>(expected,max_abs_error);} | |
#endif | |
template<typename T>inline detail::NanSensitiveFloatingPointNearMatcher<T> NanSensitiveFloatingPointNear(T expected,T max_abs_error){return detail::NanSensitiveFloatingPointNearMatcher<T>(expected,max_abs_error);}inline detail::NanSensitiveFloatingPointNearMatcher<float> NanSensitiveFloatNear(float expected,float max_abs_error){return detail::NanSensitiveFloatingPointNearMatcher<float>(expected,max_abs_error);}inline detail::NanSensitiveFloatingPointNearMatcher<double> NanSensitiveDoubleNear(double expected,double max_abs_error){return detail::NanSensitiveFloatingPointNearMatcher<double>(expected,max_abs_error);} | |
#if IUTEST_HAS_LONG_DOUBLE | |
inline detail::NanSensitiveFloatingPointNearMatcher<long double> NanSensitiveLongDoubleNear(long double expected,long double max_abs_error){return detail::NanSensitiveFloatingPointNearMatcher<long double>(expected,max_abs_error);} | |
#endif | |
template<typename T>detail::StrEqMatcher<T> StrEq(const T& expected){return detail::StrEqMatcher<T>(expected);}template<typename T>detail::StrNeMatcher<T> StrNe(const T& expected){return detail::StrNeMatcher<T>(expected);}template<typename T>detail::StrCaseEqMatcher<T> StrCaseEq(const T& expected){return detail::StrCaseEqMatcher<T>(expected);}template<typename T>detail::StrCaseNeMatcher<T> StrCaseNe(const T& expected){return detail::StrCaseNeMatcher<T>(expected);}template<typename T>detail::StartsWithMatcher<const T&> StartsWith(const T& str){return detail::StartsWithMatcher<const T&>(str);}template<typename T>detail::HasSubstrMatcher<const T&> HasSubstr(const T& str){return detail::HasSubstrMatcher<const T&>(str);}template<typename T>detail::EndsWithMatcher<const T&> EndsWith(const T& str){return detail::EndsWithMatcher<const T&>(str);}template<typename T>detail::ContainsMatcher<T> Contains(const T& expected){return detail::ContainsMatcher<T>(expected);}template<typename T>detail::EachMatcher<T> Each(const T& expected){return detail::EachMatcher<T>(expected);}template<typename T>detail::ContainerEqMatcher<T> ContainerEq(const T& expected){return detail::ContainerEqMatcher<T>(expected);}template<typename M,typename T>detail::PointwiseMatcher<M,T> Pointwise(const M& matcher,const T& expected){return detail::PointwiseMatcher<M,T>(matcher,expected);}inline detail::IsEmptyMatcher IsEmpty(){return detail::IsEmptyMatcher();}template<typename T>detail::SizeIsMatcher<T> SizeIs(const T& expected){return detail::SizeIsMatcher<T>(expected);}template<typename T>detail::AtMatcher<T> At(size_t index,const T& expected){return detail::AtMatcher<T>(index,expected);}template<typename Container>detail::ElementsAreArrayMatcher<typename Container::value_type>ElementsAreArray(const Container& container){IUTEST_USING_BEGIN_END();return detail::ElementsAreArrayMatcher<typename Container::value_type>(container.begin(),container.end());}template<typename T,size_t SIZE>detail::ElementsAreArrayMatcher<T> ElementsAreArray(const T(&v)[SIZE]){return detail::ElementsAreArrayMatcher<T>(v,v+SIZE);}template<typename Ite>detail::ElementsAreArrayMatcher<typename detail::IteratorTraits<Ite>::type>ElementsAreArray(Ite begin,Ite end){return detail::ElementsAreArrayMatcher<typename detail::IteratorTraits<Ite>::type >(begin,end);} | |
#if IUTEST_HAS_INITIALIZER_LIST | |
template<typename T>detail::ElementsAreArrayMatcher<T> ElementsAreArray(::std::initializer_list<T> l){return detail::ElementsAreArrayMatcher<T>(l.begin(),l.end());} | |
#endif | |
template<typename T>detail::ElementsAreArrayMatcher<T> ElementsAreArray(const T* a,int count){return detail::ElementsAreArrayMatcher<T>(a,a+count);} | |
#if IUTEST_HAS_MATCHER_ELEMENTSAREARRAYFORWARD | |
template<typename Container>detail::ElementsAreArrayMatcher<typename Container::value_type>ElementsAreArrayForward(const Container& container){return detail::ElementsAreArrayMatcher<typename Container::value_type>(container.begin(),container.end(),false);}template<typename T,size_t SIZE>detail::ElementsAreArrayMatcher<T> ElementsAreArrayForward(const T(&v)[SIZE]){return detail::ElementsAreArrayMatcher<T>(v,v+SIZE,false);}template<typename Ite>detail::ElementsAreArrayMatcher<typename detail::IteratorTraits<Ite>::type>ElementsAreArrayForward(Ite begin,Ite end){return detail::ElementsAreArrayMatcher<typename detail::IteratorTraits<Ite>::type >(begin,end,false);} | |
#if IUTEST_HAS_INITIALIZER_LIST | |
template<typename T>detail::ElementsAreArrayMatcher<T> ElementsAreArrayForward(::std::initializer_list<T> l){return detail::ElementsAreArrayMatcher<T>(l.begin(),l.end(),false);} | |
#endif | |
template<typename T>detail::ElementsAreArrayMatcher<T> ElementsAreArrayForward(const T* a,int count){return detail::ElementsAreArrayMatcher<T>(a,a+count,false);} | |
#endif | |
#if IUTEST_HAS_MATCHER_ELEMENTSARE | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...T>detail::ElementsAreMatcher<T...> ElementsAre(const T&... m){return detail::ElementsAreMatcher<T...>(m...);} | |
#else | |
#define II_EA_M_N(n) IUTEST_PP_CAT(ElementsAreMatcher,n) | |
#define II_D_EA(n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> detail:: II_EA_M_N(n)<IUTEST_PP_ENUM_PARAMS(n,T)> ElementsAre(IUTEST_PP_ENUM_BINARY_PARAMS(n,const T,&m)){return detail:: II_EA_M_N(n)<IUTEST_PP_ENUM_PARAMS(n,T)> (IUTEST_PP_ENUM_PARAMS(n,m));} | |
II_D_EA(1)II_D_EA(2)II_D_EA(3)II_D_EA(4)II_D_EA(5)II_D_EA(6)II_D_EA(7)II_D_EA(8)II_D_EA(9)II_D_EA(10) | |
#undef II_EA_M_N | |
#undef II_D_EA | |
#endif | |
#endif | |
template<typename T>detail::KeyMatcher<T> Key(const T& expected){return detail::KeyMatcher<T>(expected);}template<typename T1,typename T2>detail::PairMatcher<T1,T2> Pair(const T1& m1,const T2& m2){return detail::PairMatcher<T1,T2>(m1,m2);}template<typename F,typename T>detail::FieldMatcher<F,T> Field(const F& field,const T& expected){return detail::FieldMatcher<F,T>(field,expected);}template<typename P,typename T>detail::PropertyMatcher<P,T> Property(const P& prop,const T& expected){return detail::PropertyMatcher<P,T>(prop,expected);}template<typename F,typename T>detail::ResultOfMatcher<F,T> ResultOf(const F& func,const T& expected){return detail::ResultOfMatcher<F,T>(func,expected);}template<typename T>detail::PointeeMatcher<T> Pointee(const T& expected){return detail::PointeeMatcher<T>(expected);}template<typename T>detail::NotMatcher<T> Not(const T& unexpected){return detail::NotMatcher<T>(unexpected);}template<typename T>detail::AnyMatcher<T> A(){return detail::AnyMatcher<T>();}const detail::AnythingMatcher _; | |
#if IUTEST_HAS_MATCHER_REGEX | |
inline detail::RegexMatcher MatchesRegex(const ::std::string& str){return detail::RegexMatcher(detail::iuRegex(str),true);}inline detail::RegexMatcher ContainsRegex(const ::std::string& str){return detail::RegexMatcher(detail::iuRegex(str),false);} | |
#endif | |
#if IUTEST_HAS_MATCHER_ALLOF_AND_ANYOF | |
#if IUTEST_HAS_VARIADIC_TEMPLATES | |
template<typename ...T>detail::AllOfMatcher<T...> AllOf(const T&... m){return detail::AllOfMatcher<T...>(m...);}template<typename ...T>detail::AnyOfMatcher<T...> AnyOf(const T&... m){return detail::AnyOfMatcher<T...>(m...);} | |
#else | |
#define II_AAA_M_N(name,n) IUTEST_PP_CAT(IUTEST_PP_CAT(name,Matcher),n) | |
#define II_D_AAA(name,n) template<IUTEST_PP_ENUM_PARAMS(n,typename T)> detail:: II_AAA_M_N(name,n)<IUTEST_PP_ENUM_PARAMS(n,T)> name(IUTEST_PP_ENUM_BINARY_PARAMS(n,const T,&m)){return detail:: II_AAA_M_N(name,n)<IUTEST_PP_ENUM_PARAMS(n,T)> (IUTEST_PP_ENUM_PARAMS(n,m));} | |
II_D_AAA(AllOf,2)II_D_AAA(AllOf,3)II_D_AAA(AllOf,4)II_D_AAA(AllOf,5)II_D_AAA(AllOf,6)II_D_AAA(AllOf,7)II_D_AAA(AllOf,8)II_D_AAA(AllOf,9)II_D_AAA(AllOf,10)II_D_AAA(AnyOf,2)II_D_AAA(AnyOf,3)II_D_AAA(AnyOf,4)II_D_AAA(AnyOf,5)II_D_AAA(AnyOf,6)II_D_AAA(AnyOf,7)II_D_AAA(AnyOf,8)II_D_AAA(AnyOf,9)II_D_AAA(AnyOf,10) | |
#undef II_AAA_M_N | |
#undef II_D_AAA | |
#endif | |
#endif | |
template<typename T,typename M>bool Value(const T& value,const M& expected){return static_cast<bool>(detail::CastToMatcher(expected)(value));}}using namespace matchers;} | |
#endif | |
#if IUTEST_HAS_STATIC_ASSERT_TYPEEQ | |
#define StaticAssertTypeEq detail::StaticAssertTypeEqHelper | |
#endif | |
#if IUTEST_HAS_STATIC_ASSERT | |
#if (__GNUC__<4||(__GNUC__==4&&__GNUC_MINOR__<8)) | |
#define IUTEST_STATIC_ASSERT_MSG(B,Msg) static_assert(B,"static_assert: " Msg) | |
#else | |
#define IUTEST_STATIC_ASSERT_MSG(B,Msg) static_assert(B,Msg) | |
#endif | |
#else | |
#define II_STATIC_ASSERT_SIZECHECK(B) sizeof(::iutest::detail::static_assert_failure<(bool)B >) | |
#define IUTEST_STATIC_ASSERT_MSG(B,Msg) typedef ::iutest::detail::StaticAssertionTest<II_STATIC_ASSERT_SIZECHECK(B)> IUTEST_PP_CAT(iutest_static_assert_typedef_,IUTEST_PP_COUNTER) IUTEST_ATTRIBUTE_UNUSED_ | |
#endif | |
#ifdef IUTEST_STATIC_ASSERT_MSG | |
#define IUTEST_STATIC_ASSERT(...) IUTEST_STATIC_ASSERT_MSG((__VA_ARGS__),#__VA_ARGS__) | |
#endif | |
namespace iutest{namespace detail{template<typename T1,typename T2>struct StaticAssertTypeEqHelper;namespace helper{template<bool b>struct static_assert_typeeq;template<>struct static_assert_typeeq<true>{operator bool()const{return true;}};}template<typename T1,typename T2>struct StaticAssertTypeEqHelper: public helper::static_assert_typeeq<iutest_type_traits::is_same<T1,T2>::value >{};template<bool b>struct static_assert_failure;template<> struct static_assert_failure<true>{enum{value=1};};template<int x>struct StaticAssertionTest{};}}namespace iutest{class DefaultResultPrintListener:public TestEventListener{public: DefaultResultPrintListener(){}virtual ~DefaultResultPrintListener(){TestEnv::event_listeners().set_default_result_printer(0);}public: virtual void OnTestProgramStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationStart(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsSetUpStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsSetUpEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseStart(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnTestStart(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestPartResult(const TestPartResult& test_part_result) IUTEST_CXX_OVERRIDE;virtual void OnTestRecordProperty(const TestProperty& test_property) IUTEST_CXX_OVERRIDE;virtual void OnTestEnd(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseEnd(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsTearDownStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnEnvironmentsTearDownEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationEnd(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnTestProgramEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;private: void PrintTestResult(const TestInfo& test_info)const;};}namespace iutest{inline void DefaultResultPrintListener::OnTestProgramStart(const UnitTest& test){(void)(test);if(TestFlag::IsEnableFlag(TestFlag::FILTERING_TESTS)){detail::iuConsole::color_output(detail::iuConsole::yellow,"Note: iutest filter = %s\n",TestEnv::test_filter());}}inline void DefaultResultPrintListener::OnTestIterationStart(const UnitTest& test,int iteration){if(test.repeat_count()!=1){detail::iuConsole::output("\nRepeating all tests (iteration %d) . . .\n\n",iteration+1);}if(TestFlag::IsEnableFlag(TestFlag::SHUFFLE_TESTS)){detail::iuConsole::color_output(detail::iuConsole::yellow,"Note: Randomizing tests' orders with a seed of %u\n",test.random_seed());}detail::iuConsole::color_output(detail::iuConsole::green,"[==========] ");detail::iuConsole::output("Running %d tests from %d test cases.\n",test.test_to_run_count(),test.test_case_to_run_count());}inline void DefaultResultPrintListener::OnEnvironmentsSetUpStart(const UnitTest& test){(void)(test);detail::iuConsole::color_output(detail::iuConsole::green,"[----------] ");detail::iuConsole::output("Global test environment set-up.\n");}inline void DefaultResultPrintListener::OnEnvironmentsSetUpEnd(const UnitTest& test){(void)(test);}inline void DefaultResultPrintListener::OnTestCaseStart(const TestCase& test_case){detail::iuConsole::color_output(detail::iuConsole::green,"[----------] ");detail::iuConsole::output("%d tests from %s\n",test_case.test_to_run_count(),test_case.testcase_name_with_where().c_str());}inline void DefaultResultPrintListener::OnTestStart(const TestInfo& test_info){detail::iuConsole::color_output(detail::iuConsole::green,"[ RUN ] ");detail::iuConsole::output("%s.%s\n",test_info.test_case_name(),test_info.name());}inline void DefaultResultPrintListener::OnTestPartResult(const TestPartResult& test_part_result){detail::iuConsole::output(test_part_result.make_newline_message().c_str());}inline void DefaultResultPrintListener::OnTestRecordProperty(const TestProperty& test_property){detail::iuConsole::output("iutest record property:\n %s=%s\n",test_property.key(),test_property.value());}inline void DefaultResultPrintListener::PrintTestResult(const TestInfo& test_info)const{if(test_info.HasFailure()){detail::iuConsole::color_output(detail::iuConsole::red,"[ FAILED ] ");detail::iuConsole::output("%s.%s",test_info.test_case_name(),test_info.test_name_with_where().c_str());return;}if(test_info.is_skipped()){detail::iuConsole::color_output(detail::iuConsole::yellow,"[ SKIPPED ] ");detail::iuConsole::output("%s.%s",test_info.test_case_name(),test_info.name());return;}detail::iuConsole::color_output(detail::iuConsole::green,"[ OK ] ");detail::iuConsole::output("%s.%s",test_info.test_case_name(),test_info.name());}inline void DefaultResultPrintListener::OnTestEnd(const TestInfo& test_info){PrintTestResult(test_info);if(TestFlag::IsEnableFlag(TestFlag::PRINT_TIME)){detail::iuConsole::output(" (%dms)",test_info.elapsed_time());}detail::iuConsole::output("\n");}inline void DefaultResultPrintListener::OnTestCaseEnd(const TestCase& test_case){detail::iuConsole::color_output(detail::iuConsole::green,"[----------] ");detail::iuConsole::output("%d tests from %s",test_case.test_to_run_count(),test_case.name());if(TestFlag::IsEnableFlag(TestFlag::PRINT_TIME)){detail::iuConsole::output("(%dms total)",test_case.elapsed_time());}detail::iuConsole::output("\n\n");}inline void DefaultResultPrintListener::OnEnvironmentsTearDownStart(const UnitTest& test){(void)(test);detail::iuConsole::color_output(detail::iuConsole::green,"[----------] ");detail::iuConsole::output("Global test environment tear-down.\n");}inline void DefaultResultPrintListener::OnEnvironmentsTearDownEnd(const UnitTest& test){(void)(test);}inline void DefaultResultPrintListener::OnTestIterationEnd(const UnitTest& test,int iteration){(void)(iteration);detail::iuConsole::color_output(detail::iuConsole::green,"[==========] ");detail::iuConsole::output("%d tests from %d testcase ran.",test.test_to_run_count(),test.test_case_to_run_count());if(TestFlag::IsEnableFlag(TestFlag::PRINT_TIME)){detail::iuConsole::output(" (%dms total)",test.elapsed_time());}detail::iuConsole::output("\n");{{detail::iuConsole::color_output(detail::iuConsole::green,"[ PASSED ] ");detail::iuConsole::output("%d tests.\n",test.successful_test_count());}{const int count=test.reportable_disabled_test_count();if(!TestFlag::IsEnableFlag(TestFlag::RUN_DISABLED_TESTS)&&count>0){detail::iuConsole::color_output(detail::iuConsole::yellow,"[ DISABLED ] ");detail::iuConsole::output("%d tests.\n",count);if(TestFlag::IsEnableFlag(TestFlag::VERBOSE)){for(int i=0,case_count=test.total_test_case_count();i<case_count;++i){const TestCase* testcase=test.GetTestCase(i);for(int j=0,info_count=testcase->total_test_count();j<info_count;++j){const TestInfo* testinfo=testcase->GetTestInfo(j);if(testinfo->is_disabled_test()){detail::iuConsole::color_output(detail::iuConsole::yellow,"[ DISABLED ] ");detail::iuConsole::output("%s.%s\n",testinfo->test_case_name(),testinfo->name());}}}}}}{const int count=test.reportable_test_run_skipped_count();if(count>0){detail::iuConsole::color_output(detail::iuConsole::yellow,"[ SKIPPED ] ");detail::iuConsole::output("%d tests.\n",count);if(TestFlag::IsEnableFlag(TestFlag::VERBOSE)){for(int i=0,case_count=test.total_test_case_count();i<case_count;++i){const TestCase* testcase=test.GetTestCase(i);for(int j=0,info_count=testcase->total_test_count();j<info_count;++j){const TestInfo* testinfo=testcase->GetTestInfo(j);if(testinfo->is_skipped()){detail::iuConsole::color_output(detail::iuConsole::yellow,"[ SKIPPED ] ");detail::iuConsole::output("%s.%s\n",testinfo->test_case_name(),testinfo->name());}}}}}}if(!test.Passed()){const int failed_num=test.failed_test_count();detail::iuConsole::color_output(detail::iuConsole::red,"[ FAILED ] ");detail::iuConsole::output("%d %s, listed below:\n",failed_num,failed_num==1 ? "test" : "tests");for(int i=0,count=test.total_test_case_count();i<count;++i){const TestCase* testcase=test.GetTestCase(i);for(int j=0,info_count=testcase->total_test_count();j<info_count;++j){const TestInfo* testinfo=testcase->GetTestInfo(j);if(testinfo->HasFailure()){detail::iuConsole::color_output(detail::iuConsole::red,"[ FAILED ] ");detail::iuConsole::output("%s.%s\n",testinfo->test_case_name(),testinfo->name());}}if(testcase->ad_hoc_test_result()->Failed()){detail::iuConsole::color_output(detail::iuConsole::red,"[ FAILED ] ");detail::iuConsole::output("%s at SetUpTestCase/TearDownTestCase\n",testcase->name());}}if(test.ad_hoc_test_result()->Failed()){detail::iuConsole::color_output(detail::iuConsole::red,"[ FAILED ] ");detail::iuConsole::output("other than\n");}detail::iuConsole::output("\n%d FAILED %s.\n",failed_num,failed_num==1 ? "TEST" : "TESTS");}}}inline void DefaultResultPrintListener::OnTestProgramEnd(const UnitTest& test){(void)(test);}}namespace iutest{class DefaultXmlGeneratorListener:public EmptyTestEventListener{::std::string m_output_path_format;::std::string m_output_path;protected: IFile* m_fp;public: explicit DefaultXmlGeneratorListener(const ::std::string& path):m_fp(0){SetFilePath(path);}virtual ~DefaultXmlGeneratorListener(){FileClose();TestEnv::event_listeners().set_default_xml_generator(0);}public: const ::std::string& GetFilePath()const{return m_output_path;}private: void SetFilePath(const ::std::string& path){if(path.empty()){m_output_path_format.clear();m_output_path=detail::kStrings::DefaultXmlReportFileName;}else{m_output_path_format=path;const ::std::string::size_type pos=path.find('.');if(pos==::std::string::npos|| pos==path.length()-1){m_output_path_format+=detail::GetPathSeparator();m_output_path_format+=detail::kStrings::DefaultXmlReportFileName;}m_output_path=m_output_path_format;}}public: virtual void OnTestIterationStart(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnTestProgramEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;private: virtual void OnReportTest(IFile* file,const UnitTest& test);private: static void OnReportTestCase(IFile* file,const TestCase& test_case);static void OnReportTestInfo(IFile* file,const TestInfo& test_info);static void OnReportTestProperty(IFile* file,const TestResult& test_result,bool(*pfnValidate)(const ::std::string&));static void OnReportTestSkipped(IFile* file,const TestInfo& test_info);private: virtual bool FileOpen(const char* path);virtual void FileClose();protected: static void OutputXmlCDataSection(IFile* file,const char* data);static void OutputXmlAttribute(IFile* file,const char* name,const char* value);protected: static ::std::string EscapeXmlAttribute(const char* str){return EscapeXml(str,true);}static ::std::string EscapeXmlAttribute(const ::std::string str){return EscapeXml(str.c_str(),true);}static ::std::string EscapeXmlText(const char* str){return EscapeXml(str,false);}static ::std::string EscapeXml(const char* str,bool is_attribute);static IUTEST_CXX_CONSTEXPR bool IsWhitespace(char c){return c==9||c==0xA||c==0xD;}static IUTEST_CXX_CONSTEXPR bool IsValidXmlCharacter(char c){return IsWhitespace(c)||c>=0x20;}public: static bool SetUp(){::std::string xmlpath=TestEnv::get_report_xml_filepath();if(!xmlpath.empty()){TestEnv::event_listeners().set_default_xml_generator(new DefaultXmlGeneratorListener(xmlpath));return true;}return false;}};}namespace iutest{inline void DefaultXmlGeneratorListener::OnTestIterationStart(const UnitTest& test,int iteration){(void)(test);if(!m_output_path_format.empty()){m_output_path=detail::StringFormat(m_output_path_format.c_str(),iteration);if(m_output_path==m_output_path_format){m_output_path_format.clear();}if(m_fp!=0){OnReportTest(m_fp,test);FileClose();}}if(m_fp==0){FileOpen(m_output_path.c_str());}}inline void DefaultXmlGeneratorListener::OnTestProgramEnd(const UnitTest& test){if(m_fp==0){FileOpen(m_output_path.c_str());if(m_fp==0){return;}}OnReportTest(m_fp,test);FileClose();}inline void DefaultXmlGeneratorListener::OnReportTest(IFile* file,const UnitTest& test){file->Printf("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");file->Printf("<testsuites tests=\"%d\" failures=\"%d\" disabled=\"%d\" ",test.reportable_test_count(),test.failed_test_count(),test.reportable_disabled_test_count()); | |
#if IUTEST_HAS_REPORT_SKIPPED | |
file->Printf("skip=\"%d\" ",test.reportable_skip_test_count()); | |
#endif | |
file->Printf("errors=\"0\" time=\"%s\" timestamp=\"%s\" ",detail::FormatTimeInMillisecAsSecond(test.elapsed_time()).c_str(),detail::FormatTimeInMillisecAsIso8601(test.start_timestamp()).c_str());if(TestFlag::IsEnableFlag(TestFlag::SHUFFLE_TESTS)){file->Printf("random_seed=\"%d\" ",test.random_seed());}file->Printf("name=\"AllTests\"");OnReportTestProperty(file,*test.ad_hoc_test_result(),UnitTest::ValidateTestPropertyName);file->Printf(">\n");for(int i=0,count=test.total_test_case_count();i<count;++i){OnReportTestCase(file,*test.GetTestCase(i));}file->Printf("</testsuites>\n");}inline void DefaultXmlGeneratorListener::OnReportTestCase(IFile* file,const TestCase& test_case){if(test_case.reportable_test_count()<=0){return;}file->Printf(" <testsuite ");OutputXmlAttribute(file,"name",EscapeXmlAttribute(test_case.testcase_name_with_default_package_name()).c_str());file->Printf("tests=\"%d\" failures=\"%d\" disabled=\"%d\" ",test_case.reportable_test_count(),test_case.failed_test_count(),test_case.reportable_disabled_test_count()); | |
#if IUTEST_HAS_REPORT_SKIPPED | |
file->Printf("skip=\"%d\" ",test_case.reportable_skip_test_count()); | |
#endif | |
file->Printf("errors=\"0\" time=\"%s\" timestamp=\"%s\"",detail::FormatTimeInMillisecAsSecond(test_case.elapsed_time()).c_str(),detail::FormatTimeInMillisecAsIso8601(test_case.start_timestamp()).c_str());OnReportTestProperty(file,*test_case.ad_hoc_test_result(),TestCase::ValidateTestPropertyName);file->Printf(">\n");for(int i=0,count=test_case.total_test_count();i<count;++i){OnReportTestInfo(file,*test_case.GetTestInfo(i));}file->Printf(" </testsuite>\n");}inline void DefaultXmlGeneratorListener::OnReportTestInfo(IFile* file,const TestInfo& test_info){if(!test_info.is_reportable()){return;}file->Printf(" <testcase ");OutputXmlAttribute(file,"name",EscapeXmlAttribute(test_info.name()).c_str());{const char* type_param=test_info.type_param();if(type_param!=0){OutputXmlAttribute(file,"type_param",EscapeXmlAttribute(type_param).c_str());}}{const char* value_param=test_info.value_param();if(value_param!=0){OutputXmlAttribute(file,"value_param",EscapeXmlAttribute(value_param).c_str());}}if(test_info.is_ran()){file->Printf("status=\"run\" ");}else{file->Printf("status=\"notrun\" ");}file->Printf("time=\"%s\" ",detail::FormatTimeInMillisecAsSecond(test_info.elapsed_time()).c_str());OutputXmlAttribute(file,"classname",EscapeXmlAttribute(test_info.testcase_name_with_default_package_name()).c_str());OnReportTestProperty(file,*test_info.result(),TestInfo::ValidateTestPropertyName);const bool notrun=test_info.should_run()&&!test_info.is_ran();if(test_info.HasFailure()||notrun){file->Printf(">\n");for(int i=0,count=test_info.result()->total_part_count();i<count;++i){const TestPartResult& part=test_info.result()->GetTestPartResult(i);if(part.passed()){continue;}file->Printf(" <failure ");OutputXmlAttribute(file,"message",EscapeXmlAttribute(part.summary()).c_str());file->Printf("type=\"\">");::std::string message=detail::FormatCompilerIndependentFileLocation(part.file_name(),part.line_number());message+="\n";message+=detail::MultiByteStringToUTF8(part.summary());OutputXmlCDataSection(file,message.c_str());file->Printf("\n </failure>\n");}if(notrun){file->Printf(" <failure message=\"Not Run\" type=\"\">");OutputXmlCDataSection(file,"Not Run");file->Printf("\n </failure>\n");}file->Printf(" </testcase>\n");}else{ | |
#if IUTEST_HAS_REPORT_SKIPPED | |
const bool skipped=test_info.is_skipped()||!test_info.should_run();if(skipped){file->Printf(">\n");OnReportTestSkipped(file,test_info);file->Printf(" </testcase>\n");}else | |
#endif | |
{file->Printf(" />\n");}}}inline void DefaultXmlGeneratorListener::OnReportTestSkipped(IFile* file,const TestInfo& test_info){file->Printf(" <skipped type=\"iutest.skip\" ");const TestResult* tr=test_info.result();const int count=tr->total_part_count();for(int i=0;i<count;++i){const TestPartResult& part=tr->GetTestPartResult(i);if(part.skipped()){::std::string message=detail::FormatCompilerIndependentFileLocation(part.file_name(),part.line_number());message+=": ";message+=detail::MultiByteStringToUTF8(part.summary());OutputXmlAttribute(file,"message",EscapeXmlAttribute(message.c_str()).c_str());file->Printf(" />\n");return;}}if(test_info.is_disabled_test()){OutputXmlAttribute(file,"message","disabled test.");}file->Printf("/>\n");}inline void DefaultXmlGeneratorListener::OnReportTestProperty(IFile* file,const TestResult& test_result,bool(*pfnValidate)(const ::std::string&)){for(int i=0,count=test_result.test_property_count();i<count;++i){const TestProperty& prop=test_result.GetTestProperty(i);if((*pfnValidate)(prop.key())){file->Printf(" %s=\"%s\"",EscapeXmlAttribute(prop.key()).c_str(),EscapeXmlAttribute(prop.value()).c_str());}}}inline bool DefaultXmlGeneratorListener::FileOpen(const char* path){m_fp=detail::IFileSystem::New();if(m_fp==0){return false;}if(!m_fp->Open(path,IFile::OpenWrite)){fprintf(stderr,"Unable to open file \"%s\".\n",m_output_path.c_str());fflush(stderr);detail::IFileSystem::Free(m_fp);m_fp=0;return false;}return true;}inline void DefaultXmlGeneratorListener::FileClose(){if(m_fp==0){return;}m_fp->Close();detail::IFileSystem::Free(m_fp);m_fp=0;}inline void DefaultXmlGeneratorListener::OutputXmlCDataSection(IFile* file,const char* data){file->Printf("<![CDATA[");file->Write(data,strlen(data),1);file->Printf("]]>");}inline void DefaultXmlGeneratorListener::OutputXmlAttribute(IFile* file,const char* name,const char* value){file->Printf("%s=\"",name);file->Write(value,strlen(value),1);file->Printf("\" ");}inline ::std::string DefaultXmlGeneratorListener::EscapeXml(const char* str,bool is_attribute){::std::string msg;if(str!=0){for(const char* src=str;*src;++src){switch(*src){case '<': msg+="<";break;case '>': msg+=">";break;case '&': msg+="&";break;case '\'': msg+=is_attribute?"'" : "\'";break;case '\"': msg+=is_attribute?""" : "\"";break;default: {wchar_t wc=0;const int len=detail::iu_mbtowc(&wc,src,MB_CUR_MAX);if(len>1){msg+=detail::WideStringToUTF8(&wc,1);src+=len-1;}else if(IsValidXmlCharacter(*src)){if(is_attribute&&IsWhitespace(*src)){char tmp[8];detail::iu_snprintf(tmp,sizeof(tmp),"&#x%02X;",*src);msg+=tmp;}else{msg+=*src;}}}break;}}}return msg;}}namespace iutest{class JunitXmlGeneratorListener:public DefaultXmlGeneratorListener{public: explicit JunitXmlGeneratorListener(const ::std::string& path):DefaultXmlGeneratorListener(path){}virtual ~JunitXmlGeneratorListener(){}public: virtual void OnReportTest(IFile* file,const UnitTest& test) IUTEST_CXX_OVERRIDE;private: static void OnReportTestCase(IFile* file,const TestCase& test_case);static void OnReportTestInfo(IFile* file,const TestInfo& test_info);static void OnReportProperty(IFile* file,const char* name,const char* value);static void OnReportTestProperty(IFile* file,const TestResult& test_result);static void OnReportTestSkipped(IFile* file,const TestInfo& test_info);public: static bool SetUp(){::std::string xmlpath=TestEnv::get_report_junit_xml_filepath();if(!xmlpath.empty()){TestEnv::event_listeners().set_default_xml_generator(new JunitXmlGeneratorListener(xmlpath));return true;}return false;}};inline void JunitXmlGeneratorListener::OnReportTest(IFile* file,const UnitTest& test){file->Printf("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");file->Printf("<testsuites tests=\"%d\" failures=\"%d\" disabled=\"%d\" ",test.reportable_test_count(),test.failed_test_count(),test.reportable_disabled_test_count());file->Printf("errors=\"0\" time=\"%s\" ",detail::FormatTimeInMillisecAsSecond(test.elapsed_time()).c_str());file->Printf("name=\"AllTests\">\n");for(int i=0,count=test.total_test_case_count();i<count;++i){OnReportTestCase(file,*test.GetTestCase(i));}file->Printf("</testsuites>\n");}inline void JunitXmlGeneratorListener::OnReportTestCase(IFile* file,const TestCase& test_case){if(test_case.reportable_test_count()==0){return;}file->Printf(" <testsuite ");OutputXmlAttribute(file,"name",EscapeXmlAttribute(test_case.testcase_name_with_default_package_name()).c_str());file->Printf("tests=\"%d\" failures=\"%d\" disabled=\"%d\" ",test_case.reportable_test_count(),test_case.failed_test_count(),test_case.reportable_disabled_test_count());file->Printf("skipped=\"%d\" ",test_case.reportable_skip_test_count());file->Printf("errors=\"0\" time=\"%s\">\n",detail::FormatTimeInMillisecAsSecond(test_case.elapsed_time()).c_str());file->Printf(" <properties>\n");{const char* type_param=test_case.type_param();if(type_param!=0){OnReportProperty(file,"type_param",EscapeXmlAttribute(type_param).c_str());}}{for(int i=0,count=test_case.total_test_count();i<count;++i){const TestInfo& test_info=*test_case.GetTestInfo(i);const char* value_param=test_info.value_param();if(value_param!=0){OnReportProperty(file,test_info.name(),EscapeXmlAttribute(value_param).c_str());}}}OnReportTestProperty(file,*test_case.ad_hoc_test_result());file->Printf(" </properties>\n");{for(int i=0,count=test_case.total_test_count();i<count;++i){OnReportTestInfo(file,*test_case.GetTestInfo(i));}}file->Printf(" <system-out />\n");file->Printf(" <system-err />\n");file->Printf(" </testsuite>\n");}inline void JunitXmlGeneratorListener::OnReportTestInfo(IFile* file,const TestInfo& test_info){if(!test_info.is_reportable()){return;}file->Printf(" <testcase ");OutputXmlAttribute(file,"name",EscapeXmlAttribute(test_info.name()).c_str());if(test_info.is_ran()){file->Printf("status=\"run\" ");}else{file->Printf("status=\"notrun\" ");}file->Printf("time=\"%s\" ",detail::FormatTimeInMillisecAsSecond(test_info.elapsed_time()).c_str());OutputXmlAttribute(file,"classname",EscapeXmlAttribute(test_info.testcase_name_with_default_package_name()).c_str());file->Printf(">\n");const bool notrun=test_info.should_run()&&!test_info.is_ran();if(test_info.HasFailure()||notrun){for(int i=0,count=test_info.result()->total_part_count();i<count;++i){const TestPartResult& part=test_info.result()->GetTestPartResult(i);if(part.passed()){continue;}file->Printf(" <failure ");OutputXmlAttribute(file,"message",EscapeXmlAttribute(part.summary()).c_str());file->Printf("type=\"\">");::std::string message=detail::FormatCompilerIndependentFileLocation(part.file_name(),part.line_number());message+="\n";message+=detail::MultiByteStringToUTF8(part.summary());OutputXmlCDataSection(file,message.c_str());file->Printf("\n </failure>\n");}if(notrun){file->Printf(" <failure message=\"Not Run\" type=\"\">");OutputXmlCDataSection(file,"Not Run");file->Printf("\n </failure>\n");}}else{const bool skipped=test_info.is_skipped()||!test_info.should_run();if(skipped){OnReportTestSkipped(file,test_info);}}file->Printf(" </testcase>\n");}inline void JunitXmlGeneratorListener::OnReportProperty(IFile* file,const char* name,const char* value){file->Printf(" <property name=\"%s\" value=\"%s\" />\n",name,value);}inline void JunitXmlGeneratorListener::OnReportTestProperty(IFile* file,const TestResult& test_result){for(int i=0,count=test_result.test_property_count();i<count;++i){const TestProperty& prop=test_result.GetTestProperty(i);OnReportProperty(file,EscapeXmlAttribute(prop.key()).c_str(),EscapeXmlAttribute(prop.value()).c_str());}}inline void JunitXmlGeneratorListener::OnReportTestSkipped(IFile* file,const TestInfo& test_info){file->Printf(" <skipped type=\"iutest.skip\" ");const TestResult* tr=test_info.result();const int count=tr->total_part_count();for(int i=0;i<count;++i){const TestPartResult& part=tr->GetTestPartResult(i);if(part.skipped()){::std::string message=detail::FormatCompilerIndependentFileLocation(part.file_name(),part.line_number());message+=": ";message+=detail::MultiByteStringToUTF8(part.summary());OutputXmlAttribute(file,"message",EscapeXmlAttribute(message).c_str());file->Printf(" />\n");return;}}if(test_info.is_disabled_test()){OutputXmlAttribute(file,"message","disabled test.");}file->Printf("/>\n");}}namespace iutest{namespace detail{template<typename T,typename ::std::string(*GetXmlPath)()>class StderrXmlGeneratorListenerBase:public T{public: explicit StderrXmlGeneratorListenerBase(const ::std::string& path):T(path){}~StderrXmlGeneratorListenerBase(){} | |
#if IUTEST_HAS_FOPEN | |
private: StdErrorFile m_stderr;virtual bool FileOpen(const char* path){if(m_stderr.Open(path,IFile::OpenAppend)){this->m_fp=&m_stderr;return true;}return false;}virtual void FileClose(){this->m_fp=0;} | |
#endif | |
public: static bool SetUp(){::std::string xmlpath=GetXmlPath();if(!xmlpath.empty()){TestEnv::event_listeners().set_default_xml_generator(new StderrXmlGeneratorListenerBase(xmlpath));return true;}return false;}};}typedef detail::StderrXmlGeneratorListenerBase<DefaultXmlGeneratorListener,TestEnv::get_report_xml_filepath> StderrXmlGeneratorListener;typedef detail::StderrXmlGeneratorListenerBase<JunitXmlGeneratorListener,TestEnv::get_report_junit_xml_filepath> StderrJunitXmlGeneratorListener;} | |
#if IUTEST_HAS_STREAM_RESULT | |
#ifdef IUTEST_HAS_SOCKET | |
#include <arpa/inet.h> | |
#include <netdb.h> | |
namespace iutest{namespace detail{class BasicSocket{public:typedef int descriptor_t;typedef size_t length_t;static const descriptor_t INVALID_DESCRIPTOR=-1;public: BasicSocket():m_socket(INVALID_DESCRIPTOR){}~BasicSocket(void){Close();}public: bool Open(const char* host,const char* port){if(m_socket!=INVALID_DESCRIPTOR){return true;}addrinfo* servinfo=0;addrinfo hints;memset(&hints,0,sizeof(hints));hints.ai_family=AF_UNSPEC;hints.ai_socktype=SOCK_STREAM;const int err_no=getaddrinfo(host,port,&hints,&servinfo);if(err_no!=0){return false;}for(addrinfo* curr=servinfo;curr!=0;curr=curr->ai_next){const descriptor_t fd=socket(curr->ai_family,curr->ai_socktype,curr->ai_protocol);if(fd!=INVALID_DESCRIPTOR){if(connect(fd,curr->ai_addr,static_cast<length_t>(curr->ai_addrlen))!=-1){m_socket=fd;break;}Close(fd);}}freeaddrinfo(servinfo);return(m_socket!=INVALID_DESCRIPTOR);}void Close(){Close(m_socket);m_socket=INVALID_DESCRIPTOR;}void CheckLastError(){}public: static int Close(descriptor_t d){return close(d);}public: bool IsValid()const{return m_socket!=INVALID_DESCRIPTOR;}protected: descriptor_t m_socket;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(BasicSocket);};class SocketWriter:virtual public BasicSocket,public IOutStream{public: SocketWriter(){}public: bool Send(const ::std::string& message){return Write(message.c_str(),message.length(),1u);}bool SendLn(const ::std::string& message){return Send(message+"\r\n");}public: virtual bool Write(const void* buf,size_t size,size_t cnt) IUTEST_CXX_OVERRIDE{if(!IsValid()){return false;}const int size_=static_cast<int>(size);for(size_t i=0;i<cnt;++i){if(write(m_socket,buf,size_)==-1){return false;}}return true;}private: IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(SocketWriter);};class SocketReader:virtual public BasicSocket{public: SocketReader(){}public: bool Read(void* buf,size_t size){if(!IsValid()){return false;}const int size_=static_cast<int>(size);if(read(m_socket,buf,size_)==-1){return false;}return true;}private: IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(SocketReader);};class Socket:public SocketWriter,public SocketReader{public: Socket(){}};}} | |
#endif | |
namespace iutest{class StreamResultListener:public EmptyTestEventListener{public: StreamResultListener(const char* host,const char* port);public: virtual void OnTestProgramStart(const UnitTest& test) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationStart(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseStart(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnTestStart(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestPartResult(const TestPartResult& test_part_result) IUTEST_CXX_OVERRIDE;virtual void OnTestRecordProperty(const TestProperty& test_property) IUTEST_CXX_OVERRIDE;virtual void OnTestEnd(const TestInfo& test_info) IUTEST_CXX_OVERRIDE;virtual void OnTestCaseEnd(const TestCase& test_case) IUTEST_CXX_OVERRIDE;virtual void OnTestIterationEnd(const UnitTest& test,int iteration) IUTEST_CXX_OVERRIDE;virtual void OnTestProgramEnd(const UnitTest& test) IUTEST_CXX_OVERRIDE;private: ::std::string UrlEncode(const char* str);::std::string FormatBool(bool b);void Start();void SendLn(const ::std::string& message);private: detail::SocketWriter m_socket;IUTEST_PP_DISALLOW_COPY_AND_ASSIGN(StreamResultListener);public: static TestEventListener* SetUp(){::std::string addr=TestEnv::get_stream_result_to();if(addr.empty()){return 0;}const size_t pos=addr.find(':');if(pos==::std::string::npos){return 0;}TestEventListener* p=new StreamResultListener(addr.substr(0,pos).c_str(),addr.substr(pos+1).c_str());UnitTest::GetInstance()->listeners().Append(p);return p;}};} | |
#if IUTEST_HAS_STREAM_RESULT | |
namespace iutest{inline StreamResultListener::StreamResultListener(const char* host,const char* port){if(!m_socket.Open(host,port)){IUTEST_LOG_(WARNING)<<"StreamResultListener: failed connect to " <<host<<":" <<port;}}inline void StreamResultListener::OnTestProgramStart(const UnitTest& test){(void)(test);Start();SendLn("event=TestProgramStart");}inline void StreamResultListener::OnTestIterationStart(const UnitTest& test,int iteration){(void)(test);SendLn("event=TestIterationStart&iteration=" + StreamableToString(iteration));}inline void StreamResultListener::OnTestCaseStart(const TestCase& test_case){SendLn("event=TestCaseStart&name=" + StreamableToString(test_case.name()));}inline void StreamResultListener::OnTestStart(const TestInfo& test_info){SendLn("event=TestStart&name=" + StreamableToString(test_info.name()));}inline void StreamResultListener::OnTestPartResult(const TestPartResult& test_part_result){const char* filename=test_part_result.file_name();if(filename==0){filename="";}SendLn("event=TestPartResult&file=" + UrlEncode(filename)+ "&line=" + StreamableToString(test_part_result.line_number())+ "&message=" + UrlEncode(test_part_result.message()));}inline void StreamResultListener::OnTestRecordProperty(const TestProperty& test_property){SendLn("event=TestRecordProperty&name=" + UrlEncode(test_property.key())+ "&value=" + UrlEncode(test_property.value()));}inline void StreamResultListener::OnTestEnd(const TestInfo& test_info){SendLn("event=TestEnd&passed="+ FormatBool(test_info.Passed())+ "&elapsed_time=" + StreamableToString(test_info.elapsed_time())+"ms");}inline void StreamResultListener::OnTestCaseEnd(const TestCase& test_case){SendLn("event=TestCaseEnd&passed="+ FormatBool(test_case.Passed())+ "&elapsed_time=" + StreamableToString(test_case.elapsed_time())+"ms");}inline void StreamResultListener::OnTestIterationEnd(const UnitTest& test,int iteration){(void)(iteration);SendLn("event=TestIterationEnd&passed="+ FormatBool(test.Passed())+ "&elapsed_time=" + StreamableToString(test.elapsed_time())+"ms");}inline void StreamResultListener::OnTestProgramEnd(const UnitTest& test){SendLn("event=TestProgramEnd&passed=" + FormatBool(test.Passed()));m_socket.Close();}inline ::std::string StreamResultListener::UrlEncode(const char* str){::std::string result;if(str!=0){result.reserve(strlen(str)+1);for(const char* p=str;*p!='\0';++p){const char ch=*p;switch(ch){case '%': case '=': case '&': case '\n': result.append(detail::ToHexString(ch));break;default: result.push_back(ch);}}}return result;}inline ::std::string StreamResultListener::FormatBool(bool b){return b?"1" : "0";}inline void StreamResultListener::Start(){SendLn("iutest_streaming_protocol_version=1.0");}inline void StreamResultListener::SendLn(const ::std::string& message){m_socket.SendLn(message);}} | |
#endif | |
#endif | |
#define IUTEST_TEST(testcase_,tn_) IUTEST_TEST_STRICT_(testcase_,tn_ ,::iutest::Test,::iutest::internal::GetTestTypeId()) | |
#define IUTEST(testcase_,tn_) IUTEST_TEST(testcase_,tn_) | |
#define IUTEST_F(tf_,tn_) IUTEST_TEST_F_(tf_,tn_) | |
#if IUTEST_HAS_PARAM_METHOD_TEST | |
#define IUTEST_PMZ(testcase_,tn_,method_,...) II_TEST_PMZ_(testcase_,tn_ ,method_,::iutest::Test ,::iutest::internal::GetTestTypeId(),__VA_ARGS__) | |
#define IUTEST_PMZ_F(tf_,tn_,method_,...) II_TEST_PMZ_(tf_,tn_ ,method_,tf_ ,::iutest::internal::GetTypeId<tf_ >(),__VA_ARGS__) | |
#endif | |
#if IUTEST_HAS_TESTNAME_ALIAS | |
#define IUTEST_ALIAS_TESTNAME(tn_) IUTEST_ALIAS_TESTNAME_(tn_) | |
#define IUTEST_ALIAS_TESTNAME_F(tcn_,tf_) IUTEST_ALIAS_TESTNAME_F_(tcn_,tf_) | |
#endif | |
#define IUTEST_INIT(argc_,argv_) ::iutest::InitIrisUnitTest(argc_,argv_) | |
#define IUTEST_RUN_ALL_TESTS() ::iutest::UnitTestSource::GetInstance().Run() | |
#define IUTEST_SCOPED_TRACE(msg) II_S_MSG(msg) | |
#ifndef IUTEST_SUCCEED | |
#define IUTEST_SUCCEED() II_S() | |
#endif | |
#ifndef IUTEST_FAIL | |
#define IUTEST_FAIL() II_F() | |
#endif | |
#ifndef IUTEST_ADD_FAILURE | |
#define IUTEST_ADD_FAILURE() II_ADD_F() | |
#endif | |
#ifndef IUTEST_ADD_FAILURE_AT | |
#define IUTEST_ADD_FAILURE_AT(file,line) II_ADD_F_AT(file,line) | |
#endif | |
#ifndef IUTEST_SKIP | |
#define IUTEST_SKIP() IUTEST_TEST_SKIP() | |
#endif | |
#ifndef IUTEST_ASSERT | |
#define IUTEST_ASSERT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),true,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NOT | |
#define IUTEST_ASSERT_NOT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),false,IUTEST_ASSERT_FAILURE) | |
#endif | |
#if IUTEST_HAS_MATCHERS | |
#ifndef IUTEST_ASSERT_THAT | |
#define IUTEST_ASSERT_THAT(actual,matcher) IUTEST_TEST_THAT(actual,matcher,IUTEST_ASSERT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSERT_EQ | |
#define IUTEST_ASSERT_EQ(expected,actual) IUTEST_TEST_EQ(expected,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NE | |
#define IUTEST_ASSERT_NE(v1,v2) IUTEST_TEST_NE(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_LE | |
#define IUTEST_ASSERT_LE(v1,v2) IUTEST_TEST_LE(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_LT | |
#define IUTEST_ASSERT_LT(v1,v2) IUTEST_TEST_LT(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_GE | |
#define IUTEST_ASSERT_GE(v1,v2) IUTEST_TEST_GE(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_GT | |
#define IUTEST_ASSERT_GT(v1,v2) IUTEST_TEST_GT(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_TRUE | |
#define IUTEST_ASSERT_TRUE(...) IUTEST_TEST_TRUE((__VA_ARGS__),#__VA_ARGS__,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_FALSE | |
#define IUTEST_ASSERT_FALSE(...) IUTEST_TEST_FALSE((__VA_ARGS__),#__VA_ARGS__,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NULL | |
#define IUTEST_ASSERT_NULL(...) IUTEST_TEST_NULL((__VA_ARGS__),IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NOTNULL | |
#define IUTEST_ASSERT_NOTNULL(...) IUTEST_TEST_NOTNULL((__VA_ARGS__),IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_SAME | |
#define IUTEST_ASSERT_SAME(v1,v2) IUTEST_TEST_SAME(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_FLOAT_EQ | |
#define IUTEST_ASSERT_FLOAT_EQ(expected,actual) IUTEST_TEST_FLOAT_EQ(expected,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_DOUBLE_EQ | |
#define IUTEST_ASSERT_DOUBLE_EQ(expected,actual) IUTEST_TEST_DOUBLE_EQ(expected,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#if IUTEST_HAS_LONG_DOUBLE | |
#ifndef IUTEST_ASSERT_LONG_DOUBLE_EQ | |
#define IUTEST_ASSERT_LONG_DOUBLE_EQ(expected,actual) IUTEST_TEST_LONG_DOUBLE_EQ(expected,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSERT_NEAR | |
#define IUTEST_ASSERT_NEAR(v1,v2,abs_v) IUTEST_TEST_NEAR(v1,v2,abs_v,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STREQ | |
#define IUTEST_ASSERT_STREQ(exp_s,act_s) IUTEST_TEST_STREQ(exp_s,act_s,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRNE | |
#define IUTEST_ASSERT_STRNE(v1,v2) IUTEST_TEST_STRNE(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRCASEEQ | |
#define IUTEST_ASSERT_STRCASEEQ(exp_s,act_s) IUTEST_TEST_STRCASEEQ(exp_s,act_s,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRCASENE | |
#define IUTEST_ASSERT_STRCASENE(v1,v2) IUTEST_TEST_STRCASENE(v1,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_HRESULT_SUCCEEDED | |
#define IUTEST_ASSERT_HRESULT_SUCCEEDED(...) IUTEST_TEST_HRESULT_SUCCEEDED((__VA_ARGS__),IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_HRESULT_FAILED | |
#define IUTEST_ASSERT_HRESULT_FAILED(...) IUTEST_TEST_HRESULT_FAILED((__VA_ARGS__),IUTEST_ASSERT_FAILURE) | |
#endif | |
#if IUTEST_HAS_EXCEPTIONS | |
#ifndef IUTEST_ASSERT_THROW | |
#define IUTEST_ASSERT_THROW(st,exp_e) IUTEST_TEST_THROW_(st,exp_e,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_THROW_VALUE_EQ | |
#define IUTEST_ASSERT_THROW_VALUE_EQ(st,exp_e,exp_v) IUTEST_TEST_THROW_VALUE_EQ_(st,exp_e,exp_v,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_THROW_VALUE_NE | |
#define IUTEST_ASSERT_THROW_VALUE_NE(st,exp_e,v) IUTEST_TEST_THROW_VALUE_NE_(st,exp_e,v,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_THROW_VALUE_STREQ | |
#define IUTEST_ASSERT_THROW_VALUE_STREQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STREQ_(st,exp_e,exp_s,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_THROW_VALUE_STRCASEEQ | |
#define IUTEST_ASSERT_THROW_VALUE_STRCASEEQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STRCASEEQ_(st,exp_e,exp_s,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_ANY_THROW | |
#define IUTEST_ASSERT_ANY_THROW(st) IUTEST_TEST_ANY_THROW_(st,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NO_THROW | |
#define IUTEST_ASSERT_NO_THROW(st) IUTEST_TEST_NO_THROW_(st,IUTEST_ASSERT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSERT_NO_FAILURE | |
#define IUTEST_ASSERT_NO_FAILURE(st) IUTEST_TEST_NO_FAILURE_(st,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_NO_FATAL_FAILURE | |
#define IUTEST_ASSERT_NO_FATAL_FAILURE(st) IUTEST_TEST_NO_FATAL_FAILURE_(st,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_FAIL | |
#define IUTEST_ASSERT_FAIL() II_F() | |
#endif | |
#ifndef IUTEST_EXPECT | |
#define IUTEST_EXPECT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),true,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NOT | |
#define IUTEST_EXPECT_NOT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),false,IUTEST_EXPECT_FAILURE) | |
#endif | |
#if IUTEST_HAS_MATCHERS | |
#ifndef IUTEST_EXPECT_THAT | |
#define IUTEST_EXPECT_THAT(actual,matcher) IUTEST_TEST_THAT(actual,matcher,IUTEST_EXPECT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_EXPECT_EQ | |
#define IUTEST_EXPECT_EQ(expected,actual) IUTEST_TEST_EQ(expected,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NE | |
#define IUTEST_EXPECT_NE(v1,v2) IUTEST_TEST_NE(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_LE | |
#define IUTEST_EXPECT_LE(v1,v2) IUTEST_TEST_LE(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_LT | |
#define IUTEST_EXPECT_LT(v1,v2) IUTEST_TEST_LT(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_GE | |
#define IUTEST_EXPECT_GE(v1,v2) IUTEST_TEST_GE(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_GT | |
#define IUTEST_EXPECT_GT(v1,v2) IUTEST_TEST_GT(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_TRUE | |
#define IUTEST_EXPECT_TRUE(...) IUTEST_TEST_TRUE((__VA_ARGS__),#__VA_ARGS__,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_FALSE | |
#define IUTEST_EXPECT_FALSE(...) IUTEST_TEST_FALSE((__VA_ARGS__),#__VA_ARGS__,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NULL | |
#define IUTEST_EXPECT_NULL(...) IUTEST_TEST_NULL((__VA_ARGS__),IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NOTNULL | |
#define IUTEST_EXPECT_NOTNULL(...) IUTEST_TEST_NOTNULL((__VA_ARGS__),IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_SAME | |
#define IUTEST_EXPECT_SAME(v1,v2) IUTEST_TEST_SAME(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_FLOAT_EQ | |
#define IUTEST_EXPECT_FLOAT_EQ(expected,actual) IUTEST_TEST_FLOAT_EQ(expected,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_DOUBLE_EQ | |
#define IUTEST_EXPECT_DOUBLE_EQ(expected,actual) IUTEST_TEST_DOUBLE_EQ(expected,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#if IUTEST_HAS_LONG_DOUBLE | |
#ifndef IUTEST_EXPECT_LONG_DOUBLE_EQ | |
#define IUTEST_EXPECT_LONG_DOUBLE_EQ(expected,actual) IUTEST_TEST_LONG_DOUBLE_EQ(expected,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_EXPECT_NEAR | |
#define IUTEST_EXPECT_NEAR(v1,v2,abs_v) IUTEST_TEST_NEAR(v1,v2,abs_v,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STREQ | |
#define IUTEST_EXPECT_STREQ(exp_s,act_s) IUTEST_TEST_STREQ(exp_s,act_s,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRNE | |
#define IUTEST_EXPECT_STRNE(v1,v2) IUTEST_TEST_STRNE(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRCASEEQ | |
#define IUTEST_EXPECT_STRCASEEQ(exp_s,act_s) IUTEST_TEST_STRCASEEQ(exp_s,act_s,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRCASENE | |
#define IUTEST_EXPECT_STRCASENE(v1,v2) IUTEST_TEST_STRCASENE(v1,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_HRESULT_SUCCEEDED | |
#define IUTEST_EXPECT_HRESULT_SUCCEEDED(...) IUTEST_TEST_HRESULT_SUCCEEDED((__VA_ARGS__),IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_HRESULT_FAILED | |
#define IUTEST_EXPECT_HRESULT_FAILED(...) IUTEST_TEST_HRESULT_FAILED((__VA_ARGS__),IUTEST_EXPECT_FAILURE) | |
#endif | |
#if IUTEST_HAS_EXCEPTIONS | |
#ifndef IUTEST_EXPECT_THROW | |
#define IUTEST_EXPECT_THROW(st,exp_e) IUTEST_TEST_THROW_(st,exp_e,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_THROW_VALUE_EQ | |
#define IUTEST_EXPECT_THROW_VALUE_EQ(st,exp_e,exp_v) IUTEST_TEST_THROW_VALUE_EQ_(st,exp_e,exp_v,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_THROW_VALUE_NE | |
#define IUTEST_EXPECT_THROW_VALUE_NE(st,exp_e,v) IUTEST_TEST_THROW_VALUE_NE_(st,exp_e,v,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_THROW_VALUE_STREQ | |
#define IUTEST_EXPECT_THROW_VALUE_STREQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STREQ_(st,exp_e,exp_s,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_THROW_VALUE_STRCASEEQ | |
#define IUTEST_EXPECT_THROW_VALUE_STRCASEEQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STRCASEEQ_(st,exp_e,exp_s,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_ANY_THROW | |
#define IUTEST_EXPECT_ANY_THROW(st) IUTEST_TEST_ANY_THROW_(st,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NO_THROW | |
#define IUTEST_EXPECT_NO_THROW(st) IUTEST_TEST_NO_THROW_(st,IUTEST_EXPECT_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_EXPECT_NO_FAILURE | |
#define IUTEST_EXPECT_NO_FAILURE(st) IUTEST_TEST_NO_FAILURE_(st,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_NO_FATAL_FAILURE | |
#define IUTEST_EXPECT_NO_FATAL_FAILURE(st) IUTEST_TEST_NO_FATAL_FAILURE_(st,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_FAIL | |
#define IUTEST_EXPECT_FAIL() II_ADD_F() | |
#endif | |
#ifndef IUTEST_EXPECT_FAIL_AT | |
#define IUTEST_EXPECT_FAIL_AT(file,line) II_ADD_F_AT(file,line) | |
#endif | |
#ifndef IUTEST_INFORM | |
#define IUTEST_INFORM(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),true,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NOT | |
#define IUTEST_INFORM_NOT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),false,IUTEST_INFORM_FAILURE) | |
#endif | |
#if IUTEST_HAS_MATCHERS | |
#ifndef IUTEST_INFORM_THAT | |
#define IUTEST_INFORM_THAT(actual,matcher) IUTEST_TEST_THAT(actual,matcher,IUTEST_INFORM_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_INFORM_EQ | |
#define IUTEST_INFORM_EQ(expected,actual) IUTEST_TEST_EQ(expected,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NE | |
#define IUTEST_INFORM_NE(v1,v2) IUTEST_TEST_NE(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_LE | |
#define IUTEST_INFORM_LE(v1,v2) IUTEST_TEST_LE(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_LT | |
#define IUTEST_INFORM_LT(v1,v2) IUTEST_TEST_LT(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_GE | |
#define IUTEST_INFORM_GE(v1,v2) IUTEST_TEST_GE(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_GT | |
#define IUTEST_INFORM_GT(v1,v2) IUTEST_TEST_GT(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_TRUE | |
#define IUTEST_INFORM_TRUE(...) IUTEST_TEST_TRUE((__VA_ARGS__),#__VA_ARGS__,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_FALSE | |
#define IUTEST_INFORM_FALSE(...) IUTEST_TEST_FALSE((__VA_ARGS__),#__VA_ARGS__,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NULL | |
#define IUTEST_INFORM_NULL(...) IUTEST_TEST_NULL((__VA_ARGS__),IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NOTNULL | |
#define IUTEST_INFORM_NOTNULL(...) IUTEST_TEST_NOTNULL((__VA_ARGS__),IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_SAME | |
#define IUTEST_INFORM_SAME(v1,v2) IUTEST_TEST_SAME(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_FLOAT_EQ | |
#define IUTEST_INFORM_FLOAT_EQ(expected,actual) IUTEST_TEST_FLOAT_EQ(expected,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_DOUBLE_EQ | |
#define IUTEST_INFORM_DOUBLE_EQ(expected,actual) IUTEST_TEST_DOUBLE_EQ(expected,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#if IUTEST_HAS_LONG_DOUBLE | |
#ifndef IUTEST_INFORM_LONG_DOUBLE_EQ | |
#define IUTEST_INFORM_LONG_DOUBLE_EQ(expected,actual) IUTEST_TEST_LONG_DOUBLE_EQ(expected,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_INFORM_NEAR | |
#define IUTEST_INFORM_NEAR(v1,v2,abs_v) IUTEST_TEST_NEAR(v1,v2,abs_v,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STREQ | |
#define IUTEST_INFORM_STREQ(exp_s,act_s) IUTEST_TEST_STREQ(exp_s,act_s,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRNE | |
#define IUTEST_INFORM_STRNE(v1,v2) IUTEST_TEST_STRNE(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRCASEEQ | |
#define IUTEST_INFORM_STRCASEEQ(exp_s,act_s) IUTEST_TEST_STRCASEEQ(exp_s,act_s,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRCASENE | |
#define IUTEST_INFORM_STRCASENE(v1,v2) IUTEST_TEST_STRCASENE(v1,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_HRESULT_SUCCEEDED | |
#define IUTEST_INFORM_HRESULT_SUCCEEDED(...) IUTEST_TEST_HRESULT_SUCCEEDED((__VA_ARGS__),IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_HRESULT_FAILED | |
#define IUTEST_INFORM_HRESULT_FAILED(...) IUTEST_TEST_HRESULT_FAILED((__VA_ARGS__),IUTEST_INFORM_FAILURE) | |
#endif | |
#if IUTEST_HAS_EXCEPTIONS | |
#ifndef IUTEST_INFORM_THROW | |
#define IUTEST_INFORM_THROW(st,exp_e) IUTEST_TEST_THROW_(st,exp_e,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_THROW_VALUE_EQ | |
#define IUTEST_INFORM_THROW_VALUE_EQ(st,exp_e,exp_v) IUTEST_TEST_THROW_VALUE_EQ_(st,exp_e,exp_v,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_THROW_VALUE_NE | |
#define IUTEST_INFORM_THROW_VALUE_NE(st,exp_e,v) IUTEST_TEST_THROW_VALUE_NE_(st,exp_e,v,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_THROW_VALUE_STREQ | |
#define IUTEST_INFORM_THROW_VALUE_STREQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STREQ_(st,exp_e,exp_s,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_THROW_VALUE_STRCASEEQ | |
#define IUTEST_INFORM_THROW_VALUE_STRCASEEQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STRCASEEQ_(st,exp_e,exp_s,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_ANY_THROW | |
#define IUTEST_INFORM_ANY_THROW(st) IUTEST_TEST_ANY_THROW_(st,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NO_THROW | |
#define IUTEST_INFORM_NO_THROW(st) IUTEST_TEST_NO_THROW_(st,IUTEST_INFORM_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_INFORM_NO_FAILURE | |
#define IUTEST_INFORM_NO_FAILURE(st) IUTEST_TEST_NO_FAILURE_(st,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_NO_FATAL_FAILURE | |
#define IUTEST_INFORM_NO_FATAL_FAILURE(st) IUTEST_TEST_NO_FATAL_FAILURE_(st,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME | |
#define IUTEST_ASSUME(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),true,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NOT | |
#define IUTEST_ASSUME_NOT(...) IUTEST_TEST_EXPRESSION_((__VA_ARGS__),false,IUTEST_ASSUME_FAILURE) | |
#endif | |
#if IUTEST_HAS_MATCHERS | |
#ifndef IUTEST_ASSUME_THAT | |
#define IUTEST_ASSUME_THAT(actual,matcher) IUTEST_TEST_THAT(actual,matcher,IUTEST_ASSUME_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSUME_EQ | |
#define IUTEST_ASSUME_EQ(expected,actual) IUTEST_TEST_EQ(expected,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NE | |
#define IUTEST_ASSUME_NE(v1,v2) IUTEST_TEST_NE(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_LE | |
#define IUTEST_ASSUME_LE(v1,v2) IUTEST_TEST_LE(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_LT | |
#define IUTEST_ASSUME_LT(v1,v2) IUTEST_TEST_LT(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_GE | |
#define IUTEST_ASSUME_GE(v1,v2) IUTEST_TEST_GE(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_GT | |
#define IUTEST_ASSUME_GT(v1,v2) IUTEST_TEST_GT(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_TRUE | |
#define IUTEST_ASSUME_TRUE(...) IUTEST_TEST_TRUE((__VA_ARGS__),#__VA_ARGS__,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_FALSE | |
#define IUTEST_ASSUME_FALSE(...) IUTEST_TEST_FALSE((__VA_ARGS__),#__VA_ARGS__,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NULL | |
#define IUTEST_ASSUME_NULL(...) IUTEST_TEST_NULL((__VA_ARGS__),IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NOTNULL | |
#define IUTEST_ASSUME_NOTNULL(...) IUTEST_TEST_NOTNULL((__VA_ARGS__),IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_SAME | |
#define IUTEST_ASSUME_SAME(v1,v2) IUTEST_TEST_SAME(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_FLOAT_EQ | |
#define IUTEST_ASSUME_FLOAT_EQ(expected,actual) IUTEST_TEST_FLOAT_EQ(expected,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_DOUBLE_EQ | |
#define IUTEST_ASSUME_DOUBLE_EQ(expected,actual) IUTEST_TEST_DOUBLE_EQ(expected,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#if IUTEST_HAS_LONG_DOUBLE | |
#ifndef IUTEST_ASSUME_LONG_DOUBLE_EQ | |
#define IUTEST_ASSUME_LONG_DOUBLE_EQ(expected,actual) IUTEST_TEST_LONG_DOUBLE_EQ(expected,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSUME_NEAR | |
#define IUTEST_ASSUME_NEAR(v1,v2,abs_v) IUTEST_TEST_NEAR(v1,v2,abs_v,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STREQ | |
#define IUTEST_ASSUME_STREQ(exp_s,act_s) IUTEST_TEST_STREQ(exp_s,act_s,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRNE | |
#define IUTEST_ASSUME_STRNE(v1,v2) IUTEST_TEST_STRNE(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRCASEEQ | |
#define IUTEST_ASSUME_STRCASEEQ(exp_s,act_s) IUTEST_TEST_STRCASEEQ(exp_s,act_s,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRCASENE | |
#define IUTEST_ASSUME_STRCASENE(v1,v2) IUTEST_TEST_STRCASENE(v1,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_HRESULT_SUCCEEDED | |
#define IUTEST_ASSUME_HRESULT_SUCCEEDED(...) IUTEST_TEST_HRESULT_SUCCEEDED((__VA_ARGS__),IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_HRESULT_FAILED | |
#define IUTEST_ASSUME_HRESULT_FAILED(...) IUTEST_TEST_HRESULT_FAILED((__VA_ARGS__),IUTEST_ASSUME_FAILURE) | |
#endif | |
#if IUTEST_HAS_EXCEPTIONS | |
#ifndef IUTEST_ASSUME_THROW | |
#define IUTEST_ASSUME_THROW(st,exp_e) IUTEST_TEST_THROW_(st,exp_e,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_THROW_VALUE_EQ | |
#define IUTEST_ASSUME_THROW_VALUE_EQ(st,exp_e,exp_v) IUTEST_TEST_THROW_VALUE_EQ_(st,exp_e,exp_v,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_THROW_VALUE_NE | |
#define IUTEST_ASSUME_THROW_VALUE_NE(st,exp_e,v) IUTEST_TEST_THROW_VALUE_NE_(st,exp_e,v,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_THROW_VALUE_STREQ | |
#define IUTEST_ASSUME_THROW_VALUE_STREQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STREQ_(st,exp_e,exp_s,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_THROW_VALUE_STRCASEEQ | |
#define IUTEST_ASSUME_THROW_VALUE_STRCASEEQ(st,exp_e,exp_s) IUTEST_TEST_THROW_VALUE_STRCASEEQ_(st,exp_e,exp_s,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_ANY_THROW | |
#define IUTEST_ASSUME_ANY_THROW(st) IUTEST_TEST_ANY_THROW_(st,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NO_THROW | |
#define IUTEST_ASSUME_NO_THROW(st) IUTEST_TEST_NO_THROW_(st,IUTEST_ASSUME_FAILURE) | |
#endif | |
#endif | |
#ifndef IUTEST_ASSUME_NO_FAILURE | |
#define IUTEST_ASSUME_NO_FAILURE(st) IUTEST_TEST_NO_FAILURE_(st,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_NO_FATAL_FAILURE | |
#define IUTEST_ASSUME_NO_FATAL_FAILURE(st) IUTEST_TEST_NO_FATAL_FAILURE_(st,IUTEST_ASSUME_FAILURE) | |
#endif | |
namespace iutest{class UnitTestSource{public: static UnitTestSource& GetInstance(){static UnitTestSource inst;return inst;}private: UnitTestSource(){(void)(&detail::iuDebugInitialize);(void)(&detail::iuDebugBreakAlloc);TestEnv::event_listeners().set_default_result_printer(new DefaultResultPrintListener());}public: ~UnitTestSource(){TestEnv::event_listeners().set_default_result_printer(0);TestEnv::event_listeners().set_default_xml_generator(0);}public: void Initialize(){UnitTest::instance().Initialize();}int Run(){SetUpDefaultListener();return UnitTest::instance().Run();}private: void SetUpDefaultListener(){if(TestEnv::has_output_option()){do{if(StderrXmlGeneratorListener::SetUp()){break;}if(StderrJunitXmlGeneratorListener::SetUp()){break;}IUTEST_LOG_(WARNING)<<"unrecognized output format \"" <<TestEnv::get_output_option()<<"\" ignored.";}while(detail::AlwaysFalse());} | |
#if IUTEST_HAS_STREAM_RESULT | |
StreamResultListener::SetUp(); | |
#endif | |
}};namespace detail{template<typename T>inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,T argv){UnitTestSource::GetInstance().Initialize();TestEnv::ParseCommandLine(pargc,argv);TestEnv::LoadFlagFile();}}inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,char** argv){detail::InitIrisUnitTest(pargc,argv);}inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,wchar_t** argv){detail::InitIrisUnitTest(pargc,argv);}inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,const char** argv){detail::InitIrisUnitTest(pargc,argv);}inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,const wchar_t** argv){detail::InitIrisUnitTest(pargc,argv);}inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(){detail::InitIrisUnitTest<char**>(0,0);} | |
#if IUTEST_HAS_NULLPTR | |
inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(int* pargc,::std::nullptr_t){detail::InitIrisUnitTest<char**>(pargc,0);} | |
#endif | |
template<typename CharType>inline void IUTEST_ATTRIBUTE_UNUSED_ InitIrisUnitTest(::std::vector< ::std::basic_string<CharType> >& argv){UnitTestSource::GetInstance().Initialize();TestEnv::ParseCommandLine(argv);TestEnv::LoadFlagFile();}inline Environment* IUTEST_ATTRIBUTE_UNUSED_ AddGlobalTestEnvironment(Environment* env){return TestEnv::AddGlobalTestEnvironment(env);}} | |
#ifndef IUTEST_ASSERT_EQ_COLLECTIONS | |
#define IUTEST_ASSERT_EQ_COLLECTIONS(b1,e1,b2,e2) IUTEST_TEST_EQ_COLLECTIONS(b1,e1,b2,e2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_EQ_COLLECTIONS | |
#define IUTEST_EXPECT_EQ_COLLECTIONS(b1,e1,b2,e2) IUTEST_TEST_EQ_COLLECTIONS(b1,e1,b2,e2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_EQ_COLLECTIONS | |
#define IUTEST_INFORM_EQ_COLLECTIONS(b1,e1,b2,e2) IUTEST_TEST_EQ_COLLECTIONS(b1,e1,b2,e2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_EQ_COLLECTIONS | |
#define IUTEST_ASSUME_EQ_COLLECTIONS(b1,e1,b2,e2) IUTEST_TEST_EQ_COLLECTIONS(b1,e1,b2,e2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_EQ_RANGE | |
#define IUTEST_ASSERT_EQ_RANGE(expected,actual) IUTEST_TEST_EQ_RANGE(expected,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_EQ_RANGE | |
#define IUTEST_EXPECT_EQ_RANGE(expected,actual) IUTEST_TEST_EQ_RANGE(expected,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_EQ_RANGE | |
#define IUTEST_INFORM_EQ_RANGE(expected,actual) IUTEST_TEST_EQ_RANGE(expected,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_EQ_RANGE | |
#define IUTEST_ASSUME_EQ_RANGE(expected,actual) IUTEST_TEST_EQ_RANGE(expected,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRLNEQ | |
#define IUTEST_ASSERT_STRLNEQ(len,v2) IUTEST_TEST_STRLNEQ(len,v2,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRLNEQ | |
#define IUTEST_EXPECT_STRLNEQ(len,v2) IUTEST_TEST_STRLNEQ(len,v2,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRLNEQ | |
#define IUTEST_INFORM_STRLNEQ(len,v2) IUTEST_TEST_STRLNEQ(len,v2,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRLNEQ | |
#define IUTEST_ASSUME_STRLNEQ(len,v2) IUTEST_TEST_STRLNEQ(len,v2,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRIN | |
#define IUTEST_ASSERT_STRIN(substr,actual) IUTEST_TEST_STRIN(substr,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRIN | |
#define IUTEST_EXPECT_STRIN(substr,actual) IUTEST_TEST_STRIN(substr,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRIN | |
#define IUTEST_INFORM_STRIN(substr,actual) IUTEST_TEST_STRIN(substr,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRIN | |
#define IUTEST_ASSUME_STRIN(substr,actual) IUTEST_TEST_STRIN(substr,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_STRNOTIN | |
#define IUTEST_ASSERT_STRNOTIN(substr,actual) IUTEST_TEST_STRNOTIN(substr,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_STRNOTIN | |
#define IUTEST_EXPECT_STRNOTIN(substr,actual) IUTEST_TEST_STRNOTIN(substr,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_STRNOTIN | |
#define IUTEST_INFORM_STRNOTIN(substr,actual) IUTEST_TEST_STRNOTIN(substr,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_STRNOTIN | |
#define IUTEST_ASSUME_STRNOTIN(substr,actual) IUTEST_TEST_STRNOTIN(substr,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#if IUTEST_HAS_REGEX | |
#ifndef IUTEST_ASSERT_MATCHES_REGEXEQ | |
#define IUTEST_ASSERT_MATCHES_REGEXEQ(regex_s,actual) IUTEST_TEST_MATCHES_REGEXEQ(regex_s,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_MATCHES_REGEXEQ | |
#define IUTEST_EXPECT_MATCHES_REGEXEQ(regex_s,actual) IUTEST_TEST_MATCHES_REGEXEQ(regex_s,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_MATCHES_REGEXEQ | |
#define IUTEST_INFORM_MATCHES_REGEXEQ(regex_s,actual) IUTEST_TEST_MATCHES_REGEXEQ(regex_s,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_MATCHES_REGEXEQ | |
#define IUTEST_ASSUME_MATCHES_REGEXEQ(regex_s,actual) IUTEST_TEST_MATCHES_REGEXEQ(regex_s,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_MATCHES_REGEXNE | |
#define IUTEST_ASSERT_MATCHES_REGEXNE(regex_s,actual) IUTEST_TEST_MATCHES_REGEXNE(regex_s,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_MATCHES_REGEXNE | |
#define IUTEST_EXPECT_MATCHES_REGEXNE(regex_s,actual) IUTEST_TEST_MATCHES_REGEXNE(regex_s,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_MATCHES_REGEXNE | |
#define IUTEST_INFORM_MATCHES_REGEXNE(regex_s,actual) IUTEST_TEST_MATCHES_REGEXNE(regex_s,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_MATCHES_REGEXNE | |
#define IUTEST_ASSUME_MATCHES_REGEXNE(regex_s,actual) IUTEST_TEST_MATCHES_REGEXNE(regex_s,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_CONTAINS_REGEXEQ | |
#define IUTEST_ASSERT_CONTAINS_REGEXEQ(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXEQ(regex_s,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_CONTAINS_REGEXEQ | |
#define IUTEST_EXPECT_CONTAINS_REGEXEQ(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXEQ(regex_s,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_CONTAINS_REGEXEQ | |
#define IUTEST_INFORM_CONTAINS_REGEXEQ(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXEQ(regex_s,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_CONTAINS_REGEXEQ | |
#define IUTEST_ASSUME_CONTAINS_REGEXEQ(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXEQ(regex_s,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSERT_CONTAINS_REGEXNE | |
#define IUTEST_ASSERT_CONTAINS_REGEXNE(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXNE(regex_s,actual,IUTEST_ASSERT_FAILURE) | |
#endif | |
#ifndef IUTEST_EXPECT_CONTAINS_REGEXNE | |
#define IUTEST_EXPECT_CONTAINS_REGEXNE(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXNE(regex_s,actual,IUTEST_EXPECT_FAILURE) | |
#endif | |
#ifndef IUTEST_INFORM_CONTAINS_REGEXNE | |
#define IUTEST_INFORM_CONTAINS_REGEXNE(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXNE(regex_s,actual,IUTEST_INFORM_FAILURE) | |
#endif | |
#ifndef IUTEST_ASSUME_CONTAINS_REGEXNE | |
#define IUTEST_ASSUME_CONTAINS_REGEXNE(regex_s,actual) IUTEST_TEST_CONTAINS_REGEXNE(regex_s,actual,IUTEST_ASSUME_FAILURE) | |
#endif | |
#endif | |
#define IUTEST_TEST_EQ_COLLECTIONS(b1,e1,b2,e2,on_f) IUTEST_PRED_FORMAT4_(::iuutil::CmpHelperEqCollections,b1,e1,b2,e2,on_f) | |
#define IUTEST_TEST_EQ_RANGE(expected,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperEqRange,expected,actual,on_f) | |
#define IUTEST_TEST_STRLNEQ(len,v2,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperSTRLNEQ,len,v2,on_f) | |
#define IUTEST_TEST_STRIN(substr,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperSTRIN,substr,actual,on_f) | |
#define IUTEST_TEST_STRNOTIN(substr,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperSTRNOTIN,substr,actual,on_f) | |
#if IUTEST_HAS_REGEX | |
#define IUTEST_TEST_MATCHES_REGEXEQ(regex,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperMatchesRegexEq,regex,actual,on_f) | |
#define IUTEST_TEST_MATCHES_REGEXNE(regex,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperMatchesRegexNe,regex,actual,on_f) | |
#define IUTEST_TEST_CONTAINS_REGEXEQ(regex,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperContainsRegexEq,regex,actual,on_f) | |
#define IUTEST_TEST_CONTAINS_REGEXNE(regex,actual,on_f) IUTEST_PRED_FORMAT2_(::iuutil::CmpHelperContainsRegexNe,regex,actual,on_f) | |
#endif | |
namespace iuutil{template<typename T1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqIterator(T1 b1,T1 e1,T2 b2,T2 e2){int elem=0;bool result=true;::iutest::Message ar;for(elem=0;b1!=e1&&b2!=e2;++b1,++b2,++elem){if(!::iutest::internal::EqHelper<false>::Compare("","",*b1,*b2)){result=false;ar<<"\nMismatch in a position " <<elem<<": "<< ::iutest::internal::FormatForComparisonFailureMessage(*b1,*b2)<< " vs " << ::iutest::internal::FormatForComparisonFailureMessage(*b2,*b1);}}if(b1!=e1){int elem1=elem;for(;b1!=e1;++b1,++elem1){}result=false;ar<<"\nMismatch element : " <<elem1<<" vs " <<elem;}if(b2!=e2){int elem2=elem;for(;b2!=e2;++b2,++elem2){}result=false;ar<<"\nMismatch element : " <<elem<<" vs " <<elem2;}if(!result){return ::iutest::AssertionFailure()<<ar;}return ::iutest::AssertionSuccess();}template<typename T1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqCollections(const char* expr1b,const char* expr1e,const char* expr2b,const char* expr2e,T1 b1,T1 e1,T2 b2,T2 e2){if(::iutest::AssertionResult ar=CmpHelperEqIterator(b1,e1,b2,e2)){return ::iutest::AssertionSuccess();}else{return ::iutest::AssertionFailure()<<"error: Expected: { " <<expr1b<<", " <<expr1e<<" } == { "<<expr2b<<", " <<expr2e<<" }\n Actual:" <<GetAssertionResultMessage(ar);}}namespace detail{template<typename T1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,T1 b1,T1 e1,T2 b2,T2 e2){if(::iutest::AssertionResult ar=CmpHelperEqIterator(b1,e1,b2,e2)){return ::iutest::AssertionSuccess();}else{return ::iutest::AssertionFailure()<<"error: Expected: " <<expected_expr<<" == " <<actual_expr<< " \n Actual:" <<GetAssertionResultMessage(ar);}}}template<typename T1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,const T1& expected,const T2& actual){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected.begin(),expected.end(),actual.begin(),actual.end());}template<typename T1,size_t SIZE1,typename T2,size_t SIZE2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,T1(&expected)[SIZE1],T2(&actual)[SIZE2]){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected,expected+SIZE1,actual,actual+SIZE2);}template<typename T1,typename T2,size_t SIZE2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,const T1& expected,T2(&actual)[SIZE2]){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected.begin(),expected.end(),actual,actual+SIZE2);}template<typename T1,size_t SIZE1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,T1(&expected)[SIZE1],const T2& actual){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected,expected+SIZE1,actual.begin(),actual.end());} | |
#if IUTEST_HAS_INITIALIZER_LIST | |
template<typename T1,typename T2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,::std::initializer_list<T1> expected,const T2& actual){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected.begin(),expected.end(),actual.begin(),actual.end());}template<typename T1,typename T2,size_t SIZE2>::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperEqRange(const char* expected_expr,const char* actual_expr,::std::initializer_list<T1> expected,T2(&actual)[SIZE2]){return detail::CmpHelperEqRange(expected_expr,actual_expr,expected.begin(),expected.end(),actual,actual+SIZE2);} | |
#endif | |
inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRLNEQ(const char* expr1,const char* expr2,size_t len1,const char* val2){const size_t len2=strlen(val2);if(len2==len1){return ::iutest::AssertionSuccess();}return ::iutest::AssertionFailure()<<"error: Value of: " <<expr1<<" == strlen(" <<expr2<<")"<< "\n Actual: " <<val2<<" : " <<len2<<"\nExpected: " <<len1;}inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRLNEQ(const char* expr1,const char* expr2,size_t len1,const wchar_t* val2){const size_t len2=wcslen(val2);if(len2==len1){return ::iutest::AssertionSuccess();}return ::iutest::AssertionFailure()<<"error: Value of: " <<expr1<<" == wcslen(" <<expr2<<")"<< "\n Actual: " <<val2<<" : " <<len2<<"\nExpected: " <<len1;}namespace StrInHelper{inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const char* substr,const char* actual){if(substr==0||actual==0){return substr==actual;}return strstr(actual,substr)!=0;}inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const wchar_t* substr,const wchar_t* actual){if(substr==0||actual==0){return substr==actual;}return wcsstr(actual,substr)!=0;}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& substr,const ::std::basic_string<Elem,Traits,Ax>& actual){return Compare(substr.c_str(),actual.c_str());}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const Elem* substr,const ::std::basic_string<Elem,Traits,Ax>& actual){return Compare(substr,actual.c_str());}template<typename Elem,typename Traits,typename Ax>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const ::std::basic_string<Elem,Traits,Ax>& substr,const Elem* actual){return Compare(substr.c_str(),actual);}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* substr_str,const char* act_s,const T1& substr,const T2& actual){if(Compare(substr,actual)){return ::iutest::AssertionSuccess();}return ::iutest::AssertionFailure()<<"error: Expected: " << "strstr(" <<act_s<<", " <<substr_str<<") != 0"<< "\n Actual: " << "strstr(\"" <<actual<<"\", " <<substr<<") == 0";}}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRIN(const char* substr_str,const char* act_s,const T1& substr,const T2& actual){return StrInHelper::Assertion(substr_str,act_s,substr,actual);}namespace StrNotInHelper{template<typename T1,typename T2>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const T1& substr,const T2& actual){return !StrInHelper::Compare(substr,actual);}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* substr_str,const char* act_s,const T1& substr,const T2& actual){if(Compare(substr,actual)){return ::iutest::AssertionSuccess();}return ::iutest::AssertionFailure()<<"error: Expected: " << "strstr(" <<act_s<<", " <<substr_str<<") == 0"<< "\n Actual: " << "strstr(\"" <<actual<<"\", " <<substr<<") != 0";}}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperSTRNOTIN(const char* substr_str,const char* act_s,const T1& substr,const T2& actual){return StrNotInHelper::Assertion(substr_str,act_s,substr,actual);} | |
#if IUTEST_HAS_REGEX | |
namespace RegexHelper{inline bool FullMatch(const ::std::string& str,const ::iutest::internal::RE& re){return ::iutest::internal::RE::FullMatch(str,re);}inline bool FullMatch(const char* str,const ::iutest::internal::RE& re){if(str==0){return false;}return ::iutest::internal::RE::FullMatch(str,re);}inline bool PartialMatch(const ::std::string& str,const ::iutest::internal::RE& re){return ::iutest::internal::RE::PartialMatch(str,re);}inline bool PartialMatch(const char* str,const ::iutest::internal::RE& re){if(str==0){return false;}return ::iutest::internal::RE::PartialMatch(str,re);}}namespace MatchesRegexEqHelper{template<typename T1,typename T2>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const T1& regex,const T2& actual){::iutest::internal::RE iure(regex);return RegexHelper::FullMatch(actual,iure);}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* regex_s,const char* act_s,const T1& regex,const T2& actual){if(Compare(regex,actual)){return ::iutest::AssertionSuccess();}::std::string exp_s="Matches Regex (";exp_s+=regex_s;exp_s+=")";return ::iutest::internal::EqFailure(exp_s.c_str(),act_s,::iutest::PrintToString(regex),::iutest::PrintToString(actual),false);}}inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperMatchesRegexEq(const char* regex_s,const char* act_s,const char* regex,const char* actual){return MatchesRegexEqHelper::Assertion(regex_s,act_s,regex,actual);}namespace MatchesRegexNeHelper{template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* regex_s,const char* act_s,const T1& regex,const T2& actual){if(!MatchesRegexEqHelper::Compare(regex,actual)){return ::iutest::AssertionSuccess();}::std::string exp_s="Not Matches Regex (";exp_s+=regex_s;exp_s+=")";return ::iutest::internal::EqFailure(exp_s.c_str(),act_s,::iutest::PrintToString(regex),::iutest::PrintToString(actual),false);}}inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperMatchesRegexNe(const char* regex_s,const char* act_s,const char* regex,const char* actual){return MatchesRegexNeHelper::Assertion(regex_s,act_s,regex,actual);}namespace ContainsRegexEqHelper{template<typename T1,typename T2>inline bool IUTEST_ATTRIBUTE_UNUSED_ Compare(const T1& regex,const T2& actual){::iutest::internal::RE m(regex);return RegexHelper::PartialMatch(actual,m);}template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* regex_s,const char* act_s,const T1& regex,const T2& actual){if(Compare(regex,actual)){return ::iutest::AssertionSuccess();}::std::string exp_s="Contains Regex (";exp_s+=regex_s;exp_s+=")";return ::iutest::internal::EqFailure(exp_s.c_str(),act_s,::iutest::PrintToString(regex),::iutest::PrintToString(actual),false);}}inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperContainsRegexEq(const char* regex_s,const char* act_s,const char* regex,const char* actual){return ContainsRegexEqHelper::Assertion(regex_s,act_s,regex,actual);}namespace ContainsRegexNeHelper{template<typename T1,typename T2>inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ Assertion(const char* regex_s,const char* act_s,const T1& regex,const T2& actual){if(!ContainsRegexEqHelper::Compare(regex,actual)){return ::iutest::AssertionSuccess();}::std::string exp_s="Not Contains Regex (";exp_s+=regex_s;exp_s+=")";return ::iutest::internal::EqFailure(exp_s.c_str(),act_s,::iutest::PrintToString(regex),::iutest::PrintToString(actual),false);}}inline ::iutest::AssertionResult IUTEST_ATTRIBUTE_UNUSED_ CmpHelperContainsRegexNe(const char* regex_s,const char* act_s,const char* regex,const char* actual){return ContainsRegexNeHelper::Assertion(regex_s,act_s,regex,actual);} | |
#endif | |
} | |
namespace iuutil{typedef ::iutest::detail::iuConsole Console;}namespace iuutil{class QuietResultPrinter:public ::iutest::TestEventListener{public: explicit QuietResultPrinter(::iutest::TestEventListener* default_printer):m_default_printer(default_printer){}virtual ~QuietResultPrinter(){delete m_default_printer;}public: virtual void OnTestProgramStart(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestProgramStart(unit_test);}virtual void OnTestIterationStart(const ::iutest::UnitTest& unit_test,int iteration) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestIterationStart(unit_test,iteration);}virtual void OnEnvironmentsSetUpStart(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnEnvironmentsSetUpStart(unit_test);}virtual void OnEnvironmentsSetUpEnd(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnEnvironmentsSetUpEnd(unit_test);}virtual void OnTestCaseStart(const ::iutest::TestCase& test_case) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestCaseStart(test_case);}virtual void OnTestStart(const ::iutest::TestInfo& test_info) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestStart(test_info);}virtual void OnTestPartResult(const ::iutest::TestPartResult& test_part_result) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestPartResult(test_part_result);}virtual void OnTestEnd(const ::iutest::TestInfo& test_info) IUTEST_CXX_OVERRIDE{if(test_info.result()->Failed()){m_default_printer->OnTestEnd(test_info);}}virtual void OnTestCaseEnd(const ::iutest::TestCase& test_case) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestCaseEnd(test_case);}virtual void OnEnvironmentsTearDownStart(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnEnvironmentsTearDownStart(unit_test);}virtual void OnEnvironmentsTearDownEnd(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnEnvironmentsTearDownEnd(unit_test);}virtual void OnTestIterationEnd(const ::iutest::UnitTest& unit_test,int iteration) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestIterationEnd(unit_test,iteration);}virtual void OnTestProgramEnd(const ::iutest::UnitTest& unit_test) IUTEST_CXX_OVERRIDE{m_default_printer->OnTestProgramEnd(unit_test);}private: ::iutest::TestEventListener* m_default_printer;public: static ::iutest::TestEventListener* SetUp(){::iutest::TestEventListeners& listeners=::iutest::UnitTest::GetInstance()->listeners();::iutest::TestEventListener* default_printer=listeners.Release(listeners.default_result_printer());if(default_printer==0){return 0;}::iutest::TestEventListener* p=new QuietResultPrinter(default_printer);listeners.Append(p);return p;}};}namespace iuutil{inline ::std::string TestFullName(const ::iutest::TestInfo* test_info){::std::string fullname=test_info->test_case_name();fullname+=".";fullname+=test_info->name();return fullname;}inline ::std::string TestNameRemoveIndexName(const char* name){const char* const p=strrchr(name,'/');if(p==0){return name;}return ::std::string(name,p);}inline ::std::string TestCaseNameRemoveIndexName(const char* name){return TestNameRemoveIndexName(name);}inline ::std::string TestCaseNameRemoveInstantiateAndIndexName(const char* name){const char* const pkg=strrchr(name,'.');const char* const p1=strchr(name,'/');if(p1==0){return name;}if(pkg==0){return TestCaseNameRemoveIndexName(p1+1);}else{return ::std::string(name,pkg+1)+TestCaseNameRemoveIndexName(p1+1);}}inline const ::iutest::TestCase* FindTestCase(const char* testcase_name){if(testcase_name==0){return 0;}const int testcase_count=::iutest::UnitTest::GetInstance()->total_test_case_count();for(int i=0;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);if(strcmp(testcase->name(),testcase_name)==0){return testcase;}}return 0;}inline const ::iutest::TestCase* FindParamTestCase(const char* testcase_name,const ::iutest::TestCase* begin=0){if(testcase_name==0){return 0;}const int testcase_count=::iutest::UnitTest::GetInstance()->total_test_case_count();int i=0;if(begin!=0){for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);if(testcase==begin){break;}}++i;}for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);const char* testcase_origin_name=strchr(testcase->name(),'/');if(testcase_origin_name!=0){if(strcmp(testcase_origin_name+1,testcase_name)==0){return testcase;}}}return 0;}inline const ::iutest::TestCase* FindTypedTestCase(const char* testcase_name,const ::iutest::TestCase* begin=0){if(testcase_name==0){return 0;}const int testcase_count=::iutest::UnitTest::GetInstance()->total_test_case_count();int i=0;if(begin!=0){for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);if(testcase==begin){break;}}++i;}for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);if(testcase!=0){const char* name=testcase->name();if(name!=0&& strstr(name,testcase_name)==name&& name[strlen(testcase_name)]=='/'){return testcase;}}}return 0;}inline const ::iutest::TestCase* FindParamTypedTestCase(const char* testcase_name,const ::iutest::TestCase* begin=0){if(testcase_name==0){return 0;}const int testcase_count=::iutest::UnitTest::GetInstance()->total_test_case_count();int i=0;if(begin!=0){for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);if(testcase==begin){break;}}++i;}for(;i<testcase_count;++i){const ::iutest::TestCase* testcase=::iutest::UnitTest::GetInstance()->GetTestCase(i);const char* name=strchr(testcase->name(),'/');if(name!=0){++name;if(strstr(name,testcase_name)==name&& name[strlen(testcase_name)]=='/'){return testcase;}}}return 0;}inline const ::iutest::TestInfo* FindTestInfo(const ::iutest::TestCase* testcase,const char* testinfo_name){if(testcase==0||testinfo_name==0){return 0;}const int testinfo_count=testcase->total_test_count();for(int i=0;i<testinfo_count;++i){const ::iutest::TestInfo* testinfo=testcase->GetTestInfo(i);if(strcmp(testinfo->name(),testinfo_name)==0){return testinfo;}}return 0;}inline const ::iutest::TestInfo* FindTestInfo(const char* testcase_name,const char* testinfo_name){if(testcase_name==0||testinfo_name==0){return 0;}const ::iutest::TestCase* testcase=FindTestCase(testcase_name);return FindTestInfo(testcase,testinfo_name);}inline const ::iutest::TestInfo* FindParamTestInfo(const ::iutest::TestCase* testcase,const char* testinfo_name,const ::iutest::TestInfo* begin=0){if(testcase==0||testinfo_name==0){return 0;}const int testinfo_count=testcase->total_test_count();int i=0;if(begin!=0){for(;i<testinfo_count;++i){const ::iutest::TestInfo* testinfo=testcase->GetTestInfo(i);if(testinfo==begin){break;}}++i;}for(;i<testinfo_count;++i){const ::iutest::TestInfo* testinfo=testcase->GetTestInfo(i);if(testinfo!=0){const char* name=testinfo->name();if(name!=0&& strstr(name,testinfo_name)==name&& name[strlen(testinfo_name)]=='/'){return testinfo;}}}return 0;}inline const ::iutest::TestResult* TestResultPointer(const ::iutest::TestResult* result){return result;}inline const ::iutest::TestResult* TestResultPointer(const ::iutest::TestResult& result){return &result;}inline const ::iutest::TestResult* GetAdHocTestResult(){return TestResultPointer(::iutest::UnitTest::GetInstance()->ad_hoc_test_result());}inline const ::iutest::TestResult* GetTestCaseAdHocResult(const ::iutest::TestCase* test_case){return TestResultPointer(test_case->ad_hoc_test_result());}inline const ::iutest::TestResult* GetCurrentTestCaseAdHocResult(){return GetTestCaseAdHocResult(::iutest::UnitTest::GetInstance()->current_test_case());}inline const ::iutest::TestResult* GetTestResult(const ::iutest::TestInfo* test_info){return TestResultPointer(test_info->result());}inline const ::iutest::TestResult* GetCurrentTestResult(){return GetTestResult(::iutest::UnitTest::GetInstance()->current_test_info());}}namespace iuutil{} | |
#define IUTEST_FILESYSTEM_INSTANTIATE(file_class_name) II_FILESYSTEM_INSTANTIATE_(file_class_name) | |
#define II_FILESYSTEM_INSTANTIATE_(file_class_name) static ::iutest::FileSystem<file_class_name>IUTEST_ATTRIBUTE_UNUSED_ s_iutest_filesystem_ | |
#ifdef IUTEST_USE_MAIN | |
#ifdef UNICODE | |
int wmain(int argc,wchar_t** argv) | |
#else | |
int main(int argc,char** argv) | |
#endif | |
{setlocale(LC_CTYPE,"");IUTEST_INIT(&argc,argv);return IUTEST_RUN_ALL_TESTS();} | |
#endif | |
#endif |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment