1b89a7cc2SEnji Cooper // Copyright 2007, Google Inc.
2b89a7cc2SEnji Cooper // All rights reserved.
3b89a7cc2SEnji Cooper //
4b89a7cc2SEnji Cooper // Redistribution and use in source and binary forms, with or without
5b89a7cc2SEnji Cooper // modification, are permitted provided that the following conditions are
6b89a7cc2SEnji Cooper // met:
7b89a7cc2SEnji Cooper //
8b89a7cc2SEnji Cooper //     * Redistributions of source code must retain the above copyright
9b89a7cc2SEnji Cooper // notice, this list of conditions and the following disclaimer.
10b89a7cc2SEnji Cooper //     * Redistributions in binary form must reproduce the above
11b89a7cc2SEnji Cooper // copyright notice, this list of conditions and the following disclaimer
12b89a7cc2SEnji Cooper // in the documentation and/or other materials provided with the
13b89a7cc2SEnji Cooper // distribution.
14b89a7cc2SEnji Cooper //     * Neither the name of Google Inc. nor the names of its
15b89a7cc2SEnji Cooper // contributors may be used to endorse or promote products derived from
16b89a7cc2SEnji Cooper // this software without specific prior written permission.
17b89a7cc2SEnji Cooper //
18b89a7cc2SEnji Cooper // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19b89a7cc2SEnji Cooper // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20b89a7cc2SEnji Cooper // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21b89a7cc2SEnji Cooper // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22b89a7cc2SEnji Cooper // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23b89a7cc2SEnji Cooper // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24b89a7cc2SEnji Cooper // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25b89a7cc2SEnji Cooper // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26b89a7cc2SEnji Cooper // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27b89a7cc2SEnji Cooper // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28b89a7cc2SEnji Cooper // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29b89a7cc2SEnji Cooper 
30b89a7cc2SEnji Cooper // Google Mock - a framework for writing C++ mock classes.
31b89a7cc2SEnji Cooper //
32b89a7cc2SEnji Cooper // This file tests the built-in actions.
33b89a7cc2SEnji Cooper 
34b89a7cc2SEnji Cooper #include "gmock/gmock-actions.h"
3528f6c2f2SEnji Cooper 
36b89a7cc2SEnji Cooper #include <algorithm>
3728f6c2f2SEnji Cooper #include <functional>
38b89a7cc2SEnji Cooper #include <iterator>
39b89a7cc2SEnji Cooper #include <memory>
4028f6c2f2SEnji Cooper #include <sstream>
41b89a7cc2SEnji Cooper #include <string>
4228f6c2f2SEnji Cooper #include <tuple>
4328f6c2f2SEnji Cooper #include <type_traits>
4428f6c2f2SEnji Cooper #include <utility>
4528f6c2f2SEnji Cooper #include <vector>
4628f6c2f2SEnji Cooper 
47b89a7cc2SEnji Cooper #include "gmock/gmock.h"
48b89a7cc2SEnji Cooper #include "gmock/internal/gmock-port.h"
49b89a7cc2SEnji Cooper #include "gtest/gtest-spi.h"
5028f6c2f2SEnji Cooper #include "gtest/gtest.h"
5128f6c2f2SEnji Cooper #include "gtest/internal/gtest-port.h"
52b89a7cc2SEnji Cooper 
5328f6c2f2SEnji Cooper // Silence C4100 (unreferenced formal parameter) and C4503 (decorated name
5428f6c2f2SEnji Cooper // length exceeded) for MSVC.
5528f6c2f2SEnji Cooper GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100 4503)
5628f6c2f2SEnji Cooper #if defined(_MSC_VER) && (_MSC_VER == 1900)
5728f6c2f2SEnji Cooper // and silence C4800 (C4800: 'int *const ': forcing value
5828f6c2f2SEnji Cooper // to bool 'true' or 'false') for MSVC 15
5928f6c2f2SEnji Cooper GTEST_DISABLE_MSC_WARNINGS_PUSH_(4800)
6028f6c2f2SEnji Cooper #endif
6128f6c2f2SEnji Cooper 
6228f6c2f2SEnji Cooper namespace testing {
63b89a7cc2SEnji Cooper namespace {
64b89a7cc2SEnji Cooper 
6528f6c2f2SEnji Cooper using ::testing::internal::BuiltInDefaultValue;
66b89a7cc2SEnji Cooper 
TEST(TypeTraits,Negation)6728f6c2f2SEnji Cooper TEST(TypeTraits, Negation) {
6828f6c2f2SEnji Cooper   // Direct use with std types.
6928f6c2f2SEnji Cooper   static_assert(std::is_base_of<std::false_type,
7028f6c2f2SEnji Cooper                                 internal::negation<std::true_type>>::value,
7128f6c2f2SEnji Cooper                 "");
7228f6c2f2SEnji Cooper 
7328f6c2f2SEnji Cooper   static_assert(std::is_base_of<std::true_type,
7428f6c2f2SEnji Cooper                                 internal::negation<std::false_type>>::value,
7528f6c2f2SEnji Cooper                 "");
7628f6c2f2SEnji Cooper 
7728f6c2f2SEnji Cooper   // With other types that fit the requirement of a value member that is
7828f6c2f2SEnji Cooper   // convertible to bool.
7928f6c2f2SEnji Cooper   static_assert(std::is_base_of<
8028f6c2f2SEnji Cooper                     std::true_type,
8128f6c2f2SEnji Cooper                     internal::negation<std::integral_constant<int, 0>>>::value,
8228f6c2f2SEnji Cooper                 "");
8328f6c2f2SEnji Cooper 
8428f6c2f2SEnji Cooper   static_assert(std::is_base_of<
8528f6c2f2SEnji Cooper                     std::false_type,
8628f6c2f2SEnji Cooper                     internal::negation<std::integral_constant<int, 1>>>::value,
8728f6c2f2SEnji Cooper                 "");
8828f6c2f2SEnji Cooper 
8928f6c2f2SEnji Cooper   static_assert(std::is_base_of<
9028f6c2f2SEnji Cooper                     std::false_type,
9128f6c2f2SEnji Cooper                     internal::negation<std::integral_constant<int, -1>>>::value,
9228f6c2f2SEnji Cooper                 "");
9328f6c2f2SEnji Cooper }
9428f6c2f2SEnji Cooper 
9528f6c2f2SEnji Cooper // Weird false/true types that aren't actually bool constants (but should still
9628f6c2f2SEnji Cooper // be legal according to [meta.logical] because `bool(T::value)` is valid), are
9728f6c2f2SEnji Cooper // distinct from std::false_type and std::true_type, and are distinct from other
9828f6c2f2SEnji Cooper // instantiations of the same template.
9928f6c2f2SEnji Cooper //
10028f6c2f2SEnji Cooper // These let us check finicky details mandated by the standard like
10128f6c2f2SEnji Cooper // "std::conjunction should evaluate to a type that inherits from the first
10228f6c2f2SEnji Cooper // false-y input".
10328f6c2f2SEnji Cooper template <int>
10428f6c2f2SEnji Cooper struct MyFalse : std::integral_constant<int, 0> {};
10528f6c2f2SEnji Cooper 
10628f6c2f2SEnji Cooper template <int>
10728f6c2f2SEnji Cooper struct MyTrue : std::integral_constant<int, -1> {};
10828f6c2f2SEnji Cooper 
TEST(TypeTraits,Conjunction)10928f6c2f2SEnji Cooper TEST(TypeTraits, Conjunction) {
11028f6c2f2SEnji Cooper   // Base case: always true.
11128f6c2f2SEnji Cooper   static_assert(std::is_base_of<std::true_type, internal::conjunction<>>::value,
11228f6c2f2SEnji Cooper                 "");
11328f6c2f2SEnji Cooper 
11428f6c2f2SEnji Cooper   // One predicate: inherits from that predicate, regardless of value.
11528f6c2f2SEnji Cooper   static_assert(
11628f6c2f2SEnji Cooper       std::is_base_of<MyFalse<0>, internal::conjunction<MyFalse<0>>>::value,
11728f6c2f2SEnji Cooper       "");
11828f6c2f2SEnji Cooper 
11928f6c2f2SEnji Cooper   static_assert(
12028f6c2f2SEnji Cooper       std::is_base_of<MyTrue<0>, internal::conjunction<MyTrue<0>>>::value, "");
12128f6c2f2SEnji Cooper 
12228f6c2f2SEnji Cooper   // Multiple predicates, with at least one false: inherits from that one.
12328f6c2f2SEnji Cooper   static_assert(
12428f6c2f2SEnji Cooper       std::is_base_of<MyFalse<1>, internal::conjunction<MyTrue<0>, MyFalse<1>,
12528f6c2f2SEnji Cooper                                                         MyTrue<2>>>::value,
12628f6c2f2SEnji Cooper       "");
12728f6c2f2SEnji Cooper 
12828f6c2f2SEnji Cooper   static_assert(
12928f6c2f2SEnji Cooper       std::is_base_of<MyFalse<1>, internal::conjunction<MyTrue<0>, MyFalse<1>,
13028f6c2f2SEnji Cooper                                                         MyFalse<2>>>::value,
13128f6c2f2SEnji Cooper       "");
13228f6c2f2SEnji Cooper 
13328f6c2f2SEnji Cooper   // Short circuiting: in the case above, additional predicates need not even
13428f6c2f2SEnji Cooper   // define a value member.
13528f6c2f2SEnji Cooper   struct Empty {};
13628f6c2f2SEnji Cooper   static_assert(
13728f6c2f2SEnji Cooper       std::is_base_of<MyFalse<1>, internal::conjunction<MyTrue<0>, MyFalse<1>,
13828f6c2f2SEnji Cooper                                                         Empty>>::value,
13928f6c2f2SEnji Cooper       "");
14028f6c2f2SEnji Cooper 
14128f6c2f2SEnji Cooper   // All predicates true: inherits from the last.
14228f6c2f2SEnji Cooper   static_assert(
14328f6c2f2SEnji Cooper       std::is_base_of<MyTrue<2>, internal::conjunction<MyTrue<0>, MyTrue<1>,
14428f6c2f2SEnji Cooper                                                        MyTrue<2>>>::value,
14528f6c2f2SEnji Cooper       "");
14628f6c2f2SEnji Cooper }
14728f6c2f2SEnji Cooper 
TEST(TypeTraits,Disjunction)14828f6c2f2SEnji Cooper TEST(TypeTraits, Disjunction) {
14928f6c2f2SEnji Cooper   // Base case: always false.
15028f6c2f2SEnji Cooper   static_assert(
15128f6c2f2SEnji Cooper       std::is_base_of<std::false_type, internal::disjunction<>>::value, "");
15228f6c2f2SEnji Cooper 
15328f6c2f2SEnji Cooper   // One predicate: inherits from that predicate, regardless of value.
15428f6c2f2SEnji Cooper   static_assert(
15528f6c2f2SEnji Cooper       std::is_base_of<MyFalse<0>, internal::disjunction<MyFalse<0>>>::value,
15628f6c2f2SEnji Cooper       "");
15728f6c2f2SEnji Cooper 
15828f6c2f2SEnji Cooper   static_assert(
15928f6c2f2SEnji Cooper       std::is_base_of<MyTrue<0>, internal::disjunction<MyTrue<0>>>::value, "");
16028f6c2f2SEnji Cooper 
16128f6c2f2SEnji Cooper   // Multiple predicates, with at least one true: inherits from that one.
16228f6c2f2SEnji Cooper   static_assert(
16328f6c2f2SEnji Cooper       std::is_base_of<MyTrue<1>, internal::disjunction<MyFalse<0>, MyTrue<1>,
16428f6c2f2SEnji Cooper                                                        MyFalse<2>>>::value,
16528f6c2f2SEnji Cooper       "");
16628f6c2f2SEnji Cooper 
16728f6c2f2SEnji Cooper   static_assert(
16828f6c2f2SEnji Cooper       std::is_base_of<MyTrue<1>, internal::disjunction<MyFalse<0>, MyTrue<1>,
16928f6c2f2SEnji Cooper                                                        MyTrue<2>>>::value,
17028f6c2f2SEnji Cooper       "");
17128f6c2f2SEnji Cooper 
17228f6c2f2SEnji Cooper   // Short circuiting: in the case above, additional predicates need not even
17328f6c2f2SEnji Cooper   // define a value member.
17428f6c2f2SEnji Cooper   struct Empty {};
17528f6c2f2SEnji Cooper   static_assert(
17628f6c2f2SEnji Cooper       std::is_base_of<MyTrue<1>, internal::disjunction<MyFalse<0>, MyTrue<1>,
17728f6c2f2SEnji Cooper                                                        Empty>>::value,
17828f6c2f2SEnji Cooper       "");
17928f6c2f2SEnji Cooper 
18028f6c2f2SEnji Cooper   // All predicates false: inherits from the last.
18128f6c2f2SEnji Cooper   static_assert(
18228f6c2f2SEnji Cooper       std::is_base_of<MyFalse<2>, internal::disjunction<MyFalse<0>, MyFalse<1>,
18328f6c2f2SEnji Cooper                                                         MyFalse<2>>>::value,
18428f6c2f2SEnji Cooper       "");
18528f6c2f2SEnji Cooper }
18628f6c2f2SEnji Cooper 
TEST(TypeTraits,IsInvocableRV)18728f6c2f2SEnji Cooper TEST(TypeTraits, IsInvocableRV) {
18828f6c2f2SEnji Cooper   struct C {
18928f6c2f2SEnji Cooper     int operator()() const { return 0; }
19028f6c2f2SEnji Cooper     void operator()(int) & {}
19128f6c2f2SEnji Cooper     std::string operator()(int) && { return ""; };
19228f6c2f2SEnji Cooper   };
19328f6c2f2SEnji Cooper 
19428f6c2f2SEnji Cooper   // The first overload is callable for const and non-const rvalues and lvalues.
19528f6c2f2SEnji Cooper   // It can be used to obtain an int, cv void, or anything int is convertible
19628f6c2f2SEnji Cooper   // to.
19728f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<int, C>::value, "");
19828f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<int, C&>::value, "");
19928f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<int, const C>::value, "");
20028f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<int, const C&>::value, "");
20128f6c2f2SEnji Cooper 
20228f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<void, C>::value, "");
20328f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<const volatile void, C>::value, "");
20428f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<char, C>::value, "");
20528f6c2f2SEnji Cooper 
20628f6c2f2SEnji Cooper   // It's possible to provide an int. If it's given to an lvalue, the result is
20728f6c2f2SEnji Cooper   // void. Otherwise it is std::string (which is also treated as allowed for a
20828f6c2f2SEnji Cooper   // void result type).
20928f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<void, C&, int>::value, "");
21028f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<int, C&, int>::value, "");
21128f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<std::string, C&, int>::value, "");
21228f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, const C&, int>::value, "");
21328f6c2f2SEnji Cooper 
21428f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<std::string, C, int>::value, "");
21528f6c2f2SEnji Cooper   static_assert(internal::is_callable_r<void, C, int>::value, "");
21628f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<int, C, int>::value, "");
21728f6c2f2SEnji Cooper 
21828f6c2f2SEnji Cooper   // It's not possible to provide other arguments.
21928f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, C, std::string>::value, "");
22028f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, C, int, int>::value, "");
22128f6c2f2SEnji Cooper 
22228f6c2f2SEnji Cooper   // In C++17 and above, where it's guaranteed that functions can return
22328f6c2f2SEnji Cooper   // non-moveable objects, everything should work fine for non-moveable rsult
22428f6c2f2SEnji Cooper   // types too.
22528f6c2f2SEnji Cooper #if defined(GTEST_INTERNAL_CPLUSPLUS_LANG) && \
22628f6c2f2SEnji Cooper     GTEST_INTERNAL_CPLUSPLUS_LANG >= 201703L
22728f6c2f2SEnji Cooper   {
22828f6c2f2SEnji Cooper     struct NonMoveable {
22928f6c2f2SEnji Cooper       NonMoveable() = default;
23028f6c2f2SEnji Cooper       NonMoveable(NonMoveable&&) = delete;
23128f6c2f2SEnji Cooper     };
23228f6c2f2SEnji Cooper 
23328f6c2f2SEnji Cooper     static_assert(!std::is_move_constructible_v<NonMoveable>);
23428f6c2f2SEnji Cooper 
23528f6c2f2SEnji Cooper     struct Callable {
23628f6c2f2SEnji Cooper       NonMoveable operator()() { return NonMoveable(); }
23728f6c2f2SEnji Cooper     };
23828f6c2f2SEnji Cooper 
23928f6c2f2SEnji Cooper     static_assert(internal::is_callable_r<NonMoveable, Callable>::value);
24028f6c2f2SEnji Cooper     static_assert(internal::is_callable_r<void, Callable>::value);
24128f6c2f2SEnji Cooper     static_assert(
24228f6c2f2SEnji Cooper         internal::is_callable_r<const volatile void, Callable>::value);
24328f6c2f2SEnji Cooper 
24428f6c2f2SEnji Cooper     static_assert(!internal::is_callable_r<int, Callable>::value);
24528f6c2f2SEnji Cooper     static_assert(!internal::is_callable_r<NonMoveable, Callable, int>::value);
24628f6c2f2SEnji Cooper   }
24728f6c2f2SEnji Cooper #endif  // C++17 and above
24828f6c2f2SEnji Cooper 
24928f6c2f2SEnji Cooper   // Nothing should choke when we try to call other arguments besides directly
25028f6c2f2SEnji Cooper   // callable objects, but they should not show up as callable.
25128f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, int>::value, "");
25228f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, void (C::*)()>::value, "");
25328f6c2f2SEnji Cooper   static_assert(!internal::is_callable_r<void, void (C::*)(), C*>::value, "");
25428f6c2f2SEnji Cooper }
255b89a7cc2SEnji Cooper 
256b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T*>::Get() returns NULL.
TEST(BuiltInDefaultValueTest,IsNullForPointerTypes)257b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, IsNullForPointerTypes) {
25828f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<int*>::Get() == nullptr);
25928f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<const char*>::Get() == nullptr);
26028f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<void*>::Get() == nullptr);
261b89a7cc2SEnji Cooper }
262b89a7cc2SEnji Cooper 
263b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T*>::Exists() return true.
TEST(BuiltInDefaultValueTest,ExistsForPointerTypes)264b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, ExistsForPointerTypes) {
265b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<int*>::Exists());
266b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<const char*>::Exists());
267b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<void*>::Exists());
268b89a7cc2SEnji Cooper }
269b89a7cc2SEnji Cooper 
270b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T>::Get() returns 0 when T is a
271b89a7cc2SEnji Cooper // built-in numeric type.
TEST(BuiltInDefaultValueTest,IsZeroForNumericTypes)272b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, IsZeroForNumericTypes) {
273b89a7cc2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<unsigned char>::Get());
274b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<signed char>::Get());
275b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<char>::Get());
276b89a7cc2SEnji Cooper #if GMOCK_WCHAR_T_IS_NATIVE_
277b89a7cc2SEnji Cooper #if !defined(__WCHAR_UNSIGNED__)
278b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<wchar_t>::Get());
279b89a7cc2SEnji Cooper #else
280b89a7cc2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<wchar_t>::Get());
281b89a7cc2SEnji Cooper #endif
282b89a7cc2SEnji Cooper #endif
283b89a7cc2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<unsigned short>::Get());  // NOLINT
284b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<signed short>::Get());     // NOLINT
285b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<short>::Get());            // NOLINT
286b89a7cc2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<unsigned int>::Get());
287b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<signed int>::Get());
288b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<int>::Get());
289b89a7cc2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<unsigned long>::Get());       // NOLINT
290b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<signed long>::Get());          // NOLINT
291b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<long>::Get());                 // NOLINT
29228f6c2f2SEnji Cooper   EXPECT_EQ(0U, BuiltInDefaultValue<unsigned long long>::Get());  // NOLINT
29328f6c2f2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<signed long long>::Get());     // NOLINT
29428f6c2f2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<long long>::Get());            // NOLINT
295b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<float>::Get());
296b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<double>::Get());
297b89a7cc2SEnji Cooper }
298b89a7cc2SEnji Cooper 
299b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T>::Exists() returns true when T is a
300b89a7cc2SEnji Cooper // built-in numeric type.
TEST(BuiltInDefaultValueTest,ExistsForNumericTypes)301b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, ExistsForNumericTypes) {
302b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<unsigned char>::Exists());
303b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<signed char>::Exists());
304b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<char>::Exists());
305b89a7cc2SEnji Cooper #if GMOCK_WCHAR_T_IS_NATIVE_
306b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<wchar_t>::Exists());
307b89a7cc2SEnji Cooper #endif
308b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<unsigned short>::Exists());  // NOLINT
309b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<signed short>::Exists());    // NOLINT
310b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<short>::Exists());           // NOLINT
311b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<unsigned int>::Exists());
312b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<signed int>::Exists());
313b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<int>::Exists());
314b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<unsigned long>::Exists());       // NOLINT
315b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<signed long>::Exists());         // NOLINT
316b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<long>::Exists());                // NOLINT
31728f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<unsigned long long>::Exists());  // NOLINT
31828f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<signed long long>::Exists());    // NOLINT
31928f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<long long>::Exists());           // NOLINT
320b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<float>::Exists());
321b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<double>::Exists());
322b89a7cc2SEnji Cooper }
323b89a7cc2SEnji Cooper 
324b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<bool>::Get() returns false.
TEST(BuiltInDefaultValueTest,IsFalseForBool)325b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, IsFalseForBool) {
326b89a7cc2SEnji Cooper   EXPECT_FALSE(BuiltInDefaultValue<bool>::Get());
327b89a7cc2SEnji Cooper }
328b89a7cc2SEnji Cooper 
329b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<bool>::Exists() returns true.
TEST(BuiltInDefaultValueTest,BoolExists)330b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, BoolExists) {
331b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<bool>::Exists());
332b89a7cc2SEnji Cooper }
333b89a7cc2SEnji Cooper 
334b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T>::Get() returns "" when T is a
335b89a7cc2SEnji Cooper // string type.
TEST(BuiltInDefaultValueTest,IsEmptyStringForString)336b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, IsEmptyStringForString) {
337b89a7cc2SEnji Cooper   EXPECT_EQ("", BuiltInDefaultValue<::std::string>::Get());
338b89a7cc2SEnji Cooper }
339b89a7cc2SEnji Cooper 
340b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T>::Exists() returns true when T is a
341b89a7cc2SEnji Cooper // string type.
TEST(BuiltInDefaultValueTest,ExistsForString)342b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, ExistsForString) {
343b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<::std::string>::Exists());
344b89a7cc2SEnji Cooper }
345b89a7cc2SEnji Cooper 
346b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<const T>::Get() returns the same
347b89a7cc2SEnji Cooper // value as BuiltInDefaultValue<T>::Get() does.
TEST(BuiltInDefaultValueTest,WorksForConstTypes)348b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, WorksForConstTypes) {
349b89a7cc2SEnji Cooper   EXPECT_EQ("", BuiltInDefaultValue<const std::string>::Get());
350b89a7cc2SEnji Cooper   EXPECT_EQ(0, BuiltInDefaultValue<const int>::Get());
35128f6c2f2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<char* const>::Get() == nullptr);
352b89a7cc2SEnji Cooper   EXPECT_FALSE(BuiltInDefaultValue<const bool>::Get());
353b89a7cc2SEnji Cooper }
354b89a7cc2SEnji Cooper 
355b89a7cc2SEnji Cooper // A type that's default constructible.
356b89a7cc2SEnji Cooper class MyDefaultConstructible {
357b89a7cc2SEnji Cooper  public:
MyDefaultConstructible()358b89a7cc2SEnji Cooper   MyDefaultConstructible() : value_(42) {}
359b89a7cc2SEnji Cooper 
value() const360b89a7cc2SEnji Cooper   int value() const { return value_; }
361b89a7cc2SEnji Cooper 
362b89a7cc2SEnji Cooper  private:
363b89a7cc2SEnji Cooper   int value_;
364b89a7cc2SEnji Cooper };
365b89a7cc2SEnji Cooper 
366b89a7cc2SEnji Cooper // A type that's not default constructible.
367b89a7cc2SEnji Cooper class MyNonDefaultConstructible {
368b89a7cc2SEnji Cooper  public:
369b89a7cc2SEnji Cooper   // Does not have a default ctor.
MyNonDefaultConstructible(int a_value)370b89a7cc2SEnji Cooper   explicit MyNonDefaultConstructible(int a_value) : value_(a_value) {}
371b89a7cc2SEnji Cooper 
value() const372b89a7cc2SEnji Cooper   int value() const { return value_; }
373b89a7cc2SEnji Cooper 
374b89a7cc2SEnji Cooper  private:
375b89a7cc2SEnji Cooper   int value_;
376b89a7cc2SEnji Cooper };
377b89a7cc2SEnji Cooper 
TEST(BuiltInDefaultValueTest,ExistsForDefaultConstructibleType)378b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, ExistsForDefaultConstructibleType) {
379b89a7cc2SEnji Cooper   EXPECT_TRUE(BuiltInDefaultValue<MyDefaultConstructible>::Exists());
380b89a7cc2SEnji Cooper }
381b89a7cc2SEnji Cooper 
TEST(BuiltInDefaultValueTest,IsDefaultConstructedForDefaultConstructibleType)382b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, IsDefaultConstructedForDefaultConstructibleType) {
383b89a7cc2SEnji Cooper   EXPECT_EQ(42, BuiltInDefaultValue<MyDefaultConstructible>::Get().value());
384b89a7cc2SEnji Cooper }
385b89a7cc2SEnji Cooper 
TEST(BuiltInDefaultValueTest,DoesNotExistForNonDefaultConstructibleType)386b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueTest, DoesNotExistForNonDefaultConstructibleType) {
387b89a7cc2SEnji Cooper   EXPECT_FALSE(BuiltInDefaultValue<MyNonDefaultConstructible>::Exists());
388b89a7cc2SEnji Cooper }
389b89a7cc2SEnji Cooper 
390b89a7cc2SEnji Cooper // Tests that BuiltInDefaultValue<T&>::Get() aborts the program.
TEST(BuiltInDefaultValueDeathTest,IsUndefinedForReferences)391b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueDeathTest, IsUndefinedForReferences) {
39228f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ BuiltInDefaultValue<int&>::Get(); }, "");
39328f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ BuiltInDefaultValue<const char&>::Get(); }, "");
394b89a7cc2SEnji Cooper }
395b89a7cc2SEnji Cooper 
TEST(BuiltInDefaultValueDeathTest,IsUndefinedForNonDefaultConstructibleType)396b89a7cc2SEnji Cooper TEST(BuiltInDefaultValueDeathTest, IsUndefinedForNonDefaultConstructibleType) {
39728f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED(
39828f6c2f2SEnji Cooper       { BuiltInDefaultValue<MyNonDefaultConstructible>::Get(); }, "");
399b89a7cc2SEnji Cooper }
400b89a7cc2SEnji Cooper 
401b89a7cc2SEnji Cooper // Tests that DefaultValue<T>::IsSet() is false initially.
TEST(DefaultValueTest,IsInitiallyUnset)402b89a7cc2SEnji Cooper TEST(DefaultValueTest, IsInitiallyUnset) {
403b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int>::IsSet());
404b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyDefaultConstructible>::IsSet());
405b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const MyNonDefaultConstructible>::IsSet());
406b89a7cc2SEnji Cooper }
407b89a7cc2SEnji Cooper 
408b89a7cc2SEnji Cooper // Tests that DefaultValue<T> can be set and then unset.
TEST(DefaultValueTest,CanBeSetAndUnset)409b89a7cc2SEnji Cooper TEST(DefaultValueTest, CanBeSetAndUnset) {
410b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<int>::Exists());
411b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const MyNonDefaultConstructible>::Exists());
412b89a7cc2SEnji Cooper 
413b89a7cc2SEnji Cooper   DefaultValue<int>::Set(1);
414b89a7cc2SEnji Cooper   DefaultValue<const MyNonDefaultConstructible>::Set(
415b89a7cc2SEnji Cooper       MyNonDefaultConstructible(42));
416b89a7cc2SEnji Cooper 
417b89a7cc2SEnji Cooper   EXPECT_EQ(1, DefaultValue<int>::Get());
418b89a7cc2SEnji Cooper   EXPECT_EQ(42, DefaultValue<const MyNonDefaultConstructible>::Get().value());
419b89a7cc2SEnji Cooper 
420b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<int>::Exists());
421b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<const MyNonDefaultConstructible>::Exists());
422b89a7cc2SEnji Cooper 
423b89a7cc2SEnji Cooper   DefaultValue<int>::Clear();
424b89a7cc2SEnji Cooper   DefaultValue<const MyNonDefaultConstructible>::Clear();
425b89a7cc2SEnji Cooper 
426b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int>::IsSet());
427b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const MyNonDefaultConstructible>::IsSet());
428b89a7cc2SEnji Cooper 
429b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<int>::Exists());
430b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const MyNonDefaultConstructible>::Exists());
431b89a7cc2SEnji Cooper }
432b89a7cc2SEnji Cooper 
433b89a7cc2SEnji Cooper // Tests that DefaultValue<T>::Get() returns the
434b89a7cc2SEnji Cooper // BuiltInDefaultValue<T>::Get() when DefaultValue<T>::IsSet() is
435b89a7cc2SEnji Cooper // false.
TEST(DefaultValueDeathTest,GetReturnsBuiltInDefaultValueWhenUnset)436b89a7cc2SEnji Cooper TEST(DefaultValueDeathTest, GetReturnsBuiltInDefaultValueWhenUnset) {
437b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int>::IsSet());
438b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<int>::Exists());
439b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible>::IsSet());
440b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible>::Exists());
441b89a7cc2SEnji Cooper 
442b89a7cc2SEnji Cooper   EXPECT_EQ(0, DefaultValue<int>::Get());
443b89a7cc2SEnji Cooper 
44428f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ DefaultValue<MyNonDefaultConstructible>::Get(); },
44528f6c2f2SEnji Cooper                             "");
446b89a7cc2SEnji Cooper }
447b89a7cc2SEnji Cooper 
TEST(DefaultValueTest,GetWorksForMoveOnlyIfSet)448b89a7cc2SEnji Cooper TEST(DefaultValueTest, GetWorksForMoveOnlyIfSet) {
449b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<std::unique_ptr<int>>::Exists());
45028f6c2f2SEnji Cooper   EXPECT_TRUE(DefaultValue<std::unique_ptr<int>>::Get() == nullptr);
45128f6c2f2SEnji Cooper   DefaultValue<std::unique_ptr<int>>::SetFactory(
45228f6c2f2SEnji Cooper       [] { return std::make_unique<int>(42); });
453b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<std::unique_ptr<int>>::Exists());
454b89a7cc2SEnji Cooper   std::unique_ptr<int> i = DefaultValue<std::unique_ptr<int>>::Get();
455b89a7cc2SEnji Cooper   EXPECT_EQ(42, *i);
456b89a7cc2SEnji Cooper }
457b89a7cc2SEnji Cooper 
458b89a7cc2SEnji Cooper // Tests that DefaultValue<void>::Get() returns void.
TEST(DefaultValueTest,GetWorksForVoid)45928f6c2f2SEnji Cooper TEST(DefaultValueTest, GetWorksForVoid) { return DefaultValue<void>::Get(); }
460b89a7cc2SEnji Cooper 
461b89a7cc2SEnji Cooper // Tests using DefaultValue with a reference type.
462b89a7cc2SEnji Cooper 
463b89a7cc2SEnji Cooper // Tests that DefaultValue<T&>::IsSet() is false initially.
TEST(DefaultValueOfReferenceTest,IsInitiallyUnset)464b89a7cc2SEnji Cooper TEST(DefaultValueOfReferenceTest, IsInitiallyUnset) {
465b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int&>::IsSet());
466b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyDefaultConstructible&>::IsSet());
467b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible&>::IsSet());
468b89a7cc2SEnji Cooper }
469b89a7cc2SEnji Cooper 
47028f6c2f2SEnji Cooper // Tests that DefaultValue<T&>::Exists is false initially.
TEST(DefaultValueOfReferenceTest,IsInitiallyNotExisting)471b89a7cc2SEnji Cooper TEST(DefaultValueOfReferenceTest, IsInitiallyNotExisting) {
472b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int&>::Exists());
473b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyDefaultConstructible&>::Exists());
474b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible&>::Exists());
475b89a7cc2SEnji Cooper }
476b89a7cc2SEnji Cooper 
477b89a7cc2SEnji Cooper // Tests that DefaultValue<T&> can be set and then unset.
TEST(DefaultValueOfReferenceTest,CanBeSetAndUnset)478b89a7cc2SEnji Cooper TEST(DefaultValueOfReferenceTest, CanBeSetAndUnset) {
479b89a7cc2SEnji Cooper   int n = 1;
480b89a7cc2SEnji Cooper   DefaultValue<const int&>::Set(n);
481b89a7cc2SEnji Cooper   MyNonDefaultConstructible x(42);
482b89a7cc2SEnji Cooper   DefaultValue<MyNonDefaultConstructible&>::Set(x);
483b89a7cc2SEnji Cooper 
484b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<const int&>::Exists());
485b89a7cc2SEnji Cooper   EXPECT_TRUE(DefaultValue<MyNonDefaultConstructible&>::Exists());
486b89a7cc2SEnji Cooper 
487b89a7cc2SEnji Cooper   EXPECT_EQ(&n, &(DefaultValue<const int&>::Get()));
488b89a7cc2SEnji Cooper   EXPECT_EQ(&x, &(DefaultValue<MyNonDefaultConstructible&>::Get()));
489b89a7cc2SEnji Cooper 
490b89a7cc2SEnji Cooper   DefaultValue<const int&>::Clear();
491b89a7cc2SEnji Cooper   DefaultValue<MyNonDefaultConstructible&>::Clear();
492b89a7cc2SEnji Cooper 
493b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const int&>::Exists());
494b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible&>::Exists());
495b89a7cc2SEnji Cooper 
496b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<const int&>::IsSet());
497b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible&>::IsSet());
498b89a7cc2SEnji Cooper }
499b89a7cc2SEnji Cooper 
500b89a7cc2SEnji Cooper // Tests that DefaultValue<T&>::Get() returns the
501b89a7cc2SEnji Cooper // BuiltInDefaultValue<T&>::Get() when DefaultValue<T&>::IsSet() is
502b89a7cc2SEnji Cooper // false.
TEST(DefaultValueOfReferenceDeathTest,GetReturnsBuiltInDefaultValueWhenUnset)503b89a7cc2SEnji Cooper TEST(DefaultValueOfReferenceDeathTest, GetReturnsBuiltInDefaultValueWhenUnset) {
504b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<int&>::IsSet());
505b89a7cc2SEnji Cooper   EXPECT_FALSE(DefaultValue<MyNonDefaultConstructible&>::IsSet());
506b89a7cc2SEnji Cooper 
50728f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ DefaultValue<int&>::Get(); }, "");
50828f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ DefaultValue<MyNonDefaultConstructible>::Get(); },
50928f6c2f2SEnji Cooper                             "");
510b89a7cc2SEnji Cooper }
511b89a7cc2SEnji Cooper 
512b89a7cc2SEnji Cooper // Tests that ActionInterface can be implemented by defining the
513b89a7cc2SEnji Cooper // Perform method.
514b89a7cc2SEnji Cooper 
515b89a7cc2SEnji Cooper typedef int MyGlobalFunction(bool, int);
516b89a7cc2SEnji Cooper 
517b89a7cc2SEnji Cooper class MyActionImpl : public ActionInterface<MyGlobalFunction> {
518b89a7cc2SEnji Cooper  public:
Perform(const std::tuple<bool,int> & args)51928f6c2f2SEnji Cooper   int Perform(const std::tuple<bool, int>& args) override {
52028f6c2f2SEnji Cooper     return std::get<0>(args) ? std::get<1>(args) : 0;
521b89a7cc2SEnji Cooper   }
522b89a7cc2SEnji Cooper };
523b89a7cc2SEnji Cooper 
TEST(ActionInterfaceTest,CanBeImplementedByDefiningPerform)524b89a7cc2SEnji Cooper TEST(ActionInterfaceTest, CanBeImplementedByDefiningPerform) {
525b89a7cc2SEnji Cooper   MyActionImpl my_action_impl;
526b89a7cc2SEnji Cooper   (void)my_action_impl;
527b89a7cc2SEnji Cooper }
528b89a7cc2SEnji Cooper 
TEST(ActionInterfaceTest,MakeAction)529b89a7cc2SEnji Cooper TEST(ActionInterfaceTest, MakeAction) {
530b89a7cc2SEnji Cooper   Action<MyGlobalFunction> action = MakeAction(new MyActionImpl);
531b89a7cc2SEnji Cooper 
532b89a7cc2SEnji Cooper   // When exercising the Perform() method of Action<F>, we must pass
533b89a7cc2SEnji Cooper   // it a tuple whose size and type are compatible with F's argument
534b89a7cc2SEnji Cooper   // types.  For example, if F is int(), then Perform() takes a
535b89a7cc2SEnji Cooper   // 0-tuple; if F is void(bool, int), then Perform() takes a
53628f6c2f2SEnji Cooper   // std::tuple<bool, int>, and so on.
53728f6c2f2SEnji Cooper   EXPECT_EQ(5, action.Perform(std::make_tuple(true, 5)));
538b89a7cc2SEnji Cooper }
539b89a7cc2SEnji Cooper 
54028f6c2f2SEnji Cooper // Tests that Action<F> can be constructed from a pointer to
541b89a7cc2SEnji Cooper // ActionInterface<F>.
TEST(ActionTest,CanBeConstructedFromActionInterface)542b89a7cc2SEnji Cooper TEST(ActionTest, CanBeConstructedFromActionInterface) {
543b89a7cc2SEnji Cooper   Action<MyGlobalFunction> action(new MyActionImpl);
544b89a7cc2SEnji Cooper }
545b89a7cc2SEnji Cooper 
546b89a7cc2SEnji Cooper // Tests that Action<F> delegates actual work to ActionInterface<F>.
TEST(ActionTest,DelegatesWorkToActionInterface)547b89a7cc2SEnji Cooper TEST(ActionTest, DelegatesWorkToActionInterface) {
548b89a7cc2SEnji Cooper   const Action<MyGlobalFunction> action(new MyActionImpl);
549b89a7cc2SEnji Cooper 
55028f6c2f2SEnji Cooper   EXPECT_EQ(5, action.Perform(std::make_tuple(true, 5)));
55128f6c2f2SEnji Cooper   EXPECT_EQ(0, action.Perform(std::make_tuple(false, 1)));
552b89a7cc2SEnji Cooper }
553b89a7cc2SEnji Cooper 
554b89a7cc2SEnji Cooper // Tests that Action<F> can be copied.
TEST(ActionTest,IsCopyable)555b89a7cc2SEnji Cooper TEST(ActionTest, IsCopyable) {
556b89a7cc2SEnji Cooper   Action<MyGlobalFunction> a1(new MyActionImpl);
557b89a7cc2SEnji Cooper   Action<MyGlobalFunction> a2(a1);  // Tests the copy constructor.
558b89a7cc2SEnji Cooper 
559b89a7cc2SEnji Cooper   // a1 should continue to work after being copied from.
56028f6c2f2SEnji Cooper   EXPECT_EQ(5, a1.Perform(std::make_tuple(true, 5)));
56128f6c2f2SEnji Cooper   EXPECT_EQ(0, a1.Perform(std::make_tuple(false, 1)));
562b89a7cc2SEnji Cooper 
563b89a7cc2SEnji Cooper   // a2 should work like the action it was copied from.
56428f6c2f2SEnji Cooper   EXPECT_EQ(5, a2.Perform(std::make_tuple(true, 5)));
56528f6c2f2SEnji Cooper   EXPECT_EQ(0, a2.Perform(std::make_tuple(false, 1)));
566b89a7cc2SEnji Cooper 
567b89a7cc2SEnji Cooper   a2 = a1;  // Tests the assignment operator.
568b89a7cc2SEnji Cooper 
569b89a7cc2SEnji Cooper   // a1 should continue to work after being copied from.
57028f6c2f2SEnji Cooper   EXPECT_EQ(5, a1.Perform(std::make_tuple(true, 5)));
57128f6c2f2SEnji Cooper   EXPECT_EQ(0, a1.Perform(std::make_tuple(false, 1)));
572b89a7cc2SEnji Cooper 
573b89a7cc2SEnji Cooper   // a2 should work like the action it was copied from.
57428f6c2f2SEnji Cooper   EXPECT_EQ(5, a2.Perform(std::make_tuple(true, 5)));
57528f6c2f2SEnji Cooper   EXPECT_EQ(0, a2.Perform(std::make_tuple(false, 1)));
576b89a7cc2SEnji Cooper }
577b89a7cc2SEnji Cooper 
578b89a7cc2SEnji Cooper // Tests that an Action<From> object can be converted to a
579b89a7cc2SEnji Cooper // compatible Action<To> object.
580b89a7cc2SEnji Cooper 
581b89a7cc2SEnji Cooper class IsNotZero : public ActionInterface<bool(int)> {  // NOLINT
582b89a7cc2SEnji Cooper  public:
Perform(const std::tuple<int> & arg)58328f6c2f2SEnji Cooper   bool Perform(const std::tuple<int>& arg) override {
58428f6c2f2SEnji Cooper     return std::get<0>(arg) != 0;
585b89a7cc2SEnji Cooper   }
586b89a7cc2SEnji Cooper };
587b89a7cc2SEnji Cooper 
TEST(ActionTest,CanBeConvertedToOtherActionType)588b89a7cc2SEnji Cooper TEST(ActionTest, CanBeConvertedToOtherActionType) {
589b89a7cc2SEnji Cooper   const Action<bool(int)> a1(new IsNotZero);           // NOLINT
590b89a7cc2SEnji Cooper   const Action<int(char)> a2 = Action<int(char)>(a1);  // NOLINT
59128f6c2f2SEnji Cooper   EXPECT_EQ(1, a2.Perform(std::make_tuple('a')));
59228f6c2f2SEnji Cooper   EXPECT_EQ(0, a2.Perform(std::make_tuple('\0')));
593b89a7cc2SEnji Cooper }
594b89a7cc2SEnji Cooper 
595b89a7cc2SEnji Cooper // The following two classes are for testing MakePolymorphicAction().
596b89a7cc2SEnji Cooper 
597b89a7cc2SEnji Cooper // Implements a polymorphic action that returns the second of the
598b89a7cc2SEnji Cooper // arguments it receives.
599b89a7cc2SEnji Cooper class ReturnSecondArgumentAction {
600b89a7cc2SEnji Cooper  public:
601b89a7cc2SEnji Cooper   // We want to verify that MakePolymorphicAction() can work with a
602b89a7cc2SEnji Cooper   // polymorphic action whose Perform() method template is either
603b89a7cc2SEnji Cooper   // const or not.  This lets us verify the non-const case.
604b89a7cc2SEnji Cooper   template <typename Result, typename ArgumentTuple>
60528f6c2f2SEnji Cooper   Result Perform(const ArgumentTuple& args) {
60628f6c2f2SEnji Cooper     return std::get<1>(args);
60728f6c2f2SEnji Cooper   }
608b89a7cc2SEnji Cooper };
609b89a7cc2SEnji Cooper 
610b89a7cc2SEnji Cooper // Implements a polymorphic action that can be used in a nullary
611b89a7cc2SEnji Cooper // function to return 0.
612b89a7cc2SEnji Cooper class ReturnZeroFromNullaryFunctionAction {
613b89a7cc2SEnji Cooper  public:
614b89a7cc2SEnji Cooper   // For testing that MakePolymorphicAction() works when the
615b89a7cc2SEnji Cooper   // implementation class' Perform() method template takes only one
616b89a7cc2SEnji Cooper   // template parameter.
617b89a7cc2SEnji Cooper   //
618b89a7cc2SEnji Cooper   // We want to verify that MakePolymorphicAction() can work with a
619b89a7cc2SEnji Cooper   // polymorphic action whose Perform() method template is either
620b89a7cc2SEnji Cooper   // const or not.  This lets us verify the const case.
621b89a7cc2SEnji Cooper   template <typename Result>
Perform(const std::tuple<> &) const62228f6c2f2SEnji Cooper   Result Perform(const std::tuple<>&) const {
62328f6c2f2SEnji Cooper     return 0;
62428f6c2f2SEnji Cooper   }
625b89a7cc2SEnji Cooper };
626b89a7cc2SEnji Cooper 
627b89a7cc2SEnji Cooper // These functions verify that MakePolymorphicAction() returns a
628b89a7cc2SEnji Cooper // PolymorphicAction<T> where T is the argument's type.
629b89a7cc2SEnji Cooper 
ReturnSecondArgument()630b89a7cc2SEnji Cooper PolymorphicAction<ReturnSecondArgumentAction> ReturnSecondArgument() {
631b89a7cc2SEnji Cooper   return MakePolymorphicAction(ReturnSecondArgumentAction());
632b89a7cc2SEnji Cooper }
633b89a7cc2SEnji Cooper 
634b89a7cc2SEnji Cooper PolymorphicAction<ReturnZeroFromNullaryFunctionAction>
ReturnZeroFromNullaryFunction()635b89a7cc2SEnji Cooper ReturnZeroFromNullaryFunction() {
636b89a7cc2SEnji Cooper   return MakePolymorphicAction(ReturnZeroFromNullaryFunctionAction());
637b89a7cc2SEnji Cooper }
638b89a7cc2SEnji Cooper 
639b89a7cc2SEnji Cooper // Tests that MakePolymorphicAction() turns a polymorphic action
640b89a7cc2SEnji Cooper // implementation class into a polymorphic action.
TEST(MakePolymorphicActionTest,ConstructsActionFromImpl)641b89a7cc2SEnji Cooper TEST(MakePolymorphicActionTest, ConstructsActionFromImpl) {
642b89a7cc2SEnji Cooper   Action<int(bool, int, double)> a1 = ReturnSecondArgument();  // NOLINT
64328f6c2f2SEnji Cooper   EXPECT_EQ(5, a1.Perform(std::make_tuple(false, 5, 2.0)));
644b89a7cc2SEnji Cooper }
645b89a7cc2SEnji Cooper 
646b89a7cc2SEnji Cooper // Tests that MakePolymorphicAction() works when the implementation
647b89a7cc2SEnji Cooper // class' Perform() method template has only one template parameter.
TEST(MakePolymorphicActionTest,WorksWhenPerformHasOneTemplateParameter)648b89a7cc2SEnji Cooper TEST(MakePolymorphicActionTest, WorksWhenPerformHasOneTemplateParameter) {
649b89a7cc2SEnji Cooper   Action<int()> a1 = ReturnZeroFromNullaryFunction();
65028f6c2f2SEnji Cooper   EXPECT_EQ(0, a1.Perform(std::make_tuple()));
651b89a7cc2SEnji Cooper 
652b89a7cc2SEnji Cooper   Action<void*()> a2 = ReturnZeroFromNullaryFunction();
65328f6c2f2SEnji Cooper   EXPECT_TRUE(a2.Perform(std::make_tuple()) == nullptr);
654b89a7cc2SEnji Cooper }
655b89a7cc2SEnji Cooper 
656b89a7cc2SEnji Cooper // Tests that Return() works as an action for void-returning
657b89a7cc2SEnji Cooper // functions.
TEST(ReturnTest,WorksForVoid)658b89a7cc2SEnji Cooper TEST(ReturnTest, WorksForVoid) {
659b89a7cc2SEnji Cooper   const Action<void(int)> ret = Return();  // NOLINT
66028f6c2f2SEnji Cooper   return ret.Perform(std::make_tuple(1));
661b89a7cc2SEnji Cooper }
662b89a7cc2SEnji Cooper 
663b89a7cc2SEnji Cooper // Tests that Return(v) returns v.
TEST(ReturnTest,ReturnsGivenValue)664b89a7cc2SEnji Cooper TEST(ReturnTest, ReturnsGivenValue) {
665b89a7cc2SEnji Cooper   Action<int()> ret = Return(1);  // NOLINT
66628f6c2f2SEnji Cooper   EXPECT_EQ(1, ret.Perform(std::make_tuple()));
667b89a7cc2SEnji Cooper 
668b89a7cc2SEnji Cooper   ret = Return(-5);
66928f6c2f2SEnji Cooper   EXPECT_EQ(-5, ret.Perform(std::make_tuple()));
670b89a7cc2SEnji Cooper }
671b89a7cc2SEnji Cooper 
672b89a7cc2SEnji Cooper // Tests that Return("string literal") works.
TEST(ReturnTest,AcceptsStringLiteral)673b89a7cc2SEnji Cooper TEST(ReturnTest, AcceptsStringLiteral) {
674b89a7cc2SEnji Cooper   Action<const char*()> a1 = Return("Hello");
67528f6c2f2SEnji Cooper   EXPECT_STREQ("Hello", a1.Perform(std::make_tuple()));
676b89a7cc2SEnji Cooper 
677b89a7cc2SEnji Cooper   Action<std::string()> a2 = Return("world");
67828f6c2f2SEnji Cooper   EXPECT_EQ("world", a2.Perform(std::make_tuple()));
679b89a7cc2SEnji Cooper }
680b89a7cc2SEnji Cooper 
68128f6c2f2SEnji Cooper // Return(x) should work fine when the mock function's return type is a
68228f6c2f2SEnji Cooper // reference-like wrapper for decltype(x), as when x is a std::string and the
68328f6c2f2SEnji Cooper // mock function returns std::string_view.
TEST(ReturnTest,SupportsReferenceLikeReturnType)68428f6c2f2SEnji Cooper TEST(ReturnTest, SupportsReferenceLikeReturnType) {
68528f6c2f2SEnji Cooper   // A reference wrapper for std::vector<int>, implicitly convertible from it.
68628f6c2f2SEnji Cooper   struct Result {
68728f6c2f2SEnji Cooper     const std::vector<int>* v;
68828f6c2f2SEnji Cooper     Result(const std::vector<int>& vec) : v(&vec) {}  // NOLINT
689b89a7cc2SEnji Cooper   };
690b89a7cc2SEnji Cooper 
69128f6c2f2SEnji Cooper   // Set up an action for a mock function that returns the reference wrapper
69228f6c2f2SEnji Cooper   // type, initializing it with an actual vector.
69328f6c2f2SEnji Cooper   //
69428f6c2f2SEnji Cooper   // The returned wrapper should be initialized with a copy of that vector
69528f6c2f2SEnji Cooper   // that's embedded within the action itself (which should stay alive as long
69628f6c2f2SEnji Cooper   // as the mock object is alive), rather than e.g. a reference to the temporary
69728f6c2f2SEnji Cooper   // we feed to Return. This should work fine both for WillOnce and
69828f6c2f2SEnji Cooper   // WillRepeatedly.
69928f6c2f2SEnji Cooper   MockFunction<Result()> mock;
70028f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call)
70128f6c2f2SEnji Cooper       .WillOnce(Return(std::vector<int>{17, 19, 23}))
70228f6c2f2SEnji Cooper       .WillRepeatedly(Return(std::vector<int>{29, 31, 37}));
703b89a7cc2SEnji Cooper 
70428f6c2f2SEnji Cooper   EXPECT_THAT(mock.AsStdFunction()(),
70528f6c2f2SEnji Cooper               Field(&Result::v, Pointee(ElementsAre(17, 19, 23))));
70628f6c2f2SEnji Cooper 
70728f6c2f2SEnji Cooper   EXPECT_THAT(mock.AsStdFunction()(),
70828f6c2f2SEnji Cooper               Field(&Result::v, Pointee(ElementsAre(29, 31, 37))));
709b89a7cc2SEnji Cooper }
710b89a7cc2SEnji Cooper 
TEST(ReturnTest,PrefersConversionOperator)71128f6c2f2SEnji Cooper TEST(ReturnTest, PrefersConversionOperator) {
71228f6c2f2SEnji Cooper   // Define types In and Out such that:
71328f6c2f2SEnji Cooper   //
71428f6c2f2SEnji Cooper   //  *  In is implicitly convertible to Out.
71528f6c2f2SEnji Cooper   //  *  Out also has an explicit constructor from In.
71628f6c2f2SEnji Cooper   //
71728f6c2f2SEnji Cooper   struct In;
71828f6c2f2SEnji Cooper   struct Out {
71928f6c2f2SEnji Cooper     int x;
72028f6c2f2SEnji Cooper 
72128f6c2f2SEnji Cooper     explicit Out(const int val) : x(val) {}
72228f6c2f2SEnji Cooper     explicit Out(const In&) : x(0) {}
72328f6c2f2SEnji Cooper   };
72428f6c2f2SEnji Cooper 
72528f6c2f2SEnji Cooper   struct In {
72628f6c2f2SEnji Cooper     operator Out() const { return Out{19}; }  // NOLINT
72728f6c2f2SEnji Cooper   };
72828f6c2f2SEnji Cooper 
72928f6c2f2SEnji Cooper   // Assumption check: the C++ language rules are such that a function that
73028f6c2f2SEnji Cooper   // returns Out which uses In a return statement will use the implicit
73128f6c2f2SEnji Cooper   // conversion path rather than the explicit constructor.
73228f6c2f2SEnji Cooper   EXPECT_THAT([]() -> Out { return In(); }(), Field(&Out::x, 19));
73328f6c2f2SEnji Cooper 
73428f6c2f2SEnji Cooper   // Return should work the same way: if the mock function's return type is Out
73528f6c2f2SEnji Cooper   // and we feed Return an In value, then the Out should be created through the
73628f6c2f2SEnji Cooper   // implicit conversion path rather than the explicit constructor.
73728f6c2f2SEnji Cooper   MockFunction<Out()> mock;
73828f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(Return(In()));
73928f6c2f2SEnji Cooper   EXPECT_THAT(mock.AsStdFunction()(), Field(&Out::x, 19));
74028f6c2f2SEnji Cooper }
74128f6c2f2SEnji Cooper 
74228f6c2f2SEnji Cooper // It should be possible to use Return(R) with a mock function result type U
74328f6c2f2SEnji Cooper // that is convertible from const R& but *not* R (such as
74428f6c2f2SEnji Cooper // std::reference_wrapper). This should work for both WillOnce and
74528f6c2f2SEnji Cooper // WillRepeatedly.
TEST(ReturnTest,ConversionRequiresConstLvalueReference)74628f6c2f2SEnji Cooper TEST(ReturnTest, ConversionRequiresConstLvalueReference) {
74728f6c2f2SEnji Cooper   using R = int;
74828f6c2f2SEnji Cooper   using U = std::reference_wrapper<const int>;
74928f6c2f2SEnji Cooper 
75028f6c2f2SEnji Cooper   static_assert(std::is_convertible<const R&, U>::value, "");
75128f6c2f2SEnji Cooper   static_assert(!std::is_convertible<R, U>::value, "");
75228f6c2f2SEnji Cooper 
75328f6c2f2SEnji Cooper   MockFunction<U()> mock;
75428f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(Return(17)).WillRepeatedly(Return(19));
75528f6c2f2SEnji Cooper 
75628f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()());
75728f6c2f2SEnji Cooper   EXPECT_EQ(19, mock.AsStdFunction()());
75828f6c2f2SEnji Cooper }
75928f6c2f2SEnji Cooper 
76028f6c2f2SEnji Cooper // Return(x) should not be usable with a mock function result type that's
76128f6c2f2SEnji Cooper // implicitly convertible from decltype(x) but requires a non-const lvalue
76228f6c2f2SEnji Cooper // reference to the input. It doesn't make sense for the conversion operator to
76328f6c2f2SEnji Cooper // modify the input.
TEST(ReturnTest,ConversionRequiresMutableLvalueReference)76428f6c2f2SEnji Cooper TEST(ReturnTest, ConversionRequiresMutableLvalueReference) {
76528f6c2f2SEnji Cooper   // Set up a type that is implicitly convertible from std::string&, but not
76628f6c2f2SEnji Cooper   // std::string&& or `const std::string&`.
76728f6c2f2SEnji Cooper   //
76828f6c2f2SEnji Cooper   // Avoid asserting about conversion from std::string on MSVC, which seems to
76928f6c2f2SEnji Cooper   // implement std::is_convertible incorrectly in this case.
77028f6c2f2SEnji Cooper   struct S {
77128f6c2f2SEnji Cooper     S(std::string&) {}  // NOLINT
77228f6c2f2SEnji Cooper   };
77328f6c2f2SEnji Cooper 
77428f6c2f2SEnji Cooper   static_assert(std::is_convertible<std::string&, S>::value, "");
77528f6c2f2SEnji Cooper #ifndef _MSC_VER
77628f6c2f2SEnji Cooper   static_assert(!std::is_convertible<std::string&&, S>::value, "");
77728f6c2f2SEnji Cooper #endif
77828f6c2f2SEnji Cooper   static_assert(!std::is_convertible<const std::string&, S>::value, "");
77928f6c2f2SEnji Cooper 
78028f6c2f2SEnji Cooper   // It shouldn't be possible to use the result of Return(std::string) in a
78128f6c2f2SEnji Cooper   // context where an S is needed.
78228f6c2f2SEnji Cooper   //
78328f6c2f2SEnji Cooper   // Here too we disable the assertion for MSVC, since its incorrect
78428f6c2f2SEnji Cooper   // implementation of is_convertible causes our SFINAE to be wrong.
78528f6c2f2SEnji Cooper   using RA = decltype(Return(std::string()));
78628f6c2f2SEnji Cooper 
78728f6c2f2SEnji Cooper   static_assert(!std::is_convertible<RA, Action<S()>>::value, "");
78828f6c2f2SEnji Cooper #ifndef _MSC_VER
78928f6c2f2SEnji Cooper   static_assert(!std::is_convertible<RA, OnceAction<S()>>::value, "");
79028f6c2f2SEnji Cooper #endif
79128f6c2f2SEnji Cooper }
79228f6c2f2SEnji Cooper 
TEST(ReturnTest,MoveOnlyResultType)79328f6c2f2SEnji Cooper TEST(ReturnTest, MoveOnlyResultType) {
79428f6c2f2SEnji Cooper   // Return should support move-only result types when used with WillOnce.
79528f6c2f2SEnji Cooper   {
79628f6c2f2SEnji Cooper     MockFunction<std::unique_ptr<int>()> mock;
79728f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
79828f6c2f2SEnji Cooper         // NOLINTNEXTLINE
79928f6c2f2SEnji Cooper         .WillOnce(Return(std::unique_ptr<int>(new int(17))));
80028f6c2f2SEnji Cooper 
80128f6c2f2SEnji Cooper     EXPECT_THAT(mock.AsStdFunction()(), Pointee(17));
80228f6c2f2SEnji Cooper   }
80328f6c2f2SEnji Cooper 
80428f6c2f2SEnji Cooper   // The result of Return should not be convertible to Action (so it can't be
80528f6c2f2SEnji Cooper   // used with WillRepeatedly).
80628f6c2f2SEnji Cooper   static_assert(!std::is_convertible<decltype(Return(std::unique_ptr<int>())),
80728f6c2f2SEnji Cooper                                      Action<std::unique_ptr<int>()>>::value,
80828f6c2f2SEnji Cooper                 "");
80928f6c2f2SEnji Cooper }
81028f6c2f2SEnji Cooper 
81128f6c2f2SEnji Cooper // Tests that Return(v) is covariant.
812b89a7cc2SEnji Cooper 
813b89a7cc2SEnji Cooper struct Base {
operator ==testing::__anon58a2f1bc0111::Base814b89a7cc2SEnji Cooper   bool operator==(const Base&) { return true; }
815b89a7cc2SEnji Cooper };
816b89a7cc2SEnji Cooper 
817b89a7cc2SEnji Cooper struct Derived : public Base {
operator ==testing::__anon58a2f1bc0111::Derived818b89a7cc2SEnji Cooper   bool operator==(const Derived&) { return true; }
819b89a7cc2SEnji Cooper };
820b89a7cc2SEnji Cooper 
TEST(ReturnTest,IsCovariant)821b89a7cc2SEnji Cooper TEST(ReturnTest, IsCovariant) {
822b89a7cc2SEnji Cooper   Base base;
823b89a7cc2SEnji Cooper   Derived derived;
824b89a7cc2SEnji Cooper   Action<Base*()> ret = Return(&base);
82528f6c2f2SEnji Cooper   EXPECT_EQ(&base, ret.Perform(std::make_tuple()));
826b89a7cc2SEnji Cooper 
827b89a7cc2SEnji Cooper   ret = Return(&derived);
82828f6c2f2SEnji Cooper   EXPECT_EQ(&derived, ret.Perform(std::make_tuple()));
829b89a7cc2SEnji Cooper }
830b89a7cc2SEnji Cooper 
831b89a7cc2SEnji Cooper // Tests that the type of the value passed into Return is converted into T
832b89a7cc2SEnji Cooper // when the action is cast to Action<T(...)> rather than when the action is
833b89a7cc2SEnji Cooper // performed. See comments on testing::internal::ReturnAction in
834b89a7cc2SEnji Cooper // gmock-actions.h for more information.
835b89a7cc2SEnji Cooper class FromType {
836b89a7cc2SEnji Cooper  public:
FromType(bool * is_converted)837b89a7cc2SEnji Cooper   explicit FromType(bool* is_converted) : converted_(is_converted) {}
converted() const838b89a7cc2SEnji Cooper   bool* converted() const { return converted_; }
839b89a7cc2SEnji Cooper 
840b89a7cc2SEnji Cooper  private:
841b89a7cc2SEnji Cooper   bool* const converted_;
842b89a7cc2SEnji Cooper };
843b89a7cc2SEnji Cooper 
844b89a7cc2SEnji Cooper class ToType {
845b89a7cc2SEnji Cooper  public:
846b89a7cc2SEnji Cooper   // Must allow implicit conversion due to use in ImplicitCast_<T>.
ToType(const FromType & x)847b89a7cc2SEnji Cooper   ToType(const FromType& x) { *x.converted() = true; }  // NOLINT
848b89a7cc2SEnji Cooper };
849b89a7cc2SEnji Cooper 
TEST(ReturnTest,ConvertsArgumentWhenConverted)850b89a7cc2SEnji Cooper TEST(ReturnTest, ConvertsArgumentWhenConverted) {
851b89a7cc2SEnji Cooper   bool converted = false;
852b89a7cc2SEnji Cooper   FromType x(&converted);
853b89a7cc2SEnji Cooper   Action<ToType()> action(Return(x));
854b89a7cc2SEnji Cooper   EXPECT_TRUE(converted) << "Return must convert its argument in its own "
855b89a7cc2SEnji Cooper                          << "conversion operator.";
856b89a7cc2SEnji Cooper   converted = false;
85728f6c2f2SEnji Cooper   action.Perform(std::tuple<>());
858b89a7cc2SEnji Cooper   EXPECT_FALSE(converted) << "Action must NOT convert its argument "
859b89a7cc2SEnji Cooper                           << "when performed.";
860b89a7cc2SEnji Cooper }
861b89a7cc2SEnji Cooper 
862b89a7cc2SEnji Cooper // Tests that ReturnNull() returns NULL in a pointer-returning function.
TEST(ReturnNullTest,WorksInPointerReturningFunction)863b89a7cc2SEnji Cooper TEST(ReturnNullTest, WorksInPointerReturningFunction) {
864b89a7cc2SEnji Cooper   const Action<int*()> a1 = ReturnNull();
86528f6c2f2SEnji Cooper   EXPECT_TRUE(a1.Perform(std::make_tuple()) == nullptr);
866b89a7cc2SEnji Cooper 
867b89a7cc2SEnji Cooper   const Action<const char*(bool)> a2 = ReturnNull();  // NOLINT
86828f6c2f2SEnji Cooper   EXPECT_TRUE(a2.Perform(std::make_tuple(true)) == nullptr);
869b89a7cc2SEnji Cooper }
870b89a7cc2SEnji Cooper 
871b89a7cc2SEnji Cooper // Tests that ReturnNull() returns NULL for shared_ptr and unique_ptr returning
872b89a7cc2SEnji Cooper // functions.
TEST(ReturnNullTest,WorksInSmartPointerReturningFunction)873b89a7cc2SEnji Cooper TEST(ReturnNullTest, WorksInSmartPointerReturningFunction) {
874b89a7cc2SEnji Cooper   const Action<std::unique_ptr<const int>()> a1 = ReturnNull();
87528f6c2f2SEnji Cooper   EXPECT_TRUE(a1.Perform(std::make_tuple()) == nullptr);
876b89a7cc2SEnji Cooper 
877b89a7cc2SEnji Cooper   const Action<std::shared_ptr<int>(std::string)> a2 = ReturnNull();
87828f6c2f2SEnji Cooper   EXPECT_TRUE(a2.Perform(std::make_tuple("foo")) == nullptr);
879b89a7cc2SEnji Cooper }
880b89a7cc2SEnji Cooper 
881b89a7cc2SEnji Cooper // Tests that ReturnRef(v) works for reference types.
TEST(ReturnRefTest,WorksForReference)882b89a7cc2SEnji Cooper TEST(ReturnRefTest, WorksForReference) {
883b89a7cc2SEnji Cooper   const int n = 0;
884b89a7cc2SEnji Cooper   const Action<const int&(bool)> ret = ReturnRef(n);  // NOLINT
885b89a7cc2SEnji Cooper 
88628f6c2f2SEnji Cooper   EXPECT_EQ(&n, &ret.Perform(std::make_tuple(true)));
887b89a7cc2SEnji Cooper }
888b89a7cc2SEnji Cooper 
889b89a7cc2SEnji Cooper // Tests that ReturnRef(v) is covariant.
TEST(ReturnRefTest,IsCovariant)890b89a7cc2SEnji Cooper TEST(ReturnRefTest, IsCovariant) {
891b89a7cc2SEnji Cooper   Base base;
892b89a7cc2SEnji Cooper   Derived derived;
893b89a7cc2SEnji Cooper   Action<Base&()> a = ReturnRef(base);
89428f6c2f2SEnji Cooper   EXPECT_EQ(&base, &a.Perform(std::make_tuple()));
895b89a7cc2SEnji Cooper 
896b89a7cc2SEnji Cooper   a = ReturnRef(derived);
89728f6c2f2SEnji Cooper   EXPECT_EQ(&derived, &a.Perform(std::make_tuple()));
89828f6c2f2SEnji Cooper }
89928f6c2f2SEnji Cooper 
90028f6c2f2SEnji Cooper template <typename T, typename = decltype(ReturnRef(std::declval<T&&>()))>
CanCallReturnRef(T &&)90128f6c2f2SEnji Cooper bool CanCallReturnRef(T&&) {
90228f6c2f2SEnji Cooper   return true;
90328f6c2f2SEnji Cooper }
CanCallReturnRef(Unused)90428f6c2f2SEnji Cooper bool CanCallReturnRef(Unused) { return false; }
90528f6c2f2SEnji Cooper 
90628f6c2f2SEnji Cooper // Tests that ReturnRef(v) is working with non-temporaries (T&)
TEST(ReturnRefTest,WorksForNonTemporary)90728f6c2f2SEnji Cooper TEST(ReturnRefTest, WorksForNonTemporary) {
90828f6c2f2SEnji Cooper   int scalar_value = 123;
90928f6c2f2SEnji Cooper   EXPECT_TRUE(CanCallReturnRef(scalar_value));
91028f6c2f2SEnji Cooper 
91128f6c2f2SEnji Cooper   std::string non_scalar_value("ABC");
91228f6c2f2SEnji Cooper   EXPECT_TRUE(CanCallReturnRef(non_scalar_value));
91328f6c2f2SEnji Cooper 
91428f6c2f2SEnji Cooper   const int const_scalar_value{321};
91528f6c2f2SEnji Cooper   EXPECT_TRUE(CanCallReturnRef(const_scalar_value));
91628f6c2f2SEnji Cooper 
91728f6c2f2SEnji Cooper   const std::string const_non_scalar_value("CBA");
91828f6c2f2SEnji Cooper   EXPECT_TRUE(CanCallReturnRef(const_non_scalar_value));
91928f6c2f2SEnji Cooper }
92028f6c2f2SEnji Cooper 
92128f6c2f2SEnji Cooper // Tests that ReturnRef(v) is not working with temporaries (T&&)
TEST(ReturnRefTest,DoesNotWorkForTemporary)92228f6c2f2SEnji Cooper TEST(ReturnRefTest, DoesNotWorkForTemporary) {
92328f6c2f2SEnji Cooper   auto scalar_value = []() -> int { return 123; };
92428f6c2f2SEnji Cooper   EXPECT_FALSE(CanCallReturnRef(scalar_value()));
92528f6c2f2SEnji Cooper 
92628f6c2f2SEnji Cooper   auto non_scalar_value = []() -> std::string { return "ABC"; };
92728f6c2f2SEnji Cooper   EXPECT_FALSE(CanCallReturnRef(non_scalar_value()));
92828f6c2f2SEnji Cooper 
92928f6c2f2SEnji Cooper   // cannot use here callable returning "const scalar type",
93028f6c2f2SEnji Cooper   // because such const for scalar return type is ignored
93128f6c2f2SEnji Cooper   EXPECT_FALSE(CanCallReturnRef(static_cast<const int>(321)));
93228f6c2f2SEnji Cooper 
93328f6c2f2SEnji Cooper   auto const_non_scalar_value = []() -> const std::string { return "CBA"; };
93428f6c2f2SEnji Cooper   EXPECT_FALSE(CanCallReturnRef(const_non_scalar_value()));
935b89a7cc2SEnji Cooper }
936b89a7cc2SEnji Cooper 
937b89a7cc2SEnji Cooper // Tests that ReturnRefOfCopy(v) works for reference types.
TEST(ReturnRefOfCopyTest,WorksForReference)938b89a7cc2SEnji Cooper TEST(ReturnRefOfCopyTest, WorksForReference) {
939b89a7cc2SEnji Cooper   int n = 42;
940b89a7cc2SEnji Cooper   const Action<const int&()> ret = ReturnRefOfCopy(n);
941b89a7cc2SEnji Cooper 
94228f6c2f2SEnji Cooper   EXPECT_NE(&n, &ret.Perform(std::make_tuple()));
94328f6c2f2SEnji Cooper   EXPECT_EQ(42, ret.Perform(std::make_tuple()));
944b89a7cc2SEnji Cooper 
945b89a7cc2SEnji Cooper   n = 43;
94628f6c2f2SEnji Cooper   EXPECT_NE(&n, &ret.Perform(std::make_tuple()));
94728f6c2f2SEnji Cooper   EXPECT_EQ(42, ret.Perform(std::make_tuple()));
948b89a7cc2SEnji Cooper }
949b89a7cc2SEnji Cooper 
950b89a7cc2SEnji Cooper // Tests that ReturnRefOfCopy(v) is covariant.
TEST(ReturnRefOfCopyTest,IsCovariant)951b89a7cc2SEnji Cooper TEST(ReturnRefOfCopyTest, IsCovariant) {
952b89a7cc2SEnji Cooper   Base base;
953b89a7cc2SEnji Cooper   Derived derived;
954b89a7cc2SEnji Cooper   Action<Base&()> a = ReturnRefOfCopy(base);
95528f6c2f2SEnji Cooper   EXPECT_NE(&base, &a.Perform(std::make_tuple()));
956b89a7cc2SEnji Cooper 
957b89a7cc2SEnji Cooper   a = ReturnRefOfCopy(derived);
95828f6c2f2SEnji Cooper   EXPECT_NE(&derived, &a.Perform(std::make_tuple()));
95928f6c2f2SEnji Cooper }
96028f6c2f2SEnji Cooper 
96128f6c2f2SEnji Cooper // Tests that ReturnRoundRobin(v) works with initializer lists
TEST(ReturnRoundRobinTest,WorksForInitList)96228f6c2f2SEnji Cooper TEST(ReturnRoundRobinTest, WorksForInitList) {
96328f6c2f2SEnji Cooper   Action<int()> ret = ReturnRoundRobin({1, 2, 3});
96428f6c2f2SEnji Cooper 
96528f6c2f2SEnji Cooper   EXPECT_EQ(1, ret.Perform(std::make_tuple()));
96628f6c2f2SEnji Cooper   EXPECT_EQ(2, ret.Perform(std::make_tuple()));
96728f6c2f2SEnji Cooper   EXPECT_EQ(3, ret.Perform(std::make_tuple()));
96828f6c2f2SEnji Cooper   EXPECT_EQ(1, ret.Perform(std::make_tuple()));
96928f6c2f2SEnji Cooper   EXPECT_EQ(2, ret.Perform(std::make_tuple()));
97028f6c2f2SEnji Cooper   EXPECT_EQ(3, ret.Perform(std::make_tuple()));
97128f6c2f2SEnji Cooper }
97228f6c2f2SEnji Cooper 
97328f6c2f2SEnji Cooper // Tests that ReturnRoundRobin(v) works with vectors
TEST(ReturnRoundRobinTest,WorksForVector)97428f6c2f2SEnji Cooper TEST(ReturnRoundRobinTest, WorksForVector) {
97528f6c2f2SEnji Cooper   std::vector<double> v = {4.4, 5.5, 6.6};
97628f6c2f2SEnji Cooper   Action<double()> ret = ReturnRoundRobin(v);
97728f6c2f2SEnji Cooper 
97828f6c2f2SEnji Cooper   EXPECT_EQ(4.4, ret.Perform(std::make_tuple()));
97928f6c2f2SEnji Cooper   EXPECT_EQ(5.5, ret.Perform(std::make_tuple()));
98028f6c2f2SEnji Cooper   EXPECT_EQ(6.6, ret.Perform(std::make_tuple()));
98128f6c2f2SEnji Cooper   EXPECT_EQ(4.4, ret.Perform(std::make_tuple()));
98228f6c2f2SEnji Cooper   EXPECT_EQ(5.5, ret.Perform(std::make_tuple()));
98328f6c2f2SEnji Cooper   EXPECT_EQ(6.6, ret.Perform(std::make_tuple()));
984b89a7cc2SEnji Cooper }
985b89a7cc2SEnji Cooper 
986b89a7cc2SEnji Cooper // Tests that DoDefault() does the default action for the mock method.
987b89a7cc2SEnji Cooper 
988b89a7cc2SEnji Cooper class MockClass {
989b89a7cc2SEnji Cooper  public:
99028f6c2f2SEnji Cooper   MockClass() = default;
991b89a7cc2SEnji Cooper 
992b89a7cc2SEnji Cooper   MOCK_METHOD1(IntFunc, int(bool flag));  // NOLINT
993b89a7cc2SEnji Cooper   MOCK_METHOD0(Foo, MyNonDefaultConstructible());
994b89a7cc2SEnji Cooper   MOCK_METHOD0(MakeUnique, std::unique_ptr<int>());
995b89a7cc2SEnji Cooper   MOCK_METHOD0(MakeUniqueBase, std::unique_ptr<Base>());
996b89a7cc2SEnji Cooper   MOCK_METHOD0(MakeVectorUnique, std::vector<std::unique_ptr<int>>());
997b89a7cc2SEnji Cooper   MOCK_METHOD1(TakeUnique, int(std::unique_ptr<int>));
998b89a7cc2SEnji Cooper   MOCK_METHOD2(TakeUnique,
999b89a7cc2SEnji Cooper                int(const std::unique_ptr<int>&, std::unique_ptr<int>));
1000b89a7cc2SEnji Cooper 
1001b89a7cc2SEnji Cooper  private:
100228f6c2f2SEnji Cooper   MockClass(const MockClass&) = delete;
100328f6c2f2SEnji Cooper   MockClass& operator=(const MockClass&) = delete;
1004b89a7cc2SEnji Cooper };
1005b89a7cc2SEnji Cooper 
1006b89a7cc2SEnji Cooper // Tests that DoDefault() returns the built-in default value for the
1007b89a7cc2SEnji Cooper // return type by default.
TEST(DoDefaultTest,ReturnsBuiltInDefaultValueByDefault)1008b89a7cc2SEnji Cooper TEST(DoDefaultTest, ReturnsBuiltInDefaultValueByDefault) {
1009b89a7cc2SEnji Cooper   MockClass mock;
101028f6c2f2SEnji Cooper   EXPECT_CALL(mock, IntFunc(_)).WillOnce(DoDefault());
1011b89a7cc2SEnji Cooper   EXPECT_EQ(0, mock.IntFunc(true));
1012b89a7cc2SEnji Cooper }
1013b89a7cc2SEnji Cooper 
1014b89a7cc2SEnji Cooper // Tests that DoDefault() throws (when exceptions are enabled) or aborts
1015b89a7cc2SEnji Cooper // the process when there is no built-in default value for the return type.
TEST(DoDefaultDeathTest,DiesForUnknowType)1016b89a7cc2SEnji Cooper TEST(DoDefaultDeathTest, DiesForUnknowType) {
1017b89a7cc2SEnji Cooper   MockClass mock;
101828f6c2f2SEnji Cooper   EXPECT_CALL(mock, Foo()).WillRepeatedly(DoDefault());
1019b89a7cc2SEnji Cooper #if GTEST_HAS_EXCEPTIONS
1020b89a7cc2SEnji Cooper   EXPECT_ANY_THROW(mock.Foo());
1021b89a7cc2SEnji Cooper #else
102228f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ mock.Foo(); }, "");
1023b89a7cc2SEnji Cooper #endif
1024b89a7cc2SEnji Cooper }
1025b89a7cc2SEnji Cooper 
1026b89a7cc2SEnji Cooper // Tests that using DoDefault() inside a composite action leads to a
1027b89a7cc2SEnji Cooper // run-time error.
1028b89a7cc2SEnji Cooper 
VoidFunc(bool)1029b89a7cc2SEnji Cooper void VoidFunc(bool /* flag */) {}
1030b89a7cc2SEnji Cooper 
TEST(DoDefaultDeathTest,DiesIfUsedInCompositeAction)1031b89a7cc2SEnji Cooper TEST(DoDefaultDeathTest, DiesIfUsedInCompositeAction) {
1032b89a7cc2SEnji Cooper   MockClass mock;
1033b89a7cc2SEnji Cooper   EXPECT_CALL(mock, IntFunc(_))
103428f6c2f2SEnji Cooper       .WillRepeatedly(DoAll(Invoke(VoidFunc), DoDefault()));
1035b89a7cc2SEnji Cooper 
1036b89a7cc2SEnji Cooper   // Ideally we should verify the error message as well.  Sadly,
1037b89a7cc2SEnji Cooper   // EXPECT_DEATH() can only capture stderr, while Google Mock's
1038b89a7cc2SEnji Cooper   // errors are printed on stdout.  Therefore we have to settle for
1039b89a7cc2SEnji Cooper   // not verifying the message.
104028f6c2f2SEnji Cooper   EXPECT_DEATH_IF_SUPPORTED({ mock.IntFunc(true); }, "");
1041b89a7cc2SEnji Cooper }
1042b89a7cc2SEnji Cooper 
1043b89a7cc2SEnji Cooper // Tests that DoDefault() returns the default value set by
104428f6c2f2SEnji Cooper // DefaultValue<T>::Set() when it's not overridden by an ON_CALL().
TEST(DoDefaultTest,ReturnsUserSpecifiedPerTypeDefaultValueWhenThereIsOne)1045b89a7cc2SEnji Cooper TEST(DoDefaultTest, ReturnsUserSpecifiedPerTypeDefaultValueWhenThereIsOne) {
1046b89a7cc2SEnji Cooper   DefaultValue<int>::Set(1);
1047b89a7cc2SEnji Cooper   MockClass mock;
104828f6c2f2SEnji Cooper   EXPECT_CALL(mock, IntFunc(_)).WillOnce(DoDefault());
1049b89a7cc2SEnji Cooper   EXPECT_EQ(1, mock.IntFunc(false));
1050b89a7cc2SEnji Cooper   DefaultValue<int>::Clear();
1051b89a7cc2SEnji Cooper }
1052b89a7cc2SEnji Cooper 
1053b89a7cc2SEnji Cooper // Tests that DoDefault() does the action specified by ON_CALL().
TEST(DoDefaultTest,DoesWhatOnCallSpecifies)1054b89a7cc2SEnji Cooper TEST(DoDefaultTest, DoesWhatOnCallSpecifies) {
1055b89a7cc2SEnji Cooper   MockClass mock;
105628f6c2f2SEnji Cooper   ON_CALL(mock, IntFunc(_)).WillByDefault(Return(2));
105728f6c2f2SEnji Cooper   EXPECT_CALL(mock, IntFunc(_)).WillOnce(DoDefault());
1058b89a7cc2SEnji Cooper   EXPECT_EQ(2, mock.IntFunc(false));
1059b89a7cc2SEnji Cooper }
1060b89a7cc2SEnji Cooper 
1061b89a7cc2SEnji Cooper // Tests that using DoDefault() in ON_CALL() leads to a run-time failure.
TEST(DoDefaultTest,CannotBeUsedInOnCall)1062b89a7cc2SEnji Cooper TEST(DoDefaultTest, CannotBeUsedInOnCall) {
1063b89a7cc2SEnji Cooper   MockClass mock;
106428f6c2f2SEnji Cooper   EXPECT_NONFATAL_FAILURE(
106528f6c2f2SEnji Cooper       {  // NOLINT
106628f6c2f2SEnji Cooper         ON_CALL(mock, IntFunc(_)).WillByDefault(DoDefault());
106728f6c2f2SEnji Cooper       },
106828f6c2f2SEnji Cooper       "DoDefault() cannot be used in ON_CALL()");
1069b89a7cc2SEnji Cooper }
1070b89a7cc2SEnji Cooper 
1071b89a7cc2SEnji Cooper // Tests that SetArgPointee<N>(v) sets the variable pointed to by
1072b89a7cc2SEnji Cooper // the N-th (0-based) argument to v.
TEST(SetArgPointeeTest,SetsTheNthPointee)1073b89a7cc2SEnji Cooper TEST(SetArgPointeeTest, SetsTheNthPointee) {
1074b89a7cc2SEnji Cooper   typedef void MyFunction(bool, int*, char*);
1075b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgPointee<1>(2);
1076b89a7cc2SEnji Cooper 
1077b89a7cc2SEnji Cooper   int n = 0;
1078b89a7cc2SEnji Cooper   char ch = '\0';
107928f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &n, &ch));
1080b89a7cc2SEnji Cooper   EXPECT_EQ(2, n);
1081b89a7cc2SEnji Cooper   EXPECT_EQ('\0', ch);
1082b89a7cc2SEnji Cooper 
1083b89a7cc2SEnji Cooper   a = SetArgPointee<2>('a');
1084b89a7cc2SEnji Cooper   n = 0;
1085b89a7cc2SEnji Cooper   ch = '\0';
108628f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &n, &ch));
1087b89a7cc2SEnji Cooper   EXPECT_EQ(0, n);
1088b89a7cc2SEnji Cooper   EXPECT_EQ('a', ch);
1089b89a7cc2SEnji Cooper }
1090b89a7cc2SEnji Cooper 
1091b89a7cc2SEnji Cooper // Tests that SetArgPointee<N>() accepts a string literal.
TEST(SetArgPointeeTest,AcceptsStringLiteral)1092b89a7cc2SEnji Cooper TEST(SetArgPointeeTest, AcceptsStringLiteral) {
1093b89a7cc2SEnji Cooper   typedef void MyFunction(std::string*, const char**);
1094b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgPointee<0>("hi");
1095b89a7cc2SEnji Cooper   std::string str;
109628f6c2f2SEnji Cooper   const char* ptr = nullptr;
109728f6c2f2SEnji Cooper   a.Perform(std::make_tuple(&str, &ptr));
1098b89a7cc2SEnji Cooper   EXPECT_EQ("hi", str);
109928f6c2f2SEnji Cooper   EXPECT_TRUE(ptr == nullptr);
1100b89a7cc2SEnji Cooper 
1101b89a7cc2SEnji Cooper   a = SetArgPointee<1>("world");
1102b89a7cc2SEnji Cooper   str = "";
110328f6c2f2SEnji Cooper   a.Perform(std::make_tuple(&str, &ptr));
1104b89a7cc2SEnji Cooper   EXPECT_EQ("", str);
1105b89a7cc2SEnji Cooper   EXPECT_STREQ("world", ptr);
1106b89a7cc2SEnji Cooper }
1107b89a7cc2SEnji Cooper 
TEST(SetArgPointeeTest,AcceptsWideStringLiteral)1108b89a7cc2SEnji Cooper TEST(SetArgPointeeTest, AcceptsWideStringLiteral) {
1109b89a7cc2SEnji Cooper   typedef void MyFunction(const wchar_t**);
1110b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgPointee<0>(L"world");
111128f6c2f2SEnji Cooper   const wchar_t* ptr = nullptr;
111228f6c2f2SEnji Cooper   a.Perform(std::make_tuple(&ptr));
1113b89a7cc2SEnji Cooper   EXPECT_STREQ(L"world", ptr);
1114b89a7cc2SEnji Cooper 
1115b89a7cc2SEnji Cooper #if GTEST_HAS_STD_WSTRING
1116b89a7cc2SEnji Cooper 
1117b89a7cc2SEnji Cooper   typedef void MyStringFunction(std::wstring*);
1118b89a7cc2SEnji Cooper   Action<MyStringFunction> a2 = SetArgPointee<0>(L"world");
1119b89a7cc2SEnji Cooper   std::wstring str = L"";
112028f6c2f2SEnji Cooper   a2.Perform(std::make_tuple(&str));
1121b89a7cc2SEnji Cooper   EXPECT_EQ(L"world", str);
1122b89a7cc2SEnji Cooper 
1123b89a7cc2SEnji Cooper #endif
1124b89a7cc2SEnji Cooper }
1125b89a7cc2SEnji Cooper 
1126b89a7cc2SEnji Cooper // Tests that SetArgPointee<N>() accepts a char pointer.
TEST(SetArgPointeeTest,AcceptsCharPointer)1127b89a7cc2SEnji Cooper TEST(SetArgPointeeTest, AcceptsCharPointer) {
1128b89a7cc2SEnji Cooper   typedef void MyFunction(bool, std::string*, const char**);
1129b89a7cc2SEnji Cooper   const char* const hi = "hi";
1130b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgPointee<1>(hi);
1131b89a7cc2SEnji Cooper   std::string str;
113228f6c2f2SEnji Cooper   const char* ptr = nullptr;
113328f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &str, &ptr));
1134b89a7cc2SEnji Cooper   EXPECT_EQ("hi", str);
113528f6c2f2SEnji Cooper   EXPECT_TRUE(ptr == nullptr);
1136b89a7cc2SEnji Cooper 
1137b89a7cc2SEnji Cooper   char world_array[] = "world";
1138b89a7cc2SEnji Cooper   char* const world = world_array;
1139b89a7cc2SEnji Cooper   a = SetArgPointee<2>(world);
1140b89a7cc2SEnji Cooper   str = "";
114128f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &str, &ptr));
1142b89a7cc2SEnji Cooper   EXPECT_EQ("", str);
1143b89a7cc2SEnji Cooper   EXPECT_EQ(world, ptr);
1144b89a7cc2SEnji Cooper }
1145b89a7cc2SEnji Cooper 
TEST(SetArgPointeeTest,AcceptsWideCharPointer)1146b89a7cc2SEnji Cooper TEST(SetArgPointeeTest, AcceptsWideCharPointer) {
1147b89a7cc2SEnji Cooper   typedef void MyFunction(bool, const wchar_t**);
1148b89a7cc2SEnji Cooper   const wchar_t* const hi = L"hi";
1149b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgPointee<1>(hi);
115028f6c2f2SEnji Cooper   const wchar_t* ptr = nullptr;
115128f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &ptr));
1152b89a7cc2SEnji Cooper   EXPECT_EQ(hi, ptr);
1153b89a7cc2SEnji Cooper 
1154b89a7cc2SEnji Cooper #if GTEST_HAS_STD_WSTRING
1155b89a7cc2SEnji Cooper 
1156b89a7cc2SEnji Cooper   typedef void MyStringFunction(bool, std::wstring*);
1157b89a7cc2SEnji Cooper   wchar_t world_array[] = L"world";
1158b89a7cc2SEnji Cooper   wchar_t* const world = world_array;
1159b89a7cc2SEnji Cooper   Action<MyStringFunction> a2 = SetArgPointee<1>(world);
1160b89a7cc2SEnji Cooper   std::wstring str;
116128f6c2f2SEnji Cooper   a2.Perform(std::make_tuple(true, &str));
1162b89a7cc2SEnji Cooper   EXPECT_EQ(world_array, str);
1163b89a7cc2SEnji Cooper #endif
1164b89a7cc2SEnji Cooper }
1165b89a7cc2SEnji Cooper 
1166b89a7cc2SEnji Cooper // Tests that SetArgumentPointee<N>(v) sets the variable pointed to by
1167b89a7cc2SEnji Cooper // the N-th (0-based) argument to v.
TEST(SetArgumentPointeeTest,SetsTheNthPointee)1168b89a7cc2SEnji Cooper TEST(SetArgumentPointeeTest, SetsTheNthPointee) {
1169b89a7cc2SEnji Cooper   typedef void MyFunction(bool, int*, char*);
1170b89a7cc2SEnji Cooper   Action<MyFunction> a = SetArgumentPointee<1>(2);
1171b89a7cc2SEnji Cooper 
1172b89a7cc2SEnji Cooper   int n = 0;
1173b89a7cc2SEnji Cooper   char ch = '\0';
117428f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &n, &ch));
1175b89a7cc2SEnji Cooper   EXPECT_EQ(2, n);
1176b89a7cc2SEnji Cooper   EXPECT_EQ('\0', ch);
1177b89a7cc2SEnji Cooper 
1178b89a7cc2SEnji Cooper   a = SetArgumentPointee<2>('a');
1179b89a7cc2SEnji Cooper   n = 0;
1180b89a7cc2SEnji Cooper   ch = '\0';
118128f6c2f2SEnji Cooper   a.Perform(std::make_tuple(true, &n, &ch));
1182b89a7cc2SEnji Cooper   EXPECT_EQ(0, n);
1183b89a7cc2SEnji Cooper   EXPECT_EQ('a', ch);
1184b89a7cc2SEnji Cooper }
1185b89a7cc2SEnji Cooper 
1186b89a7cc2SEnji Cooper // Sample functions and functors for testing Invoke() and etc.
Nullary()1187b89a7cc2SEnji Cooper int Nullary() { return 1; }
1188b89a7cc2SEnji Cooper 
1189b89a7cc2SEnji Cooper class NullaryFunctor {
1190b89a7cc2SEnji Cooper  public:
operator ()()1191b89a7cc2SEnji Cooper   int operator()() { return 2; }
1192b89a7cc2SEnji Cooper };
1193b89a7cc2SEnji Cooper 
1194b89a7cc2SEnji Cooper bool g_done = false;
VoidNullary()1195b89a7cc2SEnji Cooper void VoidNullary() { g_done = true; }
1196b89a7cc2SEnji Cooper 
1197b89a7cc2SEnji Cooper class VoidNullaryFunctor {
1198b89a7cc2SEnji Cooper  public:
operator ()()1199b89a7cc2SEnji Cooper   void operator()() { g_done = true; }
1200b89a7cc2SEnji Cooper };
1201b89a7cc2SEnji Cooper 
Short(short n)120228f6c2f2SEnji Cooper short Short(short n) { return n; }  // NOLINT
Char(char ch)120328f6c2f2SEnji Cooper char Char(char ch) { return ch; }
120428f6c2f2SEnji Cooper 
CharPtr(const char * s)120528f6c2f2SEnji Cooper const char* CharPtr(const char* s) { return s; }
120628f6c2f2SEnji Cooper 
Unary(int x)120728f6c2f2SEnji Cooper bool Unary(int x) { return x < 0; }
120828f6c2f2SEnji Cooper 
Binary(const char * input,short n)120928f6c2f2SEnji Cooper const char* Binary(const char* input, short n) { return input + n; }  // NOLINT
121028f6c2f2SEnji Cooper 
VoidBinary(int,char)121128f6c2f2SEnji Cooper void VoidBinary(int, char) { g_done = true; }
121228f6c2f2SEnji Cooper 
Ternary(int x,char y,short z)121328f6c2f2SEnji Cooper int Ternary(int x, char y, short z) { return x + y + z; }  // NOLINT
121428f6c2f2SEnji Cooper 
SumOf4(int a,int b,int c,int d)121528f6c2f2SEnji Cooper int SumOf4(int a, int b, int c, int d) { return a + b + c + d; }
121628f6c2f2SEnji Cooper 
1217b89a7cc2SEnji Cooper class Foo {
1218b89a7cc2SEnji Cooper  public:
Foo()1219b89a7cc2SEnji Cooper   Foo() : value_(123) {}
1220b89a7cc2SEnji Cooper 
Nullary() const1221b89a7cc2SEnji Cooper   int Nullary() const { return value_; }
1222b89a7cc2SEnji Cooper 
1223b89a7cc2SEnji Cooper  private:
1224b89a7cc2SEnji Cooper   int value_;
1225b89a7cc2SEnji Cooper };
1226b89a7cc2SEnji Cooper 
1227b89a7cc2SEnji Cooper // Tests InvokeWithoutArgs(function).
TEST(InvokeWithoutArgsTest,Function)1228b89a7cc2SEnji Cooper TEST(InvokeWithoutArgsTest, Function) {
1229b89a7cc2SEnji Cooper   // As an action that takes one argument.
1230b89a7cc2SEnji Cooper   Action<int(int)> a = InvokeWithoutArgs(Nullary);  // NOLINT
123128f6c2f2SEnji Cooper   EXPECT_EQ(1, a.Perform(std::make_tuple(2)));
1232b89a7cc2SEnji Cooper 
1233b89a7cc2SEnji Cooper   // As an action that takes two arguments.
1234b89a7cc2SEnji Cooper   Action<int(int, double)> a2 = InvokeWithoutArgs(Nullary);  // NOLINT
123528f6c2f2SEnji Cooper   EXPECT_EQ(1, a2.Perform(std::make_tuple(2, 3.5)));
1236b89a7cc2SEnji Cooper 
1237b89a7cc2SEnji Cooper   // As an action that returns void.
1238b89a7cc2SEnji Cooper   Action<void(int)> a3 = InvokeWithoutArgs(VoidNullary);  // NOLINT
1239b89a7cc2SEnji Cooper   g_done = false;
124028f6c2f2SEnji Cooper   a3.Perform(std::make_tuple(1));
1241b89a7cc2SEnji Cooper   EXPECT_TRUE(g_done);
1242b89a7cc2SEnji Cooper }
1243b89a7cc2SEnji Cooper 
1244b89a7cc2SEnji Cooper // Tests InvokeWithoutArgs(functor).
TEST(InvokeWithoutArgsTest,Functor)1245b89a7cc2SEnji Cooper TEST(InvokeWithoutArgsTest, Functor) {
1246b89a7cc2SEnji Cooper   // As an action that takes no argument.
1247b89a7cc2SEnji Cooper   Action<int()> a = InvokeWithoutArgs(NullaryFunctor());  // NOLINT
124828f6c2f2SEnji Cooper   EXPECT_EQ(2, a.Perform(std::make_tuple()));
1249b89a7cc2SEnji Cooper 
1250b89a7cc2SEnji Cooper   // As an action that takes three arguments.
1251b89a7cc2SEnji Cooper   Action<int(int, double, char)> a2 =  // NOLINT
1252b89a7cc2SEnji Cooper       InvokeWithoutArgs(NullaryFunctor());
125328f6c2f2SEnji Cooper   EXPECT_EQ(2, a2.Perform(std::make_tuple(3, 3.5, 'a')));
1254b89a7cc2SEnji Cooper 
1255b89a7cc2SEnji Cooper   // As an action that returns void.
1256b89a7cc2SEnji Cooper   Action<void()> a3 = InvokeWithoutArgs(VoidNullaryFunctor());
1257b89a7cc2SEnji Cooper   g_done = false;
125828f6c2f2SEnji Cooper   a3.Perform(std::make_tuple());
1259b89a7cc2SEnji Cooper   EXPECT_TRUE(g_done);
1260b89a7cc2SEnji Cooper }
1261b89a7cc2SEnji Cooper 
1262b89a7cc2SEnji Cooper // Tests InvokeWithoutArgs(obj_ptr, method).
TEST(InvokeWithoutArgsTest,Method)1263b89a7cc2SEnji Cooper TEST(InvokeWithoutArgsTest, Method) {
1264b89a7cc2SEnji Cooper   Foo foo;
1265b89a7cc2SEnji Cooper   Action<int(bool, char)> a =  // NOLINT
1266b89a7cc2SEnji Cooper       InvokeWithoutArgs(&foo, &Foo::Nullary);
126728f6c2f2SEnji Cooper   EXPECT_EQ(123, a.Perform(std::make_tuple(true, 'a')));
1268b89a7cc2SEnji Cooper }
1269b89a7cc2SEnji Cooper 
1270b89a7cc2SEnji Cooper // Tests using IgnoreResult() on a polymorphic action.
TEST(IgnoreResultTest,PolymorphicAction)1271b89a7cc2SEnji Cooper TEST(IgnoreResultTest, PolymorphicAction) {
1272b89a7cc2SEnji Cooper   Action<void(int)> a = IgnoreResult(Return(5));  // NOLINT
127328f6c2f2SEnji Cooper   a.Perform(std::make_tuple(1));
1274b89a7cc2SEnji Cooper }
1275b89a7cc2SEnji Cooper 
1276b89a7cc2SEnji Cooper // Tests using IgnoreResult() on a monomorphic action.
1277b89a7cc2SEnji Cooper 
ReturnOne()1278b89a7cc2SEnji Cooper int ReturnOne() {
1279b89a7cc2SEnji Cooper   g_done = true;
1280b89a7cc2SEnji Cooper   return 1;
1281b89a7cc2SEnji Cooper }
1282b89a7cc2SEnji Cooper 
TEST(IgnoreResultTest,MonomorphicAction)1283b89a7cc2SEnji Cooper TEST(IgnoreResultTest, MonomorphicAction) {
1284b89a7cc2SEnji Cooper   g_done = false;
1285b89a7cc2SEnji Cooper   Action<void()> a = IgnoreResult(Invoke(ReturnOne));
128628f6c2f2SEnji Cooper   a.Perform(std::make_tuple());
1287b89a7cc2SEnji Cooper   EXPECT_TRUE(g_done);
1288b89a7cc2SEnji Cooper }
1289b89a7cc2SEnji Cooper 
1290b89a7cc2SEnji Cooper // Tests using IgnoreResult() on an action that returns a class type.
1291b89a7cc2SEnji Cooper 
ReturnMyNonDefaultConstructible(double)1292b89a7cc2SEnji Cooper MyNonDefaultConstructible ReturnMyNonDefaultConstructible(double /* x */) {
1293b89a7cc2SEnji Cooper   g_done = true;
1294b89a7cc2SEnji Cooper   return MyNonDefaultConstructible(42);
1295b89a7cc2SEnji Cooper }
1296b89a7cc2SEnji Cooper 
TEST(IgnoreResultTest,ActionReturningClass)1297b89a7cc2SEnji Cooper TEST(IgnoreResultTest, ActionReturningClass) {
1298b89a7cc2SEnji Cooper   g_done = false;
1299b89a7cc2SEnji Cooper   Action<void(int)> a =
1300b89a7cc2SEnji Cooper       IgnoreResult(Invoke(ReturnMyNonDefaultConstructible));  // NOLINT
130128f6c2f2SEnji Cooper   a.Perform(std::make_tuple(2));
1302b89a7cc2SEnji Cooper   EXPECT_TRUE(g_done);
1303b89a7cc2SEnji Cooper }
1304b89a7cc2SEnji Cooper 
TEST(AssignTest,Int)1305b89a7cc2SEnji Cooper TEST(AssignTest, Int) {
1306b89a7cc2SEnji Cooper   int x = 0;
1307b89a7cc2SEnji Cooper   Action<void(int)> a = Assign(&x, 5);
130828f6c2f2SEnji Cooper   a.Perform(std::make_tuple(0));
1309b89a7cc2SEnji Cooper   EXPECT_EQ(5, x);
1310b89a7cc2SEnji Cooper }
1311b89a7cc2SEnji Cooper 
TEST(AssignTest,String)1312b89a7cc2SEnji Cooper TEST(AssignTest, String) {
1313b89a7cc2SEnji Cooper   ::std::string x;
1314b89a7cc2SEnji Cooper   Action<void(void)> a = Assign(&x, "Hello, world");
131528f6c2f2SEnji Cooper   a.Perform(std::make_tuple());
1316b89a7cc2SEnji Cooper   EXPECT_EQ("Hello, world", x);
1317b89a7cc2SEnji Cooper }
1318b89a7cc2SEnji Cooper 
TEST(AssignTest,CompatibleTypes)1319b89a7cc2SEnji Cooper TEST(AssignTest, CompatibleTypes) {
1320b89a7cc2SEnji Cooper   double x = 0;
1321b89a7cc2SEnji Cooper   Action<void(int)> a = Assign(&x, 5);
132228f6c2f2SEnji Cooper   a.Perform(std::make_tuple(0));
1323b89a7cc2SEnji Cooper   EXPECT_DOUBLE_EQ(5, x);
1324b89a7cc2SEnji Cooper }
1325b89a7cc2SEnji Cooper 
132628f6c2f2SEnji Cooper // DoAll should support &&-qualified actions when used with WillOnce.
TEST(DoAll,SupportsRefQualifiedActions)132728f6c2f2SEnji Cooper TEST(DoAll, SupportsRefQualifiedActions) {
132828f6c2f2SEnji Cooper   struct InitialAction {
132928f6c2f2SEnji Cooper     void operator()(const int arg) && { EXPECT_EQ(17, arg); }
133028f6c2f2SEnji Cooper   };
133128f6c2f2SEnji Cooper 
133228f6c2f2SEnji Cooper   struct FinalAction {
133328f6c2f2SEnji Cooper     int operator()() && { return 19; }
133428f6c2f2SEnji Cooper   };
133528f6c2f2SEnji Cooper 
133628f6c2f2SEnji Cooper   MockFunction<int(int)> mock;
133728f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(DoAll(InitialAction{}, FinalAction{}));
133828f6c2f2SEnji Cooper   EXPECT_EQ(19, mock.AsStdFunction()(17));
133928f6c2f2SEnji Cooper }
134028f6c2f2SEnji Cooper 
134128f6c2f2SEnji Cooper // DoAll should never provide rvalue references to the initial actions. If the
134228f6c2f2SEnji Cooper // mock action itself accepts an rvalue reference or a non-scalar object by
134328f6c2f2SEnji Cooper // value then the final action should receive an rvalue reference, but initial
134428f6c2f2SEnji Cooper // actions should receive only lvalue references.
TEST(DoAll,ProvidesLvalueReferencesToInitialActions)134528f6c2f2SEnji Cooper TEST(DoAll, ProvidesLvalueReferencesToInitialActions) {
134628f6c2f2SEnji Cooper   struct Obj {};
134728f6c2f2SEnji Cooper 
134828f6c2f2SEnji Cooper   // Mock action accepts by value: the initial action should be fed a const
134928f6c2f2SEnji Cooper   // lvalue reference, and the final action an rvalue reference.
135028f6c2f2SEnji Cooper   {
135128f6c2f2SEnji Cooper     struct InitialAction {
135228f6c2f2SEnji Cooper       void operator()(Obj&) const { FAIL() << "Unexpected call"; }
135328f6c2f2SEnji Cooper       void operator()(const Obj&) const {}
135428f6c2f2SEnji Cooper       void operator()(Obj&&) const { FAIL() << "Unexpected call"; }
135528f6c2f2SEnji Cooper       void operator()(const Obj&&) const { FAIL() << "Unexpected call"; }
135628f6c2f2SEnji Cooper     };
135728f6c2f2SEnji Cooper 
135828f6c2f2SEnji Cooper     MockFunction<void(Obj)> mock;
135928f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
136028f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](Obj&&) {}))
136128f6c2f2SEnji Cooper         .WillRepeatedly(DoAll(InitialAction{}, InitialAction{}, [](Obj&&) {}));
136228f6c2f2SEnji Cooper 
136328f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
136428f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
136528f6c2f2SEnji Cooper   }
136628f6c2f2SEnji Cooper 
136728f6c2f2SEnji Cooper   // Mock action accepts by const lvalue reference: both actions should receive
136828f6c2f2SEnji Cooper   // a const lvalue reference.
136928f6c2f2SEnji Cooper   {
137028f6c2f2SEnji Cooper     struct InitialAction {
137128f6c2f2SEnji Cooper       void operator()(Obj&) const { FAIL() << "Unexpected call"; }
137228f6c2f2SEnji Cooper       void operator()(const Obj&) const {}
137328f6c2f2SEnji Cooper       void operator()(Obj&&) const { FAIL() << "Unexpected call"; }
137428f6c2f2SEnji Cooper       void operator()(const Obj&&) const { FAIL() << "Unexpected call"; }
137528f6c2f2SEnji Cooper     };
137628f6c2f2SEnji Cooper 
137728f6c2f2SEnji Cooper     MockFunction<void(const Obj&)> mock;
137828f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
137928f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](const Obj&) {}))
138028f6c2f2SEnji Cooper         .WillRepeatedly(
138128f6c2f2SEnji Cooper             DoAll(InitialAction{}, InitialAction{}, [](const Obj&) {}));
138228f6c2f2SEnji Cooper 
138328f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
138428f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
138528f6c2f2SEnji Cooper   }
138628f6c2f2SEnji Cooper 
138728f6c2f2SEnji Cooper   // Mock action accepts by non-const lvalue reference: both actions should get
138828f6c2f2SEnji Cooper   // a non-const lvalue reference if they want them.
138928f6c2f2SEnji Cooper   {
139028f6c2f2SEnji Cooper     struct InitialAction {
139128f6c2f2SEnji Cooper       void operator()(Obj&) const {}
139228f6c2f2SEnji Cooper       void operator()(Obj&&) const { FAIL() << "Unexpected call"; }
139328f6c2f2SEnji Cooper     };
139428f6c2f2SEnji Cooper 
139528f6c2f2SEnji Cooper     MockFunction<void(Obj&)> mock;
139628f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
139728f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](Obj&) {}))
139828f6c2f2SEnji Cooper         .WillRepeatedly(DoAll(InitialAction{}, InitialAction{}, [](Obj&) {}));
139928f6c2f2SEnji Cooper 
140028f6c2f2SEnji Cooper     Obj obj;
140128f6c2f2SEnji Cooper     mock.AsStdFunction()(obj);
140228f6c2f2SEnji Cooper     mock.AsStdFunction()(obj);
140328f6c2f2SEnji Cooper   }
140428f6c2f2SEnji Cooper 
140528f6c2f2SEnji Cooper   // Mock action accepts by rvalue reference: the initial actions should receive
140628f6c2f2SEnji Cooper   // a non-const lvalue reference if it wants it, and the final action an rvalue
140728f6c2f2SEnji Cooper   // reference.
140828f6c2f2SEnji Cooper   {
140928f6c2f2SEnji Cooper     struct InitialAction {
141028f6c2f2SEnji Cooper       void operator()(Obj&) const {}
141128f6c2f2SEnji Cooper       void operator()(Obj&&) const { FAIL() << "Unexpected call"; }
141228f6c2f2SEnji Cooper     };
141328f6c2f2SEnji Cooper 
141428f6c2f2SEnji Cooper     MockFunction<void(Obj&&)> mock;
141528f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
141628f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](Obj&&) {}))
141728f6c2f2SEnji Cooper         .WillRepeatedly(DoAll(InitialAction{}, InitialAction{}, [](Obj&&) {}));
141828f6c2f2SEnji Cooper 
141928f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
142028f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
142128f6c2f2SEnji Cooper   }
142228f6c2f2SEnji Cooper 
142328f6c2f2SEnji Cooper   // &&-qualified initial actions should also be allowed with WillOnce.
142428f6c2f2SEnji Cooper   {
142528f6c2f2SEnji Cooper     struct InitialAction {
142628f6c2f2SEnji Cooper       void operator()(Obj&) && {}
142728f6c2f2SEnji Cooper     };
142828f6c2f2SEnji Cooper 
142928f6c2f2SEnji Cooper     MockFunction<void(Obj&)> mock;
143028f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
143128f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](Obj&) {}));
143228f6c2f2SEnji Cooper 
143328f6c2f2SEnji Cooper     Obj obj;
143428f6c2f2SEnji Cooper     mock.AsStdFunction()(obj);
143528f6c2f2SEnji Cooper   }
143628f6c2f2SEnji Cooper 
143728f6c2f2SEnji Cooper   {
143828f6c2f2SEnji Cooper     struct InitialAction {
143928f6c2f2SEnji Cooper       void operator()(Obj&) && {}
144028f6c2f2SEnji Cooper     };
144128f6c2f2SEnji Cooper 
144228f6c2f2SEnji Cooper     MockFunction<void(Obj&&)> mock;
144328f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
144428f6c2f2SEnji Cooper         .WillOnce(DoAll(InitialAction{}, InitialAction{}, [](Obj&&) {}));
144528f6c2f2SEnji Cooper 
144628f6c2f2SEnji Cooper     mock.AsStdFunction()(Obj{});
144728f6c2f2SEnji Cooper   }
144828f6c2f2SEnji Cooper }
144928f6c2f2SEnji Cooper 
145028f6c2f2SEnji Cooper // DoAll should support being used with type-erased Action objects, both through
145128f6c2f2SEnji Cooper // WillOnce and WillRepeatedly.
TEST(DoAll,SupportsTypeErasedActions)145228f6c2f2SEnji Cooper TEST(DoAll, SupportsTypeErasedActions) {
145328f6c2f2SEnji Cooper   // With only type-erased actions.
145428f6c2f2SEnji Cooper   const Action<void()> initial_action = [] {};
145528f6c2f2SEnji Cooper   const Action<int()> final_action = [] { return 17; };
145628f6c2f2SEnji Cooper 
145728f6c2f2SEnji Cooper   MockFunction<int()> mock;
145828f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call)
145928f6c2f2SEnji Cooper       .WillOnce(DoAll(initial_action, initial_action, final_action))
146028f6c2f2SEnji Cooper       .WillRepeatedly(DoAll(initial_action, initial_action, final_action));
146128f6c2f2SEnji Cooper 
146228f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()());
146328f6c2f2SEnji Cooper 
146428f6c2f2SEnji Cooper   // With &&-qualified and move-only final action.
146528f6c2f2SEnji Cooper   {
146628f6c2f2SEnji Cooper     struct FinalAction {
146728f6c2f2SEnji Cooper       FinalAction() = default;
146828f6c2f2SEnji Cooper       FinalAction(FinalAction&&) = default;
146928f6c2f2SEnji Cooper 
147028f6c2f2SEnji Cooper       int operator()() && { return 17; }
147128f6c2f2SEnji Cooper     };
147228f6c2f2SEnji Cooper 
147328f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call)
147428f6c2f2SEnji Cooper         .WillOnce(DoAll(initial_action, initial_action, FinalAction{}));
147528f6c2f2SEnji Cooper 
147628f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()());
147728f6c2f2SEnji Cooper   }
147828f6c2f2SEnji Cooper }
147928f6c2f2SEnji Cooper 
148028f6c2f2SEnji Cooper // Tests using WithArgs and with an action that takes 1 argument.
TEST(WithArgsTest,OneArg)148128f6c2f2SEnji Cooper TEST(WithArgsTest, OneArg) {
148228f6c2f2SEnji Cooper   Action<bool(double x, int n)> a = WithArgs<1>(Invoke(Unary));  // NOLINT
148328f6c2f2SEnji Cooper   EXPECT_TRUE(a.Perform(std::make_tuple(1.5, -1)));
148428f6c2f2SEnji Cooper   EXPECT_FALSE(a.Perform(std::make_tuple(1.5, 1)));
148528f6c2f2SEnji Cooper }
148628f6c2f2SEnji Cooper 
148728f6c2f2SEnji Cooper // Tests using WithArgs with an action that takes 2 arguments.
TEST(WithArgsTest,TwoArgs)148828f6c2f2SEnji Cooper TEST(WithArgsTest, TwoArgs) {
148928f6c2f2SEnji Cooper   Action<const char*(const char* s, double x, short n)> a =  // NOLINT
149028f6c2f2SEnji Cooper       WithArgs<0, 2>(Invoke(Binary));
149128f6c2f2SEnji Cooper   const char s[] = "Hello";
149228f6c2f2SEnji Cooper   EXPECT_EQ(s + 2, a.Perform(std::make_tuple(CharPtr(s), 0.5, Short(2))));
149328f6c2f2SEnji Cooper }
149428f6c2f2SEnji Cooper 
149528f6c2f2SEnji Cooper struct ConcatAll {
operator ()testing::__anon58a2f1bc0111::ConcatAll149628f6c2f2SEnji Cooper   std::string operator()() const { return {}; }
149728f6c2f2SEnji Cooper   template <typename... I>
operator ()testing::__anon58a2f1bc0111::ConcatAll149828f6c2f2SEnji Cooper   std::string operator()(const char* a, I... i) const {
149928f6c2f2SEnji Cooper     return a + ConcatAll()(i...);
150028f6c2f2SEnji Cooper   }
150128f6c2f2SEnji Cooper };
150228f6c2f2SEnji Cooper 
150328f6c2f2SEnji Cooper // Tests using WithArgs with an action that takes 10 arguments.
TEST(WithArgsTest,TenArgs)150428f6c2f2SEnji Cooper TEST(WithArgsTest, TenArgs) {
150528f6c2f2SEnji Cooper   Action<std::string(const char*, const char*, const char*, const char*)> a =
150628f6c2f2SEnji Cooper       WithArgs<0, 1, 2, 3, 2, 1, 0, 1, 2, 3>(Invoke(ConcatAll{}));
150728f6c2f2SEnji Cooper   EXPECT_EQ("0123210123",
150828f6c2f2SEnji Cooper             a.Perform(std::make_tuple(CharPtr("0"), CharPtr("1"), CharPtr("2"),
150928f6c2f2SEnji Cooper                                       CharPtr("3"))));
151028f6c2f2SEnji Cooper }
151128f6c2f2SEnji Cooper 
151228f6c2f2SEnji Cooper // Tests using WithArgs with an action that is not Invoke().
151328f6c2f2SEnji Cooper class SubtractAction : public ActionInterface<int(int, int)> {
151428f6c2f2SEnji Cooper  public:
Perform(const std::tuple<int,int> & args)151528f6c2f2SEnji Cooper   int Perform(const std::tuple<int, int>& args) override {
151628f6c2f2SEnji Cooper     return std::get<0>(args) - std::get<1>(args);
151728f6c2f2SEnji Cooper   }
151828f6c2f2SEnji Cooper };
151928f6c2f2SEnji Cooper 
TEST(WithArgsTest,NonInvokeAction)152028f6c2f2SEnji Cooper TEST(WithArgsTest, NonInvokeAction) {
152128f6c2f2SEnji Cooper   Action<int(const std::string&, int, int)> a =
152228f6c2f2SEnji Cooper       WithArgs<2, 1>(MakeAction(new SubtractAction));
152328f6c2f2SEnji Cooper   std::tuple<std::string, int, int> dummy =
152428f6c2f2SEnji Cooper       std::make_tuple(std::string("hi"), 2, 10);
152528f6c2f2SEnji Cooper   EXPECT_EQ(8, a.Perform(dummy));
152628f6c2f2SEnji Cooper }
152728f6c2f2SEnji Cooper 
152828f6c2f2SEnji Cooper // Tests using WithArgs to pass all original arguments in the original order.
TEST(WithArgsTest,Identity)152928f6c2f2SEnji Cooper TEST(WithArgsTest, Identity) {
153028f6c2f2SEnji Cooper   Action<int(int x, char y, short z)> a =  // NOLINT
153128f6c2f2SEnji Cooper       WithArgs<0, 1, 2>(Invoke(Ternary));
153228f6c2f2SEnji Cooper   EXPECT_EQ(123, a.Perform(std::make_tuple(100, Char(20), Short(3))));
153328f6c2f2SEnji Cooper }
153428f6c2f2SEnji Cooper 
153528f6c2f2SEnji Cooper // Tests using WithArgs with repeated arguments.
TEST(WithArgsTest,RepeatedArguments)153628f6c2f2SEnji Cooper TEST(WithArgsTest, RepeatedArguments) {
153728f6c2f2SEnji Cooper   Action<int(bool, int m, int n)> a =  // NOLINT
153828f6c2f2SEnji Cooper       WithArgs<1, 1, 1, 1>(Invoke(SumOf4));
153928f6c2f2SEnji Cooper   EXPECT_EQ(4, a.Perform(std::make_tuple(false, 1, 10)));
154028f6c2f2SEnji Cooper }
154128f6c2f2SEnji Cooper 
154228f6c2f2SEnji Cooper // Tests using WithArgs with reversed argument order.
TEST(WithArgsTest,ReversedArgumentOrder)154328f6c2f2SEnji Cooper TEST(WithArgsTest, ReversedArgumentOrder) {
154428f6c2f2SEnji Cooper   Action<const char*(short n, const char* input)> a =  // NOLINT
154528f6c2f2SEnji Cooper       WithArgs<1, 0>(Invoke(Binary));
154628f6c2f2SEnji Cooper   const char s[] = "Hello";
154728f6c2f2SEnji Cooper   EXPECT_EQ(s + 2, a.Perform(std::make_tuple(Short(2), CharPtr(s))));
154828f6c2f2SEnji Cooper }
154928f6c2f2SEnji Cooper 
155028f6c2f2SEnji Cooper // Tests using WithArgs with compatible, but not identical, argument types.
TEST(WithArgsTest,ArgsOfCompatibleTypes)155128f6c2f2SEnji Cooper TEST(WithArgsTest, ArgsOfCompatibleTypes) {
155228f6c2f2SEnji Cooper   Action<long(short x, char y, double z, char c)> a =  // NOLINT
155328f6c2f2SEnji Cooper       WithArgs<0, 1, 3>(Invoke(Ternary));
155428f6c2f2SEnji Cooper   EXPECT_EQ(123,
155528f6c2f2SEnji Cooper             a.Perform(std::make_tuple(Short(100), Char(20), 5.6, Char(3))));
155628f6c2f2SEnji Cooper }
155728f6c2f2SEnji Cooper 
155828f6c2f2SEnji Cooper // Tests using WithArgs with an action that returns void.
TEST(WithArgsTest,VoidAction)155928f6c2f2SEnji Cooper TEST(WithArgsTest, VoidAction) {
156028f6c2f2SEnji Cooper   Action<void(double x, char c, int n)> a = WithArgs<2, 1>(Invoke(VoidBinary));
156128f6c2f2SEnji Cooper   g_done = false;
156228f6c2f2SEnji Cooper   a.Perform(std::make_tuple(1.5, 'a', 3));
156328f6c2f2SEnji Cooper   EXPECT_TRUE(g_done);
156428f6c2f2SEnji Cooper }
156528f6c2f2SEnji Cooper 
TEST(WithArgsTest,ReturnReference)156628f6c2f2SEnji Cooper TEST(WithArgsTest, ReturnReference) {
156728f6c2f2SEnji Cooper   Action<int&(int&, void*)> aa = WithArgs<0>([](int& a) -> int& { return a; });
156828f6c2f2SEnji Cooper   int i = 0;
156928f6c2f2SEnji Cooper   const int& res = aa.Perform(std::forward_as_tuple(i, nullptr));
157028f6c2f2SEnji Cooper   EXPECT_EQ(&i, &res);
157128f6c2f2SEnji Cooper }
157228f6c2f2SEnji Cooper 
TEST(WithArgsTest,InnerActionWithConversion)157328f6c2f2SEnji Cooper TEST(WithArgsTest, InnerActionWithConversion) {
157428f6c2f2SEnji Cooper   Action<Derived*()> inner = [] { return nullptr; };
157528f6c2f2SEnji Cooper 
157628f6c2f2SEnji Cooper   MockFunction<Base*(double)> mock;
157728f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call)
157828f6c2f2SEnji Cooper       .WillOnce(WithoutArgs(inner))
157928f6c2f2SEnji Cooper       .WillRepeatedly(WithoutArgs(inner));
158028f6c2f2SEnji Cooper 
158128f6c2f2SEnji Cooper   EXPECT_EQ(nullptr, mock.AsStdFunction()(1.1));
158228f6c2f2SEnji Cooper   EXPECT_EQ(nullptr, mock.AsStdFunction()(1.1));
158328f6c2f2SEnji Cooper }
158428f6c2f2SEnji Cooper 
158528f6c2f2SEnji Cooper // It should be possible to use an &&-qualified inner action as long as the
158628f6c2f2SEnji Cooper // whole shebang is used as an rvalue with WillOnce.
TEST(WithArgsTest,RefQualifiedInnerAction)158728f6c2f2SEnji Cooper TEST(WithArgsTest, RefQualifiedInnerAction) {
158828f6c2f2SEnji Cooper   struct SomeAction {
158928f6c2f2SEnji Cooper     int operator()(const int arg) && {
159028f6c2f2SEnji Cooper       EXPECT_EQ(17, arg);
159128f6c2f2SEnji Cooper       return 19;
159228f6c2f2SEnji Cooper     }
159328f6c2f2SEnji Cooper   };
159428f6c2f2SEnji Cooper 
159528f6c2f2SEnji Cooper   MockFunction<int(int, int)> mock;
159628f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(WithArg<1>(SomeAction{}));
159728f6c2f2SEnji Cooper   EXPECT_EQ(19, mock.AsStdFunction()(0, 17));
159828f6c2f2SEnji Cooper }
159928f6c2f2SEnji Cooper 
160028f6c2f2SEnji Cooper #ifndef GTEST_OS_WINDOWS_MOBILE
1601b89a7cc2SEnji Cooper 
1602b89a7cc2SEnji Cooper class SetErrnoAndReturnTest : public testing::Test {
1603b89a7cc2SEnji Cooper  protected:
SetUp()160428f6c2f2SEnji Cooper   void SetUp() override { errno = 0; }
TearDown()160528f6c2f2SEnji Cooper   void TearDown() override { errno = 0; }
1606b89a7cc2SEnji Cooper };
1607b89a7cc2SEnji Cooper 
TEST_F(SetErrnoAndReturnTest,Int)1608b89a7cc2SEnji Cooper TEST_F(SetErrnoAndReturnTest, Int) {
1609b89a7cc2SEnji Cooper   Action<int(void)> a = SetErrnoAndReturn(ENOTTY, -5);
161028f6c2f2SEnji Cooper   EXPECT_EQ(-5, a.Perform(std::make_tuple()));
1611b89a7cc2SEnji Cooper   EXPECT_EQ(ENOTTY, errno);
1612b89a7cc2SEnji Cooper }
1613b89a7cc2SEnji Cooper 
TEST_F(SetErrnoAndReturnTest,Ptr)1614b89a7cc2SEnji Cooper TEST_F(SetErrnoAndReturnTest, Ptr) {
1615b89a7cc2SEnji Cooper   int x;
1616b89a7cc2SEnji Cooper   Action<int*(void)> a = SetErrnoAndReturn(ENOTTY, &x);
161728f6c2f2SEnji Cooper   EXPECT_EQ(&x, a.Perform(std::make_tuple()));
1618b89a7cc2SEnji Cooper   EXPECT_EQ(ENOTTY, errno);
1619b89a7cc2SEnji Cooper }
1620b89a7cc2SEnji Cooper 
TEST_F(SetErrnoAndReturnTest,CompatibleTypes)1621b89a7cc2SEnji Cooper TEST_F(SetErrnoAndReturnTest, CompatibleTypes) {
1622b89a7cc2SEnji Cooper   Action<double()> a = SetErrnoAndReturn(EINVAL, 5);
162328f6c2f2SEnji Cooper   EXPECT_DOUBLE_EQ(5.0, a.Perform(std::make_tuple()));
1624b89a7cc2SEnji Cooper   EXPECT_EQ(EINVAL, errno);
1625b89a7cc2SEnji Cooper }
1626b89a7cc2SEnji Cooper 
1627b89a7cc2SEnji Cooper #endif  // !GTEST_OS_WINDOWS_MOBILE
1628b89a7cc2SEnji Cooper 
1629b89a7cc2SEnji Cooper // Tests ByRef().
1630b89a7cc2SEnji Cooper 
163128f6c2f2SEnji Cooper // Tests that the result of ByRef() is copyable.
TEST(ByRefTest,IsCopyable)1632b89a7cc2SEnji Cooper TEST(ByRefTest, IsCopyable) {
1633b89a7cc2SEnji Cooper   const std::string s1 = "Hi";
1634b89a7cc2SEnji Cooper   const std::string s2 = "Hello";
1635b89a7cc2SEnji Cooper 
163628f6c2f2SEnji Cooper   auto ref_wrapper = ByRef(s1);
1637b89a7cc2SEnji Cooper   const std::string& r1 = ref_wrapper;
1638b89a7cc2SEnji Cooper   EXPECT_EQ(&s1, &r1);
1639b89a7cc2SEnji Cooper 
1640b89a7cc2SEnji Cooper   // Assigns a new value to ref_wrapper.
1641b89a7cc2SEnji Cooper   ref_wrapper = ByRef(s2);
1642b89a7cc2SEnji Cooper   const std::string& r2 = ref_wrapper;
1643b89a7cc2SEnji Cooper   EXPECT_EQ(&s2, &r2);
1644b89a7cc2SEnji Cooper 
164528f6c2f2SEnji Cooper   auto ref_wrapper1 = ByRef(s1);
1646b89a7cc2SEnji Cooper   // Copies ref_wrapper1 to ref_wrapper.
1647b89a7cc2SEnji Cooper   ref_wrapper = ref_wrapper1;
1648b89a7cc2SEnji Cooper   const std::string& r3 = ref_wrapper;
1649b89a7cc2SEnji Cooper   EXPECT_EQ(&s1, &r3);
1650b89a7cc2SEnji Cooper }
1651b89a7cc2SEnji Cooper 
1652b89a7cc2SEnji Cooper // Tests using ByRef() on a const value.
TEST(ByRefTest,ConstValue)1653b89a7cc2SEnji Cooper TEST(ByRefTest, ConstValue) {
1654b89a7cc2SEnji Cooper   const int n = 0;
1655b89a7cc2SEnji Cooper   // int& ref = ByRef(n);  // This shouldn't compile - we have a
1656b89a7cc2SEnji Cooper   // negative compilation test to catch it.
1657b89a7cc2SEnji Cooper   const int& const_ref = ByRef(n);
1658b89a7cc2SEnji Cooper   EXPECT_EQ(&n, &const_ref);
1659b89a7cc2SEnji Cooper }
1660b89a7cc2SEnji Cooper 
1661b89a7cc2SEnji Cooper // Tests using ByRef() on a non-const value.
TEST(ByRefTest,NonConstValue)1662b89a7cc2SEnji Cooper TEST(ByRefTest, NonConstValue) {
1663b89a7cc2SEnji Cooper   int n = 0;
1664b89a7cc2SEnji Cooper 
1665b89a7cc2SEnji Cooper   // ByRef(n) can be used as either an int&,
1666b89a7cc2SEnji Cooper   int& ref = ByRef(n);
1667b89a7cc2SEnji Cooper   EXPECT_EQ(&n, &ref);
1668b89a7cc2SEnji Cooper 
1669b89a7cc2SEnji Cooper   // or a const int&.
1670b89a7cc2SEnji Cooper   const int& const_ref = ByRef(n);
1671b89a7cc2SEnji Cooper   EXPECT_EQ(&n, &const_ref);
1672b89a7cc2SEnji Cooper }
1673b89a7cc2SEnji Cooper 
1674b89a7cc2SEnji Cooper // Tests explicitly specifying the type when using ByRef().
TEST(ByRefTest,ExplicitType)1675b89a7cc2SEnji Cooper TEST(ByRefTest, ExplicitType) {
1676b89a7cc2SEnji Cooper   int n = 0;
1677b89a7cc2SEnji Cooper   const int& r1 = ByRef<const int>(n);
1678b89a7cc2SEnji Cooper   EXPECT_EQ(&n, &r1);
1679b89a7cc2SEnji Cooper 
1680b89a7cc2SEnji Cooper   // ByRef<char>(n);  // This shouldn't compile - we have a negative
1681b89a7cc2SEnji Cooper   // compilation test to catch it.
1682b89a7cc2SEnji Cooper 
1683b89a7cc2SEnji Cooper   Derived d;
1684b89a7cc2SEnji Cooper   Derived& r2 = ByRef<Derived>(d);
1685b89a7cc2SEnji Cooper   EXPECT_EQ(&d, &r2);
1686b89a7cc2SEnji Cooper 
1687b89a7cc2SEnji Cooper   const Derived& r3 = ByRef<const Derived>(d);
1688b89a7cc2SEnji Cooper   EXPECT_EQ(&d, &r3);
1689b89a7cc2SEnji Cooper 
1690b89a7cc2SEnji Cooper   Base& r4 = ByRef<Base>(d);
1691b89a7cc2SEnji Cooper   EXPECT_EQ(&d, &r4);
1692b89a7cc2SEnji Cooper 
1693b89a7cc2SEnji Cooper   const Base& r5 = ByRef<const Base>(d);
1694b89a7cc2SEnji Cooper   EXPECT_EQ(&d, &r5);
1695b89a7cc2SEnji Cooper 
1696b89a7cc2SEnji Cooper   // The following shouldn't compile - we have a negative compilation
1697b89a7cc2SEnji Cooper   // test for it.
1698b89a7cc2SEnji Cooper   //
1699b89a7cc2SEnji Cooper   // Base b;
1700b89a7cc2SEnji Cooper   // ByRef<Derived>(b);
1701b89a7cc2SEnji Cooper }
1702b89a7cc2SEnji Cooper 
1703b89a7cc2SEnji Cooper // Tests that Google Mock prints expression ByRef(x) as a reference to x.
TEST(ByRefTest,PrintsCorrectly)1704b89a7cc2SEnji Cooper TEST(ByRefTest, PrintsCorrectly) {
1705b89a7cc2SEnji Cooper   int n = 42;
1706b89a7cc2SEnji Cooper   ::std::stringstream expected, actual;
1707b89a7cc2SEnji Cooper   testing::internal::UniversalPrinter<const int&>::Print(n, &expected);
1708b89a7cc2SEnji Cooper   testing::internal::UniversalPrint(ByRef(n), &actual);
1709b89a7cc2SEnji Cooper   EXPECT_EQ(expected.str(), actual.str());
1710b89a7cc2SEnji Cooper }
1711b89a7cc2SEnji Cooper 
171228f6c2f2SEnji Cooper struct UnaryConstructorClass {
UnaryConstructorClasstesting::__anon58a2f1bc0111::UnaryConstructorClass171328f6c2f2SEnji Cooper   explicit UnaryConstructorClass(int v) : value(v) {}
171428f6c2f2SEnji Cooper   int value;
171528f6c2f2SEnji Cooper };
1716b89a7cc2SEnji Cooper 
171728f6c2f2SEnji Cooper // Tests using ReturnNew() with a unary constructor.
TEST(ReturnNewTest,Unary)171828f6c2f2SEnji Cooper TEST(ReturnNewTest, Unary) {
171928f6c2f2SEnji Cooper   Action<UnaryConstructorClass*()> a = ReturnNew<UnaryConstructorClass>(4000);
172028f6c2f2SEnji Cooper   UnaryConstructorClass* c = a.Perform(std::make_tuple());
172128f6c2f2SEnji Cooper   EXPECT_EQ(4000, c->value);
172228f6c2f2SEnji Cooper   delete c;
1723b89a7cc2SEnji Cooper }
1724b89a7cc2SEnji Cooper 
TEST(ReturnNewTest,UnaryWorksWhenMockMethodHasArgs)172528f6c2f2SEnji Cooper TEST(ReturnNewTest, UnaryWorksWhenMockMethodHasArgs) {
172628f6c2f2SEnji Cooper   Action<UnaryConstructorClass*(bool, int)> a =
172728f6c2f2SEnji Cooper       ReturnNew<UnaryConstructorClass>(4000);
172828f6c2f2SEnji Cooper   UnaryConstructorClass* c = a.Perform(std::make_tuple(false, 5));
172928f6c2f2SEnji Cooper   EXPECT_EQ(4000, c->value);
173028f6c2f2SEnji Cooper   delete c;
173128f6c2f2SEnji Cooper }
173228f6c2f2SEnji Cooper 
TEST(ReturnNewTest,UnaryWorksWhenMockMethodReturnsPointerToConst)173328f6c2f2SEnji Cooper TEST(ReturnNewTest, UnaryWorksWhenMockMethodReturnsPointerToConst) {
173428f6c2f2SEnji Cooper   Action<const UnaryConstructorClass*()> a =
173528f6c2f2SEnji Cooper       ReturnNew<UnaryConstructorClass>(4000);
173628f6c2f2SEnji Cooper   const UnaryConstructorClass* c = a.Perform(std::make_tuple());
173728f6c2f2SEnji Cooper   EXPECT_EQ(4000, c->value);
173828f6c2f2SEnji Cooper   delete c;
173928f6c2f2SEnji Cooper }
174028f6c2f2SEnji Cooper 
174128f6c2f2SEnji Cooper class TenArgConstructorClass {
174228f6c2f2SEnji Cooper  public:
TenArgConstructorClass(int a1,int a2,int a3,int a4,int a5,int a6,int a7,int a8,int a9,int a10)174328f6c2f2SEnji Cooper   TenArgConstructorClass(int a1, int a2, int a3, int a4, int a5, int a6, int a7,
174428f6c2f2SEnji Cooper                          int a8, int a9, int a10)
174528f6c2f2SEnji Cooper       : value_(a1 + a2 + a3 + a4 + a5 + a6 + a7 + a8 + a9 + a10) {}
174628f6c2f2SEnji Cooper   int value_;
174728f6c2f2SEnji Cooper };
174828f6c2f2SEnji Cooper 
174928f6c2f2SEnji Cooper // Tests using ReturnNew() with a 10-argument constructor.
TEST(ReturnNewTest,ConstructorThatTakes10Arguments)175028f6c2f2SEnji Cooper TEST(ReturnNewTest, ConstructorThatTakes10Arguments) {
175128f6c2f2SEnji Cooper   Action<TenArgConstructorClass*()> a = ReturnNew<TenArgConstructorClass>(
175228f6c2f2SEnji Cooper       1000000000, 200000000, 30000000, 4000000, 500000, 60000, 7000, 800, 90,
175328f6c2f2SEnji Cooper       0);
175428f6c2f2SEnji Cooper   TenArgConstructorClass* c = a.Perform(std::make_tuple());
175528f6c2f2SEnji Cooper   EXPECT_EQ(1234567890, c->value_);
175628f6c2f2SEnji Cooper   delete c;
175728f6c2f2SEnji Cooper }
175828f6c2f2SEnji Cooper 
UniquePtrSource()175928f6c2f2SEnji Cooper std::unique_ptr<int> UniquePtrSource() { return std::make_unique<int>(19); }
176028f6c2f2SEnji Cooper 
VectorUniquePtrSource()1761b89a7cc2SEnji Cooper std::vector<std::unique_ptr<int>> VectorUniquePtrSource() {
1762b89a7cc2SEnji Cooper   std::vector<std::unique_ptr<int>> out;
1763b89a7cc2SEnji Cooper   out.emplace_back(new int(7));
1764b89a7cc2SEnji Cooper   return out;
1765b89a7cc2SEnji Cooper }
1766b89a7cc2SEnji Cooper 
TEST(MockMethodTest,CanReturnMoveOnlyValue_Return)1767b89a7cc2SEnji Cooper TEST(MockMethodTest, CanReturnMoveOnlyValue_Return) {
1768b89a7cc2SEnji Cooper   MockClass mock;
1769b89a7cc2SEnji Cooper   std::unique_ptr<int> i(new int(19));
1770b89a7cc2SEnji Cooper   EXPECT_CALL(mock, MakeUnique()).WillOnce(Return(ByMove(std::move(i))));
1771b89a7cc2SEnji Cooper   EXPECT_CALL(mock, MakeVectorUnique())
1772b89a7cc2SEnji Cooper       .WillOnce(Return(ByMove(VectorUniquePtrSource())));
1773b89a7cc2SEnji Cooper   Derived* d = new Derived;
1774b89a7cc2SEnji Cooper   EXPECT_CALL(mock, MakeUniqueBase())
1775b89a7cc2SEnji Cooper       .WillOnce(Return(ByMove(std::unique_ptr<Derived>(d))));
1776b89a7cc2SEnji Cooper 
1777b89a7cc2SEnji Cooper   std::unique_ptr<int> result1 = mock.MakeUnique();
1778b89a7cc2SEnji Cooper   EXPECT_EQ(19, *result1);
1779b89a7cc2SEnji Cooper 
1780b89a7cc2SEnji Cooper   std::vector<std::unique_ptr<int>> vresult = mock.MakeVectorUnique();
1781b89a7cc2SEnji Cooper   EXPECT_EQ(1u, vresult.size());
1782b89a7cc2SEnji Cooper   EXPECT_NE(nullptr, vresult[0]);
1783b89a7cc2SEnji Cooper   EXPECT_EQ(7, *vresult[0]);
1784b89a7cc2SEnji Cooper 
1785b89a7cc2SEnji Cooper   std::unique_ptr<Base> result2 = mock.MakeUniqueBase();
1786b89a7cc2SEnji Cooper   EXPECT_EQ(d, result2.get());
1787b89a7cc2SEnji Cooper }
1788b89a7cc2SEnji Cooper 
TEST(MockMethodTest,CanReturnMoveOnlyValue_DoAllReturn)1789b89a7cc2SEnji Cooper TEST(MockMethodTest, CanReturnMoveOnlyValue_DoAllReturn) {
1790b89a7cc2SEnji Cooper   testing::MockFunction<void()> mock_function;
1791b89a7cc2SEnji Cooper   MockClass mock;
1792b89a7cc2SEnji Cooper   std::unique_ptr<int> i(new int(19));
1793b89a7cc2SEnji Cooper   EXPECT_CALL(mock_function, Call());
179428f6c2f2SEnji Cooper   EXPECT_CALL(mock, MakeUnique())
179528f6c2f2SEnji Cooper       .WillOnce(DoAll(InvokeWithoutArgs(&mock_function,
179628f6c2f2SEnji Cooper                                         &testing::MockFunction<void()>::Call),
1797b89a7cc2SEnji Cooper                       Return(ByMove(std::move(i)))));
1798b89a7cc2SEnji Cooper 
1799b89a7cc2SEnji Cooper   std::unique_ptr<int> result1 = mock.MakeUnique();
1800b89a7cc2SEnji Cooper   EXPECT_EQ(19, *result1);
1801b89a7cc2SEnji Cooper }
1802b89a7cc2SEnji Cooper 
TEST(MockMethodTest,CanReturnMoveOnlyValue_Invoke)1803b89a7cc2SEnji Cooper TEST(MockMethodTest, CanReturnMoveOnlyValue_Invoke) {
1804b89a7cc2SEnji Cooper   MockClass mock;
1805b89a7cc2SEnji Cooper 
1806b89a7cc2SEnji Cooper   // Check default value
180728f6c2f2SEnji Cooper   DefaultValue<std::unique_ptr<int>>::SetFactory(
180828f6c2f2SEnji Cooper       [] { return std::make_unique<int>(42); });
1809b89a7cc2SEnji Cooper   EXPECT_EQ(42, *mock.MakeUnique());
1810b89a7cc2SEnji Cooper 
1811b89a7cc2SEnji Cooper   EXPECT_CALL(mock, MakeUnique()).WillRepeatedly(Invoke(UniquePtrSource));
1812b89a7cc2SEnji Cooper   EXPECT_CALL(mock, MakeVectorUnique())
1813b89a7cc2SEnji Cooper       .WillRepeatedly(Invoke(VectorUniquePtrSource));
1814b89a7cc2SEnji Cooper   std::unique_ptr<int> result1 = mock.MakeUnique();
1815b89a7cc2SEnji Cooper   EXPECT_EQ(19, *result1);
1816b89a7cc2SEnji Cooper   std::unique_ptr<int> result2 = mock.MakeUnique();
1817b89a7cc2SEnji Cooper   EXPECT_EQ(19, *result2);
1818b89a7cc2SEnji Cooper   EXPECT_NE(result1, result2);
1819b89a7cc2SEnji Cooper 
1820b89a7cc2SEnji Cooper   std::vector<std::unique_ptr<int>> vresult = mock.MakeVectorUnique();
1821b89a7cc2SEnji Cooper   EXPECT_EQ(1u, vresult.size());
1822b89a7cc2SEnji Cooper   EXPECT_NE(nullptr, vresult[0]);
1823b89a7cc2SEnji Cooper   EXPECT_EQ(7, *vresult[0]);
1824b89a7cc2SEnji Cooper }
1825b89a7cc2SEnji Cooper 
TEST(MockMethodTest,CanTakeMoveOnlyValue)1826b89a7cc2SEnji Cooper TEST(MockMethodTest, CanTakeMoveOnlyValue) {
1827b89a7cc2SEnji Cooper   MockClass mock;
182828f6c2f2SEnji Cooper   auto make = [](int i) { return std::make_unique<int>(i); };
1829b89a7cc2SEnji Cooper 
1830b89a7cc2SEnji Cooper   EXPECT_CALL(mock, TakeUnique(_)).WillRepeatedly([](std::unique_ptr<int> i) {
1831b89a7cc2SEnji Cooper     return *i;
1832b89a7cc2SEnji Cooper   });
1833b89a7cc2SEnji Cooper   // DoAll() does not compile, since it would move from its arguments twice.
1834b89a7cc2SEnji Cooper   // EXPECT_CALL(mock, TakeUnique(_, _))
1835b89a7cc2SEnji Cooper   //     .WillRepeatedly(DoAll(Invoke([](std::unique_ptr<int> j) {}),
1836b89a7cc2SEnji Cooper   //     Return(1)));
1837b89a7cc2SEnji Cooper   EXPECT_CALL(mock, TakeUnique(testing::Pointee(7)))
1838b89a7cc2SEnji Cooper       .WillOnce(Return(-7))
1839b89a7cc2SEnji Cooper       .RetiresOnSaturation();
1840b89a7cc2SEnji Cooper   EXPECT_CALL(mock, TakeUnique(testing::IsNull()))
1841b89a7cc2SEnji Cooper       .WillOnce(Return(-1))
1842b89a7cc2SEnji Cooper       .RetiresOnSaturation();
1843b89a7cc2SEnji Cooper 
1844b89a7cc2SEnji Cooper   EXPECT_EQ(5, mock.TakeUnique(make(5)));
1845b89a7cc2SEnji Cooper   EXPECT_EQ(-7, mock.TakeUnique(make(7)));
1846b89a7cc2SEnji Cooper   EXPECT_EQ(7, mock.TakeUnique(make(7)));
1847b89a7cc2SEnji Cooper   EXPECT_EQ(7, mock.TakeUnique(make(7)));
1848b89a7cc2SEnji Cooper   EXPECT_EQ(-1, mock.TakeUnique({}));
1849b89a7cc2SEnji Cooper 
1850b89a7cc2SEnji Cooper   // Some arguments are moved, some passed by reference.
1851b89a7cc2SEnji Cooper   auto lvalue = make(6);
1852b89a7cc2SEnji Cooper   EXPECT_CALL(mock, TakeUnique(_, _))
1853b89a7cc2SEnji Cooper       .WillOnce([](const std::unique_ptr<int>& i, std::unique_ptr<int> j) {
1854b89a7cc2SEnji Cooper         return *i * *j;
1855b89a7cc2SEnji Cooper       });
1856b89a7cc2SEnji Cooper   EXPECT_EQ(42, mock.TakeUnique(lvalue, make(7)));
1857b89a7cc2SEnji Cooper 
1858b89a7cc2SEnji Cooper   // The unique_ptr can be saved by the action.
1859b89a7cc2SEnji Cooper   std::unique_ptr<int> saved;
1860b89a7cc2SEnji Cooper   EXPECT_CALL(mock, TakeUnique(_)).WillOnce([&saved](std::unique_ptr<int> i) {
1861b89a7cc2SEnji Cooper     saved = std::move(i);
1862b89a7cc2SEnji Cooper     return 0;
1863b89a7cc2SEnji Cooper   });
1864b89a7cc2SEnji Cooper   EXPECT_EQ(0, mock.TakeUnique(make(42)));
1865b89a7cc2SEnji Cooper   EXPECT_EQ(42, *saved);
1866b89a7cc2SEnji Cooper }
1867b89a7cc2SEnji Cooper 
186828f6c2f2SEnji Cooper // It should be possible to use callables with an &&-qualified call operator
186928f6c2f2SEnji Cooper // with WillOnce, since they will be called only once. This allows actions to
187028f6c2f2SEnji Cooper // contain and manipulate move-only types.
TEST(MockMethodTest,ActionHasRvalueRefQualifiedCallOperator)187128f6c2f2SEnji Cooper TEST(MockMethodTest, ActionHasRvalueRefQualifiedCallOperator) {
187228f6c2f2SEnji Cooper   struct Return17 {
187328f6c2f2SEnji Cooper     int operator()() && { return 17; }
187428f6c2f2SEnji Cooper   };
1875b89a7cc2SEnji Cooper 
187628f6c2f2SEnji Cooper   // Action is directly compatible with mocked function type.
187728f6c2f2SEnji Cooper   {
187828f6c2f2SEnji Cooper     MockFunction<int()> mock;
187928f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(Return17());
188028f6c2f2SEnji Cooper 
188128f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()());
188228f6c2f2SEnji Cooper   }
188328f6c2f2SEnji Cooper 
188428f6c2f2SEnji Cooper   // Action doesn't want mocked function arguments.
188528f6c2f2SEnji Cooper   {
188628f6c2f2SEnji Cooper     MockFunction<int(int)> mock;
188728f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(Return17());
188828f6c2f2SEnji Cooper 
188928f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()(0));
189028f6c2f2SEnji Cooper   }
189128f6c2f2SEnji Cooper }
189228f6c2f2SEnji Cooper 
189328f6c2f2SEnji Cooper // Edge case: if an action has both a const-qualified and an &&-qualified call
189428f6c2f2SEnji Cooper // operator, there should be no "ambiguous call" errors. The &&-qualified
189528f6c2f2SEnji Cooper // operator should be used by WillOnce (since it doesn't need to retain the
189628f6c2f2SEnji Cooper // action beyond one call), and the const-qualified one by WillRepeatedly.
TEST(MockMethodTest,ActionHasMultipleCallOperators)189728f6c2f2SEnji Cooper TEST(MockMethodTest, ActionHasMultipleCallOperators) {
189828f6c2f2SEnji Cooper   struct ReturnInt {
189928f6c2f2SEnji Cooper     int operator()() && { return 17; }
190028f6c2f2SEnji Cooper     int operator()() const& { return 19; }
190128f6c2f2SEnji Cooper   };
190228f6c2f2SEnji Cooper 
190328f6c2f2SEnji Cooper   // Directly compatible with mocked function type.
190428f6c2f2SEnji Cooper   {
190528f6c2f2SEnji Cooper     MockFunction<int()> mock;
190628f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(ReturnInt()).WillRepeatedly(ReturnInt());
190728f6c2f2SEnji Cooper 
190828f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()());
190928f6c2f2SEnji Cooper     EXPECT_EQ(19, mock.AsStdFunction()());
191028f6c2f2SEnji Cooper     EXPECT_EQ(19, mock.AsStdFunction()());
191128f6c2f2SEnji Cooper   }
191228f6c2f2SEnji Cooper 
191328f6c2f2SEnji Cooper   // Ignores function arguments.
191428f6c2f2SEnji Cooper   {
191528f6c2f2SEnji Cooper     MockFunction<int(int)> mock;
191628f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(ReturnInt()).WillRepeatedly(ReturnInt());
191728f6c2f2SEnji Cooper 
191828f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()(0));
191928f6c2f2SEnji Cooper     EXPECT_EQ(19, mock.AsStdFunction()(0));
192028f6c2f2SEnji Cooper     EXPECT_EQ(19, mock.AsStdFunction()(0));
192128f6c2f2SEnji Cooper   }
192228f6c2f2SEnji Cooper }
192328f6c2f2SEnji Cooper 
192428f6c2f2SEnji Cooper // WillOnce should have no problem coping with a move-only action, whether it is
192528f6c2f2SEnji Cooper // &&-qualified or not.
TEST(MockMethodTest,MoveOnlyAction)192628f6c2f2SEnji Cooper TEST(MockMethodTest, MoveOnlyAction) {
192728f6c2f2SEnji Cooper   // &&-qualified
192828f6c2f2SEnji Cooper   {
192928f6c2f2SEnji Cooper     struct Return17 {
193028f6c2f2SEnji Cooper       Return17() = default;
193128f6c2f2SEnji Cooper       Return17(Return17&&) = default;
193228f6c2f2SEnji Cooper 
193328f6c2f2SEnji Cooper       Return17(const Return17&) = delete;
193428f6c2f2SEnji Cooper       Return17 operator=(const Return17&) = delete;
193528f6c2f2SEnji Cooper 
193628f6c2f2SEnji Cooper       int operator()() && { return 17; }
193728f6c2f2SEnji Cooper     };
193828f6c2f2SEnji Cooper 
193928f6c2f2SEnji Cooper     MockFunction<int()> mock;
194028f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(Return17());
194128f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()());
194228f6c2f2SEnji Cooper   }
194328f6c2f2SEnji Cooper 
194428f6c2f2SEnji Cooper   // Not &&-qualified
194528f6c2f2SEnji Cooper   {
194628f6c2f2SEnji Cooper     struct Return17 {
194728f6c2f2SEnji Cooper       Return17() = default;
194828f6c2f2SEnji Cooper       Return17(Return17&&) = default;
194928f6c2f2SEnji Cooper 
195028f6c2f2SEnji Cooper       Return17(const Return17&) = delete;
195128f6c2f2SEnji Cooper       Return17 operator=(const Return17&) = delete;
195228f6c2f2SEnji Cooper 
195328f6c2f2SEnji Cooper       int operator()() const { return 17; }
195428f6c2f2SEnji Cooper     };
195528f6c2f2SEnji Cooper 
195628f6c2f2SEnji Cooper     MockFunction<int()> mock;
195728f6c2f2SEnji Cooper     EXPECT_CALL(mock, Call).WillOnce(Return17());
195828f6c2f2SEnji Cooper     EXPECT_EQ(17, mock.AsStdFunction()());
195928f6c2f2SEnji Cooper   }
196028f6c2f2SEnji Cooper }
196128f6c2f2SEnji Cooper 
196228f6c2f2SEnji Cooper // It should be possible to use an action that returns a value with a mock
196328f6c2f2SEnji Cooper // function that doesn't, both through WillOnce and WillRepeatedly.
TEST(MockMethodTest,ActionReturnsIgnoredValue)196428f6c2f2SEnji Cooper TEST(MockMethodTest, ActionReturnsIgnoredValue) {
196528f6c2f2SEnji Cooper   struct ReturnInt {
196628f6c2f2SEnji Cooper     int operator()() const { return 0; }
196728f6c2f2SEnji Cooper   };
196828f6c2f2SEnji Cooper 
196928f6c2f2SEnji Cooper   MockFunction<void()> mock;
197028f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(ReturnInt()).WillRepeatedly(ReturnInt());
197128f6c2f2SEnji Cooper 
197228f6c2f2SEnji Cooper   mock.AsStdFunction()();
197328f6c2f2SEnji Cooper   mock.AsStdFunction()();
197428f6c2f2SEnji Cooper }
197528f6c2f2SEnji Cooper 
197628f6c2f2SEnji Cooper // Despite the fanciness around move-only actions and so on, it should still be
197728f6c2f2SEnji Cooper // possible to hand an lvalue reference to a copyable action to WillOnce.
TEST(MockMethodTest,WillOnceCanAcceptLvalueReference)197828f6c2f2SEnji Cooper TEST(MockMethodTest, WillOnceCanAcceptLvalueReference) {
197928f6c2f2SEnji Cooper   MockFunction<int()> mock;
198028f6c2f2SEnji Cooper 
198128f6c2f2SEnji Cooper   const auto action = [] { return 17; };
198228f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call).WillOnce(action);
198328f6c2f2SEnji Cooper 
198428f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()());
198528f6c2f2SEnji Cooper }
198628f6c2f2SEnji Cooper 
198728f6c2f2SEnji Cooper // A callable that doesn't use SFINAE to restrict its call operator's overload
198828f6c2f2SEnji Cooper // set, but is still picky about which arguments it will accept.
198928f6c2f2SEnji Cooper struct StaticAssertSingleArgument {
199028f6c2f2SEnji Cooper   template <typename... Args>
CheckArgstesting::__anon58a2f1bc0111::StaticAssertSingleArgument199128f6c2f2SEnji Cooper   static constexpr bool CheckArgs() {
199228f6c2f2SEnji Cooper     static_assert(sizeof...(Args) == 1, "");
199328f6c2f2SEnji Cooper     return true;
199428f6c2f2SEnji Cooper   }
199528f6c2f2SEnji Cooper 
199628f6c2f2SEnji Cooper   template <typename... Args, bool = CheckArgs<Args...>()>
operator ()testing::__anon58a2f1bc0111::StaticAssertSingleArgument199728f6c2f2SEnji Cooper   int operator()(Args...) const {
199828f6c2f2SEnji Cooper     return 17;
199928f6c2f2SEnji Cooper   }
200028f6c2f2SEnji Cooper };
200128f6c2f2SEnji Cooper 
200228f6c2f2SEnji Cooper // WillOnce and WillRepeatedly should both work fine with naïve implementations
200328f6c2f2SEnji Cooper // of actions that don't use SFINAE to limit the overload set for their call
200428f6c2f2SEnji Cooper // operator. If they are compatible with the actual mocked signature, we
200528f6c2f2SEnji Cooper // shouldn't probe them with no arguments and trip a static_assert.
TEST(MockMethodTest,ActionSwallowsAllArguments)200628f6c2f2SEnji Cooper TEST(MockMethodTest, ActionSwallowsAllArguments) {
200728f6c2f2SEnji Cooper   MockFunction<int(int)> mock;
200828f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call)
200928f6c2f2SEnji Cooper       .WillOnce(StaticAssertSingleArgument{})
201028f6c2f2SEnji Cooper       .WillRepeatedly(StaticAssertSingleArgument{});
201128f6c2f2SEnji Cooper 
201228f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()(0));
201328f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()(0));
201428f6c2f2SEnji Cooper }
201528f6c2f2SEnji Cooper 
201628f6c2f2SEnji Cooper struct ActionWithTemplatedConversionOperators {
201728f6c2f2SEnji Cooper   template <typename... Args>
operator OnceAction<int(Args...)>testing::__anon58a2f1bc0111::ActionWithTemplatedConversionOperators201828f6c2f2SEnji Cooper   operator OnceAction<int(Args...)>() && {  // NOLINT
201928f6c2f2SEnji Cooper     return [] { return 17; };
202028f6c2f2SEnji Cooper   }
202128f6c2f2SEnji Cooper 
202228f6c2f2SEnji Cooper   template <typename... Args>
operator Action<int(Args...)>testing::__anon58a2f1bc0111::ActionWithTemplatedConversionOperators202328f6c2f2SEnji Cooper   operator Action<int(Args...)>() const {  // NOLINT
202428f6c2f2SEnji Cooper     return [] { return 19; };
202528f6c2f2SEnji Cooper   }
202628f6c2f2SEnji Cooper };
202728f6c2f2SEnji Cooper 
202828f6c2f2SEnji Cooper // It should be fine to hand both WillOnce and WillRepeatedly a function that
202928f6c2f2SEnji Cooper // defines templated conversion operators to OnceAction and Action. WillOnce
203028f6c2f2SEnji Cooper // should prefer the OnceAction version.
TEST(MockMethodTest,ActionHasTemplatedConversionOperators)203128f6c2f2SEnji Cooper TEST(MockMethodTest, ActionHasTemplatedConversionOperators) {
203228f6c2f2SEnji Cooper   MockFunction<int()> mock;
203328f6c2f2SEnji Cooper   EXPECT_CALL(mock, Call)
203428f6c2f2SEnji Cooper       .WillOnce(ActionWithTemplatedConversionOperators{})
203528f6c2f2SEnji Cooper       .WillRepeatedly(ActionWithTemplatedConversionOperators{});
203628f6c2f2SEnji Cooper 
203728f6c2f2SEnji Cooper   EXPECT_EQ(17, mock.AsStdFunction()());
203828f6c2f2SEnji Cooper   EXPECT_EQ(19, mock.AsStdFunction()());
203928f6c2f2SEnji Cooper }
204028f6c2f2SEnji Cooper 
2041b89a7cc2SEnji Cooper // Tests for std::function based action.
2042b89a7cc2SEnji Cooper 
Add(int val,int & ref,int * ptr)2043b89a7cc2SEnji Cooper int Add(int val, int& ref, int* ptr) {  // NOLINT
2044b89a7cc2SEnji Cooper   int result = val + ref + *ptr;
2045b89a7cc2SEnji Cooper   ref = 42;
2046b89a7cc2SEnji Cooper   *ptr = 43;
2047b89a7cc2SEnji Cooper   return result;
2048b89a7cc2SEnji Cooper }
2049b89a7cc2SEnji Cooper 
Deref(std::unique_ptr<int> ptr)2050b89a7cc2SEnji Cooper int Deref(std::unique_ptr<int> ptr) { return *ptr; }
2051b89a7cc2SEnji Cooper 
2052b89a7cc2SEnji Cooper struct Double {
2053b89a7cc2SEnji Cooper   template <typename T>
operator ()testing::__anon58a2f1bc0111::Double205428f6c2f2SEnji Cooper   T operator()(T t) {
205528f6c2f2SEnji Cooper     return 2 * t;
205628f6c2f2SEnji Cooper   }
2057b89a7cc2SEnji Cooper };
2058b89a7cc2SEnji Cooper 
UniqueInt(int i)205928f6c2f2SEnji Cooper std::unique_ptr<int> UniqueInt(int i) { return std::make_unique<int>(i); }
2060b89a7cc2SEnji Cooper 
TEST(FunctorActionTest,ActionFromFunction)2061b89a7cc2SEnji Cooper TEST(FunctorActionTest, ActionFromFunction) {
2062b89a7cc2SEnji Cooper   Action<int(int, int&, int*)> a = &Add;
2063b89a7cc2SEnji Cooper   int x = 1, y = 2, z = 3;
2064b89a7cc2SEnji Cooper   EXPECT_EQ(6, a.Perform(std::forward_as_tuple(x, y, &z)));
2065b89a7cc2SEnji Cooper   EXPECT_EQ(42, y);
2066b89a7cc2SEnji Cooper   EXPECT_EQ(43, z);
2067b89a7cc2SEnji Cooper 
2068b89a7cc2SEnji Cooper   Action<int(std::unique_ptr<int>)> a1 = &Deref;
2069b89a7cc2SEnji Cooper   EXPECT_EQ(7, a1.Perform(std::make_tuple(UniqueInt(7))));
2070b89a7cc2SEnji Cooper }
2071b89a7cc2SEnji Cooper 
TEST(FunctorActionTest,ActionFromLambda)2072b89a7cc2SEnji Cooper TEST(FunctorActionTest, ActionFromLambda) {
2073b89a7cc2SEnji Cooper   Action<int(bool, int)> a1 = [](bool b, int i) { return b ? i : 0; };
207428f6c2f2SEnji Cooper   EXPECT_EQ(5, a1.Perform(std::make_tuple(true, 5)));
207528f6c2f2SEnji Cooper   EXPECT_EQ(0, a1.Perform(std::make_tuple(false, 5)));
2076b89a7cc2SEnji Cooper 
2077b89a7cc2SEnji Cooper   std::unique_ptr<int> saved;
2078b89a7cc2SEnji Cooper   Action<void(std::unique_ptr<int>)> a2 = [&saved](std::unique_ptr<int> p) {
2079b89a7cc2SEnji Cooper     saved = std::move(p);
2080b89a7cc2SEnji Cooper   };
208128f6c2f2SEnji Cooper   a2.Perform(std::make_tuple(UniqueInt(5)));
2082b89a7cc2SEnji Cooper   EXPECT_EQ(5, *saved);
2083b89a7cc2SEnji Cooper }
2084b89a7cc2SEnji Cooper 
TEST(FunctorActionTest,PolymorphicFunctor)2085b89a7cc2SEnji Cooper TEST(FunctorActionTest, PolymorphicFunctor) {
2086b89a7cc2SEnji Cooper   Action<int(int)> ai = Double();
208728f6c2f2SEnji Cooper   EXPECT_EQ(2, ai.Perform(std::make_tuple(1)));
2088b89a7cc2SEnji Cooper   Action<double(double)> ad = Double();  // Double? Double double!
208928f6c2f2SEnji Cooper   EXPECT_EQ(3.0, ad.Perform(std::make_tuple(1.5)));
2090b89a7cc2SEnji Cooper }
2091b89a7cc2SEnji Cooper 
TEST(FunctorActionTest,TypeConversion)2092b89a7cc2SEnji Cooper TEST(FunctorActionTest, TypeConversion) {
2093b89a7cc2SEnji Cooper   // Numeric promotions are allowed.
2094b89a7cc2SEnji Cooper   const Action<bool(int)> a1 = [](int i) { return i > 1; };
2095b89a7cc2SEnji Cooper   const Action<int(bool)> a2 = Action<int(bool)>(a1);
209628f6c2f2SEnji Cooper   EXPECT_EQ(1, a1.Perform(std::make_tuple(42)));
209728f6c2f2SEnji Cooper   EXPECT_EQ(0, a2.Perform(std::make_tuple(42)));
2098b89a7cc2SEnji Cooper 
2099b89a7cc2SEnji Cooper   // Implicit constructors are allowed.
2100b89a7cc2SEnji Cooper   const Action<bool(std::string)> s1 = [](std::string s) { return !s.empty(); };
2101b89a7cc2SEnji Cooper   const Action<int(const char*)> s2 = Action<int(const char*)>(s1);
210228f6c2f2SEnji Cooper   EXPECT_EQ(0, s2.Perform(std::make_tuple("")));
210328f6c2f2SEnji Cooper   EXPECT_EQ(1, s2.Perform(std::make_tuple("hello")));
2104b89a7cc2SEnji Cooper 
2105b89a7cc2SEnji Cooper   // Also between the lambda and the action itself.
210628f6c2f2SEnji Cooper   const Action<bool(std::string)> x1 = [](Unused) { return 42; };
210728f6c2f2SEnji Cooper   const Action<bool(std::string)> x2 = [] { return 42; };
210828f6c2f2SEnji Cooper   EXPECT_TRUE(x1.Perform(std::make_tuple("hello")));
210928f6c2f2SEnji Cooper   EXPECT_TRUE(x2.Perform(std::make_tuple("hello")));
211028f6c2f2SEnji Cooper 
211128f6c2f2SEnji Cooper   // Ensure decay occurs where required.
211228f6c2f2SEnji Cooper   std::function<int()> f = [] { return 7; };
211328f6c2f2SEnji Cooper   Action<int(int)> d = f;
211428f6c2f2SEnji Cooper   f = nullptr;
211528f6c2f2SEnji Cooper   EXPECT_EQ(7, d.Perform(std::make_tuple(1)));
211628f6c2f2SEnji Cooper 
211728f6c2f2SEnji Cooper   // Ensure creation of an empty action succeeds.
211828f6c2f2SEnji Cooper   Action<void(int)>(nullptr);
2119b89a7cc2SEnji Cooper }
2120b89a7cc2SEnji Cooper 
TEST(FunctorActionTest,UnusedArguments)2121b89a7cc2SEnji Cooper TEST(FunctorActionTest, UnusedArguments) {
2122b89a7cc2SEnji Cooper   // Verify that users can ignore uninteresting arguments.
212328f6c2f2SEnji Cooper   Action<int(int, double y, double z)> a = [](int i, Unused, Unused) {
212428f6c2f2SEnji Cooper     return 2 * i;
212528f6c2f2SEnji Cooper   };
212628f6c2f2SEnji Cooper   std::tuple<int, double, double> dummy = std::make_tuple(3, 7.3, 9.44);
2127b89a7cc2SEnji Cooper   EXPECT_EQ(6, a.Perform(dummy));
2128b89a7cc2SEnji Cooper }
2129b89a7cc2SEnji Cooper 
2130b89a7cc2SEnji Cooper // Test that basic built-in actions work with move-only arguments.
TEST(MoveOnlyArgumentsTest,ReturningActions)2131b89a7cc2SEnji Cooper TEST(MoveOnlyArgumentsTest, ReturningActions) {
2132b89a7cc2SEnji Cooper   Action<int(std::unique_ptr<int>)> a = Return(1);
213328f6c2f2SEnji Cooper   EXPECT_EQ(1, a.Perform(std::make_tuple(nullptr)));
2134b89a7cc2SEnji Cooper 
2135b89a7cc2SEnji Cooper   a = testing::WithoutArgs([]() { return 7; });
213628f6c2f2SEnji Cooper   EXPECT_EQ(7, a.Perform(std::make_tuple(nullptr)));
2137b89a7cc2SEnji Cooper 
2138b89a7cc2SEnji Cooper   Action<void(std::unique_ptr<int>, int*)> a2 = testing::SetArgPointee<1>(3);
2139b89a7cc2SEnji Cooper   int x = 0;
214028f6c2f2SEnji Cooper   a2.Perform(std::make_tuple(nullptr, &x));
2141b89a7cc2SEnji Cooper   EXPECT_EQ(x, 3);
2142b89a7cc2SEnji Cooper }
2143b89a7cc2SEnji Cooper 
ACTION(ReturnArity)214428f6c2f2SEnji Cooper ACTION(ReturnArity) { return std::tuple_size<args_type>::value; }
2145b89a7cc2SEnji Cooper 
TEST(ActionMacro,LargeArity)214628f6c2f2SEnji Cooper TEST(ActionMacro, LargeArity) {
214728f6c2f2SEnji Cooper   EXPECT_EQ(
214828f6c2f2SEnji Cooper       1, testing::Action<int(int)>(ReturnArity()).Perform(std::make_tuple(0)));
214928f6c2f2SEnji Cooper   EXPECT_EQ(
215028f6c2f2SEnji Cooper       10,
215128f6c2f2SEnji Cooper       testing::Action<int(int, int, int, int, int, int, int, int, int, int)>(
215228f6c2f2SEnji Cooper           ReturnArity())
215328f6c2f2SEnji Cooper           .Perform(std::make_tuple(0, 1, 2, 3, 4, 5, 6, 7, 8, 9)));
215428f6c2f2SEnji Cooper   EXPECT_EQ(
215528f6c2f2SEnji Cooper       20,
215628f6c2f2SEnji Cooper       testing::Action<int(int, int, int, int, int, int, int, int, int, int, int,
215728f6c2f2SEnji Cooper                           int, int, int, int, int, int, int, int, int)>(
215828f6c2f2SEnji Cooper           ReturnArity())
215928f6c2f2SEnji Cooper           .Perform(std::make_tuple(0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,
216028f6c2f2SEnji Cooper                                    14, 15, 16, 17, 18, 19)));
216128f6c2f2SEnji Cooper }
2162b89a7cc2SEnji Cooper 
216328f6c2f2SEnji Cooper }  // namespace
216428f6c2f2SEnji Cooper }  // namespace testing
216528f6c2f2SEnji Cooper 
216628f6c2f2SEnji Cooper #if defined(_MSC_VER) && (_MSC_VER == 1900)
216728f6c2f2SEnji Cooper GTEST_DISABLE_MSC_WARNINGS_POP_()  // 4800
2168b89a7cc2SEnji Cooper #endif
216928f6c2f2SEnji Cooper GTEST_DISABLE_MSC_WARNINGS_POP_()  // 4100 4503
2170