1 // Copyright 2007, Google Inc.
2 // All rights reserved.
3 //
4 // Redistribution and use in source and binary forms, with or without
5 // modification, are permitted provided that the following conditions are
6 // met:
7 //
8 //     * Redistributions of source code must retain the above copyright
9 // notice, this list of conditions and the following disclaimer.
10 //     * Redistributions in binary form must reproduce the above
11 // copyright notice, this list of conditions and the following disclaimer
12 // in the documentation and/or other materials provided with the
13 // distribution.
14 //     * Neither the name of Google Inc. nor the names of its
15 // contributors may be used to endorse or promote products derived from
16 // this software without specific prior written permission.
17 //
18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 
30 
31 // Google Mock - a framework for writing C++ mock classes.
32 //
33 // This file tests the built-in actions generated by a script.
34 
35 #include "gmock/gmock-generated-actions.h"
36 
37 #include <functional>
38 #include <memory>
39 #include <sstream>
40 #include <string>
41 #include "gmock/gmock.h"
42 #include "gtest/gtest.h"
43 
44 namespace testing {
45 namespace gmock_generated_actions_test {
46 
47 using ::std::plus;
48 using ::std::string;
49 using testing::_;
50 using testing::Action;
51 using testing::ActionInterface;
52 using testing::ByRef;
53 using testing::DoAll;
54 using testing::Invoke;
55 using testing::Return;
56 using testing::ReturnNew;
57 using testing::SetArgPointee;
58 using testing::StaticAssertTypeEq;
59 using testing::Unused;
60 
61 // For suppressing compiler warnings on conversion possibly losing precision.
Short(short n)62 inline short Short(short n) { return n; }  // NOLINT
Char(char ch)63 inline char Char(char ch) { return ch; }
64 
65 // Sample functions and functors for testing various actions.
Nullary()66 int Nullary() { return 1; }
67 
68 bool g_done = false;
69 
ByConstRef(const std::string & s)70 bool ByConstRef(const std::string& s) { return s == "Hi"; }
71 
72 const double g_double = 0;
ReferencesGlobalDouble(const double & x)73 bool ReferencesGlobalDouble(const double& x) { return &x == &g_double; }
74 
75 struct UnaryFunctor {
operator ()testing::gmock_generated_actions_test::UnaryFunctor76   int operator()(bool x) { return x ? 1 : -1; }
77 };
78 
Binary(const char * input,short n)79 const char* Binary(const char* input, short n) { return input + n; }  // NOLINT
80 
SumOf5(int a,int b,int c,int d,int e)81 int SumOf5(int a, int b, int c, int d, int e) { return a + b + c + d + e; }
82 
83 struct SumOf5Functor {
operator ()testing::gmock_generated_actions_test::SumOf5Functor84   int operator()(int a, int b, int c, int d, int e) {
85     return a + b + c + d + e;
86   }
87 };
88 
Concat5(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5)89 std::string Concat5(const char* s1, const char* s2, const char* s3,
90                     const char* s4, const char* s5) {
91   return std::string(s1) + s2 + s3 + s4 + s5;
92 }
93 
SumOf6(int a,int b,int c,int d,int e,int f)94 int SumOf6(int a, int b, int c, int d, int e, int f) {
95   return a + b + c + d + e + f;
96 }
97 
98 struct SumOf6Functor {
operator ()testing::gmock_generated_actions_test::SumOf6Functor99   int operator()(int a, int b, int c, int d, int e, int f) {
100     return a + b + c + d + e + f;
101   }
102 };
103 
Concat6(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5,const char * s6)104 std::string Concat6(const char* s1, const char* s2, const char* s3,
105                     const char* s4, const char* s5, const char* s6) {
106   return std::string(s1) + s2 + s3 + s4 + s5 + s6;
107 }
108 
Concat7(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5,const char * s6,const char * s7)109 std::string Concat7(const char* s1, const char* s2, const char* s3,
110                     const char* s4, const char* s5, const char* s6,
111                     const char* s7) {
112   return std::string(s1) + s2 + s3 + s4 + s5 + s6 + s7;
113 }
114 
Concat8(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5,const char * s6,const char * s7,const char * s8)115 std::string Concat8(const char* s1, const char* s2, const char* s3,
116                     const char* s4, const char* s5, const char* s6,
117                     const char* s7, const char* s8) {
118   return std::string(s1) + s2 + s3 + s4 + s5 + s6 + s7 + s8;
119 }
120 
Concat9(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5,const char * s6,const char * s7,const char * s8,const char * s9)121 std::string Concat9(const char* s1, const char* s2, const char* s3,
122                     const char* s4, const char* s5, const char* s6,
123                     const char* s7, const char* s8, const char* s9) {
124   return std::string(s1) + s2 + s3 + s4 + s5 + s6 + s7 + s8 + s9;
125 }
126 
Concat10(const char * s1,const char * s2,const char * s3,const char * s4,const char * s5,const char * s6,const char * s7,const char * s8,const char * s9,const char * s10)127 std::string Concat10(const char* s1, const char* s2, const char* s3,
128                      const char* s4, const char* s5, const char* s6,
129                      const char* s7, const char* s8, const char* s9,
130                      const char* s10) {
131   return std::string(s1) + s2 + s3 + s4 + s5 + s6 + s7 + s8 + s9 + s10;
132 }
133 
134 // A helper that turns the type of a C-string literal from const
135 // char[N] to const char*.
CharPtr(const char * s)136 inline const char* CharPtr(const char* s) { return s; }
137 
138 // Tests InvokeArgument<N>(...).
139 
140 // Tests using InvokeArgument with a nullary function.
TEST(InvokeArgumentTest,Function0)141 TEST(InvokeArgumentTest, Function0) {
142   Action<int(int, int(*)())> a = InvokeArgument<1>();  // NOLINT
143   EXPECT_EQ(1, a.Perform(std::make_tuple(2, &Nullary)));
144 }
145 
146 // Tests using InvokeArgument with a unary function.
TEST(InvokeArgumentTest,Functor1)147 TEST(InvokeArgumentTest, Functor1) {
148   Action<int(UnaryFunctor)> a = InvokeArgument<0>(true);  // NOLINT
149   EXPECT_EQ(1, a.Perform(std::make_tuple(UnaryFunctor())));
150 }
151 
152 // Tests using InvokeArgument with a 5-ary function.
TEST(InvokeArgumentTest,Function5)153 TEST(InvokeArgumentTest, Function5) {
154   Action<int(int(*)(int, int, int, int, int))> a =  // NOLINT
155       InvokeArgument<0>(10000, 2000, 300, 40, 5);
156   EXPECT_EQ(12345, a.Perform(std::make_tuple(&SumOf5)));
157 }
158 
159 // Tests using InvokeArgument with a 5-ary functor.
TEST(InvokeArgumentTest,Functor5)160 TEST(InvokeArgumentTest, Functor5) {
161   Action<int(SumOf5Functor)> a =  // NOLINT
162       InvokeArgument<0>(10000, 2000, 300, 40, 5);
163   EXPECT_EQ(12345, a.Perform(std::make_tuple(SumOf5Functor())));
164 }
165 
166 // Tests using InvokeArgument with a 6-ary function.
TEST(InvokeArgumentTest,Function6)167 TEST(InvokeArgumentTest, Function6) {
168   Action<int(int(*)(int, int, int, int, int, int))> a =  // NOLINT
169       InvokeArgument<0>(100000, 20000, 3000, 400, 50, 6);
170   EXPECT_EQ(123456, a.Perform(std::make_tuple(&SumOf6)));
171 }
172 
173 // Tests using InvokeArgument with a 6-ary functor.
TEST(InvokeArgumentTest,Functor6)174 TEST(InvokeArgumentTest, Functor6) {
175   Action<int(SumOf6Functor)> a =  // NOLINT
176       InvokeArgument<0>(100000, 20000, 3000, 400, 50, 6);
177   EXPECT_EQ(123456, a.Perform(std::make_tuple(SumOf6Functor())));
178 }
179 
180 // Tests using InvokeArgument with a 7-ary function.
TEST(InvokeArgumentTest,Function7)181 TEST(InvokeArgumentTest, Function7) {
182   Action<std::string(std::string(*)(const char*, const char*, const char*,
183                                     const char*, const char*, const char*,
184                                     const char*))>
185       a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7");
186   EXPECT_EQ("1234567", a.Perform(std::make_tuple(&Concat7)));
187 }
188 
189 // Tests using InvokeArgument with a 8-ary function.
TEST(InvokeArgumentTest,Function8)190 TEST(InvokeArgumentTest, Function8) {
191   Action<std::string(std::string(*)(const char*, const char*, const char*,
192                                     const char*, const char*, const char*,
193                                     const char*, const char*))>
194       a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8");
195   EXPECT_EQ("12345678", a.Perform(std::make_tuple(&Concat8)));
196 }
197 
198 // Tests using InvokeArgument with a 9-ary function.
TEST(InvokeArgumentTest,Function9)199 TEST(InvokeArgumentTest, Function9) {
200   Action<std::string(std::string(*)(const char*, const char*, const char*,
201                                     const char*, const char*, const char*,
202                                     const char*, const char*, const char*))>
203       a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8", "9");
204   EXPECT_EQ("123456789", a.Perform(std::make_tuple(&Concat9)));
205 }
206 
207 // Tests using InvokeArgument with a 10-ary function.
TEST(InvokeArgumentTest,Function10)208 TEST(InvokeArgumentTest, Function10) {
209   Action<std::string(std::string(*)(
210       const char*, const char*, const char*, const char*, const char*,
211       const char*, const char*, const char*, const char*, const char*))>
212       a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8", "9", "0");
213   EXPECT_EQ("1234567890", a.Perform(std::make_tuple(&Concat10)));
214 }
215 
216 // Tests using InvokeArgument with a function that takes a pointer argument.
TEST(InvokeArgumentTest,ByPointerFunction)217 TEST(InvokeArgumentTest, ByPointerFunction) {
218   Action<const char*(const char*(*)(const char* input, short n))> a =  // NOLINT
219       InvokeArgument<0>(static_cast<const char*>("Hi"), Short(1));
220   EXPECT_STREQ("i", a.Perform(std::make_tuple(&Binary)));
221 }
222 
223 // Tests using InvokeArgument with a function that takes a const char*
224 // by passing it a C-string literal.
TEST(InvokeArgumentTest,FunctionWithCStringLiteral)225 TEST(InvokeArgumentTest, FunctionWithCStringLiteral) {
226   Action<const char*(const char*(*)(const char* input, short n))> a =  // NOLINT
227       InvokeArgument<0>("Hi", Short(1));
228   EXPECT_STREQ("i", a.Perform(std::make_tuple(&Binary)));
229 }
230 
231 // Tests using InvokeArgument with a function that takes a const reference.
TEST(InvokeArgumentTest,ByConstReferenceFunction)232 TEST(InvokeArgumentTest, ByConstReferenceFunction) {
233   Action<bool(bool (*function)(const std::string& s))> a =  // NOLINT
234       InvokeArgument<0>(std::string("Hi"));
235   // When action 'a' is constructed, it makes a copy of the temporary
236   // string object passed to it, so it's OK to use 'a' later, when the
237   // temporary object has already died.
238   EXPECT_TRUE(a.Perform(std::make_tuple(&ByConstRef)));
239 }
240 
241 // Tests using InvokeArgument with ByRef() and a function that takes a
242 // const reference.
TEST(InvokeArgumentTest,ByExplicitConstReferenceFunction)243 TEST(InvokeArgumentTest, ByExplicitConstReferenceFunction) {
244   Action<bool(bool(*)(const double& x))> a =  // NOLINT
245       InvokeArgument<0>(ByRef(g_double));
246   // The above line calls ByRef() on a const value.
247   EXPECT_TRUE(a.Perform(std::make_tuple(&ReferencesGlobalDouble)));
248 
249   double x = 0;
250   a = InvokeArgument<0>(ByRef(x));  // This calls ByRef() on a non-const.
251   EXPECT_FALSE(a.Perform(std::make_tuple(&ReferencesGlobalDouble)));
252 }
253 
254 // Tests DoAll(a1, a2).
TEST(DoAllTest,TwoActions)255 TEST(DoAllTest, TwoActions) {
256   int n = 0;
257   Action<int(int*)> a = DoAll(SetArgPointee<0>(1),  // NOLINT
258                               Return(2));
259   EXPECT_EQ(2, a.Perform(std::make_tuple(&n)));
260   EXPECT_EQ(1, n);
261 }
262 
263 // Tests DoAll(a1, a2, a3).
TEST(DoAllTest,ThreeActions)264 TEST(DoAllTest, ThreeActions) {
265   int m = 0, n = 0;
266   Action<int(int*, int*)> a = DoAll(SetArgPointee<0>(1),  // NOLINT
267                                     SetArgPointee<1>(2),
268                                     Return(3));
269   EXPECT_EQ(3, a.Perform(std::make_tuple(&m, &n)));
270   EXPECT_EQ(1, m);
271   EXPECT_EQ(2, n);
272 }
273 
274 // Tests DoAll(a1, a2, a3, a4).
TEST(DoAllTest,FourActions)275 TEST(DoAllTest, FourActions) {
276   int m = 0, n = 0;
277   char ch = '\0';
278   Action<int(int*, int*, char*)> a =  // NOLINT
279       DoAll(SetArgPointee<0>(1),
280             SetArgPointee<1>(2),
281             SetArgPointee<2>('a'),
282             Return(3));
283   EXPECT_EQ(3, a.Perform(std::make_tuple(&m, &n, &ch)));
284   EXPECT_EQ(1, m);
285   EXPECT_EQ(2, n);
286   EXPECT_EQ('a', ch);
287 }
288 
289 // Tests DoAll(a1, a2, a3, a4, a5).
TEST(DoAllTest,FiveActions)290 TEST(DoAllTest, FiveActions) {
291   int m = 0, n = 0;
292   char a = '\0', b = '\0';
293   Action<int(int*, int*, char*, char*)> action =  // NOLINT
294       DoAll(SetArgPointee<0>(1),
295             SetArgPointee<1>(2),
296             SetArgPointee<2>('a'),
297             SetArgPointee<3>('b'),
298             Return(3));
299   EXPECT_EQ(3, action.Perform(std::make_tuple(&m, &n, &a, &b)));
300   EXPECT_EQ(1, m);
301   EXPECT_EQ(2, n);
302   EXPECT_EQ('a', a);
303   EXPECT_EQ('b', b);
304 }
305 
306 // Tests DoAll(a1, a2, ..., a6).
TEST(DoAllTest,SixActions)307 TEST(DoAllTest, SixActions) {
308   int m = 0, n = 0;
309   char a = '\0', b = '\0', c = '\0';
310   Action<int(int*, int*, char*, char*, char*)> action =  // NOLINT
311       DoAll(SetArgPointee<0>(1),
312             SetArgPointee<1>(2),
313             SetArgPointee<2>('a'),
314             SetArgPointee<3>('b'),
315             SetArgPointee<4>('c'),
316             Return(3));
317   EXPECT_EQ(3, action.Perform(std::make_tuple(&m, &n, &a, &b, &c)));
318   EXPECT_EQ(1, m);
319   EXPECT_EQ(2, n);
320   EXPECT_EQ('a', a);
321   EXPECT_EQ('b', b);
322   EXPECT_EQ('c', c);
323 }
324 
325 // Tests DoAll(a1, a2, ..., a7).
TEST(DoAllTest,SevenActions)326 TEST(DoAllTest, SevenActions) {
327   int m = 0, n = 0;
328   char a = '\0', b = '\0', c = '\0', d = '\0';
329   Action<int(int*, int*, char*, char*, char*, char*)> action =  // NOLINT
330       DoAll(SetArgPointee<0>(1),
331             SetArgPointee<1>(2),
332             SetArgPointee<2>('a'),
333             SetArgPointee<3>('b'),
334             SetArgPointee<4>('c'),
335             SetArgPointee<5>('d'),
336             Return(3));
337   EXPECT_EQ(3, action.Perform(std::make_tuple(&m, &n, &a, &b, &c, &d)));
338   EXPECT_EQ(1, m);
339   EXPECT_EQ(2, n);
340   EXPECT_EQ('a', a);
341   EXPECT_EQ('b', b);
342   EXPECT_EQ('c', c);
343   EXPECT_EQ('d', d);
344 }
345 
346 // Tests DoAll(a1, a2, ..., a8).
TEST(DoAllTest,EightActions)347 TEST(DoAllTest, EightActions) {
348   int m = 0, n = 0;
349   char a = '\0', b = '\0', c = '\0', d = '\0', e = '\0';
350   Action<int(int*, int*, char*, char*, char*, char*,  // NOLINT
351              char*)> action =
352       DoAll(SetArgPointee<0>(1),
353             SetArgPointee<1>(2),
354             SetArgPointee<2>('a'),
355             SetArgPointee<3>('b'),
356             SetArgPointee<4>('c'),
357             SetArgPointee<5>('d'),
358             SetArgPointee<6>('e'),
359             Return(3));
360   EXPECT_EQ(3, action.Perform(std::make_tuple(&m, &n, &a, &b, &c, &d, &e)));
361   EXPECT_EQ(1, m);
362   EXPECT_EQ(2, n);
363   EXPECT_EQ('a', a);
364   EXPECT_EQ('b', b);
365   EXPECT_EQ('c', c);
366   EXPECT_EQ('d', d);
367   EXPECT_EQ('e', e);
368 }
369 
370 // Tests DoAll(a1, a2, ..., a9).
TEST(DoAllTest,NineActions)371 TEST(DoAllTest, NineActions) {
372   int m = 0, n = 0;
373   char a = '\0', b = '\0', c = '\0', d = '\0', e = '\0', f = '\0';
374   Action<int(int*, int*, char*, char*, char*, char*,  // NOLINT
375              char*, char*)> action =
376       DoAll(SetArgPointee<0>(1),
377             SetArgPointee<1>(2),
378             SetArgPointee<2>('a'),
379             SetArgPointee<3>('b'),
380             SetArgPointee<4>('c'),
381             SetArgPointee<5>('d'),
382             SetArgPointee<6>('e'),
383             SetArgPointee<7>('f'),
384             Return(3));
385   EXPECT_EQ(3, action.Perform(std::make_tuple(&m, &n, &a, &b, &c, &d, &e, &f)));
386   EXPECT_EQ(1, m);
387   EXPECT_EQ(2, n);
388   EXPECT_EQ('a', a);
389   EXPECT_EQ('b', b);
390   EXPECT_EQ('c', c);
391   EXPECT_EQ('d', d);
392   EXPECT_EQ('e', e);
393   EXPECT_EQ('f', f);
394 }
395 
396 // Tests DoAll(a1, a2, ..., a10).
TEST(DoAllTest,TenActions)397 TEST(DoAllTest, TenActions) {
398   int m = 0, n = 0;
399   char a = '\0', b = '\0', c = '\0', d = '\0';
400   char e = '\0', f = '\0', g = '\0';
401   Action<int(int*, int*, char*, char*, char*, char*,  // NOLINT
402              char*, char*, char*)> action =
403       DoAll(SetArgPointee<0>(1),
404             SetArgPointee<1>(2),
405             SetArgPointee<2>('a'),
406             SetArgPointee<3>('b'),
407             SetArgPointee<4>('c'),
408             SetArgPointee<5>('d'),
409             SetArgPointee<6>('e'),
410             SetArgPointee<7>('f'),
411             SetArgPointee<8>('g'),
412             Return(3));
413   EXPECT_EQ(
414       3, action.Perform(std::make_tuple(&m, &n, &a, &b, &c, &d, &e, &f, &g)));
415   EXPECT_EQ(1, m);
416   EXPECT_EQ(2, n);
417   EXPECT_EQ('a', a);
418   EXPECT_EQ('b', b);
419   EXPECT_EQ('c', c);
420   EXPECT_EQ('d', d);
421   EXPECT_EQ('e', e);
422   EXPECT_EQ('f', f);
423   EXPECT_EQ('g', g);
424 }
425 
426 // The ACTION*() macros trigger warning C4100 (unreferenced formal
427 // parameter) in MSVC with -W4.  Unfortunately they cannot be fixed in
428 // the macro definition, as the warnings are generated when the macro
429 // is expanded and macro expansion cannot contain #pragma.  Therefore
430 // we suppress them here.
431 // Also suppress C4503 decorated name length exceeded, name was truncated
432 #ifdef _MSC_VER
433 # pragma warning(push)
434 # pragma warning(disable:4100)
435 # pragma warning(disable:4503)
436 #endif
437 // Tests the ACTION*() macro family.
438 
439 // Tests that ACTION() can define an action that doesn't reference the
440 // mock function arguments.
ACTION(Return5)441 ACTION(Return5) { return 5; }
442 
TEST(ActionMacroTest,WorksWhenNotReferencingArguments)443 TEST(ActionMacroTest, WorksWhenNotReferencingArguments) {
444   Action<double()> a1 = Return5();
445   EXPECT_DOUBLE_EQ(5, a1.Perform(std::make_tuple()));
446 
447   Action<int(double, bool)> a2 = Return5();
448   EXPECT_EQ(5, a2.Perform(std::make_tuple(1, true)));
449 }
450 
451 // Tests that ACTION() can define an action that returns void.
ACTION(IncrementArg1)452 ACTION(IncrementArg1) { (*arg1)++; }
453 
TEST(ActionMacroTest,WorksWhenReturningVoid)454 TEST(ActionMacroTest, WorksWhenReturningVoid) {
455   Action<void(int, int*)> a1 = IncrementArg1();
456   int n = 0;
457   a1.Perform(std::make_tuple(5, &n));
458   EXPECT_EQ(1, n);
459 }
460 
461 // Tests that the body of ACTION() can reference the type of the
462 // argument.
ACTION(IncrementArg2)463 ACTION(IncrementArg2) {
464   StaticAssertTypeEq<int*, arg2_type>();
465   arg2_type temp = arg2;
466   (*temp)++;
467 }
468 
TEST(ActionMacroTest,CanReferenceArgumentType)469 TEST(ActionMacroTest, CanReferenceArgumentType) {
470   Action<void(int, bool, int*)> a1 = IncrementArg2();
471   int n = 0;
472   a1.Perform(std::make_tuple(5, false, &n));
473   EXPECT_EQ(1, n);
474 }
475 
476 // Tests that the body of ACTION() can reference the argument tuple
477 // via args_type and args.
ACTION(Sum2)478 ACTION(Sum2) {
479   StaticAssertTypeEq<std::tuple<int, char, int*>, args_type>();
480   args_type args_copy = args;
481   return std::get<0>(args_copy) + std::get<1>(args_copy);
482 }
483 
TEST(ActionMacroTest,CanReferenceArgumentTuple)484 TEST(ActionMacroTest, CanReferenceArgumentTuple) {
485   Action<int(int, char, int*)> a1 = Sum2();
486   int dummy = 0;
487   EXPECT_EQ(11, a1.Perform(std::make_tuple(5, Char(6), &dummy)));
488 }
489 
490 // Tests that the body of ACTION() can reference the mock function
491 // type.
Dummy(bool flag)492 int Dummy(bool flag) { return flag? 1 : 0; }
493 
ACTION(InvokeDummy)494 ACTION(InvokeDummy) {
495   StaticAssertTypeEq<int(bool), function_type>();
496   function_type* fp = &Dummy;
497   return (*fp)(true);
498 }
499 
TEST(ActionMacroTest,CanReferenceMockFunctionType)500 TEST(ActionMacroTest, CanReferenceMockFunctionType) {
501   Action<int(bool)> a1 = InvokeDummy();
502   EXPECT_EQ(1, a1.Perform(std::make_tuple(true)));
503   EXPECT_EQ(1, a1.Perform(std::make_tuple(false)));
504 }
505 
506 // Tests that the body of ACTION() can reference the mock function's
507 // return type.
ACTION(InvokeDummy2)508 ACTION(InvokeDummy2) {
509   StaticAssertTypeEq<int, return_type>();
510   return_type result = Dummy(true);
511   return result;
512 }
513 
TEST(ActionMacroTest,CanReferenceMockFunctionReturnType)514 TEST(ActionMacroTest, CanReferenceMockFunctionReturnType) {
515   Action<int(bool)> a1 = InvokeDummy2();
516   EXPECT_EQ(1, a1.Perform(std::make_tuple(true)));
517   EXPECT_EQ(1, a1.Perform(std::make_tuple(false)));
518 }
519 
520 // Tests that ACTION() works for arguments passed by const reference.
ACTION(ReturnAddrOfConstBoolReferenceArg)521 ACTION(ReturnAddrOfConstBoolReferenceArg) {
522   StaticAssertTypeEq<const bool&, arg1_type>();
523   return &arg1;
524 }
525 
TEST(ActionMacroTest,WorksForConstReferenceArg)526 TEST(ActionMacroTest, WorksForConstReferenceArg) {
527   Action<const bool*(int, const bool&)> a = ReturnAddrOfConstBoolReferenceArg();
528   const bool b = false;
529   EXPECT_EQ(&b, a.Perform(std::tuple<int, const bool&>(0, b)));
530 }
531 
532 // Tests that ACTION() works for arguments passed by non-const reference.
ACTION(ReturnAddrOfIntReferenceArg)533 ACTION(ReturnAddrOfIntReferenceArg) {
534   StaticAssertTypeEq<int&, arg0_type>();
535   return &arg0;
536 }
537 
TEST(ActionMacroTest,WorksForNonConstReferenceArg)538 TEST(ActionMacroTest, WorksForNonConstReferenceArg) {
539   Action<int*(int&, bool, int)> a = ReturnAddrOfIntReferenceArg();
540   int n = 0;
541   EXPECT_EQ(&n, a.Perform(std::tuple<int&, bool, int>(n, true, 1)));
542 }
543 
544 // Tests that ACTION() can be used in a namespace.
545 namespace action_test {
ACTION(Sum)546 ACTION(Sum) { return arg0 + arg1; }
547 }  // namespace action_test
548 
TEST(ActionMacroTest,WorksInNamespace)549 TEST(ActionMacroTest, WorksInNamespace) {
550   Action<int(int, int)> a1 = action_test::Sum();
551   EXPECT_EQ(3, a1.Perform(std::make_tuple(1, 2)));
552 }
553 
554 // Tests that the same ACTION definition works for mock functions with
555 // different argument numbers.
ACTION(PlusTwo)556 ACTION(PlusTwo) { return arg0 + 2; }
557 
TEST(ActionMacroTest,WorksForDifferentArgumentNumbers)558 TEST(ActionMacroTest, WorksForDifferentArgumentNumbers) {
559   Action<int(int)> a1 = PlusTwo();
560   EXPECT_EQ(4, a1.Perform(std::make_tuple(2)));
561 
562   Action<double(float, void*)> a2 = PlusTwo();
563   int dummy;
564   EXPECT_DOUBLE_EQ(6, a2.Perform(std::make_tuple(4.0f, &dummy)));
565 }
566 
567 // Tests that ACTION_P can define a parameterized action.
ACTION_P(Plus,n)568 ACTION_P(Plus, n) { return arg0 + n; }
569 
TEST(ActionPMacroTest,DefinesParameterizedAction)570 TEST(ActionPMacroTest, DefinesParameterizedAction) {
571   Action<int(int m, bool t)> a1 = Plus(9);
572   EXPECT_EQ(10, a1.Perform(std::make_tuple(1, true)));
573 }
574 
575 // Tests that the body of ACTION_P can reference the argument types
576 // and the parameter type.
ACTION_P(TypedPlus,n)577 ACTION_P(TypedPlus, n) {
578   arg0_type t1 = arg0;
579   n_type t2 = n;
580   return t1 + t2;
581 }
582 
TEST(ActionPMacroTest,CanReferenceArgumentAndParameterTypes)583 TEST(ActionPMacroTest, CanReferenceArgumentAndParameterTypes) {
584   Action<int(char m, bool t)> a1 = TypedPlus(9);
585   EXPECT_EQ(10, a1.Perform(std::make_tuple(Char(1), true)));
586 }
587 
588 // Tests that a parameterized action can be used in any mock function
589 // whose type is compatible.
TEST(ActionPMacroTest,WorksInCompatibleMockFunction)590 TEST(ActionPMacroTest, WorksInCompatibleMockFunction) {
591   Action<std::string(const std::string& s)> a1 = Plus("tail");
592   const std::string re = "re";
593   std::tuple<const std::string> dummy = std::make_tuple(re);
594   EXPECT_EQ("retail", a1.Perform(dummy));
595 }
596 
597 // Tests that we can use ACTION*() to define actions overloaded on the
598 // number of parameters.
599 
ACTION(OverloadedAction)600 ACTION(OverloadedAction) { return arg0 ? arg1 : "hello"; }
601 
ACTION_P(OverloadedAction,default_value)602 ACTION_P(OverloadedAction, default_value) {
603   return arg0 ? arg1 : default_value;
604 }
605 
ACTION_P2(OverloadedAction,true_value,false_value)606 ACTION_P2(OverloadedAction, true_value, false_value) {
607   return arg0 ? true_value : false_value;
608 }
609 
TEST(ActionMacroTest,CanDefineOverloadedActions)610 TEST(ActionMacroTest, CanDefineOverloadedActions) {
611   typedef Action<const char*(bool, const char*)> MyAction;
612 
613   const MyAction a1 = OverloadedAction();
614   EXPECT_STREQ("hello", a1.Perform(std::make_tuple(false, CharPtr("world"))));
615   EXPECT_STREQ("world", a1.Perform(std::make_tuple(true, CharPtr("world"))));
616 
617   const MyAction a2 = OverloadedAction("hi");
618   EXPECT_STREQ("hi", a2.Perform(std::make_tuple(false, CharPtr("world"))));
619   EXPECT_STREQ("world", a2.Perform(std::make_tuple(true, CharPtr("world"))));
620 
621   const MyAction a3 = OverloadedAction("hi", "you");
622   EXPECT_STREQ("hi", a3.Perform(std::make_tuple(true, CharPtr("world"))));
623   EXPECT_STREQ("you", a3.Perform(std::make_tuple(false, CharPtr("world"))));
624 }
625 
626 // Tests ACTION_Pn where n >= 3.
627 
ACTION_P3(Plus,m,n,k)628 ACTION_P3(Plus, m, n, k) { return arg0 + m + n + k; }
629 
TEST(ActionPnMacroTest,WorksFor3Parameters)630 TEST(ActionPnMacroTest, WorksFor3Parameters) {
631   Action<double(int m, bool t)> a1 = Plus(100, 20, 3.4);
632   EXPECT_DOUBLE_EQ(3123.4, a1.Perform(std::make_tuple(3000, true)));
633 
634   Action<std::string(const std::string& s)> a2 = Plus("tail", "-", ">");
635   const std::string re = "re";
636   std::tuple<const std::string> dummy = std::make_tuple(re);
637   EXPECT_EQ("retail->", a2.Perform(dummy));
638 }
639 
ACTION_P4(Plus,p0,p1,p2,p3)640 ACTION_P4(Plus, p0, p1, p2, p3) { return arg0 + p0 + p1 + p2 + p3; }
641 
TEST(ActionPnMacroTest,WorksFor4Parameters)642 TEST(ActionPnMacroTest, WorksFor4Parameters) {
643   Action<int(int)> a1 = Plus(1, 2, 3, 4);
644   EXPECT_EQ(10 + 1 + 2 + 3 + 4, a1.Perform(std::make_tuple(10)));
645 }
646 
ACTION_P5(Plus,p0,p1,p2,p3,p4)647 ACTION_P5(Plus, p0, p1, p2, p3, p4) { return arg0 + p0 + p1 + p2 + p3 + p4; }
648 
TEST(ActionPnMacroTest,WorksFor5Parameters)649 TEST(ActionPnMacroTest, WorksFor5Parameters) {
650   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5);
651   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5, a1.Perform(std::make_tuple(10)));
652 }
653 
ACTION_P6(Plus,p0,p1,p2,p3,p4,p5)654 ACTION_P6(Plus, p0, p1, p2, p3, p4, p5) {
655   return arg0 + p0 + p1 + p2 + p3 + p4 + p5;
656 }
657 
TEST(ActionPnMacroTest,WorksFor6Parameters)658 TEST(ActionPnMacroTest, WorksFor6Parameters) {
659   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5, 6);
660   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5 + 6, a1.Perform(std::make_tuple(10)));
661 }
662 
ACTION_P7(Plus,p0,p1,p2,p3,p4,p5,p6)663 ACTION_P7(Plus, p0, p1, p2, p3, p4, p5, p6) {
664   return arg0 + p0 + p1 + p2 + p3 + p4 + p5 + p6;
665 }
666 
TEST(ActionPnMacroTest,WorksFor7Parameters)667 TEST(ActionPnMacroTest, WorksFor7Parameters) {
668   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5, 6, 7);
669   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5 + 6 + 7, a1.Perform(std::make_tuple(10)));
670 }
671 
ACTION_P8(Plus,p0,p1,p2,p3,p4,p5,p6,p7)672 ACTION_P8(Plus, p0, p1, p2, p3, p4, p5, p6, p7) {
673   return arg0 + p0 + p1 + p2 + p3 + p4 + p5 + p6 + p7;
674 }
675 
TEST(ActionPnMacroTest,WorksFor8Parameters)676 TEST(ActionPnMacroTest, WorksFor8Parameters) {
677   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5, 6, 7, 8);
678   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8,
679             a1.Perform(std::make_tuple(10)));
680 }
681 
ACTION_P9(Plus,p0,p1,p2,p3,p4,p5,p6,p7,p8)682 ACTION_P9(Plus, p0, p1, p2, p3, p4, p5, p6, p7, p8) {
683   return arg0 + p0 + p1 + p2 + p3 + p4 + p5 + p6 + p7 + p8;
684 }
685 
TEST(ActionPnMacroTest,WorksFor9Parameters)686 TEST(ActionPnMacroTest, WorksFor9Parameters) {
687   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5, 6, 7, 8, 9);
688   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9,
689             a1.Perform(std::make_tuple(10)));
690 }
691 
ACTION_P10(Plus,p0,p1,p2,p3,p4,p5,p6,p7,p8,last_param)692 ACTION_P10(Plus, p0, p1, p2, p3, p4, p5, p6, p7, p8, last_param) {
693   arg0_type t0 = arg0;
694   last_param_type t9 = last_param;
695   return t0 + p0 + p1 + p2 + p3 + p4 + p5 + p6 + p7 + p8 + t9;
696 }
697 
TEST(ActionPnMacroTest,WorksFor10Parameters)698 TEST(ActionPnMacroTest, WorksFor10Parameters) {
699   Action<int(int)> a1 = Plus(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
700   EXPECT_EQ(10 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9 + 10,
701             a1.Perform(std::make_tuple(10)));
702 }
703 
704 // Tests that the action body can promote the parameter types.
705 
ACTION_P2(PadArgument,prefix,suffix)706 ACTION_P2(PadArgument, prefix, suffix) {
707   // The following lines promote the two parameters to desired types.
708   std::string prefix_str(prefix);
709   char suffix_char = static_cast<char>(suffix);
710   return prefix_str + arg0 + suffix_char;
711 }
712 
TEST(ActionPnMacroTest,SimpleTypePromotion)713 TEST(ActionPnMacroTest, SimpleTypePromotion) {
714   Action<std::string(const char*)> no_promo =
715       PadArgument(std::string("foo"), 'r');
716   Action<std::string(const char*)> promo =
717       PadArgument("foo", static_cast<int>('r'));
718   EXPECT_EQ("foobar", no_promo.Perform(std::make_tuple(CharPtr("ba"))));
719   EXPECT_EQ("foobar", promo.Perform(std::make_tuple(CharPtr("ba"))));
720 }
721 
722 // Tests that we can partially restrict parameter types using a
723 // straight-forward pattern.
724 
725 // Defines a generic action that doesn't restrict the types of its
726 // parameters.
ACTION_P3(ConcatImpl,a,b,c)727 ACTION_P3(ConcatImpl, a, b, c) {
728   std::stringstream ss;
729   ss << a << b << c;
730   return ss.str();
731 }
732 
733 // Next, we try to restrict that either the first parameter is a
734 // string, or the second parameter is an int.
735 
736 // Defines a partially specialized wrapper that restricts the first
737 // parameter to std::string.
738 template <typename T1, typename T2>
739 // ConcatImplActionP3 is the class template ACTION_P3 uses to
740 // implement ConcatImpl.  We shouldn't change the name as this
741 // pattern requires the user to use it directly.
742 ConcatImplActionP3<std::string, T1, T2>
Concat(const std::string & a,T1 b,T2 c)743 Concat(const std::string& a, T1 b, T2 c) {
744   GTEST_INTENTIONAL_CONST_COND_PUSH_()
745   if (true) {
746   GTEST_INTENTIONAL_CONST_COND_POP_()
747     // This branch verifies that ConcatImpl() can be invoked without
748     // explicit template arguments.
749     return ConcatImpl(a, b, c);
750   } else {
751     // This branch verifies that ConcatImpl() can also be invoked with
752     // explicit template arguments.  It doesn't really need to be
753     // executed as this is a compile-time verification.
754     return ConcatImpl<std::string, T1, T2>(a, b, c);
755   }
756 }
757 
758 // Defines another partially specialized wrapper that restricts the
759 // second parameter to int.
760 template <typename T1, typename T2>
761 ConcatImplActionP3<T1, int, T2>
Concat(T1 a,int b,T2 c)762 Concat(T1 a, int b, T2 c) {
763   return ConcatImpl(a, b, c);
764 }
765 
TEST(ActionPnMacroTest,CanPartiallyRestrictParameterTypes)766 TEST(ActionPnMacroTest, CanPartiallyRestrictParameterTypes) {
767   Action<const std::string()> a1 = Concat("Hello", "1", 2);
768   EXPECT_EQ("Hello12", a1.Perform(std::make_tuple()));
769 
770   a1 = Concat(1, 2, 3);
771   EXPECT_EQ("123", a1.Perform(std::make_tuple()));
772 }
773 
774 // Verifies the type of an ACTION*.
775 
ACTION(DoFoo)776 ACTION(DoFoo) {}
ACTION_P(DoFoo,p)777 ACTION_P(DoFoo, p) {}
ACTION_P2(DoFoo,p0,p1)778 ACTION_P2(DoFoo, p0, p1) {}
779 
TEST(ActionPnMacroTest,TypesAreCorrect)780 TEST(ActionPnMacroTest, TypesAreCorrect) {
781   // DoFoo() must be assignable to a DoFooAction variable.
782   DoFooAction a0 = DoFoo();
783 
784   // DoFoo(1) must be assignable to a DoFooActionP variable.
785   DoFooActionP<int> a1 = DoFoo(1);
786 
787   // DoFoo(p1, ..., pk) must be assignable to a DoFooActionPk
788   // variable, and so on.
789   DoFooActionP2<int, char> a2 = DoFoo(1, '2');
790   PlusActionP3<int, int, char> a3 = Plus(1, 2, '3');
791   PlusActionP4<int, int, int, char> a4 = Plus(1, 2, 3, '4');
792   PlusActionP5<int, int, int, int, char> a5 = Plus(1, 2, 3, 4, '5');
793   PlusActionP6<int, int, int, int, int, char> a6 = Plus(1, 2, 3, 4, 5, '6');
794   PlusActionP7<int, int, int, int, int, int, char> a7 =
795       Plus(1, 2, 3, 4, 5, 6, '7');
796   PlusActionP8<int, int, int, int, int, int, int, char> a8 =
797       Plus(1, 2, 3, 4, 5, 6, 7, '8');
798   PlusActionP9<int, int, int, int, int, int, int, int, char> a9 =
799       Plus(1, 2, 3, 4, 5, 6, 7, 8, '9');
800   PlusActionP10<int, int, int, int, int, int, int, int, int, char> a10 =
801       Plus(1, 2, 3, 4, 5, 6, 7, 8, 9, '0');
802 
803   // Avoid "unused variable" warnings.
804   (void)a0;
805   (void)a1;
806   (void)a2;
807   (void)a3;
808   (void)a4;
809   (void)a5;
810   (void)a6;
811   (void)a7;
812   (void)a8;
813   (void)a9;
814   (void)a10;
815 }
816 
817 // Tests that an ACTION_P*() action can be explicitly instantiated
818 // with reference-typed parameters.
819 
ACTION_P(Plus1,x)820 ACTION_P(Plus1, x) { return x; }
ACTION_P2(Plus2,x,y)821 ACTION_P2(Plus2, x, y) { return x + y; }
ACTION_P3(Plus3,x,y,z)822 ACTION_P3(Plus3, x, y, z) { return x + y + z; }
ACTION_P10(Plus10,a0,a1,a2,a3,a4,a5,a6,a7,a8,a9)823 ACTION_P10(Plus10, a0, a1, a2, a3, a4, a5, a6, a7, a8, a9) {
824   return a0 + a1 + a2 + a3 + a4 + a5 + a6 + a7 + a8 + a9;
825 }
826 
TEST(ActionPnMacroTest,CanExplicitlyInstantiateWithReferenceTypes)827 TEST(ActionPnMacroTest, CanExplicitlyInstantiateWithReferenceTypes) {
828   int x = 1, y = 2, z = 3;
829   const std::tuple<> empty = std::make_tuple();
830 
831   Action<int()> a = Plus1<int&>(x);
832   EXPECT_EQ(1, a.Perform(empty));
833 
834   a = Plus2<const int&, int&>(x, y);
835   EXPECT_EQ(3, a.Perform(empty));
836 
837   a = Plus3<int&, const int&, int&>(x, y, z);
838   EXPECT_EQ(6, a.Perform(empty));
839 
840   int n[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
841   a = Plus10<const int&, int&, const int&, int&, const int&, int&, const int&,
842       int&, const int&, int&>(n[0], n[1], n[2], n[3], n[4], n[5], n[6], n[7],
843                               n[8], n[9]);
844   EXPECT_EQ(55, a.Perform(empty));
845 }
846 
847 class NullaryConstructorClass {
848  public:
NullaryConstructorClass()849   NullaryConstructorClass() : value_(123) {}
850   int value_;
851 };
852 
853 // Tests using ReturnNew() with a nullary constructor.
TEST(ReturnNewTest,NoArgs)854 TEST(ReturnNewTest, NoArgs) {
855   Action<NullaryConstructorClass*()> a = ReturnNew<NullaryConstructorClass>();
856   NullaryConstructorClass* c = a.Perform(std::make_tuple());
857   EXPECT_EQ(123, c->value_);
858   delete c;
859 }
860 
861 class UnaryConstructorClass {
862  public:
UnaryConstructorClass(int value)863   explicit UnaryConstructorClass(int value) : value_(value) {}
864   int value_;
865 };
866 
867 // Tests using ReturnNew() with a unary constructor.
TEST(ReturnNewTest,Unary)868 TEST(ReturnNewTest, Unary) {
869   Action<UnaryConstructorClass*()> a = ReturnNew<UnaryConstructorClass>(4000);
870   UnaryConstructorClass* c = a.Perform(std::make_tuple());
871   EXPECT_EQ(4000, c->value_);
872   delete c;
873 }
874 
TEST(ReturnNewTest,UnaryWorksWhenMockMethodHasArgs)875 TEST(ReturnNewTest, UnaryWorksWhenMockMethodHasArgs) {
876   Action<UnaryConstructorClass*(bool, int)> a =
877       ReturnNew<UnaryConstructorClass>(4000);
878   UnaryConstructorClass* c = a.Perform(std::make_tuple(false, 5));
879   EXPECT_EQ(4000, c->value_);
880   delete c;
881 }
882 
TEST(ReturnNewTest,UnaryWorksWhenMockMethodReturnsPointerToConst)883 TEST(ReturnNewTest, UnaryWorksWhenMockMethodReturnsPointerToConst) {
884   Action<const UnaryConstructorClass*()> a =
885       ReturnNew<UnaryConstructorClass>(4000);
886   const UnaryConstructorClass* c = a.Perform(std::make_tuple());
887   EXPECT_EQ(4000, c->value_);
888   delete c;
889 }
890 
891 class TenArgConstructorClass {
892  public:
TenArgConstructorClass(int a1,int a2,int a3,int a4,int a5,int a6,int a7,int a8,int a9,int a10)893   TenArgConstructorClass(int a1, int a2, int a3, int a4, int a5,
894                          int a6, int a7, int a8, int a9, int a10)
895     : value_(a1 + a2 + a3 + a4 + a5 + a6 + a7 + a8 + a9 + a10) {
896   }
897   int value_;
898 };
899 
900 // Tests using ReturnNew() with a 10-argument constructor.
TEST(ReturnNewTest,ConstructorThatTakes10Arguments)901 TEST(ReturnNewTest, ConstructorThatTakes10Arguments) {
902   Action<TenArgConstructorClass*()> a =
903       ReturnNew<TenArgConstructorClass>(1000000000, 200000000, 30000000,
904                                         4000000, 500000, 60000,
905                                         7000, 800, 90, 0);
906   TenArgConstructorClass* c = a.Perform(std::make_tuple());
907   EXPECT_EQ(1234567890, c->value_);
908   delete c;
909 }
910 
911 // Tests that ACTION_TEMPLATE works when there is no value parameter.
ACTION_TEMPLATE(CreateNew,HAS_1_TEMPLATE_PARAMS (typename,T),AND_0_VALUE_PARAMS ())912 ACTION_TEMPLATE(CreateNew,
913                 HAS_1_TEMPLATE_PARAMS(typename, T),
914                 AND_0_VALUE_PARAMS()) {
915   return new T;
916 }
917 
TEST(ActionTemplateTest,WorksWithoutValueParam)918 TEST(ActionTemplateTest, WorksWithoutValueParam) {
919   const Action<int*()> a = CreateNew<int>();
920   int* p = a.Perform(std::make_tuple());
921   delete p;
922 }
923 
924 // Tests that ACTION_TEMPLATE works when there are value parameters.
ACTION_TEMPLATE(CreateNew,HAS_1_TEMPLATE_PARAMS (typename,T),AND_1_VALUE_PARAMS (a0))925 ACTION_TEMPLATE(CreateNew,
926                 HAS_1_TEMPLATE_PARAMS(typename, T),
927                 AND_1_VALUE_PARAMS(a0)) {
928   return new T(a0);
929 }
930 
TEST(ActionTemplateTest,WorksWithValueParams)931 TEST(ActionTemplateTest, WorksWithValueParams) {
932   const Action<int*()> a = CreateNew<int>(42);
933   int* p = a.Perform(std::make_tuple());
934   EXPECT_EQ(42, *p);
935   delete p;
936 }
937 
938 // Tests that ACTION_TEMPLATE works for integral template parameters.
ACTION_TEMPLATE(MyDeleteArg,HAS_1_TEMPLATE_PARAMS (int,k),AND_0_VALUE_PARAMS ())939 ACTION_TEMPLATE(MyDeleteArg,
940                 HAS_1_TEMPLATE_PARAMS(int, k),
941                 AND_0_VALUE_PARAMS()) {
942   delete std::get<k>(args);
943 }
944 
945 // Resets a bool variable in the destructor.
946 class BoolResetter {
947  public:
BoolResetter(bool * value)948   explicit BoolResetter(bool* value) : value_(value) {}
~BoolResetter()949   ~BoolResetter() { *value_ = false; }
950  private:
951   bool* value_;
952 };
953 
TEST(ActionTemplateTest,WorksForIntegralTemplateParams)954 TEST(ActionTemplateTest, WorksForIntegralTemplateParams) {
955   const Action<void(int*, BoolResetter*)> a = MyDeleteArg<1>();
956   int n = 0;
957   bool b = true;
958   BoolResetter* resetter = new BoolResetter(&b);
959   a.Perform(std::make_tuple(&n, resetter));
960   EXPECT_FALSE(b);  // Verifies that resetter is deleted.
961 }
962 
963 // Tests that ACTION_TEMPLATES works for template template parameters.
ACTION_TEMPLATE(ReturnSmartPointer,HAS_1_TEMPLATE_PARAMS (template<typename Pointee> class,Pointer),AND_1_VALUE_PARAMS (pointee))964 ACTION_TEMPLATE(ReturnSmartPointer,
965                 HAS_1_TEMPLATE_PARAMS(template <typename Pointee> class,
966                                       Pointer),
967                 AND_1_VALUE_PARAMS(pointee)) {
968   return Pointer<pointee_type>(new pointee_type(pointee));
969 }
970 
TEST(ActionTemplateTest,WorksForTemplateTemplateParameters)971 TEST(ActionTemplateTest, WorksForTemplateTemplateParameters) {
972   const Action<std::shared_ptr<int>()> a =
973       ReturnSmartPointer<std::shared_ptr>(42);
974   std::shared_ptr<int> p = a.Perform(std::make_tuple());
975   EXPECT_EQ(42, *p);
976 }
977 
978 // Tests that ACTION_TEMPLATE works for 10 template parameters.
979 template <typename T1, typename T2, typename T3, int k4, bool k5,
980           unsigned int k6, typename T7, typename T8, typename T9>
981 struct GiantTemplate {
982  public:
GiantTemplatetesting::gmock_generated_actions_test::GiantTemplate983   explicit GiantTemplate(int a_value) : value(a_value) {}
984   int value;
985 };
986 
ACTION_TEMPLATE(ReturnGiant,HAS_10_TEMPLATE_PARAMS (typename,T1,typename,T2,typename,T3,int,k4,bool,k5,unsigned int,k6,class,T7,class,T8,class,T9,template<typename T> class,T10),AND_1_VALUE_PARAMS (value))987 ACTION_TEMPLATE(ReturnGiant,
988                 HAS_10_TEMPLATE_PARAMS(
989                     typename, T1,
990                     typename, T2,
991                     typename, T3,
992                     int, k4,
993                     bool, k5,
994                     unsigned int, k6,
995                     class, T7,
996                     class, T8,
997                     class, T9,
998                     template <typename T> class, T10),
999                 AND_1_VALUE_PARAMS(value)) {
1000   return GiantTemplate<T10<T1>, T2, T3, k4, k5, k6, T7, T8, T9>(value);
1001 }
1002 
TEST(ActionTemplateTest,WorksFor10TemplateParameters)1003 TEST(ActionTemplateTest, WorksFor10TemplateParameters) {
1004   using Giant = GiantTemplate<std::shared_ptr<int>, bool, double, 5, true, 6,
1005                               char, unsigned, int>;
1006   const Action<Giant()> a = ReturnGiant<int, bool, double, 5, true, 6, char,
1007                                         unsigned, int, std::shared_ptr>(42);
1008   Giant giant = a.Perform(std::make_tuple());
1009   EXPECT_EQ(42, giant.value);
1010 }
1011 
1012 // Tests that ACTION_TEMPLATE works for 10 value parameters.
ACTION_TEMPLATE(ReturnSum,HAS_1_TEMPLATE_PARAMS (typename,Number),AND_10_VALUE_PARAMS (v1,v2,v3,v4,v5,v6,v7,v8,v9,v10))1013 ACTION_TEMPLATE(ReturnSum,
1014                 HAS_1_TEMPLATE_PARAMS(typename, Number),
1015                 AND_10_VALUE_PARAMS(v1, v2, v3, v4, v5, v6, v7, v8, v9, v10)) {
1016   return static_cast<Number>(v1) + v2 + v3 + v4 + v5 + v6 + v7 + v8 + v9 + v10;
1017 }
1018 
TEST(ActionTemplateTest,WorksFor10ValueParameters)1019 TEST(ActionTemplateTest, WorksFor10ValueParameters) {
1020   const Action<int()> a = ReturnSum<int>(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
1021   EXPECT_EQ(55, a.Perform(std::make_tuple()));
1022 }
1023 
1024 // Tests that ACTION_TEMPLATE and ACTION/ACTION_P* can be overloaded
1025 // on the number of value parameters.
1026 
ACTION(ReturnSum)1027 ACTION(ReturnSum) { return 0; }
1028 
ACTION_P(ReturnSum,x)1029 ACTION_P(ReturnSum, x) { return x; }
1030 
ACTION_TEMPLATE(ReturnSum,HAS_1_TEMPLATE_PARAMS (typename,Number),AND_2_VALUE_PARAMS (v1,v2))1031 ACTION_TEMPLATE(ReturnSum,
1032                 HAS_1_TEMPLATE_PARAMS(typename, Number),
1033                 AND_2_VALUE_PARAMS(v1, v2)) {
1034   return static_cast<Number>(v1) + v2;
1035 }
1036 
ACTION_TEMPLATE(ReturnSum,HAS_1_TEMPLATE_PARAMS (typename,Number),AND_3_VALUE_PARAMS (v1,v2,v3))1037 ACTION_TEMPLATE(ReturnSum,
1038                 HAS_1_TEMPLATE_PARAMS(typename, Number),
1039                 AND_3_VALUE_PARAMS(v1, v2, v3)) {
1040   return static_cast<Number>(v1) + v2 + v3;
1041 }
1042 
ACTION_TEMPLATE(ReturnSum,HAS_2_TEMPLATE_PARAMS (typename,Number,int,k),AND_4_VALUE_PARAMS (v1,v2,v3,v4))1043 ACTION_TEMPLATE(ReturnSum,
1044                 HAS_2_TEMPLATE_PARAMS(typename, Number, int, k),
1045                 AND_4_VALUE_PARAMS(v1, v2, v3, v4)) {
1046   return static_cast<Number>(v1) + v2 + v3 + v4 + k;
1047 }
1048 
TEST(ActionTemplateTest,CanBeOverloadedOnNumberOfValueParameters)1049 TEST(ActionTemplateTest, CanBeOverloadedOnNumberOfValueParameters) {
1050   const Action<int()> a0 = ReturnSum();
1051   const Action<int()> a1 = ReturnSum(1);
1052   const Action<int()> a2 = ReturnSum<int>(1, 2);
1053   const Action<int()> a3 = ReturnSum<int>(1, 2, 3);
1054   const Action<int()> a4 = ReturnSum<int, 10000>(2000, 300, 40, 5);
1055   EXPECT_EQ(0, a0.Perform(std::make_tuple()));
1056   EXPECT_EQ(1, a1.Perform(std::make_tuple()));
1057   EXPECT_EQ(3, a2.Perform(std::make_tuple()));
1058   EXPECT_EQ(6, a3.Perform(std::make_tuple()));
1059   EXPECT_EQ(12345, a4.Perform(std::make_tuple()));
1060 }
1061 
1062 
1063 }  // namespace gmock_generated_actions_test
1064 }  // namespace testing
1065