aboutsummaryrefslogtreecommitdiffstats
path: root/googlemock/include/gmock/gmock-matchers.h
diff options
context:
space:
mode:
Diffstat (limited to 'googlemock/include/gmock/gmock-matchers.h')
-rw-r--r--googlemock/include/gmock/gmock-matchers.h156
1 files changed, 141 insertions, 15 deletions
diff --git a/googlemock/include/gmock/gmock-matchers.h b/googlemock/include/gmock/gmock-matchers.h
index 7d136af9..15cad1f1 100644
--- a/googlemock/include/gmock/gmock-matchers.h
+++ b/googlemock/include/gmock/gmock-matchers.h
@@ -270,6 +270,7 @@
#include "gmock/internal/gmock-internal-utils.h"
#include "gmock/internal/gmock-port.h"
+#include "gmock/internal/gmock-pp.h"
#include "gtest/gtest.h"
// MSVC warning C5046 is new as of VS2017 version 15.8.
@@ -4813,29 +4814,154 @@ PolymorphicMatcher<internal::variant_matcher::VariantMatcher<T> > VariantWith(
::testing::internal::MakePredicateFormatterFromMatcher(matcher), value)
// MATCHER* macroses itself are listed below.
-#define MATCHER(name, description) GMOCK_INTERNAL_MATCHER(name, description)
+#define MATCHER(name, description) \
+ class name##Matcher \
+ : public ::testing::internal::MatcherBaseImpl<name##Matcher> { \
+ public: \
+ template <typename arg_type> \
+ class gmock_Impl : public ::testing::MatcherInterface<const arg_type&> { \
+ public: \
+ gmock_Impl() {} \
+ bool MatchAndExplain( \
+ const arg_type& arg, \
+ ::testing::MatchResultListener* result_listener) const override; \
+ void DescribeTo(::std::ostream* gmock_os) const override { \
+ *gmock_os << FormatDescription(false); \
+ } \
+ void DescribeNegationTo(::std::ostream* gmock_os) const override { \
+ *gmock_os << FormatDescription(true); \
+ } \
+ \
+ private: \
+ ::std::string FormatDescription(bool negation) const { \
+ ::std::string gmock_description = (description); \
+ if (!gmock_description.empty()) { \
+ return gmock_description; \
+ } \
+ return ::testing::internal::FormatMatcherDescription(negation, #name, \
+ {}); \
+ } \
+ }; \
+ }; \
+ GTEST_ATTRIBUTE_UNUSED_ inline name##Matcher name() { return {}; } \
+ template <typename arg_type> \
+ bool name##Matcher::gmock_Impl<arg_type>::MatchAndExplain( \
+ const arg_type& arg, \
+ ::testing::MatchResultListener* result_listener GTEST_ATTRIBUTE_UNUSED_) \
+ const
+
#define MATCHER_P(name, p0, description) \
- GMOCK_INTERNAL_MATCHER_P(name, description, p0)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP, description, (p0))
#define MATCHER_P2(name, p0, p1, description) \
- GMOCK_INTERNAL_MATCHER_P2(name, description, p0, p1)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP2, description, (p0, p1))
#define MATCHER_P3(name, p0, p1, p2, description) \
- GMOCK_INTERNAL_MATCHER_P3(name, description, p0, p1, p2)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP3, description, (p0, p1, p2))
#define MATCHER_P4(name, p0, p1, p2, p3, description) \
- GMOCK_INTERNAL_MATCHER_P4(name, description, p0, p1, p2, p3)
-#define MATCHER_P5(name, p0, p1, p2, p3, p4, description) \
- GMOCK_INTERNAL_MATCHER_P5(name, description, p0, p1, p2, p3, p4)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP4, description, (p0, p1, p2, p3))
+#define MATCHER_P5(name, p0, p1, p2, p3, p4, description) \
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP5, description, \
+ (p0, p1, p2, p3, p4))
#define MATCHER_P6(name, p0, p1, p2, p3, p4, p5, description) \
- GMOCK_INTERNAL_MATCHER_P6(name, description, p0, p1, p2, p3, p4, p5)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP6, description, \
+ (p0, p1, p2, p3, p4, p5))
#define MATCHER_P7(name, p0, p1, p2, p3, p4, p5, p6, description) \
- GMOCK_INTERNAL_MATCHER_P7(name, description, p0, p1, p2, p3, p4, p5, p6)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP7, description, \
+ (p0, p1, p2, p3, p4, p5, p6))
#define MATCHER_P8(name, p0, p1, p2, p3, p4, p5, p6, p7, description) \
- GMOCK_INTERNAL_MATCHER_P8(name, description, p0, p1, p2, p3, p4, p5, p6, p7)
-#define MATCHER_P9(name, p0, p1, p2, p3, p4, p5, p6, p7, p8, description) \
- GMOCK_INTERNAL_MATCHER_P9(name, description, p0, p1, p2, p3, p4, p5, p6, p7, \
- p8)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP8, description, \
+ (p0, p1, p2, p3, p4, p5, p6, p7))
+#define MATCHER_P9(name, p0, p1, p2, p3, p4, p5, p6, p7, p8, description) \
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP9, description, \
+ (p0, p1, p2, p3, p4, p5, p6, p7, p8))
#define MATCHER_P10(name, p0, p1, p2, p3, p4, p5, p6, p7, p8, p9, description) \
- GMOCK_INTERNAL_MATCHER_P10(name, description, p0, p1, p2, p3, p4, p5, p6, \
- p7, p8, p9)
+ GMOCK_INTERNAL_MATCHER(name, name##MatcherP10, description, \
+ (p0, p1, p2, p3, p4, p5, p6, p7, p8, p9))
+
+#define GMOCK_INTERNAL_MATCHER(name, full_name, description, args) \
+ template <GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAMS(args)> \
+ class full_name : public ::testing::internal::MatcherBaseImpl< \
+ full_name<GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args)>> { \
+ public: \
+ using full_name::MatcherBaseImpl::MatcherBaseImpl; \
+ template <typename arg_type> \
+ class gmock_Impl : public ::testing::MatcherInterface<const arg_type&> { \
+ public: \
+ explicit gmock_Impl(GMOCK_INTERNAL_MATCHER_FUNCTION_ARGS(args)) \
+ : GMOCK_INTERNAL_MATCHER_FORWARD_ARGS(args) {} \
+ bool MatchAndExplain( \
+ const arg_type& arg, \
+ ::testing::MatchResultListener* result_listener) const override; \
+ void DescribeTo(::std::ostream* gmock_os) const override { \
+ *gmock_os << FormatDescription(false); \
+ } \
+ void DescribeNegationTo(::std::ostream* gmock_os) const override { \
+ *gmock_os << FormatDescription(true); \
+ } \
+ GMOCK_INTERNAL_MATCHER_MEMBERS(args) \
+ \
+ private: \
+ ::std::string FormatDescription(bool negation) const { \
+ ::std::string gmock_description = (description); \
+ if (!gmock_description.empty()) { \
+ return gmock_description; \
+ } \
+ return ::testing::internal::FormatMatcherDescription( \
+ negation, #name, \
+ ::testing::internal::UniversalTersePrintTupleFieldsToStrings( \
+ ::std::tuple<GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args)>( \
+ GMOCK_INTERNAL_MATCHER_MEMBERS_USAGE(args)))); \
+ } \
+ }; \
+ }; \
+ template <GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAMS(args)> \
+ inline full_name<GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args)> name( \
+ GMOCK_INTERNAL_MATCHER_FUNCTION_ARGS(args)) { \
+ return full_name<GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args)>( \
+ GMOCK_INTERNAL_MATCHER_ARGS_USAGE(args)); \
+ } \
+ template <GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAMS(args)> \
+ template <typename arg_type> \
+ bool full_name<GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args)>::gmock_Impl< \
+ arg_type>::MatchAndExplain(const arg_type& arg, \
+ ::testing::MatchResultListener* \
+ result_listener GTEST_ATTRIBUTE_UNUSED_) \
+ const
+
+#define GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAMS(args) \
+ GMOCK_PP_TAIL( \
+ GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAM, , args))
+#define GMOCK_INTERNAL_MATCHER_TEMPLATE_PARAM(i_unused, data_unused, arg) \
+ , typename arg##_type
+
+#define GMOCK_INTERNAL_MATCHER_TYPE_PARAMS(args) \
+ GMOCK_PP_TAIL(GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_TYPE_PARAM, , args))
+#define GMOCK_INTERNAL_MATCHER_TYPE_PARAM(i_unused, data_unused, arg) \
+ , arg##_type
+
+#define GMOCK_INTERNAL_MATCHER_FUNCTION_ARGS(args) \
+ GMOCK_PP_TAIL(dummy_first GMOCK_PP_FOR_EACH( \
+ GMOCK_INTERNAL_MATCHER_FUNCTION_ARG, , args))
+#define GMOCK_INTERNAL_MATCHER_FUNCTION_ARG(i, data_unused, arg) \
+ , arg##_type gmock_p##i
+
+#define GMOCK_INTERNAL_MATCHER_FORWARD_ARGS(args) \
+ GMOCK_PP_TAIL(GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_FORWARD_ARG, , args))
+#define GMOCK_INTERNAL_MATCHER_FORWARD_ARG(i, data_unused, arg) \
+ , arg(::std::forward<arg##_type>(gmock_p##i))
+
+#define GMOCK_INTERNAL_MATCHER_MEMBERS(args) \
+ GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_MEMBER, , args)
+#define GMOCK_INTERNAL_MATCHER_MEMBER(i_unused, data_unused, arg) \
+ const arg##_type arg;
+
+#define GMOCK_INTERNAL_MATCHER_MEMBERS_USAGE(args) \
+ GMOCK_PP_TAIL(GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_MEMBER_USAGE, , args))
+#define GMOCK_INTERNAL_MATCHER_MEMBER_USAGE(i_unused, data_unused, arg) , arg
+
+#define GMOCK_INTERNAL_MATCHER_ARGS_USAGE(args) \
+ GMOCK_PP_TAIL(GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_MATCHER_ARG_USAGE, , args))
+#define GMOCK_INTERNAL_MATCHER_ARG_USAGE(i, data_unused, arg_unused) \
+ , gmock_p##i
} // namespace testing